J'ai un champ de saisie qui fait apparaître un menu déroulant personnalisé. Je voudrais la fonctionnalité suivante :
- Lorsque l'utilisateur clique n'importe où en dehors du champ de saisie, le menu doit être supprimé.
- Si, plus précisément, l'utilisateur clique sur un div à l'intérieur du menu, ce dernier doit être supprimé, et un traitement spécial doit être effectué en fonction de la division sur laquelle on a cliqué.
Voici ma mise en œuvre :
Le champ de saisie a un onblur()
qui supprime le menu (en définissant la valeur de l'événement innerHTML
à une chaîne vide) lorsque l'utilisateur clique en dehors du champ de saisie. Les divs à l'intérieur du menu ont également onclick()
les événements qui exécutent le traitement spécial.
Le problème est que le onclick()
ne se déclenchent jamais lorsque l'on clique sur le menu, car le champ d'entrée onblur()
se déclenche en premier et supprime le menu, y compris l'option onclick()
s !
J'ai résolu le problème en séparant les divs du menu. onclick()
en onmousedown()
y onmouseup()
et la mise en place d'un drapeau global lors de l'abaissement de la souris, qui est effacé lors du relèvement de la souris, de manière similaire à ce qui a été suggéré dans le document intitulé cette réponse . Parce que onmousedown()
incendies avant onblur()
l'indicateur de validité sera activé dans onblur()
si l'on clique sur l'une des divisions du menu, mais pas si l'on clique ailleurs sur l'écran. Si le menu a été cliqué, je retourne immédiatement de la page onblur()
sans effacer le menu, puis attendez que le bouton onclick()
pour se déclencher, à ce moment-là je peux supprimer le menu en toute sécurité.
Existe-t-il une solution plus élégante ?
Le code ressemble à quelque chose comme ceci :
<div class="menu" onmousedown="setFlag()" onmouseup="doProcessing()">...</div>
<input id="input" onblur="removeMenu()" ... />
var mouseflag;
function setFlag() {
mouseflag = true;
}
function removeMenu() {
if (!mouseflag) {
document.getElementById('menu').innerHTML = '';
}
}
function doProcessing(id, name) {
mouseflag = false;
...
}