jQuery 将焦点设置在 div contenteditable 元素上

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2388164/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-26 13:24:14  来源:igfitidea点击:

Set focus on div contenteditable element

jqueryfocuscontenteditable

提问by sanceray3

I have a <div contenteditable=true>where I define by a WYSIWYG some elements. For example <p>,<h1>, etc. I would like to put directly the focus on one of this elements.

我有一个<div contenteditable=true>由 WYSIWYG 定义的一些元素。例如<p><h1>等等。我想直接把重点放在这个元素之一上。

For example on <p id="p_test">. But it seems that focus()function doesn't work on <div>elements, <p>elements...

例如在<p id="p_test">. 但似乎该focus()功能不适用于<div>元素,<p>元素......

Is there a another means to define the focus in my case?

在我的情况下,是否有另一种方法来定义焦点?

回答by chris97ong

Old post but none of the solutions worked for me. I figured it out eventually though:

旧帖子,但没有一个解决方案对我有用。不过我最终想通了:

var div = document.getElementById('contenteditablediv');
setTimeout(function() {
    div.focus();
}, 0);

回答by Dima Vidmich

In modern browsers you can use:

在现代浏览器中,您可以使用:

var p = document.getElementById('contentEditableElementId'),
    s = window.getSelection(),
    r = document.createRange();
r.setStart(p, 0);
r.setEnd(p, 0);
s.removeAllRanges();
s.addRange(r);

But if your element is empty I got some strange problems so for empty elements you can do this:

但是如果你的元素是空的,我会遇到一些奇怪的问题,所以对于空元素,你可以这样做:

var p = document.getElementById('contentEditableElementId'),
    s = window.getSelection(),
    r = document.createRange();
p.innerHTML = '\u00a0';
r.selectNodeContents(p);
s.removeAllRanges();
s.addRange(r);
document.execCommand('delete', false, null);

After deleting nbsp cursor stays inside p element

删除 nbsp 光标后留在 p 元素内

P.S. just ordinary space doesn't work for me

PS只是普通空间对我不起作用

回答by Vlad

I noticed that jQuery focus() did not work for my contenteditable DIV with width and height of 0. I replaced it with .get(0).focus() - the native javascript focus method - and it works.

我注意到 jQuery focus() 不适用于我的宽度和高度为 0 的 contenteditable DIV。我将它替换为 .get(0).focus() - 原生 javascript 焦点方法 - 并且它有效。

回答by Eye

In case someone, who uses MediumEditorthat manages contenteditableelement, stumbles upon this issue, the following has worked for me:

如果有人使用管理元素的MediumEditor 偶然发现contenteditable这个问题,以下对我有用

editor.selectElement(editorDOMNode);
  1. editoris an instance of MediumEditor.
  2. editorDOMNodeis a reference to the actual contenteditableDOM node.
  3. It is also possible to focus on a specific child node within the editor as follows:

    editor.selectElement(editorDOMNode.childNodes[0]);
    
  1. editor是 的一个实例MediumEditor
  2. editorDOMNode是对实际contenteditableDOM 节点的引用。
  3. 也可以关注编辑器中的特定子节点,如下所示:

    editor.selectElement(editorDOMNode.childNodes[0]);
    

回答by wafs

A lot of the time if you can't call .focus()on an element, it's because the tabIndex is -1, which means the tab key can't focus on it when you're pressing tab to navigate.

很多时候如果你不能调用.focus()一个元素,那是因为 tabIndex 是 -1,这意味着当你按 Tab 键导航时,tab 键不能聚焦在它上面。

Changing your tabIndex to >= 0 will let you focus on the elements. If you need to do it dynamically, you can just add a tabindex >= 0 to your element in the event listener.

将 tabIndex 更改为 >= 0 将使您专注于元素。如果您需要动态执行此操作,只需在事件侦听器中向元素添加 tabindex >= 0 即可。

回答by Surmon

You can try this code, it can auto focus in your last insert location.

你可以试试这个代码,它可以自动聚焦在你上次插入的位置。

let p = document.getElementById('contenteditablediv')
let s = window.getSelection()
let r = document.createRange()
r.setStart(p, p.childElementCount)
r.setEnd(p, p.childElementCount)
s.removeAllRanges()
s.addRange(r)

回答by M.Calugaru

To build further on @Surmon answer. If you are looking to auto focus right after your last letter/number in the text instead of the last insertion location (last insertion location will move the cursor to a new line if the child nodes are enclosed in block type tags and not plain text) then apply this small modification:

进一步建立@Surmon 答案。如果您希望在文本中的最后一个字母/数字而不是最后一个插入位置之后立即自动聚焦(如果子节点包含在块类型标签中而不是纯文本中,则最后一个插入位置会将光标移动到新行)然后应用这个小修改:

r.setStart(p.lastChild, 1);
r.setEnd(p.lastChild, 1);

This is an extended function that checks if the editor/element has any child nodes and depending on the situation sets the cursor accordingly at the end:

这是一个扩展函数,用于检查编辑器/元素是否有任何子节点,并根据情况在末尾相应地设置光标:

let p = document.getElementById('contenteditablediv');
p.focus();  // alternatively use setTimeout(() => { p.focus(); }, 0);
// this is enough to focus an empty element (at least in Chrome)

if (p.hasChildNodes()) {  // if the element is not empty
  let s = window.getSelection();
  let r = document.createRange();
  let e = p.childElementCount > 0 ? p.lastChild : p;  
  r.setStart(e, 1); 
  r.setEnd(e, 1);    
  s.removeAllRanges();
  s.addRange(r);
} 

回答by Brian P Johnson

Bind a "click" event handler to all elements within the contenteditable div, and change the class/style on click (i.e. add class "focused" to the element);

为 contenteditable div 内的所有元素绑定一个“click”事件处理程序,并在单击时更改类/样式(即向元素添加类“focused”);

You can identify, to the user, which element has focus by adding style such as a colorful border or an inner box-shadow. Then when you want to access the focused element in your jQuery script, just do something like this:

您可以通过添加样式(例如彩色边框或内部框阴影)来向用户标识哪个元素具有焦点。然后,当您想访问 jQuery 脚本中的焦点元素时,只需执行以下操作:

var focused = $('.focused');

var focused = $('.focused');