Gunnar Bittersmann: Eingabefeld als Button

Ich habe ein Eingabefeld (readonly), beim Click darauf soll dessen Inhalt in die Zwischenablage kopiert werden.

Dass der Click auf ein Eingabefeld eine Aktion auslöst, dürfte befremdlich sein. Zum Auslösen von Aktionen sind Buttons da; mein erster Gedanke war also <input type="button">. Funktioniert aber nicht, da es die select()-Methode nur für Texteingabefelder, nicht aber für Buttons gibt.

Das Ding muss also <input type="text"> bleiben. Macht es Sinn, dem Eingabefeld role="button" zu verpassen?

Wenn das Ding so in die Rolle eines Buttons schlüpft, sollte es kein zugeordnetes label-Element haben, oder? (Aber natürlich eine aussagekräftige Beschriftung – per aria-label oder aria-labeledby.)

Wie in diesem Codepen?

<span id="accessible-label">copy to clipboard:</span>
<input value="some text" readonly="" role="button" aria-labeledby="accessible-label"/>

LLAP 🖖

--
„Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
  1. Lieber Gunnar,

    warum kann es nicht ein zweites Element, nämlich den echten Button geben?

    Liebe Grüße

    Felix Riesterer

    1. @@Felix Riesterer

      warum kann es nicht ein zweites Element, nämlich den echten Button geben?

      Kann es auch. Werde ich später vielleicht auch machen.

      Im Moment will es erstmal ohne größere Umbauten tastaturbedienbar machen.

      LLAP 🖖

      --
      „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
      1. Hallo,

        Im Moment will es erstmal ohne größere Umbauten tastaturbedienbar machen.

        tastaturbedienbar kriege ich mit klicken und readonly irgendwie nicht unter einen Hut. Es klingt (zumindest ohne weitere Erklärung) paradox.

        So long,
         Martin

        --
        Ein Tag, an dem du nicht wenigstens einmal gelacht hast, ist ein verlorener Tag.
        1. @@Der Martin

          tastaturbedienbar kriege ich mit klicken und readonly irgendwie nicht unter einen Hut. Es klingt (zumindest ohne weitere Erklärung) paradox.

          Das Ding soll sich wie ein Button verhalten: bei Leertaste und Enter eine Aktion auslösen.

          LLAP 🖖

          --
          „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
      2. Im Moment will es erstmal ohne größere Umbauten tastaturbedienbar machen.

        [Strg]+[c] kopiert ins Clipboard. MFG

        1. @@Emil

          [Strg]+[c] kopiert ins Clipboard.

          Und vorher muss man noch den Text selektieren. Der Aufwand soll dem Nutzer eben abgenommen werden; Kopieren soll per one-click möglich sein.

          LLAP 🖖

          --
          „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
          1. [Strg]+[c] kopiert ins Clipboard.

            Und vorher muss man noch den Text selektieren.

            Nein, muss man nicht. Man muss lediglich per JS feststellen ob eine bestimmte Taste bzw. Tastenkombination gedrückt wurde. Den Text kriegst dann wie üblich mit input.value ohne dass der selektiert sein muss. MFG

            1. Hallo Emil,

              ich wollte schon losflamen, habe aber dann nochmal in der MDN geguckt. Autsch. Eigene Finger verbrannt.

              Den Text zu kriegen ist ja kein Problem, dazu war keine Info nötig. Das Übertragen ins Clipboard ist die Schwierigkeit. Der "klassische" Weg mit document.execCommand("copy") will eine Selection haben.

              Aber es gibt auch noch das Clipboard-Objekt aus navigator.clipboard, mit der Methode writeText(), mit der man den so empfangenen Text ins Clipboard bringt!

              Den habe ich nämlich eben nicht gefunden, weil mich die MDN auf Abwege geführt hatte auf denen stand dass man nur Bilder ins Clipboard bringen könne, aber das war das Web-Extension API, nicht das Clipboard API. Zumindest für Chrome und Fuchs soll es funktionieren. Edge (noch) nicht, IE auch nicht, Safari hat ein Fragezeichen.

              Fragt sich dann nur, wie der Fallback für inkompatible Browser aussehen kann... Vermutlich dann doch ein vestecktes input-Feld.

              Rolf

              --
              sumpsi - posui - clusi
              1. Ich denke auch, daß man, wenn man eine Anwendung tastaturbedienbar machen will, eben auch die Tastatur als Eingabegerät vorsieht und nicht auf Klickereignisse der Maus wartet. MFG

                1. Hallo Emil,

                  Ich denke auch, daß man, wenn man eine Anwendung tastaturbedienbar machen will, eben auch die Tastatur als Eingabegerät vorsieht und nicht auf Klickereignisse der Maus wartet.

                  Die Anwendung soll mit jedem Eingabegerät bedienbar sein.

                  Bis demnächst
                  Matthias

                  --
                  Pantoffeltierchen haben keine Hobbys.
                  ¯\_(ツ)_/¯
        2. @@Emil

          [Strg]+[c] kopiert ins Clipboard.

          Nein, das tut [ctrl]+[c] nicht. [cmd ⌘]+[c] kopiert in die Zwischenablage. 😜 (f/k/a Apfeltaste)

          LLAP 🖖

          --
          „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
          1. Hallo,

            [Strg]+[c] kopiert ins Clipboard.

            Nein, das tut [ctrl]+[c] nicht. [cmd ⌘]+[c] kopiert in die Zwischenablage. 😜 (f/k/a Apfeltaste)

            das mag bei einer Minderheit der Systeme da draußen so sein. Und da, wo Ctrl-C funktioniert, geht in den allermeisten Fällen alternativ auch Ctrl-Ins.

            Ciao,
             Martin

            --
            Ein Tag, an dem du nicht wenigstens einmal gelacht hast, ist ein verlorener Tag.
      3. @@Gunnar Bittersmann

        warum kann es nicht ein zweites Element, nämlich den echten Button geben?

        Kann es auch. Werde ich später vielleicht auch machen.

        Hab ich jetzt gemacht: Eingabefeld + Button.

        Und da das Eingabefeld bei entsprechender Buttonbeschriftung („Link kopieren“) nicht sichtbar sein muss, <input type="hidden"/>. – Geht nicht; select() tut’s dann nicht. Dito bei <input hidden=""/>. Auch mit display: none oder visibility: hidden nicht.

        Also das Eingabefeld visuell versteckt. Und da das auch im Screenreader nicht vorgelesen werden soll, aria-hidden="true". Meist hat man ja wenn, dann eins der beiden. Hier visually-hidden und aria-hidden am selben Element.

        LLAP 🖖

        --
        „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
        1. @@Gunnar Bittersmann

          Also das Eingabefeld visuell versteckt. Und da das auch im Screenreader nicht vorgelesen werden soll, aria-hidden="true". Meist hat man ja wenn, dann eins der beiden. Hier visually-hidden und aria-hidden am selben Element.

          Auf Erics Geheiß noch das notwendige tabindex="-1" ergänzt. Und auch readonly.

          LLAP 🖖

          --
          „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
          1. Hej Gunnar,

            @@Gunnar Bittersmann

            Also das Eingabefeld visuell versteckt. Und da das auch im Screenreader nicht vorgelesen werden soll, aria-hidden="true". Meist hat man ja wenn, dann eins der beiden. Hier visually-hidden und aria-hidden am selben Element.

            Auf Erics Geheiß noch das notwendige tabindex="-1" ergänzt. Und auch readonly.

            Ich wollte es gerade sagen: bei all der notwendigen Unterstützung für Blinde, die Sehenden nicht vergessen. 😉

            Marc

            --
            Ceterum censeo Google esse delendam
            1. Hej Gunnar,

              @@Gunnar Bittersmann

              Mit meinem iPhone (aktuelles iOS) geht es immer noch nicht…

              Ich kann auch keinen Cursor setzen oder so - einmal ist es mir gelungen, den Text mit der eingebauten iOS-Funktionalität zu kopieren, so als gäbe es da keine Unterstützung von Dir. Das klappte beim wiederholten Versuch aber auch nicht - schon beim Versuch den Text zu markieren bin ich gescheitert…

              Ist das bei Dir nicht so?

              Außerdem: wie weist du in einer echten Anwendung auf diese Funktion hin? Intuitiv ist das ja nicht. Ich jedenfalls käme nicht auf die Idee. Ich weiß auch nicht, ob ich möchte, dass mir ein unbedarfter Klick auf eine vermeintlich harmlose Stelle das überschreibt, was ich vielleicht absichtlich im Cache habe.

              So interessant die Tüftelei ist und so sehr ich Deine Geduld dabei bewundere: für mich sind da noch allerhand Fragen offen und ich finde noch nicht, dass die Lösung für den Produktiv-Einsatz geeignet ist.

              Marc

              --
              Ceterum censeo Google esse delendam
              1. @@marctrix

                Mit meinem iPhone (aktuelles iOS) geht es immer noch nicht…

                In dem Codepen hab ich auch nichts geändert. (Hätte ich wohl erwähnen sollen.)

                Außerdem: wie weist du in einer echten Anwendung auf diese Funktion hin?

                Icon und Text „Link kopieren“.

                LLAP 🖖

                --
                „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
                1. Hej Gunnar,

                  @@marctrix

                  Außerdem: wie weist du in einer echten Anwendung auf diese Funktion hin?

                  Icon und Text „Link kopieren“.

                  Da würde ich intuitiv drauf klicken oder touchen. Kenne das so von anderen Seiten (z.B. Blindtext-Generatoren).

                  Um den Text selbst würde ich mit meiner Maus einen Bogen machen…

                  Wenn ich den Text mit der Tastatur auswählen wollen würde, würde ich das auch tun - denn der (vermeintliche Button, also Icon mit Text) kommt ja erst danach, nehme ich an? Oder steht der davor und merke ich als Sehender Keyboard-Nutzer, dass ich dann nicht erst bis zu dem Text muss, den ich kopieren will?

                  Irgendwie kann ich mir noch nicht vorstellen, dass das wirklich intuitiv wird…

                  Andererseits habe ich viel Vertrauen in Dich. Bin gespannt, würde das gerne mal live sehen.

                  Marc

                  --
                  Ceterum censeo Google esse delendam
                  1. Hallo marctrix,

                    Irgendwie kann ich mir noch nicht vorstellen, dass das wirklich intuitiv wird…

                    Websites wie Github machen das schon seit längerem. Ich finde eigentlich, dass das ganz gut funktioniert; ich zumindest habe es sofort verstanden.

                    LG,
                    CK

                    1. Hej Christian,

                      Hallo marctrix,

                      Irgendwie kann ich mir noch nicht vorstellen, dass das wirklich intuitiv wird…

                      Websites wie Github machen das schon seit längerem. Ich finde eigentlich, dass das ganz gut funktioniert; ich zumindest habe es sofort verstanden.

                      Bei Gitlab gibt es tatsächlich auch so was. Liegt wohl an mir, dass ich die URL immer anklicke und dann mit Strg-C übernehme. - Ich mag es nicht, wenn man je nach Anwendung/Seite etwas unterschiedlich machen muss. So lange beides geht ist das dann ja aber kein Nachteil…

                      -- Marc

                      Ceterum censeo Google esse delendam

  2. Liest sich wie keine gute Idee. Denn obwohl sie wegen der JS-Funktion naheliegen mag, würdest Du ja gegen eine der ARIA-Regeln verstossen, wonach Du die Semantik eines Elements nicht verändern sollst (wenn es eine hat). Und das würdest Du ja hier tun.

    Grüße aus Mainz,

    Jens Grochtdreis

    1. @@Flocke

      würdest Du ja gegen eine der ARIA-Regeln verstossen, wonach Du die Semantik eines Elements nicht verändern sollst

      Ja, gleich die erste Regel: Verwende nicht ARIA, wenn du nicht musst. Das heißt, bei Neubauten die richtigen Elemente verwenden.

      ARIA lässt sich aber auch nutzen, um bei Altbauten die Barrierefreiheit zu verbessern (ohne alles umbauen zu müssen) – und dabei eben die Rolle von Elementen zu ändern.

      LLAP 🖖

      --
      „Wer durch Wissen und Erfahrung der Klügere ist, der sollte nicht nachgeben. Und nicht aufgeben.“ —Kurt Weidemann
  3. Tach!

    Ich habe ein Eingabefeld (readonly), beim Click darauf soll dessen Inhalt in die Zwischenablage kopiert werden.

    Dass der Click auf ein Eingabefeld eine Aktion auslöst, dürfte befremdlich sein. Zum Auslösen von Aktionen sind Buttons da; mein erster Gedanke war also

    Wer bist du und was hast du mit Gunnar gemacht? Sein erster Gedanke wäre, dem Auftraggeber diese Funktionalität auszureden. Zumindest predigt er das immer anderen, dass man das als Entwickler so machen müsse.

    Das Ding muss also <input type="text"> bleiben. Macht es Sinn, dem Eingabefeld role="button" zu verpassen?

    Dazu wäre die Frage zu klären, was das Attribut konkret bewirkt und was passiert, wenn es nicht mehr da ist.

    Wenn das Ding so in die Rolle eines Buttons schlüpft, sollte es kein zugeordnetes label-Element haben, oder? (Aber natürlich eine aussagekräftige Beschriftung – per aria-label oder aria-labeledby.)

    Wie in diesem Codepen?

    <span id="accessible-label">copy to clipboard:</span>
    <input value="some text" readonly="" role="button" aria-labeledby="accessible-label"/>
    

    Auch hier wieder die Frage, was die Konsequenzen wären, und was an einem Span besser als an einem Label ist. Warum soll das Label nur für Nichtsehende als solches gekennzeichnet sein und sich nicht auch für den Rest des Publikums als solches verhalten, beispielsweise beim Draufklicken den "Button" auslösen?

    dedlfix.

  4. Dass der Click auf ein Eingabefeld eine Aktion auslöst, dürfte befremdlich sein. Zum Auslösen von Aktionen sind Buttons da; mein erster Gedanke war also <input type="button">. Funktioniert aber nicht, da es die select()-Methode nur für Texteingabefelder, nicht aber für Buttons gibt.

    Wenn du die Clipboard API benutzen kannst, dann gehts auch mit einem Button.

    Mit Midas, also deinem bisherigen Ansatz, könnte es auch möglich sein wenn du auf den Komfort von der select-Methode verzichtest und die Markierung mit den entsprechenden Midas-Befehlen selbst setzt. Sicher bin ich mir da aber nicht.

  5. Hej Gunnar,

    Wie in diesem Codepen?

    <span id="accessible-label">copy to clipboard:</span>
    <input value="some text" readonly="" role="button" aria-labeledby="accessible-label"/>
    

    Bei mir im iPhone funktioniert das nicht.

    Soll ich mal Marco und oder Domingos bitten, das mit dem Screenreader zu testen?

    Grundsätzlich spricht nicht nur die erste Regel gegen die Änderung mittels role. Es ist generell kein gutes Vorgehen.

    Native HTML semantics should still be used whenever possible, but ARIA is useful when certain design patterns or interactions make it impossible to do so. For example, a complex tabbed-interface has no semantic equivalent with HTML, but a role="tablist" and its related attributes can be added to provide this detail to screen readers.

    Deine Seite müsste überarbeitet werden. Dass du das nicht tust, hat sicher andere Gründe. Vermutlich kommst du an den Code nicht ran.

    Mir scheint hier Strg+C die bessere Lösung.

    Zumal es nicht in Ordnung wäre, Blinden den Hinweis zu geben, dass der Text kopiert werden kann, den meisten Menschen diese Information aber vorenthalten wird.

    Fazit: Es funktioniert nicht mit dem iPhone, Screenreader sind fraglich, widerspricht best practices, wird vermutlich vergessen und so immer im Code bleiben, erhöht den Test-Aufwand, ist für sehende unverständlich und löst kein Problem (ein Klick mehr ist kein Problem).

    Die vielen Nachteile überwiegen den kleinen Vorteil.

    Marc

    --
    Ceterum censeo Google esse delendam
  6. Hallo Gunnar,

    ich dachte ich hätte eine Lösung, aber sie geht nur mit Chrome, nicht mit Firefox. Der Fuchs kopiert nur den Span, nicht den Button. Sehr merkwürdig. range.toString() ergibt bei beiden Browsern den Buttontext, aber das copy-Command ignoriert beim Fuchs die Inhalte von Buttons. Selbst dann, wenn ich ein div um den button lege und ein span hinein.

    Den IE habe ich nicht getestet (weil jsFiddle und Codepen unter IE streiken).

    Aber vielleicht kannst Du dem Fuchs mit einem versteckten Eingabefeld nachhelfen, in das Du den Buttontext kopierst.

    <button class="click2copy">Copy me</button>
    <span class="click2copy">Don't make a clickable span!</span>
    
    document.body.addEventListener("click", click2copyListener);
    
    function click2copyListener(event) {
      if (!event.target.classList.contains("click2copy")) return;
    
      // IE ab Version 9
      if (window.getSelection) {
         let selection = window.getSelection();
         let range = document.createRange();
    
         range.selectNode(event.target);
    
         selection.removeAllRanges();
         selection.addRange(range);
    
         document.execCommand("copy");
    
         selection.removeAllRanges();
      }
    }
    

    Rolf

    --
    sumpsi - posui - clusi