커서가 Javascript / jquery를 사용하는 곳에 텍스트 삽입


167

텍스트 상자가 많은 페이지가 있습니다. 누군가가 링크를 클릭하면 커서가있는 곳에 단어가 삽입되거나 포커스가있는 텍스트 상자에 추가되기를 원합니다.

예를 들어, 커서 / 포커스가 'apple'이라는 텍스트 상자에 있고 '[email]'이라는 링크를 클릭하면 텍스트 상자에 'apple bob@example.com'이라고 말하고 싶습니다.

어떻게해야합니까? 초점이 라디오 / 드롭 다운 / 비 텍스트 상자 요소에있을 경우 어떻게됩니까? 텍스트 상자에 마지막으로 초점을 맞춘 것을 기억할 수 있습니까?


WYSISYG 편집기의 기초이기 때문에 가능하다고 생각합니다.
Ian Elliott


이 질문을 해 주셔서 감사합니다 ... 이제 Chrome 확장 프로그램으로 커서에 "[버전]"을 (를) 삽입 할 수 있습니다!
haykam

실행 취소를 지원하는 간단한 모듈을 찾고 있다면 insert-text-textarea를 시도하십시오 . IE8 + 지원이 필요한 경우 insert-text-at-cursor 패키지를 사용해보십시오 .
fregante

답변:


241

여기 에서 사용 하십시오 :

function insertAtCaret(areaId, text) {
  var txtarea = document.getElementById(areaId);
  if (!txtarea) {
    return;
  }

  var scrollPos = txtarea.scrollTop;
  var strPos = 0;
  var br = ((txtarea.selectionStart || txtarea.selectionStart == '0') ?
    "ff" : (document.selection ? "ie" : false));
  if (br == "ie") {
    txtarea.focus();
    var range = document.selection.createRange();
    range.moveStart('character', -txtarea.value.length);
    strPos = range.text.length;
  } else if (br == "ff") {
    strPos = txtarea.selectionStart;
  }

  var front = (txtarea.value).substring(0, strPos);
  var back = (txtarea.value).substring(strPos, txtarea.value.length);
  txtarea.value = front + text + back;
  strPos = strPos + text.length;
  if (br == "ie") {
    txtarea.focus();
    var ieRange = document.selection.createRange();
    ieRange.moveStart('character', -txtarea.value.length);
    ieRange.moveStart('character', strPos);
    ieRange.moveEnd('character', 0);
    ieRange.select();
  } else if (br == "ff") {
    txtarea.selectionStart = strPos;
    txtarea.selectionEnd = strPos;
    txtarea.focus();
  }

  txtarea.scrollTop = scrollPos;
}
<textarea id="textareaid"></textarea>
<a href="#" onclick="insertAtCaret('textareaid', 'text to insert');return false;">Click Here to Insert</a>


7
이것은 훌륭하게 작동했지만 모든 텍스트 편집기와 마찬가지로 선택한 텍스트 교체를 처리하지는 않습니다. 이것은 포스터의 원래 질문에 필요하지 않을 수도 있지만 필요한 경우 'strPos'를 'txtArea.selectionEnd'로 간단히 바꿀 수 있습니다. 아래의 답변은 이전 버전의 IE를 지원할 필요가없는 경우 브라우저 감지 코드 제거와 함께 이것을 보여줍니다.
Jeffrey Harmon

로 모든 요소를 ​​선택할 수있는 방법이 areaId있습니까?
haykam

1
이와 같은 기능을 삽입하면 선택한 텍스트를 자동으로 삭제할 수 있습니다. function deleteTxt() { var ele = document.getElementById('yourTextarea'); var text = ele.value; text = text.slice(0, ele.selectionStart) + text.slice(ele.selectionEnd); ele.value = text; return text; }
NSTuttle

마우스 위치에 텍스트를 삽입하는 방법?
Thamarai T

당신은 최고예요!
Ecko Santoso

156

더 짧은 버전 일수록 이해하기 쉬울 수 있습니까?

    jQuery("#btn").on('click', function() {
        var $txt = jQuery("#txt");
        var caretPos = $txt[0].selectionStart;
        var textAreaTxt = $txt.val();
        var txtToAdd = "stuff";
        $txt.val(textAreaTxt.substring(0, caretPos) + txtToAdd + textAreaTxt.substring(caretPos) );
    });
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>

<textarea id="txt" rows="15" cols="70">There is some text here.</textarea>
<input type="button" id="btn" value="OK" />

jquery로 포인터의 현재 위치에서 텍스트 상자에 텍스트를 추가하는 방법 에 대한 응답으로 이것을 썼습니다 .


