rock gwt ui's with polymer elements
TRANSCRIPT
![Page 1: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/1.jpg)
ROCK GWT UI'S WITH POLYMER ELEMENTS
![Page 2: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/2.jpg)
1. Motivations2. What are web components3. What’s polymer4. JsInterop5. GWT consuming web components6. introducing gwt-polymer-elements7. Demo: full-stack gwt app using polymer and rest
services.
Agenda
![Page 3: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/3.jpg)
Motivationspublic void onScrollMove(ScrollMoveEvent event) { int y = scrollPanel.getY(); if (header != null) { if (y > header.getStateSwitchPosition() && headerState != PullState.PULLED) { headerState = PullState.PULLED; scrollPanel.setMinScrollY(0); if (headerPullhandler != null) headerPullhandler.onPullStateChanged(header, headerState); } else { if (y <= header.getStateSwitchPosition() && headerState != PullState.NORMAL) { headerState = PullState.NORMAL; scrollPanel.setMinScrollY(-header.getHeight()); if (headerPullhandler != null) headerPullhandler.onPullStateChanged(header, headerState); } } header.onScroll(y); }
int y_off = y; if (footer != null && y < -footer.getHeight()) { if (footerState == PullState.PULLED) { y_off = y_off - footer.getHeight(); } if (footerState == PullState.NORMAL) { y_off = y_off + footer.getHeight(); } if (y_off < (scrollPanel.getMaxScrollY() - footer.getStateSwitchPosition()) && footerState != PullState.PULLED) { footerState = PullState.PULLED; scrollPanel.setMaxScrollY(scrollPanel.getMaxScrollY() - footer.getHeight()); if (footerPullhandler != null) { footerPullhandler.onPullStateChanged(footer, footerState); } } else { if (y_off > (scrollPanel.getMaxScrollY() - footer.getStateSwitchPosition()) && footerState != PullState.NORMAL) { footerState = PullState.NORMAL; scrollPanel.setMaxScrollY(scrollPanel.getMaxScrollY() + footer.getHeight()); if (footerPullhandler != null) { footerPullhandler.onPullStateChanged(footer, footerState); } } } footer.onScroll(y_off - scrollPanel.getMaxScrollY()); }}
Former Gwt Ui Development- Verbose code- Slow Debug & Test- Difficult to share- Ugly widgetset & no
mobile
Gwt + Web Components- Standard specs.- Ready to use elements- Designers friendly- Active Development
- Google- Vaadin
![Page 4: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/4.jpg)
gwt-classic vs gwt-polymer
6.500 LOChttp://gwt-mobilewebapp.appspot.com/
750 LOChttp://manolo.github.io/gwt-polymer-chat-app/demo/
![Page 5: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/5.jpg)
Vaadin vision of Web Components
![Page 6: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/6.jpg)
What are Web Components?
![Page 7: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/7.jpg)
Problem: DOM unique treebody { background-color: white; }
![Page 8: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/8.jpg)
Solution: Shadow DOM
body { background-color: white; }
![Page 9: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/9.jpg)
Encapsulation
![Page 10: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/10.jpg)
Composition
![Page 11: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/11.jpg)
Community
![Page 12: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/12.jpg)
Web ComponentsState of the art
![Page 13: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/13.jpg)
Browser support
![Page 14: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/14.jpg)
Polyfill
![Page 15: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/15.jpg)
Activity
![Page 16: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/16.jpg)
What’s Polymer
![Page 17: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/17.jpg)
Polymer- Polymer makes it easier and faster to create anything
from a button to a complete application across desktop, mobile, and beyond.
- Polymer ecosystem enables sharing UI components between developers.
- JS estable API & polyfills- Production ready reusable components- Documentation system
- Let's GWT take advantage of the JS ecosystem to create amazing UIs.
![Page 18: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/18.jpg)
Catalog- Iron Elements- Paper Elements -> Material Design- Neon Elements- Platinum Elements- Google Elements
- Vaadin Elements
![Page 19: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/19.jpg)
JsInterop
![Page 20: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/20.jpg)
1. Why JsInteropa. Nowadays most GWT big projects interact with JS libs.b. JSNI is a bad option for complex scenarios
2. JsInterop magic allows interact natively with Js. No JSNI anymore!a. @JsTypeb. @JsProperty @JsConstructor @JsMethod @JsFunction c. Issues ? : experimental, does not extend JSO
3. Elemental-2.0 Interfaces for all HTMLa. Window, Document, Element, Style, Events, …b. Issue: not available yet 2.8.x ?
4. Code generationa. Let’s explore ways to create java boilerplate code
GWT JsInterop
![Page 21: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/21.jpg)
GWT:Consuming Web Components
![Page 22: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/22.jpg)
1. Code Interfaces for Native Objects (Elemental-2)2. Code methods for interacting with Web
Components Spec (create, import ...).3. Define an annotated Java Interface per component,
event or behavior.- Extends HTMLElement or Event
4. Optionally Wrap each Interface in a Widget class for classic GWT apps.
Steps to consume WC in Java
![Page 23: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/23.jpg)
Interfaces for native JS objects
@JsTypepublic interface HTMLElement extends Element {}
@JsTypepublic interface Element extends Node { @JsProperty String getInnerHTML(); @JsProperty DOMTokenList getClassList();
void setAttribute(String name, String value); String getAttribute(String name); void removeAttribute(String name);}
@JsTypepublic interface Node extends EventTarget {}
@JsTypepublic interface EventTarget { void addEventListener(String type, EventListener listener);}
Elemental-2 (gwt-2.8.1)
![Page 24: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/24.jpg)
Utility methods public class Polymer { ... // Ensures that the tagName has been registered, otherwise injects // the appropriate <import> tag in the document header public static void ensureHTMLImport(String tagName) { if ( !registered(tagName)) { String href = GWT.getModuleBaseForStaticFiles() + "bower_components/" + tagName + "/" + tagName + ".html";
Polymer.Base.importHref(href); } } // Returns a new instance of the Element. It loads the webcomponent // if not loaded yet. public static <T> T createElement(String tagName) { ensureHTMLImport(tagName); return (T)Document.get().createElement(tagName); } ...}
![Page 25: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/25.jpg)
The WebComponentElement.java
@JsTypepublic interface PaperButton extends HTMLElement {
@JsProperty PaperButton setLabel(String val); @JsProperty String getLabel();
@JsProperty PaperButton setRaisedButton(boolean val); @JsProperty boolean getRaisedButton();
@JsProperty PaperButton setIcon(String val); @JsProperty String getIcon();
}
![Page 26: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/26.jpg)
Consuming WC in Java (Element API)
// Create a new instance of PaperButton PaperButtonElement button = Polymer.create(PaperButtonElement.TAG);
// Set some properties button.icon("polymer"); button.label("Polymer"); button.raisedButton(false);
// Add event listeners button.addEventListener("click", e -> { });
// Append to the document document.get().ppendChild(button);
![Page 27: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/27.jpg)
The WebComponentWidget.javapublic class PaperButton extends PolymerWidget { //Default Constructor. public PaperButton() { this(""); } //Constructor used by UIBinder public PaperButton(String html) { this(PaperButtonElement.TAG, html); } // Used when this element is extended by another. protected PaperButton(String tag, String html) { super(tag, html); }
// Gets a handle to the Polymer object's underlying DOM element. public PaperButtonElement getPolymerElement() { return (PaperButtonElement) getElement(); } public boolean isRaised() { return getPolymerElement().isRaised(); }}
public class PolymerWidget extends HTMLPanel { public PolymerWidget(String tag, String src, String html) { super(tag, html); Polymer.ensureCustomElement(getElement(), src); } ...}
![Page 28: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/28.jpg)
Consuming WC in Java (Widget API)
// Widgets allow consume WC using the GWT classic way.PaperButton button = new PaperButton();
button.addClickHandler(new ClickHandler() { public void onClick(ClickEvent event) { // ... }});
RootPanel.get().add(button);
![Page 29: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/29.jpg)
Consuming WC in UIBinder<ui:UiBinder xmlns:ui='urn:ui:com.google.gwt.uibinder' xmlns:g='urn:import:com.google.gwt.user.client.ui' xmlns:p='urn:import:com.vaadin.components.gwt.polymer.client.widget'>
<ui:style> .container paper-button.colored { background: #4285f4; color: #fff; }</ui:style>
<g:HTMLPanel> <!-- to use widgets we don’t need to import webcomponents by hand --> <p:PaperButton toggle="" raised="" active="" addStyleNames="{style.colored}">active</p:PaperButton>
<!-- to use elements it’s mandatory to import webcomponents previously --> <paper-button raised="" noink="">Click me</paper-button></g:HTMLPanel>
![Page 30: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/30.jpg)
IntroducingVaadin gwt-polymer
![Page 31: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/31.jpg)
Two Projects1. gwt-api-generator: It’s a code generator to produce
GWT wrappers for JS componentsa. Scrapes source documentationb. Right now polymer, but considering other sources.c. Uses standard JS libraries to parse components.
- node.js, npm, bower, gulp- hydrolysis parser + lodash.template
2. gwt-polymer-elements: a ready-to-use library for using polymer elements in gwt (iron, paper, neon, vaadin)a. Version 1.2.1.0.alpha1 (polymer 1.2.1)
b. Still under definition, expect package name changes, etc
![Page 32: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/32.jpg)
gwt-polymer-elements
GWT
PaperButtonWidget
PolymerWidget
HTMLElement
PaperButtonElement
Polymer
paper-button.html
polimer.jsJsInterop
Vaadingwt-api-generator
![Page 33: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/33.jpg)
1. Add java dependency to your project.- vaadin-gwt-polymer-elements-1.2.1.0-alpha1.jar
2. Inherit it in your GWT module- <inherits name="com.vaadin.polymer.Elements"/>
3. Use new Widgets or Elements as usual- Document.get().createElement("PaperSliderElement")
4. Run mvn clean install to produce your package .jar5. Everything is contained in the artefact
- polyfill, components, java code.
gwt-polymer-elements (bundle)
![Page 34: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/34.jpg)
1. Install the generator - sudo npm install gwt-api-generator -g
2. Install all the components you need for your project.- bower install my-github-account/my-custom-polymer-element
3. Run the script to generate .java classes- gwt-api-generator [--pom --groupId=xx --artifactId=xx]
4. Run mvn clean install to produce your gwt-package .jar
gwt-api-generator (custom elements)
![Page 35: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/35.jpg)
gwt-api-generator goals
1. Very little code to maintain.a. 1500 LOC / 100 KB
2. But it produces a lot of java codea. 50000 LOC (paper & core elements)
3. It uses native JS parsers for JS code.a. The same tools that polymer developers useb. No GWT generators nor APT processors.
4. Standard tools for web developers.a. They can deliver gwt libraries without knowing any java
![Page 36: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/36.jpg)
Demo:Building a full stack app
![Page 37: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/37.jpg)
Demo Application
GWT
Polymer
PouchDB CouchDB
- Responsive- Material Design- Online/Offline- Real Time
![Page 38: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/38.jpg)
Demo Components
- GWT + Polymer- CouchDB is a database that completely embraces
the web. - Store your data with JSON documents- Access your data via HTTP- Serve pages directly
- PouchDB is database inspired by Apache CouchDB that is designed to run well within the browser.
![Page 39: Rock GWT UI's with Polymer Elements](https://reader031.vdocuments.site/reader031/viewer/2022020119/586f861c1a28ab54768b541f/html5/thumbnails/39.jpg)
Demo
http://manolo.github.io/gwt-polymer-chat-app/demo/https://github.com/manolo/gwt-polymer-chat-app