【问题标题】:Javascript - highlighting half bolded words from selected textJavascript - 突出显示选定文本中的半粗体字
【发布时间】:2017-01-10 16:34:17
【问题描述】:

我想将“utert”这个词用带有背景css的span标签括起来以突出显示。

我可以在$('div').text()的基础上使用单词的开始索引和结束索引来选择完整的单词。

但是在用 span 标签括起来这个选定的单词时,我无法突出显示它,因为这个单词包含 "uter</strong>t" 并且它无法将 span 括在它周围。

我需要做些什么来突出这些半粗体、斜体、下划线的单词?

$scope.getTextNodesIn = function (node) {
    var textNodes = [];
    if (node.nodeType == 3) {
        textNodes.push(node);
    } else {
        var children = node.childNodes;
        for (var i = 0, len = children.length; i < len; ++i) {
            textNodes.push.apply(textNodes, $scope.getTextNodesIn(children[i]));
        }
    }
    return textNodes;
}

$scope.setSelectionRange = function(el, start, end) {
    if (document.createRange && window.getSelection) {

        var range = document.createRange();
        range.selectNodeContents(el);

        var textNodes = $scope.getTextNodesIn(el);
        var foundStart = false;
        var charCount = 0, endCharCount;
        for (var i = 0, textNode; textNode = textNodes[i++]; ) {
            endCharCount = charCount + textNode.length;
            if (!foundStart && start >= charCount && (start < endCharCount || (start == endCharCount && i <= textNodes.length))) {
                range.setStart(textNode, start - charCount);
                foundStart = true;
            }
            if (foundStart && end <= endCharCount) {
                range.setEnd(textNode, end - charCount);
                break;
            }
            charCount = endCharCount;

        }

        var sel = window.getSelection();
        sel.removeAllRanges();
        sel.addRange(range);

    } else if (document.selection && document.body.createTextRange) {
        var textRange = document.body.createTextRange();
        textRange.moveToElementText(el);
        textRange.collapse(true);
        textRange.moveEnd("character", end);
        textRange.moveStart("character", start);
        textRange.select();
    }
}

$scope.makeEditableAndHighlight = function(colour) {

    var content,span,sel;
    sel = window.getSelection();
    if (sel.rangeCount && sel.getRangeAt) {
        range = sel.getRangeAt(0);
    }
    if (range) {
        sel.removeAllRanges();
        sel.addRange(range);
    }
    // Use HiliteColor since some browsers apply BackColor to the whole block
    //document.designMode = "on";
    /*if (!document.execCommand("HiliteColor", false, colour)) {
        document.execCommand("backColor", false, colour);
    }*/

    var range = window.getSelection().getRangeAt(0);

    if(range.commonAncestorContainer.toString() != '[object Text]')
    {

        if(typeof window.getSelection().anchorNode.parentElement != 'undefined')
            var cloneContent = window.getSelection().focusNode.parentElement;
        else
            var cloneContent = window.getSelection().focusNode.parentNode;
        span = document.createElement('SPAN');
        span.className='startIndex-'+startIndex+' endIndex-'+endIndex+'';
        span.style.background = 'pink';
        span.innerHTML = range.toString();
        //cloneContent.outerHTML.replace(range.toString(),span.outerHTML);
        $(cloneContent).replaceWith(cloneContent.outerHTML.replace(range.toString(),span.outerHTML));
        return;
    }
    else
    {
        content = $(content).text();
    }

    content = range.cloneContents();
    range.deleteContents();
    span = document.createElement('SPAN');
    span.className='startIndex-'+startIndex+' endIndex-'+endIndex+'';
    span.style.background = 'pink';
    span.appendChild(content);
    var htmlContent = span.innerHTML;
    range.insertNode(span);

    /*if(window.getSelection().focusNode.parentNode.style.backgroundColor == 'pink')
    {
        var parent_node = getOutterMostParent(window.getSelection().focusNode);
         $(listId).addClass('startIndex-'+ parseInt(startIndex) +' endIndex-'+parseInt(endIndex));
    }   
    document.designMode = "off";*/
    sel.removeAllRanges();
    //range.detach();

}

$scope.highlight = function(colour) {
    var range, sel;
    if (window.getSelection) {
        // IE9 and non-IE
        try {
            //if (!document.execCommand("backColor", false, colour)) {
                $scope.makeEditableAndHighlight(colour);
            //}
        } catch (ex) {
            $scope.makeEditableAndHighlight(colour)
        }
    } else if (document.selection && document.selection.createRange) {
        // IE <= 8 case
        range = document.selection.createRange();
        range.execCommand("backColor", false, colour);
    }
}

$scope.selectAndHighlightRange=function(id, start, end) {
    $scope.setSelectionRange(id, start, end);
    $scope.highlight("pink");
}

【问题讨论】:

  • 向我们展示您的代码。不是全部...只是相关部分。
  • 这段代码好吗?

标签: javascript range highlighting


【解决方案1】:

您可以使用 1 个 div 和 2 个 span,并为 2 个 span 使用不同的 css 类。

并使用你想要实现的css规则

<div><span class="bolder">uter</span><span class="no-bolder">t</span></div>

在 css 部分:

span.bolder {
  font-weight: bold;
}

span.bolder {
  font-weight: bold;
  background-color: yellow;
}
&lt;div&gt;&lt;span class="bolder"&gt;uter&lt;/span&gt;&lt;span class="no-bolder"&gt;t&lt;/span&gt;&lt;/div&gt;

【讨论】:

  • 你能显示包装所选部分的确切代码吗?
  • 你甚至不需要更粗的类,我只是写了它以防你想添加更多的 css 规则
  • 想用 span 的用法用背景色高亮选中的单词。
  • 如何用 span 标签括起来像“utert”这样的文本。有没有人用javascript解决这个问题?
  • 为什么要附上它?你可以有一个没有样式的跨度,只需打开和关闭一个 CSS 类......我认为没有任何特别好的理由不拥有两个跨度......
猜你喜欢
  • 2014-03-12
  • 1970-01-01
  • 2015-10-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多