【问题标题】:contenteditable on doubleclick双击内容可编辑
【发布时间】:2014-02-05 23:46:19
【问题描述】:

我有一个带有一些文本的p 标签,我正在尝试使其成为contenteditable,但只能在双击时使用。当我点击它时,如何防止浏览器将光标放在 p 上,并且只有在我双击时才这样做? jQuery:

    p.dblclick(function(e){
        p.css("cursor", "text");
    })
    .focusout(function(){
        p.css("cursor", "default");
    })
    .click(function(e){
        console.log('focus p');
        e.stopPropagation();
        $("body").focus(); // not stopping Chrome from placing cursor
    });

我可以默认将contenteditable设为false,然后在dbleclick设为true,然后再执行p.focus(),但这意味着我无法将光标放在我点击的位置。另一方面,我可以在第一次单击后使其内容可编辑,然后等待 1.5 秒的 dobuleclick,如果没有发生则取消它,但如果发生了,那么内容将是可编辑的,第二次单击将触发将光标放置在正确的位置。但是,它并不是那么流畅,并且在这 1 秒半的时间内可以编辑内容。

有什么想法吗?

回答: 如果有人感兴趣,我继续实现 timer 方法,因为我认为没有其他方法......这是代码

var DELAY = 700, clicks = 0, timer = null;
p.focusout(function(){
    p.css("cursor", "default");
    p.prop("contenteditable", false);
})
.click(function(e){
    clicks++;
    p.prop("contenteditable", true);
    if(clicks == 1){
        timer = setTimeout(function() {
            p.prop("contenteditable", false);
            //alert("Single Click");  //perform single-click action
            clicks = 0;             //after action performed, reset counter
        }, DELAY);
    } else {
        clearTimeout(timer);    //prevent single-click action
       // alert("Double Click");  //perform double-click action
        clicks = 0;             //after action performed, reset counter
    }

});

【问题讨论】:

标签: javascript jquery contenteditable


【解决方案1】:

在这里试试这个工作fiddle

 <p ondblclick="this.contentEditable=true;this.className='inEdit';" onblur="this.contentEditable=false;this.className='';" contenteditable="false" class="">This paragraph uses some simple script to be editable. Double-click the text to begin editing.</p>

【讨论】:

  • 这说明了我的观点——双击它就可以编辑了,需要再单击一次才能开始编辑。但我希望它能够在双击后直接开始编辑并将光标放在我单击的位置
  • @zavr 在 dblclick 中添加 this.focus();
  • 效果很好,我将ondblclick 调整为onclick,所以第一次点击可以编辑内容,第二次点击选择,不需要聚焦。
【解决方案2】:

这是一个适合我的解决方案:

<script>
function listenForDoubleClick(element) {
  element.contentEditable = true;
  setTimeout(function() {
    if (document.activeElement !== element) {
      element.contentEditable = false;
    }
  }, 300);
}
</script>

<p onclick="listenForDoubleClick(this);" onblur="this.contentEditable=false;">Double-click the text to begin editing.</p>

这是一个有效的小提琴:https://jsfiddle.net/dtL3xzfb/

它使用超时事件检查文本是否在一定时间内(300ms)内被选中,如果文本没有被选中(通过第二次点击),它将再次将 content editable 设置为 false:内容可编辑第一次单击后参数设置为 true,因此第二次单击时将选择文本。

【讨论】:

  • 完美! +1。我只会添加背景颜色来暗示 DOM 中的某些内容发生了变化。当 contentEditable 恢复为 false 时,背景颜色将恢复为原始颜色。
【解决方案3】:

您可以像 How to disable text selection using jQuery? 一样使文本无法选择:

var p = $('p');

p.attr('unselectable', 'on')
    .css('user-select', 'none')
    .on('selectstart', false);

p.dblclick(function (e) {
    p.css("cursor", "text")
        .attr('contenteditable', true)
        .attr('unselectable', 'off')
        .css('user-select', 'inherit')
        .off('selectstart', false)
        .focus();

});

p.focusout(function () {
    p.css("cursor", "default")
        .attr('unselectable', 'on')
        .attr('contenteditable', false)
        .css('user-select', 'none')
        .on('selectstart', false);
});

【讨论】:

  • 谢谢。虽然文本不可选择,但文本光标仍位于 Chrome 中(我可以使用箭头来移动它)。
  • 我没有理解你所说的“文本光标仍然放置”的意思,我在我的 Chrome 测试环境中看不到它。
  • 我尝试手动设置焦点,但这不是解决方案,因为我没有将光标放在我点击的位置
【解决方案4】:

如果使用 React,你可以使用组件

import _ from 'lodash'
import { useState } from 'react'

const inputValue = (e: any): string => e.target.value

function isEnterOrEscapeKeyEvent(event: React.KeyboardEvent<HTMLInputElement>) {
    return event.key === 'Enter' || event.key === 'Escape'
}

const EditOnDblClick = () => {
    const [isEditing, setisEditing] = useState(false)
    const [text, settext] = useState('yoga chitta')

    const onEditEnd = () => {
        setisEditing(false)
    }

    return isEditing ? (
        <input
            value={text}
            className="bg-transparent border-2 border-black border-solid"
            onKeyDown={(event) => {
                if (isEnterOrEscapeKeyEvent(event)) {
                    event.preventDefault()
                    event.stopPropagation()
                    onEditEnd()
                }
            }}
            onChange={_.flow(inputValue, settext)}
            onBlur={onEditEnd}
            autoFocus
        />
    ) : (
        <div className="select-none" onDoubleClick={() => setisEditing(true)}>
            {text}
        </div>
    )
}

export default EditOnDblClick

注意:类来自tailwindcss

【讨论】:

    猜你喜欢
    • 2014-05-20
    • 2021-01-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多