11
로 값을 변경 한 후 캐럿 위치를 복원 할 수도 있습니다 document.getElementById("txt").selectionStart = caretPos + txtToAdd.length.
Bludwarf

1
고맙습니다. 참고로 "selectionStart"속성은 jquery 선택기 $ ( "#")를 통해 존재하지 않습니다. document.getElementById ()
Lego

1
jsfiddle.net/NaHTw/802은 약간의 추가와 솔루션을 붙인 것과 선택한 영역 대체하기 위해 추가
패트릭

3
글쎄, 당신이 jQuery를 멀리 제거하려고한다면, 당신은 그것을 모두 제거 할 수 있습니다 . ; ^)
ruffin

8
: 그냥 도움말을, 여기에 캐럿 위치에 완벽한 솔루션 복원 플러스 붙여 넣은 내용으로 선택 영역을 대체의 jsfiddle.net/NaHTw/1028
AlfaTeK

41

George Claghorn의 승인 된 답변은 단순히 커서 위치에 텍스트를 삽입하는 데 효과적이었습니다. 사용자가 텍스트를 선택했지만 해당 텍스트를 바꾸려면 (대부분의 텍스트에서 기본 환경) 'back'변수를 설정할 때 약간 변경해야합니다.

또한 이전 버전의 IE를 지원할 필요가없는 경우 최신 버전은 textarea.selectionStart를 지원하므로 모든 브라우저 감지 및 IE 특정 코드를 제거 할 수 있습니다.

다음은 최소한 Chrome 및 IE11에서 작동하며 선택한 텍스트 교체를 처리하는 단순화 된 버전입니다.

function insertAtCaret(areaId, text) {
    var txtarea = document.getElementById(areaId);
    var scrollPos = txtarea.scrollTop;
    var caretPos = txtarea.selectionStart;

    var front = (txtarea.value).substring(0, caretPos);
    var back = (txtarea.value).substring(txtarea.selectionEnd, txtarea.value.length);
    txtarea.value = front + text + back;
    caretPos = caretPos + text.length;
    txtarea.selectionStart = caretPos;
    txtarea.selectionEnd = caretPos;
    txtarea.focus();
    txtarea.scrollTop = scrollPos;
}

이것은 좋지만 요소 maxlength를 고려 하지 않으므로 삽입 후의 결과 값이 최대 값보다 길 수 있습니다.
mbomb007 19

22

위의 코드는 IE에서 작동하지 않았습니다. 이 답변을 기반으로 한 코드가 있습니다.

나는 getElementById다른 방식으로 요소를 참조 할 수 있도록 꺼내었다 .

function insertAtCaret(element, text) {
  if (document.selection) {
    element.focus();
    var sel = document.selection.createRange();
    sel.text = text;
    element.focus();
  } else if (element.selectionStart || element.selectionStart === 0) {
    var startPos = element.selectionStart;
    var endPos = element.selectionEnd;
    var scrollTop = element.scrollTop;
    element.value = element.value.substring(0, startPos) +
      text + element.value.substring(endPos, element.value.length);
    element.focus();
    element.selectionStart = startPos + text.length;
    element.selectionEnd = startPos + text.length;
    element.scrollTop = scrollTop;
  } else {
    element.value += text;
    element.focus();
  }
}
input{width:100px}
label{display:block;margin:10px 0}
<label for="in2copy">Copy text from: <input id="in2copy" type="text" value="x"></label>
<label for="in2ins">Element to insert: <input id="in2ins" type="text" value="1,2,3" autofocus></label>
<button onclick="insertAtCaret(document.getElementById('in2ins'),document.getElementById('in2copy').value)">Insert</button>

편집 : 실행중인 스 니펫을 추가했습니다 .jQuery가 사용되지 않습니다 .


요소가 jquery 객체입니까? element.value와 element.focus ()는 둘 다 작동하지 않습니다 ...
Scott Stafford

7
element.focus()DOMElements에 합법적 인 자바 스크립트 방법은 다음과 같습니다 w3schools.com/jsref/met_html_focus.asp
oliverseal은

1
가장 좋은 아이디어는 IE 호환성을 떨어 뜨리는 것입니다.
ar2015

2
네, 7 년 전에이 답변을 썼습니다. 이 시점에서 IE 11은 지원되는 최소 버전이며 위의 코드가 작동합니다.
Collin Anderson

6

@quick_sliv 답변 사용 :

function insertAtCaret(el, text) {
    var caretPos = el.selectionStart;
    var textAreaTxt = el.value;
    el.value = textAreaTxt.substring(0, caretPos) + text + textAreaTxt.substring(caretPos);
};

4

JQuery와 JavaScript를 통해 TextBox의 현재 커서 위치에 일부 텍스트를 삽입하는 방법

