Vérifier si l'élément est visible dans le DOM

Existe-t-il un moyen de vérifier si un élément est visible en JS pur (sans jQuery) ?

Ainsi, par exemple, dans cette page : Performance Bikes, si vous passez la souris sur Deals (dans le menu supérieur), une fenêtre de deals apparaît, mais au début elle n'était pas affichée. Elle est dans le HTML mais elle n'est pas visible.

Donc, étant donné un élément DOM, comment puis-je vérifier s'il est visible ou non ? J'ai essayé :

window.getComputedStyle(my_element)['display']);

mais ça n'a pas l'air de fonctionner. Je me demande quels attributs je dois vérifier. Cela me vient à l'esprit :

display !== 'none'
visibility !== 'hidden'

Y en a-t-il d'autres que je pourrais oublier ?

Solution

Selon [cette documentation MDN][1], la propriété offsetParent d'un élément renvoie null lorsque celui-ci, ou l'un de ses parents, est masqué par la propriété display style. Assurez-vous simplement que l'élément n'est pas fixe. Un script pour vérifier cela, si vous n'avez pas d'éléments position : fixed; sur votre page, pourrait ressembler à ceci :

// Where el is the DOM element you'd like to test for visibility
function isHidden(el) {
    return (el.offsetParent === null)
}

D'un autre côté, si vous avez *d'éléments à position fixe qui pourraient être pris dans cette recherche, vous devrez malheureusement (et lentement) utiliser [window.getComputedStyle()][2]. La fonction dans ce cas pourrait être :

// Where el is the DOM element you'd like to test for visibility
function isHidden(el) {
    var style = window.getComputedStyle(el);
    return (style.display === 'none')
}

L'option #2 est probablement un peu plus simple car elle prend en compte plus de cas limites, mais je parie qu'elle est aussi beaucoup plus lente, donc si vous devez répéter cette opération plusieurs fois, le mieux est de l'éviter.

[1] : https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement.offsetParent [2] : https://developer.mozilla.org/en-US/docs/Web/API/Window.getComputedStyle

Commentaires (19)

Ceci peut vous aider : Masquez l'élément en le positionnant à l'extrême gauche, puis vérifiez la propriété offsetLeft. Si vous voulez utiliser jQuery, vous pouvez simplement vérifier le sélecteur :visible et obtenir l'état de visibilité de l'élément.

HTML :

<div id="myDiv">Hello</div>

CSS :


#myDiv{
   position:absolute;
   left : -2000px;
}


#myDiv{
    visibility:hidden;
}

javaScript :

var myStyle = document.getElementById("myDiv").offsetLeft;

if(myStyle < 0){
     alert("Div is hidden!!");
}

jQuery :

if(  $("#MyElement").is(":visible") == true )
{  
     alert("Div is hidden!!");        
}

jsFiddle

Commentaires (7)

Si nous ne faisons que collecter les moyens de base pour détecter la visibilité, je n'oublie pas :

opacity > 0.01; // probably more like .1 to actually be visible, but YMMV

Et quant à la façon d'obtenir des attributs :

element.getAttribute(attributename);

Donc, dans votre exemple :

document.getElementById('snDealsPanel').getAttribute('visibility');

Mais quoi ? Cela ne fonctionne pas ici. Regardez de plus près et vous constaterez que la visibilité est mise à jour non pas en tant qu'attribut de l'élément, mais en utilisant la propriété style. C'est l'un des nombreux problèmes que l'on rencontre lorsqu'on essaie de faire ce que vous faites. Entre autres : vous ne pouvez pas garantir qu'il y a réellement quelque chose à voir dans un élément, simplement parce que sa visibilité, son affichage et son opacité ont tous des valeurs correctes. Il se peut qu'il n'ait pas de contenu ou qu'il n'ait pas de hauteur et de largeur. Un autre objet peut le masquer. Pour plus de détails, une recherche rapide sur Google révèle [ceci][1], et inclut même une bibliothèque pour tenter de résoudre le problème. (YMMV)

Jetez un coup d'œil à ce qui suit, qui sont des doublons possibles de cette question, avec d'excellentes réponses, y compris un aperçu du puissant John Resig. Cependant, votre cas d'utilisation spécifique est légèrement différent du cas standard, je m'abstiendrai donc de le signaler :

  • Comment savoir si un élément du DOM est visible dans la fenêtre d'affichage actuelle ?
  • [Comment vérifier si un élément est vraiment visible avec javascript ?] [4]

(EDIT : OP DIT QU&#8217IL GRATTE DES PAGES, IL NE LES CRÉE PAS, DONC CE QUI SUIT N&#8217EST PAS APPLICABLE) Une meilleure option ? Lier la visibilité des éléments aux propriétés du modèle et faire en sorte que la visibilité dépende toujours de ce modèle, comme Angular le fait avec ng-show. Vous pouvez le faire en utilisant l'outil de votre choix : Angular, JS simple, n'importe quoi. Mieux encore, vous pouvez modifier l'implémentation du DOM au fil du temps, mais vous serez toujours en mesure de lire l'état du modèle, au lieu du DOM. Lire votre vérité à partir du DOM est mauvais. Et lent. Il est bien mieux de vérifier le modèle, et de faire confiance à votre implémentation pour assurer que l'état du DOM reflète le modèle. (Et utiliser des tests automatisés pour confirmer cette hypothèse).

[1] : http://useallfive.com/thoughts/javascript-tool-detect-if-a-dom-element-is-truly-visible/ [2] : https://stackoverflow.com/questions/123999/how-to-tell-if-a-dom-element-is-visible-in-the-current-viewport [3] : https://stackoverflow.com/questions/7311749/how-to-determine-whether-a-specific-dom-element-is-visible-or-not [4] : https://stackoverflow.com/questions/704758/how-to-check-if-an-element-is-really-visible-with-javascript

Commentaires (1)