it-swarm.com.de

Chrome zählt falsche Zeichen im Textbereich mit dem Attribut maxlength

Hier ist ein Beispiel:

$(function() {
  $('#test').change(function() {
    $('#length').html($('#test').val().length)
  })
})
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<textarea id=test maxlength=10></textarea>
length = <span id=length>0</span>

Füllen Sie den Textbereich mit Zeilen (ein Zeichen in einer Zeile), bis der Browser zulässt . Wenn Sie fertig sind, verlassen Sie den Textbereich, und der js-Code berechnet auch die Zeichen.

In meinem Fall konnte ich also nur 7 Zeichen (einschließlich Leerzeichen) eingeben, bevor Chrome mich stoppte. Der Wert des Attributs Maxlength ist 10:

imgur

39
Roman Pominov

Ihre Wagenrückläufer werden in Bezug auf die maximale Länge jeweils als 2 Zeichen betrachtet.

1\r\n
1\r\n
1\r\n
1

Aber es scheint, dass das Javascript nur einen der \r\n (ich bin nicht sicher welcher) ist, was sich nur auf 7 summiert.

27
Neal

So erhalten Sie Ihren Javascript-Code, der der Zeichenmenge entspricht, die nach Ansicht des Browsers im Textbereich enthalten ist:

http://jsfiddle.net/FjXgA/53/

$(function () {
    $('#test').keyup(function () {
        var x = $('#test').val();

        var newLines = x.match(/(\r\n|\n|\r)/g);
        var addition = 0;
        if (newLines != null) {
            addition = newLines.length;
        }

        $('#length').html(x.length + addition);
    })
})

Grundsätzlich zählen Sie nur die gesamten Zeilenumbrüche in der Textbox und addieren jeweils 1 zur Zeichenanzahl. 

34
Tim

Aus unbekannten Gründen konvertiert jQuery immer alle Zeilenumbrüche im Wert von <textarea> in ein einzelnes Zeichen. Das heißt, wenn der Browser \r\n für eine neue Zeile angibt, stellt jQuery sicher, dass es nur \n im Rückgabewert von .val() ist.

Chrome und Firefox zählen die Länge von <textarea>-Tags für "maxlength" auf dieselbe Weise.

Die HTTP-Spezifikation besteht jedoch darauf, dass Zeilenumbrüche als \r\n dargestellt werden. Daher werden jQuery, Webkit und Firefox alles falsch verstanden.

Das Ergebnis ist, dass "maxlength" für <textarea>-Tags praktisch unbrauchbar ist, wenn Ihr serverseitiger Code wirklich eine feste Maximalgröße für einen Feldwert hat. 

edit - An diesem Punkt (Ende 2014) sieht es so aus, als würde sich Chrome (38) korrekt verhalten. Firefox (33) zählt jedoch noch nicht jede Rückkehr als 2 Zeichen.

14
Pointy

Es scheint, dass die richtige Methode, basierend auf der obigen Antwort von Pointy, darin besteht, alle neuen Zeilen als zwei Zeichen zu zählen. Dies standardisiert es für alle Browser und stimmt überein, was gesendet wird, wenn es veröffentlicht wird.

Wir könnten also der Spezifikation folgen und alle Vorkommen eines Wagenrücklaufs, der nicht von einer neuen Zeile gefolgt wird, und alle neuen Zeilen, die nicht von einem Wagenrücklauf gefolgt werden, durch ein Wagenrücklaufpaar ersetzen.

var len = $('#test').val().replace(/\r(?!\n)|\n(?!\r)/g, "\r\n").length;

Verwenden Sie dann diese Variable, um die Länge des Textbereichs anzuzeigen oder zu begrenzen usw.

13
matt

Es sieht so aus, als würde Javascript auch die Länge eines neuen Linienzeichens berücksichtigen.

Versuchen Sie es mit:


var x = $('#test').val();

x = x.replace(/(\r\n|\n|\r)/g,"");    

$('#length').html(x.length);

Ich habe es in deiner Geige benutzt und es hat funktioniert. Hoffe das hilft.

3
anuragsn7

Das liegt daran, dass eine neue Zeile eigentlich 2 Byte und damit 2 lange ist. JavaScript sieht das nicht so und wird daher nur 1 zählen, also 7 (3 neue Zeilen).

