[javascript] 터치 장치의 버튼에 끈적임 호버 효과를 방지하는 방법

항상 표시되는 이전 및 다음 버튼으로 회전식 메뉴를 만들었습니다. 이 버튼은 호버 상태이며 파란색으로 바뀝니다. iPad와 같은 터치 장치에서는 호버 상태가 고정되어 있으므로 버튼을 탭한 후에도 파란색으로 유지됩니다. 나는 그것을 원하지 않습니다.

  • 각 버튼에 no-hover클래스 ontouchend를 추가하고 CSS를 다음과 같이 만들 수는 button:not(.no-hover):hover { background-color:
    blue; }
    있지만 성능에 좋지 않을 수 있으며 크롬 북 픽셀 (터치 스크린과 마우스가 모두있는)과 같은 기기를 올바르게 처리하지 못합니다.

  • touch클래스를 추가하고 documentElementCSS를 다음과 같이 만들 수 있습니다 . html:not(.touch) button:hover { background-color: blue;
    }
    그러나 터치와 마우스가 모두있는 장치에서는 제대로 작동하지 않습니다.

내가 선호하는 것은 호버 상태를 제거하는 것 ontouchend입니다. 그러나 가능하지 않은 것 같습니다. 다른 요소에 초점을 맞추더라도 호버 상태가 제거되지 않습니다. 다른 요소를 수동으로 두드리는 것이지만 JavaScript에서 트리거 할 수없는 것 같습니다.

내가 찾은 모든 솔루션이 불완전한 것처럼 보입니다. 완벽한 솔루션이 있습니까?



답변

DOM에서 링크를 일시적으로 제거하여 호버 상태를 제거 할 수 있습니다. http://testbug.handcraft.com/ipad.html을 참조하십시오


CSS에는 다음이 있습니다.

:hover {background:red;}

JS에는 다음이 있습니다.

function fix()
{
    var el = this;
    var par = el.parentNode;
    var next = el.nextSibling;
    par.removeChild(el);
    setTimeout(function() {par.insertBefore(el, next);}, 0)
}

그런 다음 HTML에 다음이 있습니다.

<a href="#" ontouchend="this.onclick=fix">test</a>


답변

일단 CSS 미디어 쿼리 레벨 4가 구현되어, 당신은이 작업을 수행 할 수 있습니다 :

@media (hover: hover) {
    button:hover {
        background-color: blue;
    }
}

또는 영어로 : “브라우저가 올바른 / 진짜 / 실제 / 비 에뮬레이트 호버링을 지원하는 경우 (예 : 마우스와 같은 기본 입력 장치가있는 경우) button마우스를 올렸을 때이 스타일을 적용하십시오 .”

Media Queries Level 4의이 부분은 지금까지 최첨단 Chrome에서만 구현 되었으므로 이를 처리하기 위해 폴리 필작성했습니다 . 이를 사용하여 위의 미래형 CSS를 다음과 같이 변환 할 수 있습니다.

html.my-true-hover button:hover {
    background-color: blue;
}

( .no-touch기술 의 변형 ) 그런 다음 호버링 지원을 감지하는 동일한 폴리 필에서 클라이언트 측 JavaScript를 사용하여 my-true-hover클래스 의 존재 여부를 적절하게 토글 할 수 있습니다 .

$(document).on('mq4hsChange', function (e) {
    $(document.documentElement).toggleClass('my-true-hover', e.trueHover);
});


답변

완벽한 솔루션이없는 일반적인 문제입니다. 호버 동작은 마우스에 유용하며 대부분 터치하면 해 롭습니다. 문제는 크롬 북 픽셀 및 표면과 같이 터치와 마우스를 동시에 지원하는 기기입니다.

내가 찾은 가장 깨끗한 솔루션은 장치가 터치 입력을 지원하지 않는 경우에만 호버 동작을 활성화하는 것입니다.

var isTouch =  !!("ontouchstart" in window) || window.navigator.msMaxTouchPoints > 0;

if( !isTouch ){
    // add class which defines hover behavior
}

물론 지원할 수있는 장치에서 호버링을 잃게됩니다. 그러나 때로는 마우스 오버가 링크 자체보다 많은 영향을 미칩니다. 예를 들어 요소를 가리킬 때 메뉴를 표시하려고 할 수 있습니다. 이 방법을 사용하면 터치가 있는지 테스트하고 조건부로 다른 이벤트를 첨부 할 수 있습니다.

나는 이것을 iPhone, iPad, Chromebook Pixel, Surface 및 다양한 Android 기기에서 테스트했습니다. 일반적인 USB 터치 입력 (스타일러스 등)이 믹스에 추가 될 때 작동한다는 보장은 없습니다.


답변

Modernizr 을 사용하면 터치가없는 장치를 위해 특히 호버를 대상으로 지정할 수 있습니다.

(참고 : 이것은 StackOverflow의 스 니펫 시스템에서 실행되지 않습니다. 대신 jsfiddle을 확인하십시오 )

/* this one is sticky */
#regular:hover, #regular:active {
  opacity: 0.5;
}

/* this one isn't */
html.no-touch #no-touch:hover, #no-touch:active {
  opacity: 0.5;
}

참고 :active이 필요하지 않습니다 함께 대상으로하는 .no-touch이 같은 모바일 및 데스크톱 모두에서 예상 작동하기 때문에.


답변

$("#elementwithhover").click(function() {
  // code that makes element or parent slide or otherwise move out from under mouse. 

  $(this).clone(true).insertAfter($(this));
  $(this).remove();
});


답변

에서 모바일에 스티커 가져가 처리하는 4 가지 방법 : 여기에 동적으로 추가하거나 “제거하는 방법 can touch사용자의 현재 입력 유형에 따라 문서에”클래스. 사용자가 터치와 마우스 / 트랙 패드 사이를 전환 할 수있는 하이브리드 장치에서도 작동합니다.

<script>

;(function(){
    var isTouch = false //var to indicate current input type (is touch versus no touch) 
    var isTouchTimer
    var curRootClass = '' //var indicating current document root class ("can-touch" or "")

    function addtouchclass(e){
        clearTimeout(isTouchTimer)
        isTouch = true
        if (curRootClass != 'can-touch'){ //add "can-touch' class if it's not already present
            curRootClass = 'can-touch'
            document.documentElement.classList.add(curRootClass)
        }
        isTouchTimer = setTimeout(function(){isTouch = false}, 500) //maintain "istouch" state for 500ms so removetouchclass doesn't get fired immediately following a touch event
    }

    function removetouchclass(e){
        if (!isTouch && curRootClass == 'can-touch'){ //remove 'can-touch' class if not triggered by a touch event and class is present
            isTouch = false
            curRootClass = ''
            document.documentElement.classList.remove('can-touch')
        }
    }

    document.addEventListener('touchstart', addtouchclass, false) //this event only gets called when input type is touch
    document.addEventListener('mouseover', removetouchclass, false) //this event gets called when input type is everything from touch to mouse/ trackpad
})();

</script>


답변

호버를 지원하지 않는 장치의 호버 효과를 무시할 수 있습니다. 처럼:

.my-thing {
    color: #BADA55;
}

.my-thing:hover {
    color: hotpink;
}

@media (hover: none) {
    .my-thing {
        color: #BADA55;
    }
}

iOS 12에서 테스트 및 검증

이것을 지적하기위한 모자 팁 https://stackoverflow.com/a/50285058/178959