AngularJS Wie erzwingt man, dass eine Eingabe bei Unschärfe neu gerendert wird

Habe ich einige benutzerdefinierte Validierung code, umfasst eine $formatter. (I-store-Währung in pence für die Richtigkeit, aber die Anzeige in Pfund.pence.)

Wenn der Benutzer schreibt '10' in den Eingang (das ist ein Gültiger Wert), die Eingabe bleibt die Anzeige '10', nachdem Sie in das nächste Feld.

Ich würde es gerne anzeigen, 10,00 für die Konsistenz.

Wenn das Modell geändert, der Wert auf 1000, dann das Formatierungsprogramm würde das Feld '10.00'.

Möchte ich den formatter laufen auf dem Feld.blur() (so lange, wie die Eingabe gültig ist).

Mein problem ist, dass wenn ich den Modell-Wert von 10 zu 10, es gibt verständlicherweise keine Veränderung, und so ist das Feld nicht neu gerendert.

code:

var CURRENCY_REGEXP = /^\-?\d+(\.?\d?\d?)?$/;
app.directive('currency', function() {
  return {
    require: 'ngModel',
    link: function(scope, elm, attrs, ctrl) {
      ctrl.$parsers.unshift(function(viewValue) {
        if (CURRENCY_REGEXP.test(viewValue)) {
          //it is valid
          ctrl.$setValidity('currency', true);
          console.log("valid");
          return viewValue * 100;
        } else if (viewValue === '') {
          return 0;
        } else {
          //it is invalid, return undefined (no model update)
          ctrl.$setValidity('currency', false);
          console.log("invalid");
          return undefined;
        }
      });
      ctrl.$formatters.push(function(modelValue) {
         if (modelValue === 0) { //we're using integer pence, so this is safe
             return '';
         }
         return (modelValue / 100).toFixed(2); 
      });
    }
  };
});

P. S. Das hat nichts zu tun mit Angular built-in "Währung".


Update: ich habe ein 'renderOnBlur" - Richtlinie, nach Andy ' s Antwort. Es wird aufgerufen, aber den Aufruf der render-Methode nicht re-Rendern Sie die Eingabe. also '10' bleibt wie '10', statt Sie direkt zu verändern, um '10.00', wie gewünscht.

(Wenn das Modell value-änderungen in diesen Bereichen sind Sie korrekt gerendert, wobei die 2 Nachkommastellen.)

Der Seite, die Andy erwähnt http://docs.angularjs.org/api/ng.directive:ngModel.NgModelController sagt, dass Sie implementieren müssen, um $render selbst. Das scheint komisch, da die Eingänge bereits richtig gerendert, wenn der Modell-Wert-änderungen.

app.directive('renderOnBlur', function() {
    return {
        require: 'ngModel',
        restrict: 'A',
        link: function(scope, elm, attrs, ctrl) {
            elm.bind('blur', function() {
                console.log('rendering ctrl', ctrl);
                ctrl.$render();
            });
        }
    };  
});

P. S. ich habe keine Ahnung, was restrict: 'A', tut - es ist wahr, cargo-Kult-Programmierung am schlimmsten. Die require: 'ngModel', scheint notwendig zum Auffüllen der ctrl parameter.


Inspiriert durch die Antwort von @Dan Doyen, ich schrieb es so:

app.directive('renderOnBlur', function() {
    return {
        require: 'ngModel',
        restrict: 'A',
        link: function(scope, elm, attrs, ctrl) {
            elm.bind('blur', function() {
                var viewValue = ctrl.$modelValue;
                for (var i in ctrl.$formatters) {
                    viewValue = ctrl.$formatters[i](viewValue);
                }
                ctrl.$viewValue = viewValue;
                ctrl.$render();
            });
        }
    };  
});

Dies hat den Vorteil, dass generische für jede $formatter, anstatt die Wiederholung der formatter-code wie in Dan ' s Antwort.

Kommentar zu dem Problem
10.00 === 10 //true; .00 nicht bedeutet, dass alles, was auf javascript Kommentarautor: Renan Tomal Fernandes
@ShadowBelmolve siehe bitte den Kommentar unter deiner Antwort. Sie haben Erfahrung mit AngularJS? Kommentarautor: fadedbee
restrict: 'A' bedeutet, dass Sie nur erlauben wollen, die Richtlinie verwendet werden wie ein Attribut <input Rendern-on-blur>, es gibt 4 verschiedene Arten von Einschränkungen, die anderen sind 'E'lement <render-on-blur> 'C'lass <input class='render-on-blur'> und Co BIN'ment (was weniger verwendet - siehe doc). Sie können mehrere restrict: 'EAC' Kommentarautor: Dan Doyon
Über $formatter, der Angular-Dokumentation steht, dass "Die Funktionen werden in umgekehrter array um, jeder übergibt den Wert bis zum nächsten." Die Richtlinie nennt Sie in der falschen Reihenfolge. Dachte nur ich würde beachten das für jemand anderes zu sein, als dieses etwas mich bei der Arbeit mit mehreren Formatierer. Kommentarautor: Dark Falcon
Deine Lösung gepostet werden sollte, da eine Antwort zu. Ich benutzte es, um fix ein ähnliches Problem vielen Dank!!! Sollten Sie auch präzise, dass es basiert auf der Winkel-source code Kommentarautor: glepretre

InformationsquelleAutor der Frage fadedbee | 2012-07-08

Schreibe einen Kommentar