2013-02-17 12 views
8

dieses Stück HTML Gegeben:Wie erstelle ich ein wiederverwendbares Partial für doppelte Markup in ember.js?

<div id="email_field" class="control-group"> 
    <label class="control-label" for="account.email">Email</label> 
    <div id="email_input" class="controls"> 
    <input id="account.email" name="account.email" type="text" placeholder="[email protected]"> 
    <span class="help-block">We just need a valid email address.</span> 
    </div> 
</div> 

Wie schalte ich diese in eine wiederverwendbare Teil für was auch immer Attribut ich will? IE: E-Mail, Passwort, Passwort-Bestätigung, etc.

Ich würde eine Art Ansicht Hierarchie annehmen, aber ich bin mir nicht ganz sicher.

EDIT: Nach der weiteren Exploration Ich habe {{view}} und {{render}} ausgeknockt und dachte genau, was ich brauche:

Ich möchte: 1. Verwenden Sie eine bestimmte Ansicht (InputView) 2. Verwenden Sie ein spezifische Controller (vorzugsweise ähnlich genannt: InputController) ({{view}} tut dies nicht, glaube ich) 3. Lage sein, diese mehrfach zu verwenden ({{render}} kann dies nicht tun) 4. in der Lage sein, in Werte passieren ({{render}} kann‘ t dies tun)

Beispiel:

<!-- templates/application.hbs --> 
{{foo "input" name="Email" id="account.email" placeholder="[email protected]"}} 

// controllers/input.js 
Application.InputController = Ember.ObjectController.extend({ 
    type: "text" 
}); 

// views/input.js 
Application.InputView = Ember.View.extend({ 
    templateName: "form/input" 
}); 

<!-- templates/form/input.hbs --> 
<input {{bindAttr id="id" name="name" type="type" placeholder="placeholder"}}> 

Antwort

3

I würde eine Ansicht erstellen, die alle Parameter nimmt, die variabel sind. Wie zum Beispiel:

{{view App.FormEntity 
    name="email" 
    placeholder="My placeholder..." 
    help="We just need a valid email address." 
    valueBinding="value" 
}} 

Von dort aus konnte man das Etikett extrahieren, um die verschiedenen Klassennamen, und dann Ember.TextField, um den Wert zu binden.

Nachdem Sie all diese Argumente übergeben in die Ansicht haben, sollte es schön und einfach sein, das Markup mit einer Mischung aus bindAttr s, ein paar berechneten Eigenschaften und Ember Helfer (wie die Ember.TextField) zu erstellen.

+1

Große Antwort, danke, aber es lässt mich fragen, welcher Controller die Ansicht sucht, wenn Sie bindAttr verwenden? Ich kann das aus den Unterlagen nicht entnehmen. – krainboltgreene

+1

Nun, jede Ansicht sollte Zugriff auf einen Controller haben. Wenn Sie sich in der IndexRoute befinden, hat die Indexansicht standardmäßig Zugriff auf IndexController. Wenn Sie eine Ansicht in diese Indexansicht einfügen, erbt diese Ansicht den IndexController. Vielleicht hilft das: http://stackoverflow.com/questions/14802223/different-rendering-techniques-in-emberjs-handlebars-template/14802424#14802424 – Wildhoney

+0

Interessant, aber hilft mir nicht, denke ich? Ich möchte, dass dieser Helfer seinen eigenen Controller hat. Oder genauer gesagt, habe ich Werte berechnet, die ich nicht an IndexController anhängen möchte. – krainboltgreene

1

Ich bin neu zu Emberjs und auf der Suche nach ziemlich genau die gleiche Sache, aber könnten Sie nicht auch einfach http://emberjs.com/guides/templates/writing-helpers/ dafür verwenden? Ich werde es selbst versuchen, so kann mehr Updates geben, wenn das klappt.