방법

  1. 현재 커서 위치 찾기
  2. 복사 할 텍스트 가져 오기
  3. 저기에 텍스트를 설정
  4. 커서 위치 업데이트

여기에 2 개의 TextBox와 버튼이 있습니다. 텍스트 상자에서 특정 위치를 클릭 한 다음 버튼을 클릭하여 다른 텍스트 상자의 텍스트를 이전 텍스트 상자의 위치에 붙여 넣습니다.

여기서 주요 문제는 텍스트를 붙여 넣을 현재 커서 위치를 얻는 것입니다.

//Textbox on which to be pasted
<input type="text" id="txtOnWhichToBePasted" />

//Textbox from where to be pasted
<input type="text" id="txtFromWhichToBePasted" />


//Button on which click the text to be pasted
<input type="button" id="btnInsert" value="Insert"/>


<script type="text/javascript">

$(document).ready(function () {
    $('#btnInsert').bind('click', function () {
            var TextToBePasted = $('#txtFromWhichToBePasted').value;
            var ControlOnWhichToBePasted = $('#txtOnWhichToBePasted');

            //Paste the Text
            PasteTag(ControlOnWhichToBePasted, TextToBePasted);
        });
    });

//Function Pasting The Text
function PasteTag(ControlOnWhichToBePasted,TextToBePasted) {
    //Get the position where to be paste

    var CaretPos = 0;
    // IE Support
    if (document.selection) {

        ControlOnWhichToBePasted.focus();
        var Sel = document.selection.createRange();

        Sel.moveStart('character', -ctrl.value.length);

        CaretPos = Sel.text.length;
    }
    // Firefox support
    else if (ControlOnWhichToBePasted.selectionStart || ControlOnWhichToBePasted.selectionStart == '0')
        CaretPos = ControlOnWhichToBePasted.selectionStart;

    //paste the text
    var WholeString = ControlOnWhichToBePasted.value;
    var txt1 = WholeString.substring(0, CaretPos);
    var txt2 = WholeString.substring(CaretPos, WholeString.length);
    WholeString = txt1 + TextToBePasted + txt2;
    var CaretPos = txt1.length + TextToBePasted.length;
    ControlOnWhichToBePasted.value = WholeString;

    //update The cursor position 
    setCaretPosition(ControlOnWhichToBePasted, CaretPos);
}

function setCaretPosition(ControlOnWhichToBePasted, pos) {

    if (ControlOnWhichToBePasted.setSelectionRange) {
        ControlOnWhichToBePasted.focus();
        ControlOnWhichToBePasted.setSelectionRange(pos, pos);
    }
    else if (ControlOnWhichToBePasted.createTextRange) {
        var range = ControlOnWhichToBePasted.createTextRange();
        range.collapse(true);
        range.moveEnd('character', pos);
        range.moveStart('character', pos);
        range.select();
    }
}

</script>

3

현재 커서 위치에 텍스트를 추가하려면 두 단계가 필요합니다.

  1. 현재 커서 위치에 텍스트 추가
  2. 현재 커서 위치 업데이트

데모 : https://codepen.io/anon/pen/qZXmgN

Chrome 48, Firefox 45, IE 11 및 Edge 25에서 테스트

JS :

function addTextAtCaret(textAreaId, text) {
    var textArea = document.getElementById(textAreaId);
    var cursorPosition = textArea.selectionStart;
    addTextAtCursorPosition(textArea, cursorPosition, text);
    updateCursorPosition(cursorPosition, text, textArea);
}
function addTextAtCursorPosition(textArea, cursorPosition, text) {
    var front = (textArea.value).substring(0, cursorPosition);
    var back = (textArea.value).substring(cursorPosition, textArea.value.length);
    textArea.value = front + text + back;
}
function updateCursorPosition(cursorPosition, text, textArea) {
    cursorPosition = cursorPosition + text.length;
    textArea.selectionStart = cursorPosition;
    textArea.selectionEnd = cursorPosition;
    textArea.focus();    
}

HTML :

<div>
    <button type="button" onclick="addTextAtCaret('textArea','Apple')">Insert Apple!</button>
    <button type="button" onclick="addTextAtCaret('textArea','Mango')">Insert Mango!</button>
    <button type="button" onclick="addTextAtCaret('textArea','Orange')">Insert Orange!</button>
</div>
<textarea id="textArea" rows="20" cols="50"></textarea>

2

마지막 JavaScript 텍스트 상자를 추적하기 위해 다음 JavaScript를 사용할 수 있다고 생각합니다.

<script>
var holdFocus;

function updateFocus(x)
{
    holdFocus = x;
}

function appendTextToLastFocus(text)
{
    holdFocus.value += text;
}
</script>

용법:

