jQuery keydown回调仅侦听外部<ul>而不是内部<li>元素

时间:2015-07-20 12:19:10

标签: javascript jquery html contenteditable

嘿所以这是我制作的代码演示

<!DOCTYPE html>
<html>
<head>
  <script src="https://code.jquery.com/jquery-1.11.3.min.js"></script>
</head>
<body>
<ul contenteditable class="outerList">
<li class="innerElement">Hello</li>
<li class="innerElement">World</li>
<li class="innerElement">Hello World</li>
</ul>
<script>
    $(".outerList").keydown(function () {
      console.log("I am the outer ul");
    });
    $(".innerElement").keydown(function() {
      console.log("I am an inner element");
    });
    </script>
</body>
</html>

这是运行它的jsFiddle

http://jsfiddle.net/scrbovyr/

基本上我有一个内容可编辑的UL,我想要捕获回车键并传入我自己的自定义功能。但是我需要知道keydown事件被抛出的LI元素。并且如演示中所示,我似乎只能将keydown事件侦听器(或任何事件侦听器)绑定到外部UL元素。有没有办法将keydown事件附加到每个LI?或者至少有一种方法可以将它附加到UL,但仍然告诉它来自哪个孩子?

在此先感谢,如果有任何其他信息有帮助,请与我们联系!

2 个答案:

答案 0 :(得分:2)

您必须将contenteditable添加到li元素才能实现这一目标。您将contenteditable设置为ul元素,因此,该事件将绑定到该元素,您可以编辑li元素,但它们没有设置contenteditable ,因此不会触发这些元素的键盘事件。

<ul class="outerList">
    <li contenteditable class="innerElement">Hello</li>
    <li contenteditable class="innerElement">World</li>
    <li contenteditable class="innerElement">Hello World</li>
</ul>

然后:

$(".innerElement").keydown(function() {
  console.log("I am an inner element");
});

答案 1 :(得分:2)

您可以检查当前选择的节点

如果您不想让每个li成为contenteditable元素,您可以将元素放在当前选择或插入位置并对其进行检查。

嵌入式示例显示了如何使用Web API Interface for contenteditable selections实现此目的。 (我在Chrome中对此进行了测试,但可能需要其他逻辑才能实现跨浏览器兼容性。)

值得注意的是,可以某些事件侦听器绑定到contenteditable元素的子元素。例如,click事件可能绑定到li元素,如嵌入式示例中所示。

&#13;
&#13;
$(document).ready(function() {
    
    function getCurrentNode() {
        var node = window.getSelection().getRangeAt(0).commonAncestorContainer;
        return node.nodeType === 1 ? node : node.parentNode;     
    }
    $('.outerList').on('click keyup', function (e) {
        var $target  = $(getCurrentNode()),
            $closest = $target.closest('b');
        console.log(e.type);
        console.log('I am the outer ul');
        console.log($target);
        
        // Optional. Filter by clostest selector.
        if ($closest.length) {
            console.log('Target matches selector', $closest);
        }
    });
    $('.innerElement').on('click', function (e) {
        console.log(e.type);
        console.log('I am an inner element');
    });
});
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul contenteditable class="outerList">
      <li class="innerElement">Hello</li>
      <li class="innerElement"><i>Hello</i></li>
      <li class="innerElement"><b><i>Hello</i></b></li>
      <li class="innerElement"><b>Hello</b></li>
      <li class="innerElement">Hello</li>
      <li class="innerElement">Hello</li>
  </ul>
&#13;
&#13;
&#13;