Souris et DIV: gestion des évènements HTML

La reconnaissance en JavaScript des mouvements de la souris à l'intérieur d'un calque.

Sur ce calque de 300 x 400 pixels nous allons voir comment connaître la position de la souris. Vous pouvez déplacer la souris au-dessus du calque ou cliquer à l'intérieur.

Pour connaître la position de la souris, on utilise ce code:

var xMousePos = 0;
var yMousePos = 0;
document.onmousemove = function(e)
{
  xMousePos = e.clientX + window.pageXOffset;
  yMousePos = e.clientY + window.pageYOffset;
};

On voit que le gestionnaire d'évènement est associé au document entier. On pourrait l'associer au calque seul, mais selon mon expérience en production, le résultat est moins efficace.

Pour connaître la position de la souris dans le calque il faudra donc déduire la marge supérieure et la marge gauche du calque par rapport au document. Ce que l'on fait avec le code suivant, en supposant que l'objet représentant le div soit nommé mydiv:

var x = xMousePos - mydiv.offsetLeft;
var y = yMousePos - mydiv.offsetTop;	

A partir de là on peut afficher la position de la souris quand elle survole le calque avec le gestionnaire d'évènement onmousemove:

mydiv.onmousemove = function()
{
  var x = xMousePos - mydiv.offsetLeft;
  var y = yMousePos - mydiv.offsetTop;
  mydiv.style.cursor='wait';
  if(x > mydiv.offsetWidth - 4)
    mydiv.style.cursor='e-resize';
  if(y > mydiv.offsetHeight - 4)
    mydiv.style.cursor='n-resize';
  document.getElementById("message").innerHTML = "Pos x = " + x + "/" + 
      mydiv.offsetWidth +  " y = " + y + 
      "/" +mydiv.offsetHeight;
}

Cette fonction modifie aussi le curseur de la souris quand il passe sur la bordure du calque ou quand il est à l'intérieur.

On voit que la largeur et la hauteur sont de 408/308 pixels et non de 400/300 comme spécifié dans la feuille de style ce qui vient de l'ajout par le navigateur de la bordure. On peut supprimer cette valeur ajoutée avec cette propriété pour le div:

-moz-box-sizing:border-box; 
-webkit-box-sizing:border-box;
box-sizing:border-box;

La position de la souris dans le calque ne sera pas 0 dans le coin supérieur gauche si la feuille de style de votre page contient des balises en position:absolute, ce qui est le cas à l'origine de cette page pour la balise content. Pour la démonstration, j'ai donc dû surcharger la feuille de style de cette page pour remplacer la position absolue par la valeur static et remplacer top et left par des marges (en fait top et left sont ignorés avec une position statique):

#content
{
  position:static;
  margin-left:220px;
  margin-top:84px;
} 

Cela a le même effet pour le design de la page.

On peut aussi afficher la position de la souris quand l'utilisateur clique à l'intérieur du calque.

function update(e)
{
  var x = xMousePos - mydiv.offsetLeft;
  var y = yMousePos - mydiv.offsetTop;
  alert("x=" + x + " y=" + y);
}

mydiv.onclick = update;

Ici j'utilise une fonction séparée pour la démonstration. On aurait pu utiliser une fonction lambda comme on l'a fait pour onmousemove.

Voici finalement le code complet de la démonstration:

<script>
var mydiv = document.getElementById("mydiv");

var xMousePos = 0;
var yMousePos = 0;
document.onmousemove = function(e)
{
  xMousePos = e.clientX + window.pageXOffset;
  yMousePos = e.clientY + window.pageYOffset;
};

function update(e)
{
  var x = xMousePos - mydiv.offsetLeft;
  var y = yMousePos - mydiv.offsetTop;
  alert("x=" + x + " y=" + y);
}

mydiv.onclick = update;

mydiv.onmousemove = function()
{
  var x = xMousePos - mydiv.offsetLeft;
  var y = yMousePos - mydiv.offsetTop;
  mydiv.style.cursor='wait';
  if(x > mydiv.offsetWidth - 4)
    mydiv.style.cursor='e-resize';
  if(y > mydiv.offsetHeight - 4)
    mydiv.style.cursor='n-resize';
  document.getElementById("message").innerHTML = "Pos x = " + x + "/" + 
      mydiv.offsetWidth +  " y = " + y + 
      "/" +mydiv.offsetHeight;
}
</script>  

On dispose ainsi de tous les éléments nécessaires pour utiliser la souris en rapport avec une balise div, ou tout autre élément car ces propriétés s'appliquent à la plupart des balises HTML (à l'exception notamment des iframes).

Pour aller plus loin avec la souris, de nouvelles fonctions seront nécessaires qui seront certainement déjà disponibles dans un framework. Par exemple, si l'on veut redimensionner le calque avec la souris il vaut mieux utiliser un des frameworks les plus populaires, tel que jQuery resizable un plugin spécialisé pour le redimensionnement d'un calque.

© 2012-2014 Xul.fr