如何修复光标在 Android Chrome 上的内联 contenteditable 中跳转?

Posted

技术标签:

【中文标题】如何修复光标在 Android Chrome 上的内联 contenteditable 中跳转?【英文标题】:How to fix cursor jumping in inline contenteditable on Android Chrome? 【发布时间】:2021-09-12 04:15:48 【问题描述】:

我遇到了一个奇怪的问题:

html 中具有预定义内容的 contenteditable <span> 上,每当您开始输入新单词时,文本光标都会跳回到某个点。它跳转到的位置在原始内容的末尾。

例子:

<span contenteditable>foo</span>

这发生在使用 Gboard 10.6.02.371892758-release-arm64-v8a 的 android Chrome 91.0.4472.120、Android 11 上。 我还在桌面 Chrome 和 ios Safari 上进行了测试。那里无法重现问题,只有 Andriod Chrome。

对于<p><div> 等块元素不会发生这种情况,但如果我将display:inline 设置为<p> 使用css,则问题与跨度相同。

如果元素最初不包含文本(例如<span contenteditable></span>)也不会发生这种情况,即使用户随后对其进行编辑以包含文本也是如此。

关于为什么会发生这种情况的任何想法?这似乎是 Chrome/Android 的某种错误。是否有解决方法/修复它?

注意:我需要使用 contenteditable 和 inline,因为我希望元素在不占用整行的情况下换行,因此不能选择 input 或 textarea。

【问题讨论】:

【参考方案1】:

这是我找到的解决方法。

如果在选择/聚焦元素时使用Range.insertNode() 将文本添加到空元素,则不会触发问题。

因此,我们可以清除内容,选择元素,然后在元素被聚焦时使用此方法重新插入原始内容,以防止出现问题。

const onFocus = (e) => 
    const selection = window.getSelection();
    const selectionRange = new Range();

    const originalContent = e.target.textContent;

    // Clear the content and select in the empty element
    e.target.textContent = '';
    selectionRange.selectNodeContents(e.target);
    selection.removeAllRanges();
    selection.addRange(selectionRange);

    // Re-insert the content and set the cursor at the end
    const textNode = document.createTextNode(originalContent);
    selectionRange.insertNode(textNode);
    selectionRange.selectNodeContents(textNode);
    selectionRange.collapse(false);


const element = document.getElementById('element');
element.addEventListener('focus', onFocus, once : true);
<span id="element" contenteditable>foo</span>

副作用:我无法在重新插入后将插入符号重置为其初始位置,因此我将光标放在了内容的末尾。这意味着点击文本的中间将转到末尾,但用户始终可以在元素获得焦点后再次点击。

【讨论】:

以上是关于如何修复光标在 Android Chrome 上的内联 contenteditable 中跳转?的主要内容,如果未能解决你的问题,请参考以下文章

光标:Mac Chrome 上的指针问题

sh 修复oh-my-zsh默认主题的“➜”和“✗”,使某些终端下的光标位置错误(例如Mosh Chrome App,Termius [Chrome App]

如何在 Android 设备上的 Chrome 上启用调试?

如何修复 Android 上的图像下载/保存错误

如何更改禁用的单选按钮/复选框上的丑陋光标图像

如何利用Chrome devTools调试android手机上的web网站