6

私は次のものを持っていますdiv

<div id="query" style="width:500px; height:200px;border:1px solid black"
 spellcheck="false" contenteditable="true"></div>​

クライアントがSQLクエリを記述できる場所。Space私がやろうとしていたのは、クライアントがaを押した直後に入力した単語をラップし、入力した単語に応じてspanこのスパンを特定することです。class

クライアントタイプの場合、selectこの選択した単語をdivで次のようにラップする必要があります。

<span class='select'> SELECT </span> <span> emp_name </span>

CSS

.select{color:blue ;text-transform:uppercase;}

それは何をするかと非常に似てjsFiddleいます。どうすればこれを達成できますか?

これが私がこれまでに試したことです:jsFiddle

$(function(){
    $('div').focus() ;
    $('div').keyup(function(e){
        //console.log(e.keyCode) ;
        if(e.keyCode == 32){
            var txt = $('div').text() ;
            var x = 'SELECT' ;
            $('div:contains("'+x+'")').wrap("<span style='color:blue ;
      text-transform:uppercase;'>") ;
            if(txt == 'SELECT'){
                console.log('found') ; // why This Doesn't do any thing  ?
            }

        }
    });

});
4

2 に答える 2

3

私は、あなたが最初に持っていたものからいくつかの変更を加えて、概念実証を行いました。下記参照、

デモ:http: //jsfiddle.net/cgy69/

$(function() {
    $('div').focus();
    var x = ['SELECT', 'WHERE', 'FROM'];
    $('div').keyup(function(e) {
        //console.log(e.keyCode) ;
        if (e.keyCode == 32) {

            //using .text() remove prev span inserts
            var text = $.trim($(this).text()).split(' ');            
            $.each(text, function(i, v) {
                $.each(x, function(j, xv) {
                    if (v.toUpperCase() === xv) {
                        text[i] = '<span style="color: blue; text-transform: uppercase;">' + v + '</span>';    
                    }                                        
                });
            });

            $(this).html(text.join(' ') + '&nbsp;');

            setEndOfContenteditable(this);
        }
    });

    function setEndOfContenteditable(contentEditableElement) {
        var range, selection;
        if (document.createRange) //Firefox, Chrome, Opera, Safari, IE 9+
        {
            range = document.createRange(); //Create a range (a range is a like the selection but invisible)
            range.selectNodeContents(contentEditableElement); //Select the entire contents of the element with the range
            range.collapse(false); //collapse the range to the end point. false means collapse to end rather than the start
            selection = window.getSelection(); //get the selection object (allows you to change selection)
            selection.removeAllRanges(); //remove any selections already made
            selection.addRange(range); //make the range you have just created the visible selection
        }
        else if (document.selection) //IE 8 and lower
        {
            range = document.body.createTextRange(); //Create a range (a range is a like the selection but invisible)
            range.moveToElementText(contentEditableElement); //Select the entire contents of the element with the range
            range.collapse(false); //collapse the range to the end point. false means collapse to end rather than the start
            range.select(); //Select the range (make it the visible selection
        }
    }
});

これをさらに拡張して処理します

  1. バックスペース
  2. 以前の挿入からのHTMLコンテンツ
  3. カーソル位置部分的に完了しましたが、途中で編集すると、まだキャレットが台無しになります。

もっと..

于 2012-11-06T21:53:34.670 に答える
0

要素から始めて、そのcontenteditable要素を直接操作することで、必要に応じてマークアップを置き換えることができますinnerHtml

$('#query-container').on('keyup', function(e){
  var $this = $(this);
  //(?!\<\/b\>) negative lookahead is used so that anything already wrapped
  //into a markup tag would not get wrapped again
  $this.html($this.html().replace(/(SELECT|UPDATE|DELETE)(?!\<\/b\>)/gi, '<b>$1</b>'));
  setEndOfContenteditable(this);
});

IMOこれはより読みやすいオプションです。前の回答からrangeselectメソッドを追加すると、フィドルが機能します

于 2012-11-07T01:03:19.977 に答える