มีวิธีตรวจสอบว่าปุ่มเมาส์ค้างใน JavaScript หรือไม่?
ฉันรู้เกี่ยวกับเหตุการณ์ "มูสดาวน์" แต่นั่นไม่ใช่สิ่งที่ฉันต้องการ บางครั้งหลังจากกดปุ่มเมาส์ฉันต้องการตรวจจับว่ายังกดอยู่หรือไม่
เป็นไปได้หรือไม่
มีวิธีตรวจสอบว่าปุ่มเมาส์ค้างใน JavaScript หรือไม่?
ฉันรู้เกี่ยวกับเหตุการณ์ "มูสดาวน์" แต่นั่นไม่ใช่สิ่งที่ฉันต้องการ บางครั้งหลังจากกดปุ่มเมาส์ฉันต้องการตรวจจับว่ายังกดอยู่หรือไม่
เป็นไปได้หรือไม่
คำตอบ:
เกี่ยวกับโซลูชันของ Pax: จะไม่ทำงานหากผู้ใช้คลิกมากกว่าหนึ่งปุ่มโดยตั้งใจหรือไม่ตั้งใจ อย่าถามฉันว่าฉันรู้ได้อย่างไร :-(.
รหัสที่ถูกต้องควรเป็นเช่นนั้น:
var mouseDown = 0;
document.body.onmousedown = function() {
++mouseDown;
}
document.body.onmouseup = function() {
--mouseDown;
}
ด้วยการทดสอบดังนี้:
if(mouseDown){
// crikey! isn't she a beauty?
}
หากคุณต้องการทราบว่าปุ่มใดถูกกดให้เตรียม mouseDown อาร์เรย์ของตัวนับและนับแยกต่างหากสำหรับปุ่มแยกกัน:
// let's pretend that a mouse doesn't have more than 9 buttons
var mouseDown = [0, 0, 0, 0, 0, 0, 0, 0, 0],
mouseDownCount = 0;
document.body.onmousedown = function(evt) {
++mouseDown[evt.button];
++mouseDownCount;
}
document.body.onmouseup = function(evt) {
--mouseDown[evt.button];
--mouseDownCount;
}
ตอนนี้คุณสามารถตรวจสอบว่าปุ่มใดถูกกดอย่างแน่นอน:
if(mouseDownCount){
// alright, let's lift the little bugger up!
for(var i = 0; i < mouseDown.length; ++i){
if(mouseDown[i]){
// we found it right there!
}
}
}
ตอนนี้ขอเตือนว่าโค้ดด้านบนจะใช้ได้เฉพาะกับเบราว์เซอร์ที่เข้ากันได้มาตรฐานที่ส่งหมายเลขปุ่มให้คุณโดยเริ่มจาก 0 ขึ้นไป IE ใช้มาสก์บิตของปุ่มที่กดในปัจจุบัน:
ดังนั้นปรับรหัสของคุณให้เหมาะสม! ฉันปล่อยให้เป็นแบบฝึกหัด
และอย่าลืมว่า IE ใช้วัตถุเหตุการณ์ส่วนกลางที่เรียกว่า ... "เหตุการณ์"
อนึ่ง IE มีคุณลักษณะที่เป็นประโยชน์ในกรณีของคุณ: เมื่อเบราว์เซอร์อื่นส่ง "ปุ่ม" เฉพาะสำหรับเหตุการณ์ปุ่มเมาส์ (onclick, onmousedown และ onmouseup) IE จะส่งด้วย onmousemove ด้วย ดังนั้นคุณสามารถเริ่มฟัง onmousemove เมื่อคุณต้องการทราบสถานะปุ่มและตรวจสอบปุ่ม evt. ทันทีที่คุณได้รับ - ตอนนี้คุณรู้แล้วว่าปุ่มเมาส์ใดถูกกด:
// for IE only!
document.body.onmousemove = function(){
if(event.button){
// aha! we caught a feisty little sheila!
}
};
แน่นอนว่าคุณจะไม่ได้อะไรเลยถ้าเธอเล่นตายและไม่เคลื่อนไหว
ลิงค์ที่เกี่ยวข้อง:
อัปเดต # 1 : ฉันไม่รู้ว่าทำไมฉันถึงดำเนินการกับเอกสารรูปแบบของโค้ด จะดีกว่าถ้าแนบตัวจัดการเหตุการณ์เข้ากับเอกสารโดยตรง
event.buttons
เข้ากับทริกเกอร์เหตุการณ์ที่คุณใช้โดยไม่ต้องใช้ตัวแปรที่บันทึกไว้ภายนอก ฉันถามคำถามใหม่เอี่ยม (เนื่องจากเหตุการณ์เมาส์อัพของฉันไม่ได้เกิดขึ้นเสมอไปดังนั้นวิธีนี้จึงไม่ได้ผลสำหรับฉัน) และได้รับคำตอบนั้นภายใน 5 นาที
นี่เป็นคำถามเก่าและคำตอบที่นี่ดูเหมือนว่าส่วนใหญ่สนับสนุนให้ใช้mousedown
และmouseup
ติดตามว่ามีการกดปุ่มหรือไม่ แต่ตามที่คนอื่น ๆ ได้ชี้ให้เห็นmouseup
จะเริ่มทำงานเมื่อดำเนินการภายในเบราว์เซอร์เท่านั้นซึ่งอาจทำให้สูญเสียสถานะปุ่ม
อย่างไรก็ตามMouseEvent (ตอนนี้) จะระบุว่าปุ่มใดถูกผลักในขณะนี้:
MouseEvent.buttons
MouseEvent.which
( buttons
จะไม่ได้กำหนดไว้สำหรับ Safari) หมายเหตุ: which
ใช้ตัวเลขที่แตกต่างกันbuttons
สำหรับคลิกขวาและกลางเมื่อลงทะเบียนdocument
แล้วmousemove
จะเริ่มทำงานทันทีที่เคอร์เซอร์เปิดเบราว์เซอร์อีกครั้งดังนั้นหากผู้ใช้ออกสู่ภายนอกสถานะจะได้รับการอัปเดตทันทีที่พวกเขาเลื่อนเมาส์กลับเข้าไปข้างใน
การใช้งานอย่างง่ายอาจมีลักษณะดังนี้:
var leftMouseButtonOnlyDown = false;
function setLeftButtonState(e) {
leftMouseButtonOnlyDown = e.buttons === undefined
? e.which === 1
: e.buttons === 1;
}
document.body.onmousedown = setLeftButtonState;
document.body.onmousemove = setLeftButtonState;
document.body.onmouseup = setLeftButtonState;
หากจำเป็นต้องใช้สถานการณ์ที่ซับซ้อนมากขึ้น (ปุ่มต่างๆ / ปุ่มหลายปุ่ม / ปุ่มควบคุม) โปรดดูเอกสาร MouseEvent เมื่อไร / ถ้า Safari ยกเกมขึ้นสิ่งนี้จะง่ายขึ้น
e.buttons
จะเป็น1+2=3
ดังนั้นe.buttons === 1
จะเป็นเท็จ) หากคุณต้องการตรวจสอบว่าปุ่มหลักหยุดทำงานหรือไม่ แต่ไม่สนใจสถานะปุ่มอื่น ๆ ให้ทำดังนี้(e.buttons & 1) === 1
MouseEvent.buttons
ดูเหมือนว่า7
มันคิดว่าปุ่ม Primary, Secondary และ Auxilary ทั้งหมดถูกกดเข้าด้วยกัน ฉันไม่แน่ใจว่าทำไมถึงเป็นเช่นนั้น - คุณใช้เมาส์ขั้นสูงหรือไม่? ถ้าเป็นเช่นนั้นอาจคุ้มค่าที่จะลองใช้แบบพื้นฐาน หากคุณเพียงแค่ต้องการดำเนินการต่อคุณสามารถใช้การตรวจสอบแบบบิตเพื่อให้แน่ใจว่ากดปุ่มซ้ายและไม่สนใจสิ่งอื่นใด เช่น. MouseEvent.buttons & 1 === 1
.
ฉันคิดว่าแนวทางที่ดีที่สุดคือการเก็บบันทึกสถานะปุ่มเมาส์ของคุณเองดังนี้:
var mouseDown = 0;
document.body.onmousedown = function() {
mouseDown = 1;
}
document.body.onmouseup = function() {
mouseDown = 0;
}
จากนั้นในรหัสของคุณในภายหลัง:
if (mouseDown == 1) {
// the mouse is down, do what you have to do.
}
วิธีแก้ปัญหาไม่ดี เราสามารถ "ติดเมาส์" บนเอกสารจากนั้นจึง "วางเมาส์" นอกเบราว์เซอร์และในกรณีนี้เบราว์เซอร์จะยังคงคิดว่าเมาส์ไม่ทำงาน
ทางออกเดียวที่ดีคือการใช้วัตถุ IE.event
ฉันรู้ว่านี่เป็นโพสต์เก่า แต่ฉันคิดว่าการติดตามปุ่มเมาส์โดยใช้เมาส์ขึ้น / ลงรู้สึกอึดอัดเล็กน้อยดังนั้นฉันจึงพบทางเลือกที่อาจดึงดูดใจบางคน
<style>
div.myDiv:active {
cursor: default;
}
</style>
<script>
function handleMove( div ) {
var style = getComputedStyle( div );
if (style.getPropertyValue('cursor') == 'default')
{
// You're down and moving here!
}
}
</script>
<div class='myDiv' onmousemove='handleMove(this);'>Click and drag me!</div>
ตัวเลือกที่ใช้งานอยู่จะจัดการกับการคลิกเมาส์ได้ดีกว่าการเลื่อนเมาส์ขึ้น / ลงคุณเพียงแค่ต้องการวิธีอ่านสถานะนั้นในเหตุการณ์ onmousemove ด้วยเหตุนี้ฉันจึงต้องโกงและอาศัยข้อเท็จจริงที่ว่าเคอร์เซอร์เริ่มต้นคือ "อัตโนมัติ" และฉันเพิ่งเปลี่ยนเป็น "ค่าเริ่มต้น" ซึ่งเป็นสิ่งที่อัตโนมัติเลือกโดยค่าเริ่มต้น
คุณสามารถใช้อะไรก็ได้ในออบเจ็กต์ที่ส่งคืนโดย getComputedStyle ที่คุณสามารถใช้เป็นแฟล็กโดยไม่ทำให้หน้าตาของเพจของคุณเสียไปเช่น border-color
ฉันต้องการตั้งค่ารูปแบบที่ผู้ใช้กำหนดเองในส่วน: active แต่ฉันไม่สามารถใช้งานได้ มันจะดีกว่าถ้าเป็นไปได้
ตัวอย่างต่อไปนี้จะพยายามเรียกใช้ฟังก์ชัน "doStuff" 2 วินาทีหลังจากเหตุการณ์ mouseDown เกิดขึ้นใน document.body หากผู้ใช้ยกปุ่มขึ้นเหตุการณ์ mouseUp จะเกิดขึ้นและยกเลิกการดำเนินการที่ล่าช้า
ฉันขอแนะนำให้ใช้วิธีการบางอย่างสำหรับการแนบเหตุการณ์ข้ามเบราว์เซอร์ - การตั้งค่าคุณสมบัติการเลื่อนลงและเมาส์อัพทำได้อย่างชัดเจนเพื่อทำให้ตัวอย่างง่ายขึ้น
function doStuff() {
// does something when mouse is down in body for longer than 2 seconds
}
var mousedownTimeout;
document.body.onmousedown = function() {
mousedownTimeout = window.setTimeout(doStuff, 2000);
}
document.body.onmouseup = function() {
window.clearTimeout(mousedownTimeout);
}
ฉันไม่แน่ใจว่าทำไมคำตอบก่อนหน้านี้ไม่ได้ผลสำหรับฉัน แต่ฉันคิดหาวิธีแก้ปัญหานี้ในช่วงเวลาที่ยูเรก้า ไม่เพียง แต่ใช้งานได้ แต่ยังหรูหราที่สุด:
เพิ่มในแท็กเนื้อหา:
onmouseup="down=0;" onmousedown="down=1;"
จากนั้นทดสอบและดำเนินการmyfunction()
ถ้าdown
เท่ากับ1
:
onmousemove="if (down==1) myfunction();"
หากคุณกำลังทำงานในหน้าที่ซับซ้อนที่มีตัวจัดการเหตุการณ์ของเมาส์ฉันขอแนะนำให้จัดการเหตุการณ์เมื่อจับภาพ (แทนที่จะเป็นลูกโป่ง) การทำเช่นนี้เพียงแค่ตั้งค่าพารามิเตอร์ที่ 3 ของการaddEventListener
true
นอกจากนี้คุณอาจต้องการตรวจสอบเพื่อให้แน่ใจว่าคุณกำลังจัดการโต้ตอบกับผู้ใช้จริงและไม่ได้เหตุการณ์ของเมาส์เช่นevent.which
elem.dispatchEvent(new Event('mousedown'))
var isMouseDown = false;
document.addEventListener('mousedown', function(event) {
if ( event.which ) isMouseDown = true;
}, true);
document.addEventListener('mouseup', function(event) {
if ( event.which ) isMouseDown = false;
}, true);
เพิ่มตัวจัดการในเอกสาร (หรือหน้าต่าง) แทน document.body มีความสำคัญ b / c เพื่อให้แน่ใจว่าเหตุการณ์การวางเมาส์นอกหน้าต่างยังคงถูกบันทึกไว้
คุณสามารถรวม @Pax และคำตอบของฉันเพื่อให้ได้ระยะเวลาที่เมาส์หยุดทำงาน:
var mousedownTimeout,
mousedown = 0;
document.body.onmousedown = function() {
mousedown = 0;
window.clearInterval(mousedownTimeout);
mousedownTimeout = window.setInterval(function() { mousedown += 200 }, 200);
}
document.body.onmouseup = function() {
mousedown = 0;
window.clearInterval(mousedownTimeout);
}
หลังจากนั้น:
if (mousedown >= 2000) {
// do something if the mousebutton has been down for at least 2 seconds
}
คุณต้องจัดการ MouseDown และ MouseUp และตั้งค่าสถานะหรือบางอย่างเพื่อติดตาม "ในภายหลังลงที่ถนน" ... :(
การใช้MouseEvent api เพื่อตรวจสอบปุ่มที่กดหากมี:
document.addEventListener('mousedown', (e) => console.log(e.buttons))
กลับ :
ตัวเลขแทนปุ่มอย่างน้อยหนึ่งปุ่ม สำหรับการกดปุ่มมากกว่าหนึ่งปุ่มพร้อมกันค่าต่างๆจะรวมกัน (เช่น 3 คือหลัก + รอง)
0 : No button or un-initialized 1 : Primary button (usually the left button) 2 : Secondary button (usually the right button) 4 : Auxilary button (usually the mouse wheel button or middle button) 8 : 4th button (typically the "Browser Back" button) 16 : 5th button (typically the "Browser Forward" button)
เมื่อใช้ jQuery วิธีแก้ปัญหาต่อไปนี้จะจัดการแม้กระทั่ง "ลากออกจากเพจแล้วปล่อยเคส"
$(document).mousedown(function(e) {
mouseDown = true;
}).mouseup(function(e) {
mouseDown = false;
}).mouseleave(function(e) {
mouseDown = false;
});
ฉันไม่รู้ว่ามันจัดการกับปุ่มเมาส์หลายปุ่มอย่างไร หากมีวิธีเริ่มการคลิกนอกหน้าต่างให้นำเมาส์ไปที่หน้าต่างสิ่งนี้อาจทำงานไม่ถูกต้องเช่นกัน
ด้านล่างตัวอย่าง jQuery เมื่อเมาส์มีค่ามากกว่า $ (". element") สีจะเปลี่ยนไปตามปุ่มเมาส์ที่กด
var clicableArea = {
init: function () {
var self = this;
('.element').mouseover(function (e) {
self.handlemouseClick(e, $(this));
}).mousedown(function (e) {
self.handlemouseClick(e, $(this));
});
},
handlemouseClick: function (e, element) {
if (e.buttons === 1) {//left button
element.css('background', '#f00');
}
if (e.buttons === 2) { //right buttom
element.css('background', 'none');
}
}
};
$(document).ready(function () {
clicableArea.init();
});
ตามที่กล่าวไว้ @Jack เมื่อmouseup
เกิดขึ้นนอกหน้าต่างเบราว์เซอร์เราจะไม่รู้ตัว ...
window.addEventListener('mouseup', mouseUpHandler, false);
window.addEventListener('mousedown', mouseDownHandler, false);
mouseup
งานในกรณีใดกรณีหนึ่ง: var mousedown = 0;
$(function(){
document.onmousedown = function(e){
mousedown = mousedown | getWindowStyleButton(e);
e = e || window.event;
console.log("Button: " + e.button + " Which: " + e.which + " MouseDown: " + mousedown);
}
document.onmouseup = function(e){
mousedown = mousedown ^ getWindowStyleButton(e);
e = e || window.event;
console.log("Button: " + e.button + " Which: " + e.which + " MouseDown: " + mousedown);
}
document.oncontextmenu = function(e){
// to suppress oncontextmenu because it blocks
// a mouseup when two buttons are pressed and
// the right-mouse button is released before
// the other button.
return false;
}
});
function getWindowStyleButton(e){
var button = 0;
if (e) {
if (e.button === 0) button = 1;
else if (e.button === 1) button = 4;
else if (e.button === 2) button = 2;
}else if (window.event){
button = window.event.button;
}
return button;
}
เวอร์ชันข้ามเบราว์เซอร์นี้ใช้งานได้ดีสำหรับฉัน
ไม่สามารถตรวจสอบได้ว่ามันลงหลังจากเหตุการณ์หรือไม่ แต่คุณสามารถตรวจสอบได้ว่ามันขึ้น ... ถ้ามันขึ้น .. แสดงว่าไม่ลงอีกต่อไป: P lol
ดังนั้นผู้ใช้จึงกดปุ่มลง (เหตุการณ์ onMouseDown) ... และหลังจากนั้นคุณจะตรวจสอบว่าขึ้นหรือไม่ (onMouseUp) แม้ว่าจะยังไม่ขึ้นคุณสามารถทำสิ่งที่ต้องการได้