Jak wykryć zdarzenie zmiany w obszarze tekstowym za pomocą javascript?
Próbuję wykryć, ile znaków pozostało dostępnych podczas pisania.
Próbowałem użyć zdarzenia onchange, ale wydaje się, że działa tylko wtedy, gdy nie ma ostrości.
javascript
teepusink
źródło
źródło
onkeyup
to straszne zdarzenie dla wykrycia wejścia. Użyjoninput
ionpropertychange
(do obsługi IE).onchange
jest wywoływany, gdy występuje wycinanie / wklejanie z menu kontekstowego.Jest rok 2012, nadeszła era post-PC, a my wciąż musimy zmagać się z czymś tak podstawowym jak to. To powinno być bardzo proste .
Dopóki to marzenie się nie spełni, oto najlepszy sposób na zrobienie tego, cross-browser: użyj kombinacji zdarzeń
input
ionpropertychange
, na przykład:var area = container.querySelector('textarea'); if (area.addEventListener) { area.addEventListener('input', function() { // event handling code for sane browsers }, false); } else if (area.attachEvent) { area.attachEvent('onpropertychange', function() { // IE-specific event handling code }); }
input
Wydarzenie zajmuje IE9 +, FF, Chrome, Opera i Safari , aonpropertychange
dba o IE8 (działa również z IE6 i 7, ale istnieją pewne błędy).Zaletą używania
input
ionpropertychange
jest to, że nie uruchamiają się niepotrzebnie (jak podczas naciskania klawiszyCtrl
lubShift
); więc jeśli chcesz uruchomić stosunkowo kosztowną operację, gdy zmienia się zawartość obszaru tekstowego, to jest droga do zrobienia .Teraz IE, jak zawsze, wykonuje połowiczną robotę, wspierając to: ani
input
nieonpropertychange
uruchamia się w IE, gdy znaki są usuwane z obszaru tekstu. Jeśli więc chcesz zająć się usuwaniem znaków w IE, użyjkeypress
(w przeciwieństwie do używaniakeyup
/keydown
, ponieważ uruchamiają się one tylko raz, nawet jeśli użytkownik naciśnie i przytrzyma klawisz).Źródło: http://www.alistapart.com/articles/expanding-text-areas-made-elegant/
EDYCJA: Wydaje się, że nawet powyższe rozwiązanie nie jest idealne, jak słusznie wskazano w komentarzach: obecność
addEventListener
właściwości w obszarze tekstowym nie oznacza, że pracujesz z rozsądną przeglądarką; podobnie obecnośćattachEvent
dobra nie implikuje IE. Jeśli chcesz, aby Twój kod był naprawdę szczelny, powinieneś rozważyć zmianę tego. Zobacz komentarz Tim Down dla wskazówek.źródło
addEventListener
nie oznacza obsługiinput
zdarzenia lub odwrotnie); wykrywanie funkcji byłoby lepsze. Zobacz ten wpis na blogu, aby omówić ten temat.oninput
jak powinniśmy to zrobić, ale prawdopodobnie nie powinieneś używać goaddEventListener
jako testu obsługi przeglądarki. +1 w każdym przypadku.keypress
zdarzenia do obsługi tego przypadku w IE9 (i być może także późniejszych wersjach).input
procedurę obsługi zdarzeń można również zdefiniować, implementując.oninput
właściwość obiektu.Nie testowano w przeglądarce Firefox.
var isIE = /*@cc_on!@*/false; // Note: This line breaks closure compiler... function SuperDuperFunction() { // DoSomething } function SuperDuperFunctionBecauseMicrosoftMakesIEsuckIntentionally() { if(isIE) // For Chrome, oninput works as expected SuperDuperFunction(); } <textarea id="taSource" class="taSplitted" rows="4" cols="50" oninput="SuperDuperFunction();" onpropertychange="SuperDuperFunctionBecauseMicrosoftMakesIEsuckIntentionally();" onmousemove="SuperDuperFunctionBecauseMicrosoftMakesIEsuckIntentionally();" onkeyup="SuperDuperFunctionBecauseMicrosoftMakesIEsuckIntentionally();"> Test </textarea>
źródło
Wiem, że to nie jest dokładnie twoje pytanie, ale pomyślałem, że może się przydać. W przypadku niektórych aplikacji dobrze jest mieć funkcję zmiany uruchamianą nie za każdym razem, gdy naciśnięty zostanie klawisz. Można to osiągnąć za pomocą czegoś takiego:
var text = document.createElement('textarea'); text.rows = 10; text.cols = 40; document.body.appendChild(text); text.onkeyup = function(){ var callcount = 0; var action = function(){ alert('changed'); } var delayAction = function(action, time){ var expectcallcount = callcount; var delay = function(){ if(callcount == expectcallcount){ action(); } } setTimeout(delay, time); } return function(eventtrigger){ ++callcount; delayAction(action, 1200); } }();
Działa to poprzez sprawdzenie, czy w pewnym okresie opóźnienia wystąpiło nowsze zdarzenie. Powodzenia!
źródło
Wiem, że to pytanie było specyficzne dla JavaScript, jednak wydaje się, że nie ma dobrego, przejrzystego sposobu na ZAWSZE wykrycie, kiedy obszar tekstowy zmienia się we wszystkich obecnych przeglądarkach. Dowiedziałem się, że jquery zajął się tym za nas. Obsługuje nawet zmiany menu kontekstowego w obszarach tekstowych. Ta sama składnia jest używana niezależnie od typu wejścia.
$('div.lawyerList').on('change','textarea',function(){ // Change occurred so count chars... });
lub
$('textarea').on('change',function(){ // Change occurred so count chars... });
źródło
bind("input cut paste"...
i działa jak urok - pisanie, wycinanie i wklejanie za pomocą klawiatury lub menu kontekstowego; nawet przeciągnij / upuść tekstu.change
zdarzenia dlatextarea
.Możesz słuchać zdarzenia przy zmianie obszaru tekstowego i wprowadzać zmiany, jak chcesz. Oto jeden przykład.
const textArea = document.getElementById('my_text_area'); textArea.addEventListener('input', () => { var textLn = textArea.value.length; if(textLn >= 100) { textArea.style.fontSize = '10pt'; } })
<html> <textarea id='my_text_area' rows="4" cols="50" style="font-size:40pt"> This text will change font after 100. </textarea> </html>
źródło
Kluczowanie powinno wystarczyć, jeśli jest sparowane z atrybutem walidacji / wzorca wejścia HTML5. Dlatego utwórz wzorzec (wyrażenie regularne), aby sprawdzić poprawność danych wejściowych i działaj na podstawie statusu .checkValidity (). Coś jak poniżej może działać. W twoim przypadku chciałbyś, aby wyrażenie regularne odpowiadało długości. Moje rozwiązanie jest używane / demonstracyjne online tutaj .
<input type="text" pattern="[a-zA-Z]+" id="my-input"> var myInput = document.getElementById = "my-input"; myInput.addEventListener("keyup", function(){ if(!this.checkValidity() || !this.value){ submitButton.disabled = true; } else { submitButton.disabled = false; } });
źródło
Kod, którego użyłem dla IE 11 bez jQuery i tylko dla pojedynczego obszaru tekstowego:
JavaScript:
// Impede que o comentário tenha mais de num_max caracteres var internalChange= 0; // important, prevent reenter function limit_char(max) { if (internalChange == 1) { internalChange= 0; return; } internalChange= 1; // <form> and <textarea> are the ID's of your form and textarea objects <form>.<textarea>.value= <form>.<textarea>.value.substring(0,max); }
i html:
<TEXTAREA onpropertychange='limit_char(5)' ...
źródło
Spróbuj tego. To proste, a ponieważ jest rok 2016, jestem pewien, że będzie działać na większości przeglądarek.
<textarea id="text" cols="50" rows="5" onkeyup="check()" maxlength="15"></textarea> <div><span id="spn"></span> characters left</div> function check(){ var string = document.getElementById("url").value var left = 15 - string.length; document.getElementById("spn").innerHTML = left; }
źródło
Najlepszą rzeczą, jaką możesz zrobić, jest ustawienie funkcji, która ma być wywoływana w określonym czasie i ta funkcja, aby sprawdzić zawartość obszaru tekstowego.
self.setInterval('checkTextAreaValue()', 50);
źródło