0

我的要求是,在文本框中,用户可以跳到选项卡上 [] 中包含的下一个单词,例如 Hi [this] is [an] 示例。测试 [this] 因此,当我的光标位于 Hi 并且我执行 tab out 时,[this] 中包含的字符会突出显示,当我再次执行 tabl out 时,以下 [an] 中的下一个字符会突出显示。这工作正常

现在的要求是需要突出显示包含 [] 之间的特殊字符的任何文本

案例1:当我有尾随时]]],它只突出显示前导[[[并忽略]]]] 例如 选项卡上忽略训练的屏幕截图]]]]

案例 2:如果有多个尾随]ee ,[]]]][测试],理想情况下是一个单独的表格,它应该转到包含的下一个文本,[]但用户必须在每次训练中标记 4 次一个选项卡]才能转到下一个[文本] 在此处输入图像描述

强文本代码是

$(document).ready(function() {
    $('textarea').highlightTextarea({
        color : '#0475D1',
        words : [ "/(\[.*?\])/g" ],
        textColor : '#000000'
    });
    $('textarea').live('keydown', function(e) {
        var keyCode = e.keyCode || e.which;
        if (keyCode == 9) {
            var currentIndex = getCaret($(this).get(0))
            selectText($(this), currentIndex);
            return false;
        }
    });
});

function selectText(element, currentIndex) {
    var rSearchTerm = new RegExp(/(\[.*?\])/);
    var ind = element.val().substr(currentIndex).search(rSearchTerm)
    currentIndex = (ind == -1 ? 0 : currentIndex);
    ind = (ind == -1 ? element.val().search(rSearchTerm) : ind);
    currentIndex = (ind == -1 ? 0 : currentIndex);
    var lasInd = (element.val().substr(currentIndex).search(rSearchTerm) == -1 ? 0
            : element.val().substr(currentIndex).indexOf(']'));
    var input = element.get(0);
    if (input.setSelectionRange) {
        input.focus();
        input.setSelectionRange(ind + currentIndex, lasInd + 1 + currentIndex);
    } else if (input.createTextRange) {
        var range = input.createTextRange();
        range.collapse(true);
        range.moveEnd('character', lasInd + 1 + currentIndex);
        range.moveStart('character', ind + currentIndex);
        range.select();
    }
}

function getCaret(el) {
    if (el.selectionEnd) {
        return el.selectionEnd;
    } else if (document.selection) {
        el.focus();
        var r = document.selection.createRange();
        if (r == null) {
            return 0;
        }
        var re = el.createTextRange(), rc = re.duplicate();
        re.moveToBookmark(r.getBookmark());
        rc.setEndPoint('EndToStart', re);
        return rc.text.length;
    }
    return 0;
}

请让我知道处理上述两种情况

4

3 回答 3

2

首先,正则表达式应该是:

var rSearchTerm = /(\[.*?\]+)/;

用于+匹配\]模式末尾的一个或多个。此外,您不需要new RegExp()正则表达式文字。

下一个问题是您正在使用以下代码设置选择的结束位置:

element.val().substr(currentIndex).indexOf(']')

Using.indexOf(']')查找之后的第一个 ,而不是当前匹配中的最后一个。如果你使用而不是,你可以找到最后一个,因为返回一个数组,其中包含匹配的字符串的详细信息 - 你可以从中计算出匹配的长度 - 并给出匹配的索引。]currentIndex.match().search().match()

此外,反复调用element.val()element.val().substr()既难以阅读又效率低下 - 使用该值创建一个变量。.search()并且多次调用并使用所有这些?:三元表达式来继续决定应该将哪些索引变量调整为新值,这很难阅读和混淆。最后,我只是猜到了您要做什么并像这样重写它:

function selectText(element, currentIndex) {
    var rSearchTerm =  /(\[.*?\]+)/;
    var val = element.val();
    var matchStartPos, matchEndPos;
    var m = val.substr(currentIndex).match(rSearchTerm);
    if (!m){                             // if it didn't match
        currentIndex = 0;                // wrap back to the beginning
        m = val.match(rSearchTerm);      // and try to match again
    }
    console.log(m);
    if (m) {
        matchStartPos = m.index;
        matchEndPos = matchStartPos + m[0].length;
    } else {
        currentIndex = 0;
        matchStartPos = 0;
        matchEndPos = 0;
    }
    var input = element.get(0);
    if (input.setSelectionRange) {
        input.focus();
        input.setSelectionRange(matchStartPos + currentIndex, matchEndPos + currentIndex);
    } else if (input.createTextRange) {
        var range = input.createTextRange();
        range.collapse(true);
        range.moveEnd('character', matchEndPos + currentIndex);
        range.moveStart('character', matchStartPos + currentIndex);
        range.select();
    }
}

工作演示:http: //jsbin.com/ewajoy/2/edit

于 2013-07-03T12:18:42.443 回答
1

你可以用这个正则表达式来做到这一点

(\[[^\[\]]*)+([^\[\]]*\])+

演示

于 2013-07-03T11:27:33.093 回答
1

您需要调整正则表达式以匹配末尾多个方括号。目前"/(\[.*?\])/g"只会匹配一个方括号。

试试这个"/(\[.*?\]*)/g"

于 2013-07-03T11:02:22.483 回答