Javascript 检测按钮是单击真实用户还是由脚本触发

Javascript 检测按钮是单击真实用户还是由脚本触发,javascript,events,onclick,Javascript,Events,Onclick,是否有任何方法可以让我检测按钮点击是否由真实用户执行,而不是用户加载到浏览器开发人员控制台或其他浏览器开发人员工具上的某种自动方法(javascript) 我在不同的stackoverflow帖子中尝试了以下建议的方法,但没有一个有效。 参考: 脚本检测方法已尝试但失败: mybutton.click(function (e) { if (!e.which) { //Triggered by code NOT Actually clicked alert(

是否有任何方法可以让我检测按钮点击是否由真实用户执行,而不是用户加载到浏览器开发人员控制台或其他浏览器开发人员工具上的某种自动方法(javascript)

我在不同的stackoverflow帖子中尝试了以下建议的方法,但没有一个有效。 参考:

脚本检测方法已尝试但失败:

mybutton.click(function (e) {
    if (!e.which) {
        //Triggered by code NOT Actually clicked
        alert(' e.which - not a real button click')
    } else if ('isTrusted' in e && !e.isTrsuted) {
        //Triggered by code NOT Actually clicked
        alert(' e.isTrusted - not a real button click')
    } else if (e.originalEvent === undefined) {
        //Triggered by code NOT Actually clicked
        alert(' e.originalEvent - not a realbutton click')
    }
    //                  else if (!e.focus) {
    //                      //triggered  // does not detect e.focus on a real btn click
    //                      alert(' e.focus - not a realbutton click')
    //                  }
    else {
        // Button hopefully clicked by a real user and not a script
    }
})
如果我从Chrome浏览器控制台运行以下脚本来触发按钮单击,则上面的任何方法都不会将其捕获为由脚本触发

var button = document.getElementById("btnSubmit");
button.click();
==========================================================================

感谢您的回复,感谢stackoverflow提供了一个非常棒的网站,促进了如此多的知识共享,并为我们技术人员节省了数不清的时间

看来我还没有可靠的方法。所有3种浏览器(FF、IE和Chrome)都提供了开发者/控制台界面,用户可以在我的网页上运行/注入javascript。看起来,每个浏览器的风格捕获的某些事件属性值略有不同。例如:Chrome捕捉了脚本激活的cick和使用e.screenX的真实用户之间的差异,但在IE中:e.screenX对于脚本单击(合成)和用户按钮单击具有相同的值

以下检测方法要么根本不起作用,要么在不同的浏览器中不一致:e.which e.isTrsuted e.originalEvent(event.source!=window)(e.distance!=null)

mousedown事件似乎仅由实际用户的按钮单击触发,但我必须假设除了按钮单击事件之外,还有一些脚本方法可以模拟mousedown

$(me.container + ' .mybutton').mousedown(function (e) { 
    alert('mouseisdown real button click'); 
}

如果任何人都能找到一种可靠的方法,可以跨多个浏览器工作,检测合成(脚本)按钮单击和用户按钮单击之间的差异,您将获得超级英雄的身份。

出于安全考虑,当您使用javascript触发事件时,它的注册方式与用户触发事件时的注册方式不同。控制台记录
ev
对象,您将看到这两种情况之间的显著差异

mybutton.click(function(ev) {
  console.log(ev);
});
以下是两种情况的一些示例输出:

jQuery.Event
currentTarget: button
data: null
delegateTarget: button
handleObj: Object
isTrigger: true
jQuery191011352501437067986: true
namespace: ""
namespace_re: null
result: undefined
target: button
timeStamp: 1360472753601
type: "mousedown"
__proto__: Object

jQuery.Event {originalEvent: MouseEvent, type: "mousedown", isDefaultPrevented:     function, timeStamp: 1360472840714, jQuery191011352501437067986: true…}
altKey: false
bubbles: true
button: 0
buttons: undefined
cancelable: true
clientX: 39
clientY: 13
ctrlKey: false
currentTarget: button
data: null
delegateTarget: button
eventPhase: 2
fromElement: null
handleObj: Object
isDefaultPrevented: function returnFalse() {
jQuery191011352501437067986: true
metaKey: false
offsetX: 37
offsetY: 11
originalEvent: MouseEvent
pageX: 39
pageY: 13
relatedTarget: null
screenX: 1354
screenY: 286
shiftKey: false
target: button
timeStamp: 1360472840714
toElement: button
type: "mousedown"
view: Window
which: 1
__proto__: Object
在这里

或Javascript:

document.getElementsByTagName('button')[0].onmousedown = function(e) {
 if(e.which) {
    alert(1); // original click
 }
}
document.getElementsByTagName('button')[0].onmousedown();
您可以在小提琴中看到,它不会让触发器函数调用,但只有当鼠标按下按钮时才会调用。如果在按钮上触发了自动点击,则
e.
未定义,很容易被捕获


更新:

当鼠标点击按钮时,事件e通常会记录鼠标指针的位置。尝试以下方法:

   if(e.screenX && e.screenX != 0 && e.screenY && e.screenY != 0){
     alert("real button click");
   }

不,不可能在所有情况下都这样

正如其他答案所提到的,您可以查找鼠标坐标(clientX/Y和screenX/Y),如果它们不存在,您可以假设这可能不是人类生成的动作

但是,如果用户单击按钮并使用空格键单击它,或者不使用鼠标单击它,坐标也将为零,此方法将错误地将其确定为脚本式单击

// This will produce what appears to be a user-generated click.
function simulateClick(element) {
  var evt = document.createEvent("MouseEvents");
  evt.initMouseEvent("click", true, true, window,
    0, 110, 111, 10, 11, false, false, false, false, 0, null);
  element.dispatchEvent(evt);
}
此外,如果脚本使用
dispatchEvent
而不是
单击
,则可以为事件提供坐标。在这种情况下,此方法将错误地将其标识为用户生成的单击

// This will produce what appears to be a user-generated click.
function simulateClick(element) {
  var evt = document.createEvent("MouseEvents");
  evt.initMouseEvent("click", true, true, window,
    0, 110, 111, 10, 11, false, false, false, false, 0, null);
  element.dispatchEvent(evt);
}

使用“event.isTrusted”知道事件是由Javascript或用户单击触发的

示例代码:

<!DOCTYPE html>
<html>
<head>
  <title>Page Title</title>
</head>
<body>

  <input type="text" id="myInput">
  <button id="myBtn" onclick="callFunction(event)">Click Me</button>

  <script>
    function callFunction(event) {
      console.log(event.isTrusted); // true only when user clicks 'Click Me' button
    }
    window.onload = function () {
      let event = new Event("click");
      callFunction(event); // false
    }
    var input = document.getElementById("myInput");
    // Execute a function when the user releases a key on the keyboard
    input.addEventListener("keyup", function (event) {
      if (event.keyCode === 13) {
        event.preventDefault();
        document.getElementById("myBtn").click(); // false
      }
    });
  </script>

</body>

</html>

页面标题
点击我
函数调用函数(事件){
console.log(event.isTrusted);//仅当用户单击“单击我”按钮时为true
}
window.onload=函数(){
让事件=新事件(“单击”);
callFunction(event);//false
}
var input=document.getElementById(“myInput”);
//当用户释放键盘上的键时执行一个函数
input.addEventListener(“键控”,函数(事件){
如果(event.keyCode===13){
event.preventDefault();
document.getElementById(“myBtn”)。单击();//false
}
});

Good fiddle,我刚刚添加了一个console.log,这样他就可以看到我在回答中描述的输出,如果他愿意的话@KyleWeller先生,您也可以将其添加到我的答案中。@AspiringAqib您是否尝试过
document.getElementsByTagName('button')[0]。单击()?@AspiringAqib这有什么用?充其量,您已经找到了一种注册事件的方法,该事件在您调用元素上的click方法时不会触发。这不符合问题的要求。如果用户点击按钮并按下空格键“点击”它会怎么样?这是一个拖动示例,问题说明了点击事件的问题。在Chrome中,点击按钮事件:e显示脚本点击和实际点击的(e.originalEvent.type=='mousedown')。在不同的浏览器中是否有其他属性是不同的和一致的?对于Chrome来说是有效的,但在IE开发控制台中不是。在IE e.screenX中,手动按钮和脚本按钮都有+值。单击截至目前,我看不到接受的答案。更糟糕的是,我不愿意接受。对于firefox e.isTrusted的作品,其他人不知道。e、 isTrsuted不起作用;-)