jQuery - *:not()不排除元素

时间:2016-12-09 17:44:10

标签: jquery jquery-selectors

我的目标是禁用除<kbd><textarea>标记之外的任何地方的右键单击。我使用*:not(kbd,textarea)排除停用右键单击 - .on('contextmenu', function(e){ e.preventDefault(); });。我可以右键点击<kbd><textarea>标签,但我不能。这很糟糕。

&#13;
&#13;
$(document).ready(function(){
  $('*:not(kbd,textarea)').on('contextmenu', function(e){
      e.preventDefault();
  });
});
&#13;
div {
  width: 170px;
  height: 170px;
  background-color: green;
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
<kbd>right click me</kbd>
<textarea>right click me</textarea>
can't right click me
</div>
&#13;
&#13;
&#13;

1 个答案:

答案 0 :(得分:2)

要明确:*:not(kbd,textarea)工作正常。问题与在浏览器中处理事件的方式有关。

大多数事件都在冒泡,contextmenu does as well。由于<kbd><textarea>元素位于<div>内,因此绑定到<div>的事件处理程序将始终取消contextmenu事件。

根据您的确切用例,您可以简单地检查事件是否源自元素本身,并且仅在这种情况下阻止它:

&#13;
&#13;
$(document).ready(function(){
  $('*:not(kbd,textarea)').on('contextmenu', function(e){
      if (this === e.target) {
        e.preventDefault();
      }
  });
});
&#13;
div {
  width: 170px;
  height: 170px;
  background-color: green;
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
<kbd>right click me</kbd>
<textarea>right click me</textarea>
can't right click me
</div>
&#13;
&#13;
&#13;

但是,不是将处理程序绑定到每个元素,而是使用事件委派。将处理程序绑定到文档的根目录并检查事件的来源:

&#13;
&#13;
$(document).ready(function(){
  $('body').on('contextmenu', function(e){
      if (!$(e.target).is('kbd,textarea')) {
        e.preventDefault();
      }
  });
});
&#13;
div {
  width: 170px;
  height: 170px;
  background-color: green;
}
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div>
<kbd>right click me</kbd>
<textarea>right click me</textarea>
can't right click me
</div>
&#13;
&#13;
&#13;