HTML 텍스트 상자에서 키보드 캐럿 위치 설정


173

텍스트 상자에서 키보드 캐럿을 특정 위치로 이동하는 방법을 아는 사람이 있습니까?

예를 들어, 텍스트 상자 (예 : 텍스트 영역이 아닌 입력 요소)에 50자가 있고 캐럿을 문자 20 앞에 배치하려면 어떻게해야합니까?

이것은 jQuery 가 필요한 텍스트 영역에서 jQuery 커서 위치 설정이라는 질문과 차별화됩니다 .

답변:


205

Josh Stodola의 Javascript를 사용하여 텍스트 상자 또는 TextArea에서 키보드 캐럿 위치 설정 에서 발췌

텍스트 상자 나 텍스트 영역의 원하는 위치에 캐럿을 삽입 할 수있는 일반 기능 :

function setCaretPosition(elemId, caretPos) {
    var elem = document.getElementById(elemId);

    if(elem != null) {
        if(elem.createTextRange) {
            var range = elem.createTextRange();
            range.move('character', caretPos);
            range.select();
        }
        else {
            if(elem.selectionStart) {
                elem.focus();
                elem.setSelectionRange(caretPos, caretPos);
            }
            else
                elem.focus();
        }
    }
}

첫 번째 예상 매개 변수는 키보드 캐럿을 삽입하려는 요소의 ID입니다. 요소를 찾을 수 없으면 아무 일도 일어나지 않습니다. 두 번째 매개 변수는 캐럿 위치 인덱스입니다. 0은 키보드 캐럿을 처음에 배치합니다. elements 값의 문자 수보다 큰 수를 전달하면 키보드 캐럿이 끝에 놓입니다.

IE6 이상, Firefox 2, Opera 8, Netscape 9, SeaMonkey 및 Safari에서 테스트되었습니다. 불행히도 Safari에서는 onfocus 이벤트와 함께 작동하지 않습니다).

위의 기능을 사용하여 키보드 캐럿이 포커스를받을 때 페이지의 모든 텍스트 영역의 끝으로 이동하도록 강제하는 예 :

function addLoadEvent(func) {
    if(typeof window.onload != 'function') {
        window.onload = func;
    }
    else {
        if(func) {
            var oldLoad = window.onload;

            window.onload = function() {
                if(oldLoad)
                        oldLoad();

                func();
            }
        }
    }
}

// The setCaretPosition function belongs right here!

function setTextAreasOnFocus() {
/***
 * This function will force the keyboard caret to be positioned
 * at the end of all textareas when they receive focus.
 */
    var textAreas = document.getElementsByTagName('textarea');

    for(var i = 0; i < textAreas.length; i++) {
        textAreas[i].onfocus = function() {
            setCaretPosition(this.id, this.value.length);
        }
    }

    textAreas = null;
}

addLoadEvent(setTextAreasOnFocus);

4
if(elem.selectionStart)jhnns의 답변에서 지적한 것처럼 selectionStart가 0이면 중단됩니다.
mpartel

1
이것은 나를 위해 작동하지 않습니다. 실제 텍스트 상자를 클릭하면 캐럿 위치가 처음에 있어야합니다. 내 바이올린을 확인 jsfiddle.net/khx2w
elad.chen

setCaretPosition 함수는 정상적으로 작동합니다. 그러나 addActionHandler 함수는 그렇지 않습니다. 그러나 그것 없이도 커서를 초점으로 움직일 수 없었습니다. 브라우저가 클릭 위치를 기준으로 커서 위치 자체를 설정하기 때문일 가능성이 높습니다. 내가 말할 수있는 것에서 그 주위에 방법이없는 것 같지만 완전히 틀릴 수 있습니다.
GJK

IE9, FF25에서 작동하지만 Chrome 30에서는 작동하지 않습니다.
엄버 페룰

나는이 elem.value = elem.value.replace(/^9/g,'+79')코드에서. 이후 OperaMINI 커서에서 +. 이 기능은 도움이되지 않습니다
eri

52

답변의 링크가 깨졌습니다.이 링크가 작동해야합니다 (모든 크레딧은 blog.vishalon.net으로 이동 하십시오 ).

http://snipplr.com/view/5144/getset-cursor-in-html-textarea/

코드가 다시 손실되는 경우 다음 두 가지 주요 기능이 있습니다.

function doGetCaretPosition(ctrl)
{
 var CaretPos = 0;

 if (ctrl.selectionStart || ctrl.selectionStart == 0)
 {// Standard.
  CaretPos = ctrl.selectionStart;
 }
 else if (document.selection)
 {// Legacy IE
  ctrl.focus ();
  var Sel = document.selection.createRange ();
  Sel.moveStart ('character', -ctrl.value.length);
  CaretPos = Sel.text.length;
 }

 return (CaretPos);
}


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

1
기본 기능의 경우 +1이지만 일부 조정이 필요합니다 . range 방법을 사용할 때 행 수는 "pos"에서 빼야합니다.
Rob W

36

실제로이 솔루션이 실제로 필요했으며 일반적인 기준 솔루션 ( 입력에 초점을 맞춘 다음 값을 자체와 동일하게 설정 ) 이 브라우저 간 작동하지 않으므로 모든 것을 조정하고 편집하여 시간을 보냈습니다. @ kd7 의 코드를 바탕으로 내가 생각해 낸 것입니다.

즐겨! IE6 +, Firefox, Chrome, Safari, Opera에서 작동

크로스 브라우저 캐럿 위치 지정 기술 (예 : 커서를 END로 이동)

// ** USEAGE ** (returns a boolean true/false if it worked or not)
// Parameters ( Id_of_element, caretPosition_you_want)

