Binding Components from a PolymerTemplate
You can add child components to templates using the Component or Element API.
|
Note
|
Added items to the PolymerTemplate only show up on screen if added to the ShadowRoot of
the template if it doesn’t have a <slot> see. Using <slot> in PolymerTemplates
|
By using the @Id annotation, you can get a server-side Component or Element,
for an element only defined in the PolymerTemplate html file for the client side to
use on the server.
|
Note
|
The Component/Element needs to have the same @Tag as the actual element that is wired.
This means that you can not wire a <span id="content"></span> to a @Id("content") Div content
|
Here is the content of the HTML template file which has a placeholder div element with a "content" identifier. This element is mapped to a Div component in Java code below to set a Component as a child for it.
Source code
HTML
<dom-module id="main-page">
<template>
<div id="header">Main page</div>
<div id="content"></div>
<hr>
<div id="footer">
<a href="mailto:someone@example.com?Subject=Hello%20again" target="_top">Send Mail</a>
</div>
</template>
<script>
class MainPage extends Polymer.Element {
static get is() {
return 'main-page'
}
}
customElements.define(MainPage.is, MainPage);
</script>
</dom-module>You can implement the method that wires a Component to the content of your template element.
Source code
Java
@Tag("main-page")
@HtmlImport("/com/example/MainPage.html")
public class MainPage extends PolymerTemplate<TemplateModel> {
@Id("content")
private Div content;
public void setContent(Component content) {
this.content.removeAll();
this.content.add(content);
}
}The @Id annotation is used to map a component to an element created by the template
on the client that has the identifier "content".
A component instance of the declared type is created automatically and wired to the actual dom element and injected into the 'container' field.
Now you can set any Component as a content for the MainPage class:
Source code
Java
MainPage page = new MainPage();
page.setContent(new Label("Hello!"));In the Polymer template class example above, the div element with
"footer" identifier could also be mapped via Div component and
@Id("footer") annotation. But neither its hierarchical
structure nor attributes/properties are available on the server side via API.
The injected Div instance doesn’t have any server side child even though
there is the anchor a element available on the client side. The injected instance
getChildren() method returns an empty Stream.
Similar to this the getText() method of the Div instance injected via
@Id("header") returns an empty string.
So server side Component/Element read methods are not always in sync
with the client-side. But you still may use mutation API methods from the server side
like appendChild/setProperty/setAttribute. Getter methods returns values
which have been set from the server side only.
|
Note
|
The created Element is virtually mapped to be connected to the ShadowRoot of the
PolymerTemplate even if it would be deeper in the shadow tree.
The virtually mapped components can not be removed from the DOM by removing them on the
server side.
|
|
Note
|
The declared type used in an @Id injection declaration must have a default constructor to be able to instantiate it.
|
|
Tip
|
The @Id annotation can also be used to inject an Element instance instead of a Component instance in case you want to use low level API or there is no appropriate HTML component available.
|
|
Note
|
You can detect whether a component is part of a Template by using the isTemplateMapped method. See the Integrating components in a PolymerTemplate tutorial for more details.
|