2017-04-26 1 views
11

Ich bin ein wenig verwirrt.Wann sollten eckige Klammern [] in Anweisungen @Inputs verwendet werden und wann nicht?

Sehen Sie diese einfache Richtlinie:

@Directive({ 
     selector: '[myDirective]' 
    }) 
    export class MyDirective { 

     private text: string; 
     private enabled: boolean; 

     @Input() myDirective:string; 

     @Input('myText') 
     set myText(val: string) { 
     this.text = val; 
     } 

     @Input('myEnabled') 
     set myEnabled(val: boolean) { 
     this.enabled = val; 
     } 

     ngOnInit() { 

     console.log("myDirective string: " + this.myDirective); 
     console.log("myText string: " + this.text); 
     console.log("myEnabled boolean: " + this.enabled); 
    } 
} 

wenn meine html wie folgt aussehen:

<div [myDirective]="myDefaultText" [myEnabled]="true" [myText]="abc"></div> 

Der Ausgang wird sein:

myDirective string: myDefaultText real value // good 
myEnabled boolean: true      // good 
myText string: undefined      // Why? 

Wenn ich die [Löschen] aus myText:

<div [myDirective]="myDefaultText" [myEnabled]="true" myText="abc"></div> 

wird der Ausgang sein:

myDirective string: myDefaultText real value // good 
myEnabled boolean: true      // good 
myText string: abc       // GOOD 

ich auch die [] von myEnabled entfernen kann und es auch funktionieren. Also hier ist meine Verwirrung - wenn ich eckige Klammern verwenden muss [] und wenn nicht, während ich möchte, dass der Benutzer myDirective verwenden wird nie fragen müssen, ob oder wenn nicht, ich denke, die eckigen Klammern [] sollte immer da sein . Sind sie nicht?

Antwort

10

Wenn Sie [] verwenden, um an eine @Input() zu binden, handelt es sich im Grunde um einen Vorlagenausdruck.

Auf die gleiche Weise würde die Anzeige {{abc}} nichts anzeigen (es sei denn, Sie hatten tatsächlich eine Variable namens abc).

Wenn Sie einen String @Input() haben, und Sie wollen, dass es zu einer konstanten Zeichenfolge binden, könnten Sie es binden wie folgt aus: [myText]=" 'some text' ", oder kurz gesagt, wie eine normale HTML-Attribut: myText="some text".

Der Grund [myEnabled]="true" arbeitete, weil true ein gültiger Vorlagenausdruck ist, der natürlich zu dem boolean true ausgewertet wird.

+1

Ich habe nicht einmal gedacht, dass das tatsächlich passiert, bist du sicher?Der Fragesteller erwähnte, dass '[myDirective] =" myDefaultText "' die Eingabe "myDefaultText real ** value **" lieferte, obwohl ich den tatsächlichen Wert von 'myDefaultText' meinte, was bedeutet, dass es immer noch als Ausdruck behandelt wird. – Amit

+1

Ich lag falsch. Verpasste den "echten Wert". –

+2

Dies wird in der aktuellen Angular 4-Dokumentation auf [dieser Seite] (https://angular.io/guide/template-syntax#one-time-string-initialization) behandelt. – 2Aguy

6

Die Klammern geben Angular an, den Vorlagenausdruck zu bewerten. Wenn Sie die Klammern weglassen, behandelt Angular die Zeichenfolge als Konstante und initialisiert die Zieleigenschaft mit dieser Zeichenfolge. Es bewertet die Zeichenfolge nicht!

Sie machen den folgenden Fehler nicht:

<!-- ERROR: HeroDetailComponent.hero expects a 
     Hero object, not the string "currentHero" --> 
    <hero-detail hero="currentHero"></hero-detail> 

Kontrolle: https://angular.io/docs/ts/latest/guide/template-syntax.html#!#property-binding

2

Bindung [] für Objekte ist, ohne dass es der Wert Zeichenfolge ist. Sei vorsichtig mit Typen.

Im Code

<div [myDirective]="myDefaultText" [myEnabled]="true" [myText]="abc"></div> 

Sie das Objekt zu binden, haben versucht, aber das Objekt nicht verfügbar ist, so ist es Wert undefined. Auf der anderen Seite, wenn Sie die Bindung entfernen, dann ist das Objekt weg, Sie haben nur einen string Wert der Eigenschaft zugewiesen.

+1

Stellen Sie sicher, dass Sie 'myEnabled = "false" 'nicht ausführen, da dies als String ausgewertet wird und da' 'false' 'tatsächlich ein truthiger Wert ist, verhält es sich nicht wie erwartet. –

+0

Wo hast du das gesehen? –

Verwandte Themen