jquery input zaznacz wszystko na fokus

326

Używam tego kodu, aby spróbować zaznaczyć cały tekst w polu, gdy użytkownik skupia się na polu. Co się dzieje, zaznacza wszystko na sekundę, a następnie jest niezaznaczone, a kursor pisania zostaje w miejscu, w którym kliknąłem ...

$("input[type=text]").focus(function() {
   $(this).select();
});

Chcę, żeby wszystko pozostało wybrane.

Tim
źródło
Jaka przeglądarka wydaje mi się działać poprawnie w FF?
R0MANARMY
8
Chrome = błąd dla tego
wowo_999,
1
Korzystałem z Chrome, ale .click () rozwiązuje problem :)
Tim
4
Uwaga: Akceptowana tutaj odpowiedź rozwiązuje tylko połowę problemu. To sprawia, że ​​zaznaczenie działa, ale utrudnia późniejsze cofnięcie wyboru przy kolejnych kliknięciach. Lepsze rozwiązanie można znaleźć tutaj: stackoverflow.com/questions/3380458/...
SDC

Odpowiedzi:

480

Spróbuj użyć clickzamiast focus. Wygląda na to, że działa zarówno w przypadku myszy, jak i kluczowych zdarzeń (przynajmniej w Chrome / Mac):

jQuery <wersja 1.7:

$("input[type='text']").click(function () {
   $(this).select();
});

jQuery wersja 1.7+:

$("input[type='text']").on("click", function () {
   $(this).select();
});

Oto demo

karim79
źródło
62
Problem polega na tym, że nie można już zaznaczać fragmentu tekstu myszką, po kliknięciu wybierany jest pełny tekst.
Helin Wang
6
Nie jest to dla mnie realne rozwiązanie. Stwarza to problem opisany przez Wanga.
Marquez,
1
Poniżej znajduje się rozwiązanie Nianpeng, które działa również z zaznaczaniem tekstu myszy.
Philibert Perusse
4
@AwQiruiGuo $ .fn.on („kliknięcie”, ..) może zużywać mniej pamięci i pracować z dynamicznie dodawanymi elementami potomnymi.
Ricky Boyce
7
Nie działa to podczas ustawiania ostrości pola podczas tabulacji.
Colin Breame
65

Myślę, że tak się dzieje:

focus()
   UI tasks related to pre-focus
   callbacks
       select()
   UI tasks related to focus (which unselect again)

Obejściem może być asynchroniczne wywoływanie funkcji select (), dzięki czemu działa ona całkowicie po focus ():

$("input[type=text]").focus(function() { 
    var save_this = $(this);
    window.setTimeout (function(){ 
       save_this.select(); 
    },100);
});
Piskvor opuścił budynek
źródło
3
$ („input [type = text]”). focus (function () {var save_this = $ (this); window.setTimeout (function () {save_this.select ();}, 100);});
etienne
@etienne: Oh, dobra uwaga: obsługa thisjest nieco nieoczekiwana w takich zakresach. Zaktualizuję kod.
Piskvor opuścił budynek
3
wartość limitu czasu równa 0 również wydaje się być w porządku, a funkcja „focusin ()” również działa z tą metodą.
Tanguy
4
tak, nie musisz nawet ustawiać okresu. 0 wystarczy, ponieważ przekroczą limit czasu na końcu bieżącego stosu wywołań. oznacza to, że zdarzenia skupienia i kliknięcia zapalają się, a następnie uruchamia się twoja funkcja
Joshua Bambrick
1
Wydaje się, że w przypadku przekroczenia limitu czasu 0 zdarzenie „kliknięcie” może zostać uruchomione w późniejszej ramce, odznaczając to pole ponownie. Uważam, że limit czasu 10 wydaje się działać całkiem dobrze - bez zauważalnego opóźnienia, ale bardziej niezawodny niż 0.
phil
57

Myślę, że to lepsze rozwiązanie. W przeciwieństwie do zwykłego zaznaczania w zdarzeniu onclick, nie przeszkadza to zaznaczaniu / edytowaniu tekstu za pomocą myszy. Działa z większymi silnikami renderującymi, w tym IE8.