setCaretPosition('IDHERE', 10); // example

고기와 감자는 기본적으로 @ kd7 의 setCaretPosition이며, 가장 큰 조정은 if (el.selectionStart || el.selectionStart === 0)파이어 폭스에서 selectionStart는 0 에서 시작 합니다.

크롬에서 가장 큰 문제는 단지 .focus()충분하지 않다는 것입니다 (모든 텍스트를 계속 선택했습니다!) 따라서 el.value = el.value;우리는 함수를 호출하기 전에 자체의 가치를 스스로 설정했으며 이제는 selectionStart 를 사용하기위한 입력 .

function setCaretPosition(elemId, caretPos) {
    var el = document.getElementById(elemId);

    el.value = el.value;
    // ^ this is used to not only get "focus", but
    // to make sure we don't have it everything -selected-
    // (it causes an issue in chrome, and having it doesn't hurt any other browser)

    if (el !== null) {

        if (el.createTextRange) {
            var range = el.createTextRange();
            range.move('character', caretPos);
            range.select();
            return true;
        }

        else {
            // (el.selectionStart === 0 added for Firefox bug)
            if (el.selectionStart || el.selectionStart === 0) {
                el.focus();
                el.setSelectionRange(caretPos, caretPos);
                return true;
            }

            else  { // fail city, fortunately this never happens (as far as I've tested) :)
                el.focus();
                return false;
            }
        }
    }
}

@mcpDESIGNS 텍스트 입력에 초점을 맞출 때이 기능을 사용하려고하는데 아무데도 없습니다. 순수한 자바 스크립트를 사용 하여이 기능을 적용하는 데 도움을 줄 수 있습니까?
elad.chen

@ elad.chen 텍스트 상자에 초점을 맞추 자마자 텍스트 상자의 끝에 배치하려고합니까?
Mark Pieszak-Trilon.io

@mcpDESIGNS 요소가 초점을 맞추 자마자 필드의 시작 부분에 커서를 놓고 싶습니다. 바이올린을보십시오 : jsfiddle.net/KuLTU/3
elad.chen

@ elad.chen 늦게 반응해서 죄송합니다! search_field_focus 함수 .onclick대신에 해당 이벤트를 변경 .onfocus하십시오
Mark Pieszak-Trilon.io

2
el.value = el.value; [...] if(el !== null)-나는이 두 줄을 바꾸겠다. elnull 인 경우 는 el.value = el.value실패하므로 행은에 있어야합니다 if.
BackSlash

21

selectionStart가 우연히 0 일 때 elem.selectionStart가 false로 평가되므로 kd7의 대답을 약간 조정했습니다.

function setCaretPosition(elem, caretPos) {
    var range;

    if (elem.createTextRange) {
        range = elem.createTextRange();
        range.move('character', caretPos);
        range.select();
    } else {
        elem.focus();
        if (elem.selectionStart !== undefined) {
            elem.setSelectionRange(caretPos, caretPos);
        }
    }
}

5

IE와 Chrome에서 테스트 한이 문제를 해결하는 쉬운 방법을 찾았습니다.

function setCaret(elemId, caret)
 {
   var elem = document.getElementById(elemId);
   elem.setSelectionRange(caret, caret);
 }

텍스트 상자 ID와 캐럿 위치를이 함수로 전달하십시오.


3

일부 텍스트 상자에 초점을 맞출 필요가 있고 유일한 문제는 전체 텍스트가 강조 표시되고 캐럿이 끝에 있기를 원한다는 것입니다. 그러한 경우에는 포커스 후 텍스트 상자 값을 스스로 설정하는이 트릭을 사용할 수 있습니다.

$("#myinputfield").focus().val($("#myinputfield").val());

2
<!DOCTYPE html>
<html>
<head>
<title>set caret position</title>
<script type="application/javascript">
//<![CDATA[
window.onload = function ()
{
 setCaret(document.getElementById('input1'), 13, 13)
}

function setCaret(el, st, end)
{
 if (el.setSelectionRange)
 {
  el.focus();
  el.setSelectionRange(st, end);
 }
 else
 {
  if (el.createTextRange)
  {
   range = el.createTextRange();
   range.collapse(true);
   range.moveEnd('character', end);
   range.moveStart('character', st);
   range.select();
  }
 }
}
//]]>
</script>
</head>
<body>

<textarea id="input1" name="input1" rows="10" cols="30">Happy kittens dancing</textarea>

<p>&nbsp;</p>

</body>
</html>

2
function SetCaretEnd(tID) {
    tID += "";
    if (!tID.startsWith("#")) { tID = "#" + tID; }
    $(tID).focus();
    var t = $(tID).val();
    if (t.length == 0) { return; }
    $(tID).val("");
    $(tID).val(t);
    $(tID).scrollTop($(tID)[0].scrollHeight); }

잡히지 않은 TypeError : 개체 [object HTMLInputElement]에 'startsWith'메서드가 없습니다
bobpaul

1
@bobpaul : tID요소 개체 자체가 아니라 요소의 id 여야합니다. 요소 객체를 전달하는 경우이 방법에서 첫 번째 두 줄을 제거하면 작동합니다.
awe

2

다음과 같은 조건을 수정합니다.

function setCaretPosition(elemId, caretPos)
{
 var elem = document.getElementById(elemId);
 if (elem)
 {
  if (typeof elem.createTextRange != 'undefined')
  {
   var range = elem.createTextRange();
   range.move('character', caretPos);
   range.select();
  }
  else
  {
   if (typeof elem.selectionStart != 'undefined')
    elem.selectionStart = caretPos;
   elem.focus();
  }
 }
}
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.