在 mouseup 文本选择 + HTML5/jQuery 上覆盖突出显示的文本

Posted

技术标签:

【中文标题】在 mouseup 文本选择 + HTML5/jQuery 上覆盖突出显示的文本【英文标题】:Overwrite highlighted text on mouseup text selection+ HTML5/jQuery 【发布时间】:2019-08-17 05:49:41 【问题描述】:

我有一些由 ML 模型在 100 多个段落中生成的内容,每个段落都有一些突出显示的内容。

有时,突出显示的数据不正确,我们希望用户选择文本并再次突出显示以更正它。

<p> Contrary to popular belief, <span class='highlighted'>Lorem</span>Ipsum is not simply random text. It has roots in a piece of popular classical Latin literature from 45 <span class='highlighted'>BC</span>, making it over 2000 years old.</p>

在这个例子中,用户可能想要选择:

    Lo​​rem Ipsum 拉丁文 公元前 45 年 2000年​​i>

以下代码适用于 #2 和 #4,但我无法为 #1 和 #3 执行此操作,因为它已经突出显示。

我正在使用getSelectionText()这个函数来选择文本。

$('div.content>p').on('mouseup', function(e)
    var toselected = getSelectionText();
    var para = $(this).html();
    var start = para.indexOf(toselected);
    var end = start + toselected.length;
    var html = para.replace(toselected, '<span class="highlighted">' toselected + '</span>');
    var obj = "content": $(this).text(), "indices_range":[[start, end]]
    $.post('/update/<content_id>', data:tojson(obj), function()        $(e.target).html(html);) 

);

还想知道,如果相同的文本出现两次或多次,我如何获得开始、结束索引,例如。 popular.?

【问题讨论】:

您希望用户能够取消突出显示之前突出显示的内容吗? "有时,突出显示的数据不正确,我们希望用户选择文本并将其突出显示。" @zer00ne - 间接是,如果选择突出显示,则取消突出显示,并突出显示整个正确的单词/短语。 我正在创建类似的东西并完全恢复/设置选择。首先,每个 html 元素在我的代码中都有唯一的 id。我将 contenteditable 设置为 true,对于选定的文本,我设置背景颜色并关闭 contenteditable。参数 startOffset endOffset startID, endID - 正确恢复选择。 range.setStart(el, offset); range.setEnd(el, offset);见:developer.mozilla.org/en-US/docs/Web/API/range/setStart 【参考方案1】:

使用Range 和Selection API 来控制文本节点的选择。不要使用&lt;span&gt;,而是使用&lt;mark&gt; 标签。 使用&lt;mark&gt;的原因

100% 语义 它的使用并不常见,这意味着 CSS 选择器冲突的可能性很小。 默认情况下,它已经突出显示了它的内容。

用法:像往常一样用鼠标突出显示文本。 &lt;mark&gt;s 不嵌套(这是一件好事)。要删除突出显示的区域,请使用鼠标右键单击它。

const mark = event => 
  const current = event.currentTarget;
  const target = event.target;
  const select = document.getSelection();
  if (event.which === 1) 
    const range = select.getRangeAt(0);
    const text = range.toString();
    const content = range.extractContents();
    const mark = document.createElement('MARK');
    mark.textContent = text;
    range.insertNode(mark);
   else if (event.which === 3) 
    event.preventDefault();
    if (target.tagName === 'MARK') 
      const text = target.textContent;
      const tNode = document.createTextNode(text);
      target.parentNode.replaceChild(tNode, target);
    
  
  select.removeAllRanges();
  current.normalize();
  return false;


$(document).on("contextmenu mouseup", mark);
::selection 
  background: tomato;
  color: white;
<p> Contrary to popular belief, <mark>Lorem</mark>Ipsum is not simply random text. It has roots in a piece of popular classical Latin literature from 45 <mark>BC</mark>, making it over 2000 years old.</p>

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

【讨论】:

以上是关于在 mouseup 文本选择 + HTML5/jQuery 上覆盖突出显示的文本的主要内容,如果未能解决你的问题,请参考以下文章

在jQuery中同时拥有mousedown / mouseup和dblclick

AngularJS - 在 Chrome 中选择文本触发父级中的 ng-click

在对象外部开始单击时防止 MouseUp

NSButton mouseDown mouseUp 在启用时表现不同

在触摸设备上触发 mousedown 和 mouseup

vb.net中对mouseUp事件的疑惑