6859799d7f0ff85994452c04c2aa568d74e35476 chmalee Fri Sep 8 14:02:48 2023 -0700 Fix mouseovers not going away when moving away from them, refs #31365 diff --git src/hg/js/utils.js src/hg/js/utils.js index ad09d68..d5e0d2c 100644 --- src/hg/js/utils.js +++ src/hg/js/utils.js @@ -3867,64 +3867,80 @@ popUpEl.style.left = leftOffset + "px"; popUpEl.style.top = topOffset + "px"; } function replaceReserved(txt) { /* This should somehow be made more general so we can stop worrying about * user made tracks with whatever characters in it */ if (!txt) { throw new Error("trying to replace null txt"); } return txt.replace(/[^A-Za-z0-9_]/g, "_"); } // the current mouseover timer, for showing the mouseover after a delay var mouseoverTimer; +// the timer for when a user is moving the mouse after already bringing up +// a pop up, there may be many items close together and we want the user +// to bring up those mouseovers +var mousemoveTimer; +var showDiffMouseover = false; // signal handler for when mousemove has gone far enough away from the pop up // we can't use removeEventListener because the function call is hard to keep // track of because of a bounded this keyword var mousemoveSignal; // The div that moves around the users screen with the visible mouseover text var mouseoverContainer; function hideMouseoverText(ele) { /* Actually hides the tooltip text */ let tooltipTarget = ele; tooltipTarget.classList.remove("isShown"); tooltipTarget.style.opacity = "0"; tooltipTarget.style.visibility = "hidden"; } +function mousemoveTimerHelper(e) { + showDiffMouseover = true; + clearTimeout(mousemoveTimer); + mousemoveTimer = undefined; +} + function mousemoveHelper(e) { /* Helper function for deciding whether to keep a tooltip visible upon a mousemove event */ - if ($(".tooltip.isShown").length > 0) { - return; + if (mousemoveTimer === undefined) { + // if we are over another mouseable element we want to show that one instead + // use this timer to do so + showDiffMouseover = false; + mousemoveTimer = setTimeout(mousemoveTimerHelper, 100, e); } let targetBox = this.getBoundingClientRect(); let mouseX = e.clientX; let mouseY = e.clientY; // currently allow the mouse to move in a 45 pixel box around the element if ( mouseX >= (targetBox.left - 45) && mouseX <= (targetBox.right + 45) && - mouseY >= (targetBox.top - 45) && mouseY <= (targetBox.bottom + 45) ) { - // keep the mouseover showing + mouseY >= (targetBox.top - 45) && mouseY <= (targetBox.bottom + 45) + && !showDiffMouseover) { return; } else { // now that we are going to hide the pop up we can remove the event listener // for whether we wanted to keep the pop up or not + if ($(".tooltip.isShown").length > 0) { console.log("hiding mouseover in mousemove helper:"); console.log(this); hideMouseoverText(this); + } mousemoveSignal.abort(); } } function showMouseoverText(e) { // actually show the mouseover text e.preventDefault(); referenceElement = e.target; if (!e.target.getAttribute("mouseoverid")) { // corner case: the side slice and grey control bar slice are weird, the td // container has the title tag, while the img or a element receives the mouseover // event, so we need to go back up the tree to find the mouseoverid for those elems while (referenceElement.parentElement && !referenceElement.getAttribute("mouseoverid")) { referenceElement = referenceElement.parentElement; }