<input type="textbox" onfocus="updateFocus(this)" />
<a href="#" onclick="appendTextToLastFocus('textToAppend')" />

이전 솔루션 (gclaghorn으로 소품)은 텍스트 영역을 사용하고 커서의 위치도 계산하므로 원하는 것에 더 좋습니다. 반면에, 이것이 당신이 찾고있는 것이라면 더 가벼울 것입니다.


좋은 생각. jquery를 사용하여 특정 클래스를 가진 각 텍스트 상자에 각 텍스트 상자의 HTML에 "onfocus = ..."를 넣지 않고이 이벤트를 적용했습니다. 그러나 좋은 접근 방식 :)
클릭하여 투표하십시오

1

Internet Explorer 9에서 허용되는 답변이 작동하지 않습니다. 확인한 후 브라우저 검색이 제대로 작동하지 않아 Internet Explorer에있을 때 ff (firefox)를 감지했습니다 .

방금이 변경을 수행했습니다.

if ($.browser.msie) 

대신에:

if (br == "ie") { 

결과 코드는 다음과 같습니다.

function insertAtCaret(areaId,text) {
    var txtarea = document.getElementById(areaId);
    var scrollPos = txtarea.scrollTop;
    var strPos = 0;
    var br = ((txtarea.selectionStart || txtarea.selectionStart == '0') ? 
        "ff" : (document.selection ? "ie" : false ) );

    if ($.browser.msie) { 
        txtarea.focus();
        var range = document.selection.createRange();
        range.moveStart ('character', -txtarea.value.length);
        strPos = range.text.length;
    }
    else if (br == "ff") strPos = txtarea.selectionStart;

    var front = (txtarea.value).substring(0,strPos);  
    var back = (txtarea.value).substring(strPos,txtarea.value.length); 
    txtarea.value=front+text+back;
    strPos = strPos + text.length;
    if (br == "ie") { 
        txtarea.focus();
        var range = document.selection.createRange();
        range.moveStart ('character', -txtarea.value.length);
        range.moveStart ('character', strPos);
        range.moveEnd ('character', 0);
        range.select();
    }
    else if (br == "ff") {
        txtarea.selectionStart = strPos;
        txtarea.selectionEnd = strPos;
        txtarea.focus();
    }
    txtarea.scrollTop = scrollPos;
}



0

컨텐츠 편집 가능, HTML 또는 기타 DOM 요소 선택

에 캐럿을 삽입하려는 <div contenteditable="true">경우, 특히 편집 가능한 컨테이너 내에 자식이있는 경우 훨씬 어려워집니다.

Rangy 라이브러리를 사용하여 정말 운이 좋았습니다 .

다음과 같은 훌륭한 기능이 많이 있습니다.

  • 위치 또는 선택 저장
  • 그런 다음 나중에 위치 또는 선택을 복원하십시오.
  • 선택 HTML 또는 일반 텍스트 가져 오기
  • 많은 사람들 중에서

마지막으로 확인한 온라인 데모는 작동하지 않았지만 리포지토리에는 작동하는 데모가 있습니다. 시작하려면 Git 또는 NPM에서 간단히 Repo를 다운로드 한 다음 ./rangy/demos/index.html을여십시오.

캐럿 위치 및 텍스트 선택 작업이 쉬워집니다!


0

이 질문에 대한 답변은 오래 전에 게시되었으며 Google 검색을 통해 그 문제를 발견했습니다. HTML5는 setRangeText () 메소드 를 포함 하는 HTMLInputElement API 를 제공합니다.이 메소드는 또는 요소 의 텍스트 범위를 새로운 문자열로 대체 합니다.<input><textarea>

element.setRangeText('abc');

위는 내부에 만들어 선택 대체 할 element과를 abc. 대체 할 입력 값 부분을 지정할 수도 있습니다.

element.setRangeText('abc', 3, 5);

위의 값은 입력 값의 4 번째에서 6 번째 문자를로 바꿉니다 abc. 다음 문자열 중 하나를 4 번째 매개 변수로 제공하여 텍스트를 바꾼 후 선택을 설정하는 방법을 지정할 수도 있습니다.

  • 'preserve'선택을 유지하려고합니다. 이것이 기본값입니다.
  • 'select' 새로 삽입 된 텍스트를 선택합니다.
  • 'start' 선택한 텍스트를 삽입 된 텍스트 바로 앞으로 이동합니다.
  • 'end' 삽입 된 텍스트 바로 다음으로 선택을 이동합니다.

브라우저 호환성

setRangeText 의 MDN 페이지 는 브라우저 호환성 데이터를 제공하지 않지만 기본적으로 모든 최신 브라우저 인 IE 9 이상, Edge 12 이상인 HTMLInputElement.setSelectionRange () 와 같습니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.