Update: Ok, ich habe es zur Arbeit. Ich habe ein neuer Helfer Ordner mit FormgeneratorHelper.js und der folgenden Code ein:

Ember.Handlebars.registerBoundHelper('control-group', function (options) { 
    var name = options.hash.test.capitalize(); 
    console.log(name); 
    return new Handlebars.SafeString('<div class="control-group"> \ 
      <label class="control-label" for="input' + name + '">' + name + '</label> \ 
      <div class="controls"> \ 
       <input type="text" id="input' + name + '" placeholder="' + name + '" /> \ 
      </div> \ 
     </div>'); 
}); 

Ein dann, egal in welcher Vorlage können Sie tun:

{{control-group test="email"}} 

Ich mag die Idee Helfer zu verwenden, Aber wenn Sie einfaches Javascript (im Gegensatz zu CoffeScript) verwenden und mehr als eine Codezeile haben, wird es leider ein bisschen hässlich. Aber werde wahrscheinlich immer noch diese Methode verwenden.

+0

Während das scheint zu tun, was ich will, das ist definitiv nicht, wie ich es tun will. Es wird so nicht zu halten. – krainboltgreene

1

Wie mache ich daraus ein wiederverwendbares Partial für welches Attribut ich will?IE: E-Mail, Passwort, Passwort Bestätigung, etc.

Was Sie wollen, ist der experimentelle {{control}} Helfer. Der Kontrollhelfer wird derzeit entwickelt und gilt als experimentell. Um es zu aktivieren, setzen Sie ENV.EXPERIMENTAL_CONTROL_HELPER = true, bevor Sie Ember anfordern.

Ich möchte: 1. Verwenden Sie eine bestimmte Ansicht (InputView) 2. Verwenden Sie einen bestimmten Controller (vorzugsweise ähnlich genannt: InputController) ({{Ansicht}} tut dies nicht, glaube ich)

Standardmäßig erwartet der Steuerelementhelper einen Vorlagennamen. Dieser Vorlagenname wird verwendet, um eine übereinstimmende Ansicht und einen passenden Controller zu suchen. So zum Beispiel:

App.InputView = Ember.View.extend() 
App.InputController = Ember.Controller.extend() 
{{control input}} 

See:

  1. Lage sein, diese mehrfach zu verwenden ({{}} machen kann nicht tun Sie dies)

A control can be used multiple times

  1. der Lage sein, in Werte übergeben ({{}} machen kann dies nicht tun)

Wie der {{view}} Helfer wird {{control}} willkürlich akzeptieren Name/Wert-Paare. Wie in Ihrem Beispiel könnte man Optionen manuell an den Steuerhelfer übergeben. Wie die {{view}} Helfer werden diese Optionen Eigenschaften auf der View-Instanz:

<!-- templates/form/input.hbs --> 
<label class="control-label" {{bindAttr for="view.inputId"}}> 
    {{view.label}} 
</label> 
<div class="controls"> 
    <input {{bindAttr id="view.inputId" name="view.name" type="type" placeholder="view.placeholder"}}> 
    <span class="help-block">{{view.help}}</span> 
</div> 

// controllers/form_input.js 
App.FormInputController = Ember.ObjectController.extend({ 
    type: "text" 
}); 

// views/form_input.js 
App.FormInputView = Ember.View.extend({ 
    classNames: ["control-group"] 
}); 

<!-- templates/application.hbs --> 
{{control "form/input" 
    inputId="account.email" 
    name="email" 
    label="Email" 
    placeholder="[email protected]" 
    help="We just need a valid email address." 
}} 

diesen jsbin Siehe zum Beispiel Arbeits

Denken Sie auch daran, dass A control can specify a model to use in its template - mit dieser an Ort und Stelle können wir Eigenschaften binden Daten zu modellieren. Auch if a controller's model changes, its child controllers are destroyed, so dass das Steuerelement wie erwartet zurückgesetzt wird, wenn das Modell ausgelagert wird.