$('input').on('focus', function (e) {
    $(this)
        .one('mouseup', function () {
            $(this).select();
            return false;
        })
        .select();
});

http://jsfiddle.net/25Mab/9/

użytkownik2072367
źródło
4
Działa to tylko w przypadku istniejących pól, oto aktualizacja powiązania z nowymi polami wejściowymi: jsfiddle.net
adriaan
Czasami fokus można podać bez kliknięcia, a to dobrze go obsługuje. Z tego powodu jest to dla mnie najczystsza odpowiedź - nawet jeśli za każdym razem, gdy dane wejściowe są skoncentrowane, a nie jednym kliknięciem, mogą pojawić się wiszące detektory zdarzeń, znacznie lepsze niż setTimeout
ilovett
Nie pozwala to na drugie kliknięcie w danych numerycznych, aby wybrać inną część tekstu za pomocą myszy. select()Wydaje się, że usunięcie drugiego działa.
dperish
Jeszcze lepiej z dodatkowym$('input[autofocus]').select();
Daniel Bleisteiner
38

Istnieje kilka przyzwoitych odpowiedzi, a @ user2072367 jest moją ulubioną, ale ma nieoczekiwany wynik, gdy skupiasz się za pomocą karty zamiast kliknięcia. (nieoczekiwany wynik: aby zaznaczyć tekst normalnie po fokusie za pomocą karty, należy kliknąć jeden dodatkowy czas)

