如何获取contenteditable div中用户编辑/创建的具体元素?
解决contenteditable div中动态p标签的keyup事件问题
首先,你遇到的问题核心是动态生成的DOM元素无法触发预先绑定的事件——当你直接执行$(".pad p").keyup(...)时,页面上还没有那些用户输入后才生成的p标签,所以这个绑定只会作用于当时已存在的p,新生成的自然不会响应。
这里有两种靠谱的解决思路:
思路1:使用事件委托绑定p标签的keyup事件
把事件绑定在父元素.pad上,利用事件冒泡机制来监听子元素(包括动态生成的p)的事件。这样不管后续生成多少个p标签,只要它们是.pad的子元素,就能触发事件:
$(".pad").on("keyup", "p", function(e) { doSomething(); // 这里的`this`就是当前正在编辑的p元素 const theEditedElement = this; // 你可以直接用这个元素做后续操作,比如修改样式、获取内容等 });
这种方式的好处是代码简洁,而且自动适配所有动态生成的p标签,不需要每次生成p后再手动绑定事件。
思路2:在原有的.pad keyup事件中获取当前编辑的元素
如果你想保留原有的.pad绑定逻辑,只需要在事件回调里通过光标位置找到当前编辑的元素即可。因为contenteditable中,用户编辑的位置对应光标所在的DOM节点,我们可以通过window.getSelection()来获取这个节点:
$(".pad").keyup(function(e) { const selection = window.getSelection(); if (selection.rangeCount === 0) return; // 没有选中内容时直接返回 let editedNode = selection.getRangeAt(0).commonAncestorContainer; // 处理文本节点的情况(光标可能在文本节点内,需要取它的父元素) if (editedNode.nodeType === Node.TEXT_NODE) { editedNode = editedNode.parentNode; } // 确认找到的节点是`.pad`下的p标签 const theEditedElement = $(editedNode).closest(".pad p")[0]; if (theEditedElement) { doSomething(theEditedElement); // 现在你可以用theEditedElement访问当前编辑的p元素了 } });
补充说明
- 为什么不能直接用
e.target?因为在contenteditable中,e.target可能是文本节点(nodeType=3),而不是你想要的p标签,所以需要额外判断并向上查找父元素。 - 事件委托是处理动态DOM元素事件的标准方案,推荐优先使用思路1,代码更简洁且性能更优(只绑定一个事件在父元素上,而不是多个事件在子元素)。
内容的提问来源于stack exchange,提问作者Osman
相关产品推荐
相关产品推荐

