2016-02-22 23 views
6

Ich baue eine modale Komponente in Angular 2 (und TypeScript), die verschiedene Ansichten/Seiten haben wird. Es wird keine Tabs haben, aber das Konzept ist ziemlich ähnlich. Im Grunde kämpfe ich darum, einen Ansatz dafür zu finden.Array von Komponenten in Angular ausgeben 2

Innerhalb meiner modalen Komponente möchte ich die verschiedenen Ansichten/Seiten ausgeben. Jede Komponente sollte selbst eine Komponente sein, da sie kein Markup gemeinsam hat. Außerdem werden sie Daten von Serviceklassen abrufen, daher muss ich in der Lage sein, für jede Ansicht spezifische Logik zu schreiben.

Im Grunde, was ich will, ist so etwas wie:

// Within my modal component's template 
<div *ngFor="#view of views"> 
    // Render view component here 
</div> 

Wo views eine Anordnung der Komponenten sein könnte, zum Beispiel. Mein erstes und wichtigstes Problem ist, dass ich nicht sicher bin, wie ich eine Sammlung meiner Ansichten (Komponenten) ausgeben soll.

Wie kann ich eine Sammlung von Komponenten innerhalb einer anderen Komponente ausgeben?

Ich brauche auch eine Möglichkeit, Ansichten zu verstecken und zu zeigen, was das einzige ist, was die Ansichten gemeinsam haben. Ich dachte daran, eine isActive Variable zu den Ansichten hinzuzufügen und basierend darauf anzuzeigen/auszublenden. Wäre es eine schlechte Übung für die Sichtenkomponenten, entweder eine ModalView Schnittstelle zu implementieren oder von einer Basisklasse zu erweitern, um diese Logik hinzuzufügen? Von meiner modalen Komponente möchte ich steuern können, welche Ansicht angezeigt wird, also brauche ich die Ansichten, um diese Logik gemeinsam zu haben.

Ich hoffe, es ist klar, was ich tun möchte. Die Lösung mag einfach sein, aber im Moment bin ich ein bisschen verwirrt darüber, wie ich das anstellen soll. Ein Codebeispiel würde sehr geschätzt werden!

Antwort

4

Sie können eine "Komponentenfactory" als eine Direktive erstellen, die entsprechende Komponenten mithilfe von DynamicComponentLoader basierend auf Parametern lädt, die Sie von Ihrem Modal übergeben haben.

<component-factory *ngFor="#view of views" 
    (loaded)="addComponent($event)" 
    [name]="view.name" 
    [visible]="view.visible"></component-factory> 

@Directive({ selector: 'component-factory' }) 
class ComponentFactory { 
    @Input() name; 
    @Input() visible; 
    @Output() loaded = new EventEmitter(); 
    constructor(
    private _dcl: DynamicComponentLoader, 
    private _eref: ElementRef) { 

    // import OneCmp, TwoCmp in this file... 
    private components: { one: OneCmp, two: TwoCmp } 

    ngOnInit() { 
    this._dcl.loadNextToLocation(
     this.components[this.name], 
     this._eref) 
     // pass values to the loaded components 
     // and send it's instance to the parent 
     .then((ref: ComponentRef) => { 
     ref.instance.visible = this.visible; 
     this.loaded.emit(ref.instance) 
     }); 
    } 
} 
+0

Oh, das, vielen Dank genial aussieht! Ich denke, dass, falls ich weiter mit meinen Ansichten interagieren muss, ich den Code aus der Richtlinie herausziehen und diese Logik in die modale Komponente einbetten (oder zumindest auf die Fabrik verweisen), denn dann kann ich Referenzen behalten zu den geladenen Komponenten. Wenn Sie Feedback zu diesem Ansatz haben, würde ich es gerne hören. Trotzdem habe ich jetzt einen sehr nützlichen Referenzcode, also Daumen hoch! – Andy0708

+0

Ich dachte, dass die Richtlinie wiederverwendbarer wäre. Sie können eine Referenz zurück an die Elternkomponente durch '@Output()' senden, indem Sie '(ref: ComponentRef)' emittieren und sie im Modal sammeln. – Sasxa

+0

Der Code wurde aktualisiert ... – Sasxa

1

Angular2 Render dynamisch Vorlage

import { Component, View, DynamicComponentLoader, ElementRef} from 'angular2/core'; import {bootstrap} from 'angular2/platform/browser' 

@Component({ 
    selector: 'some-component', 
    properties: ['greeting'], 
    template: ` 
    <b>{{ greeting }}</b> 
    ` 
}) 
class SomeComponent { } 




@Component({ 
    selector: 'app' 
}) 
@View({ 
    template: ` 
    <h1>Before container</h1> 
    <div #container></div> 
    <h2>After container</h2> 
    ` 
}) 
class App { 
    loader: DynamicComponentLoader; 
    elementRef: ElementRef; 

    constructor(loader: DynamicComponentLoader, elementRef: ElementRef) { 
    this.laoder = loader; 
    this.elementRef = elementRef; 

    // Some async action (maybe ajax response with html in it) 
    setTimeout(() => this.renderTemplate(` 
     <div> 
    <h2>Hello</h2> 
    <some-component greeting="Oh, hey"></some-component> 
     </div> 

vollständigen Code: https://github.com/guyoung/GyPractice-Angular2Advanced/tree/master/apps/dynamically_render_template

Verwandte Themen