To skrzypek naprawia ten mały błąd i dodatkowo przechowuje $ (this) w zmiennej, aby uniknąć zbędnego wyboru DOM. Sprawdź to! (:

Testowane w IE> 8

$('input').on('focus', function() {
    var $this = $(this)
        .one('mouseup.mouseupSelect', function() {
            $this.select();
            return false;
        })
        .one('mousedown', function() {
            // compensate for untriggered 'mouseup' caused by focus via tab
            $this.off('mouseup.mouseupSelect');
        })
        .select();
});
animowany gif
źródło
2
+1 Twoje i @ user2072367 rozwiązania są najczystsze w całym tym wątku i szkoda, że ​​nie było sposobu, aby szybciej dostać się na szczyt.
KyleMit
1
Działa nawet, jeśli użytkownik próbuje sam zaznaczyć cały tekst, brawo.
Vitani
Dla mnie to nie działa na ie11 w Windows 8.1. Działa w ie11 na Windows 7 i Windows 10
Lars Thomas Bredland
1
@ LarsThomasBredland Właśnie próbowałem na Win 8.1 + ie11 i działa zgodnie z oczekiwaniami. Co dla ciebie „nie działa”?
animatedgif
Po prostu nic nie wybiera. (Testowałem na innym Win8 i działa tam - ten sam poziom systemu
operacyjnego
21

Po dokładnej analizie proponuję to jako znacznie czystsze rozwiązanie w tym wątku:

$("input").focus(function(){
    $(this).on("click.a keyup.a", function(e){      
        $(this).off("click.a keyup.a").select();
    });
});

Demo w jsFiddle

Problem:

Oto kilka wyjaśnień:

Najpierw rzućmy okiem na kolejność zdarzeń, gdy klikniesz myszką lub tabulujesz w polu.
Możemy zarejestrować wszystkie odpowiednie zdarzenia w następujący sposób:

$("input").on("mousedown focus mouseup click blur keydown keypress keyup change",
              function(e) { console.log(e.type); });

wydarzenia fokusowe

Uwaga : Zmieniłem to rozwiązanie tak, aby używało, clicka nie mouseupjak ma to miejsce później w potoku zdarzeń i wydawało się, że powoduje pewne problemy w firefoxie zgodnie z komentarzem @ Jocie

Niektóre przeglądarki próbują ustawić kursor podczas mouseupclick zdarzeń lub . Ma to sens, ponieważ możesz uruchomić kursor w jednej pozycji i przeciągnąć, aby podświetlić jakiś tekst. Nie może oznaczać pozycji karetki, dopóki nie podniesiesz myszy. Funkcje, które obsługują, focussą przeznaczone, aby reagować zbyt wcześnie, pozostawiając przeglądarkę nadpisującą twoje pozycjonowanie.

Ale pocieranie polega na tym, że naprawdę chcemy obsłużyć zdarzenie skupiające. Daje nam znać, kiedy ktoś wszedł na boisko po raz pierwszy. Po tym momencie nie chcemy nadal zastępować zachowań związanych z wyborem użytkownika.

Rozwiązanie:

Zamiast tego, w focusmodule obsługi zdarzeń, możemy szybko dołączyć detektory zdarzeń click(kliknięcie) i keyup(tab in), które mają zostać uruchomione.

Uwaga : Keyup zdarzenia tab będzie faktycznie uruchamiane w nowym polu wejściowym, a nie w poprzednim

Chcemy odpalić wydarzenie tylko raz. Możemy użyć .one("click keyup), ale wywołałoby to obsługę zdarzeń jeden raz dla każdego typu zdarzenia . Zamiast tego, jak tylko naciśniemy przycisk myszy lub przycisk klawiatury, wywołamy naszą funkcję. Pierwszą rzeczą, którą zrobimy, jest usunięcie programów obsługi obu. W ten sposób nie będzie miało znaczenia, czy włożyliśmy tabulator, czy wtargnęliśmy. Funkcja powinna zostać wykonana dokładnie raz.

Uwaga : większość przeglądarek naturalnie zaznacza cały tekst podczas zdarzenia na karcie, ale jak zauważył animatedgif , nadal chcemy obsłużyć to keyupzdarzenie, w przeciwnym mouseuprazie wydarzenie będzie się utrzymywać za każdym razem, gdy będziemy w nim zakładać. Słuchamy obu, abyśmy mogli włączyć od słuchaczy, jak tylko przetworzymy wybór.

Teraz możemy zadzwonić select()po dokonaniu wyboru przeglądarki, więc z pewnością zastąpimy domyślne zachowanie.

Wreszcie, dla dodatkowej ochrony, możemy dodać przestrzenie nazw zdarzeń do funkcji mouseupi, keyupaby .off()metoda nie usuwała żadnych innych detektorów, które mogłyby być w grze.


Testowane w IE 10+, FF 28+ i Chrome 35+


Alternatywnie, jeśli chcesz rozszerzyć jQuery o wywołaną funkcję once, która uruchomi się dokładnie raz dla dowolnej liczby zdarzeń :

$.fn.once = function (events, callback) {
    return this.each(function () {
        var myCallback = function (e) {
            callback.call(this, e);
            $(this).off(events, myCallback);
        };
        $(this).on(events, myCallback);
    });
};

Następnie możesz uprościć kod w następujący sposób:

$("input").focus(function(){
    $(this).once("click keyup", function(e){      
        $(this).select();
    });
});

Demo w skrzypcach

KyleMit
źródło
W przeglądarce Firefox 31 w systemie Windows kod zaznacza tekst tylko przy każdym drugim kliknięciu, gdy klikniesz między dwoma polami tekstowymi
Vitani
1
@Jocie, nie jestem pewien, dlaczego jest naprzemiennie, ale wygląda na to, że FF obsługuje zaznaczanie tekstu w clickzdarzeniu, które jest dalej niż w potoku mouseup. Ponieważ chcemy obsłużyć koniec zaznaczenia tak późno, jak to możliwe, aby dać nam największą szansę na przesłonięcie przeglądarki, użycie kliknięcia zamiast myszy powinno załatwić sprawę. Testowane w FF, Chrome i IE.
KyleMit
1
Dziękuję Ci! Wreszcie rozwiązanie, które naprawdę działa we wszystkich przeglądarkach!
Vincent
1
Tak! To też działało dla mnie! Dziękuję Ci. To powinna być oficjalna odpowiedź
Fandango68,
1
@RiZKiT onenie będzie go wycinać, ponieważ „Program obsługi jest wykonywany raz na element dla każdego typu zdarzenia . Automatycznie wyłączy zdarzenie, które je uruchomiło, ale drugi nadal pozostanie w pobliżu i i tak offzajmie się nimi. Zobacz moje pytanie: funkcja, która uruchomi się dokładnie raz dla dowolnej liczby zdarzeń
KyleMit,
13

Spowoduje to wykonanie pracy i uniknięcie problemu polegającego na tym, że nie można już zaznaczać części tekstu za pomocą myszy.

$("input[type=text]").click(function() {
    if(!$(this).hasClass("selected")) {
        $(this).select();
        $(this).addClass("selected");
    }
});
$("input[type=text]").blur(function() {
    if($(this).hasClass("selected")) {
        $(this).removeClass("selected");
    }
});
Nianpeng
źródło
1
Ważne, aby zachować możliwość zaznaczania części tekstu za pomocą myszy. Używam tego i jego A1
Philibert Perusse
2
Zbyt wiele się tutaj dzieje, użyj rozwiązania focus / mouseup
George
@George user2072367's jest całkiem dobry, ale ma kilka poważnych wad. Sprawdź moje rozwiązanie (:
animatedgif
6

Ta wersja działa na iOS, a także naprawia standardowe przeciąganie, aby wybrać na Windows Chrome

var srcEvent = null;

$("input[type=text],input[type=number]")

    .mousedown(function (event) {
        srcEvent = event;
    })

    .mouseup(function (event) {
        var delta = Math.abs(event.clientX - srcEvent.clientX) 
                  + Math.abs(event.clientY - srcEvent.clientY);

        var threshold = 2;
        if (delta <= threshold) {
                   try {
                        // ios likes this but windows-chrome does not on number fields
                        $(this)[0].selectionStart = 0;
                        $(this)[0].selectionEnd = 1000;
                    } catch (e) {
                        // windows-chrome likes this
                        $(this).select();
                    }
        }
    });

http://jsfiddle.net/Zx2sc/2/

anihilnina
źródło
Edytowano, aby dodać brzydkie try / catch do uspokojenia przeglądarek
anihilnine
5

Problem z większością tych rozwiązań polega na tym, że nie działają one poprawnie podczas zmiany pozycji kursora w polu wprowadzania.

onmouseupZdarzenie zmienia położenia kursora w tej dziedzinie, który jest zwolniony po onfocus(przynajmniej w Chrome i FF). Jeśli bezwarunkowo odrzucisz, mouseupużytkownik nie będzie mógł zmienić pozycji kursora za pomocą myszy.

function selectOnFocus(input) {
    input.each(function (index, elem) {
        var jelem = $(elem);
        var ignoreNextMouseUp = false;

        jelem.mousedown(function () {
            if (document.activeElement !== elem) {
                ignoreNextMouseUp = true;
            }
        });
        jelem.mouseup(function (ev) {
            if (ignoreNextMouseUp) {
                ev.preventDefault();
                ignoreNextMouseUp = false;
            }
        });
        jelem.focus(function () {
            jelem.select();
        });
    });
}
selectOnFocus($("#myInputElement"));

Kod warunkowo uniemożliwi mouseupzachowanie domyślne, jeśli pole nie jest aktualnie aktywne. Działa w tych przypadkach:

  • kliknięcie, gdy pole nie jest skupione
  • kliknięcie, gdy pole jest aktywne
  • tabulacja w pole

Testowałem to w Chrome 31, FF 26 i IE 11.

Colin Breame
źródło
Działa to doskonale w przypadku zdarzeń kliknięcia, ale jeśli
użyję klawisza
4

Znalazłem świetne rozwiązanie, czytając ten wątek

$(function(){

    jQuery.selectText('input:text');
    jQuery.selectText('input:password');

});

jQuery.extend( {
    selectText: function(s) { 
        $(s).live('focus',function() {
            var self = $(this);
            setTimeout(function() {self.select();}, 0);
        });
    }
});
RafaelTSCS
źródło
... co jest zasadniczo taką samą odpowiedzią jak Piskvor .
Oliver
nie zapomnij o wszystkich innych typach tekstu HTML5, np. „input [type = email]”
jamiebarrow
3

Pochodzę z końca 2016 roku i ten kod działa tylko w najnowszych wersjach jquery (w tym przypadku jquery-2.1.3.js).

if ($(element).is("input")) {
    $(element).focus(function () {
        $(element).select();
    });
}
Aaron
źródło
2

Używając FF 16.0.2 i jquery 1.8.3, cały kod w odpowiedzi nie działał.
Używam takiego kodu i pracuję.

$("input[type=text]").focus().select();
GusDeCooL
źródło
4
To nie odpowiada na pytanie, jak wybrać zawartość pola wprowadzania, gdy użytkownik skupi pole . Spowoduje to natychmiastowe ustawienie i wybranie kodu, bez udziału użytkownika.
saluce
@saluce nie rozumiem o co ci chodzi? to, czego pytający chce, gdy wybiera pole, zaznacza cały bieżący tekst. Mój kod powinien to zrobić. Używam go nawet do mojego projektu, jako do czasu, kiedy piszę tę odpowiedź.
GusDeCooL,
1
Ten kod będzie się skupiał i wybierał wszystko podczas działania, ale sam w sobie kod nie jest powiązany ze zdarzeniem generowanym przez użytkownika , takim jak kliknięcie pola tekstowego. Na przykład $("input[type=text]").on('click', function () { $(this).focus.select(); })powoduje, że fokus i wybór mają miejsce, gdy użytkownik kliknie pole, ponieważ jest on wykonywany, gdy użytkownik kliknie pole. Bez modułu obsługi zdarzeń kod nie odpowiada na pytanie, stąd opinia i komentarz. Zasadniczo masz część „cały bieżący tekst jest zaznaczony”, ale nie część „kiedy wybiera pole”.
saluce
1
@GusDeCooL dość zabawnie (chociaż nie jest to dokładnie to, o co prosił) Chciałem uzyskać taki sam efekt, jak to zrobiłeś w tej sprawie :)
Robbie Averill
2
var timeOutSelect;
$("input[type=text]").focus(function() { 
        var save_this = $(this);
        clearTimeout(timeOutSelect);
        timeOutSelect = window.setTimeout (function(){ 
                save_this.select(); 
        }, 100);
});

Użyj clearTimeout dla większego bezpieczeństwa, jeśli szybko przełączasz się między dwoma wejściami. ClearTimeout wyczyść stary limit czasu ...

asimov
źródło
Edytuj z więcej informacji. Odradzane są tylko odpowiedzi kodowe i „wypróbuj to”, ponieważ nie zawierają one treści, które można przeszukiwać, i nie wyjaśniają, dlaczego ktoś powinien „wypróbować”. Staramy się być tutaj zasobem wiedzy.
Brian Tompsett - 汤 莱恩
2

Działa świetnie z natywnym JavaScript select().

$("input[type=text]").focus(function(event) {
   event.currentTarget.select();
});

lub ogólnie:

$("input[type=text]")[0].select()
Tobi G.
źródło
1

Lub możesz po prostu użyć <input onclick="select()">Works perfect.

tectiv3
źródło
nie, nie robi. działa na wybór całości. ale spróbuj ręcznie zaznaczyć część tekstu, nie będziesz w stanie tego zrobić.
Sujay Phadke
1

Możesz użyć prostego kodu:

$('#idname').select();
Rubén Ruíz
źródło
Oczywiście przy użyciu jQuery
Rubén Ruíz
0
<script>$.ready( $("input[type=text]").attr("onclick" , "this.select()"));<script>
trikon
źródło
Prawdopodobnie zostanie to oznaczone jako odpowiedź niskiej jakości, ponieważ nie ma żadnego wyjaśnienia, co się dzieje.
tumultous_rooster
Twoje $.readyjest nieprawidłowe Musisz przekazać mu funkcję, aby opóźniała do attrmomentu, gdy dokument będzie gotowy. Robisz to natychmiast, a następnie przekazujesz kolekcję elementów do $.ready.
doug65536
Unikaj także „kliknięcia”, szczególnie w ten sposób. Zastosowanie addEventListener.
doug65536
0

Zawsze używam requestAnimationFrame()do przeskakiwania wewnętrznych mechanizmów po zdarzeniu i działa to doskonale w Firefoksie. Nie testowałem w Chrome.

$("input[type=text]").on('focus', function() {
    requestAnimationFrame(() => $(this).select());
});
RP Pedraza
źródło