1
Rene Pot

Hier ist eine universellere Lösung, die die jQuery-Funktion "val" überschreibt. Wir werden diese Ausgabe in Kürze in einen Blog-Beitrag umwandeln und hier verlinken.

var originalVal = $.fn.val;
$.fn.val = function (value) {
    if (typeof value == 'undefined') {
        // Getter

        if ($(this).is("textarea")) {
            return originalVal.call(this)
                .replace(/\r\n/g, '\n')     // reduce all \r\n to \n
                .replace(/\r/g, '\n')       // reduce all \r to \n (we shouldn't really need this line. this is for paranoia!)
                .replace(/\n/g, '\r\n');    // expand all \n to \r\n

            // this two-step approach allows us to not accidentally catch a perfect \r\n
            //   and turn it into a \r\r\n, which wouldn't help anything.
        }

        return originalVal.call(this);
    }
    else {
        // Setter
        return originalVal.call(this, value);
    }
};
1
Stachu
var value = $('#textarea').val();
var numberOfLineBreaks = (value.match(/\n/g)||[]).length;
$('#textarea').attr("maxlength",500+numberOfLineBreaks);

funktioniert einwandfrei bei google schon in IE muss man das script vermeiden! In IE wird die 'break-line' nur einmal gezählt, also vermeiden Sie diese Lösung in IE!

0
Fabio

Die Textbereiche sind zwischen den Browsern immer noch nicht vollständig synchron. Ich bemerkte zwei Hauptprobleme: Wagenrücklauf und Zeichencodierung

Wagenrücklauf

Standardmäßig werden 2 Zeichen \r\n (Windows-Stil) bearbeitet.

Das Problem ist, dass Chrome und Firefox es als ein Zeichen zählt. Sie können es auch auswählen, um zu beobachten, dass ein unsichtbares Zeichen als Leerzeichen ausgewählt ist.

Eine Problemumgehung finden Sie hier:

var length = $.trim($(this).val()).split(" ").join("").split('\n').join('').length;

JQuery Word zählt, wenn Benutzer Zeilenumbruch eingeben

Internet Explorer hingegen zählt es als 2 Zeichen.

Ihre Vertretung ist:

Binär: 00001101 00001010

Hex: 0D0A

und werden in UTF-8 als 2 Zeichen dargestellt und für die maximale Länge als 2 Zeichen gezählt.

Die HTML-Entitäten können sein

1) Erstellt aus Javascript Code:

<textarea id='txa'></textarea>

document.getElementById("txa").value = String.fromCharCode(13, 10);

2) Aus dem Inhalt des Textbereichs analysiert:

Ansi-Code: # 13; # 10;

<textarea>Line one.&#13;&#10;Line two.</textarea>

3) Wird über die Eingabetaste der Tastatur eingegeben

4) Definiert als mehrzeiliger Inhalt der Textbox

<textarea>Line one.
Line two.</textarea>

Zeichenkodierung

Die Zeichenkodierung eines Eingabefeldes wie eines Textfeldes ist unabhängig von der Zeichenkodierung der Seite. Dies ist wichtig, wenn Sie die Bytes zählen möchten. Wenn Sie also einen Meta-Header zum Definieren der ANSI-Codierung Ihrer Seite haben (mit 1 Byte pro Zeichen), ist der Inhalt Ihrer Textbox immer noch UTF-8 mit 2 Byte pro Zeichen.

Eine Problemumgehung für die Zeichenkodierung finden Sie hier:

function htmlEncode(value){
  // Create a in-memory div, set its inner text (which jQuery automatically encodes)
  // Then grab the encoded contents back out. The div never exists on the page.
  return $('<div/>').text(value).html();
}

function htmlDecode(value){
  return $('<div/>').html(value).text();
}

HTML-Codierung geht verloren, wenn Attribut aus Eingabefeld gelesen wird

0
profimedica

Wenn Sie die verbleibende Länge des Textbereichs erhalten möchten, können Sie match für die Zeichenfolge verwenden, die die Zeilenumbrüche enthält.

HTML:

<textarea id="content" rows="5" cols="15" maxlength="250"></textarea>

JS:

var getContentWidthWithNextLine = function(){
    return 250 - content.length + (content.match(/\n/g)||[]).length;
}
0
Rubi saini