Upgrade to Pro — share decks privately, control downloads, hide ads and more …

The Modern State of Web Components - A Glimmer ...

The Modern State of Web Components - A Glimmer of Hope

The browser support of web components has been getting increasingly better over the past few years and besides other component libraries, including Polymer or X-Tag, the Ember community presents its own new library - Glimmer.js - enabling you to create easy-to-use web components today.
in this talk we will cover browser support, polyfilling and how Glimmer.js can help us to create reusable components for our web apps today. Alongside a component demo we will see how we can build and ship our Glimmer based web components and have a look at promising API developments for the future.

This talk was first presented at EmberCamp London 2017.

Jessy Jordan

July 12, 2017
Tweet

More Decks by Jessy Jordan

Other Decks in Programming

Transcript

  1. JESSICA JORDAN ‣ in Berlin ‣ Software Engineer @ ‣

    Co-Organizer @ Berlin & Berlin jjordan_dev jessica-jordan
  2. WEB COMPONENTS THE WEB COMPONENT SPEC - CUSTOM ELEMENTS V1

    CUSTOM ELEMENTS HTML IMPORT SHADOW DOM TEMPLATE See also W3C working draft on custom elements
  3. WEB COMPONENTS - CUSTOM ELEMENTS V1 CUSTOMELEMENTREGISTRY INTERFACE let options

    = { extends: HTMLTagName }; customElements.define(name, constructor, options);
  4. WEB COMPONENTS - CUSTOM ELEMENTS V1 CREATING CUSTOM ELEMENTS More

    on the MDN Guide on Custom Elements class LinkedImage extends HTMLElement { constructor() { super(); var img = document.createElement('img'); img.alt = this.getAttribute('data-name'); img.src = this.getAttribute('data-img'); img.width = '150'; img.height = '150'; // …more setup work img.addEventListener('click', () => { window.location = this.getAttribute('data-url'); }); } customElements.define(‘linked-image’, LinkedImage);
  5. WEB COMPONENTS - CUSTOM ELEMENTS V1 CREATING CUSTOM ELEMENTS More

    on the MDN Guide on Custom Elements <linked-image data-name=“Zoey by Lindsey Wilson" data-img="https://emberjs.com/images/zoey.png" data-url=“https://emberjs.com"> </linked-image>
  6. WEB COMPONENTS THE WEB COMPONENT SPEC - BROWSER SUPPORT CUSTOM

    ELEMENTS HTML IMPORT SHADOW DOM TEMPLATE See also "Are we componentized yet?" by Jon Rimmer
  7. WEB COMPONENTS - BROWSER SUPPORT BROWSER SUPPORT CUSTOM ELEMENTS HTML

    IMPORT SHADOW DOM ✅ ✅ CUSTOM ELEMENTS SHADOW DOM ✴ ⛔ ⛔
  8. WEB COMPONENTS - BROWSER SUPPORT THE WEB COMPONENT SPEC -

    BROWSER SUPPORT CUSTOM ELEMENTS HTML IMPORT SHADOW DOM ⛔ ✅ ✴ ⛔ ⛔ HTML IMPORT
  9. WEB COMPONENTS - TOOLS & LIBRARIES LIBRARIES ‣ Polymer ‣

    Bosonic ‣ SkateJS ‣ Slim.js ‣ X-Tag ‣ ….and now there’s even more …
  10. GLIMMER.JS - BUILDING WEB COMPONENTS GETTING STARTED yarn add -g

    ember-cli // install latest release v2.14 ember new glimmer-poll -b @glimmer/blueprint —-web-component
  11. glimmer-poll |── config | |—- environment.js | |—- module-map.ts |

    |—- resolver-configuration.ts | |── dist |── src | |── ui | | |── components | | | └── my-app | | | |── component.ts | | | |── template.hbs | | | | | |── styles | | | └── app.css | | | | | |── index.html | | | |── index.ts | |── main.ts | |── ember-cli-build.js | ... other files ... GLIMMER.JS - BUILDING WEB COMPONENTS
  12. GLIMMER.JS - BUILDING WEBCOMPONENTS APP BOOTUP // glimmer-poll/src/index.ts import App

    from './main'; import initializeCustomElements from '@glimmer/web-component'; // … const app = new App(); const containerElement = document.getElementById('app'); // … app.renderComponent('glimmer-poll', containerElement, null); app.boot(); initializeCustomElements(app, ['glimmer-poll']);
  13. GLIMMER.JS - BUILDING WEBCOMPONENTS INITIALIZING THE CUSTOM ELEMENT function initializeCustomElement(app:

    Application, name: string): void { // creating a GlimmerElement instance from HTMLElement function GlimmerElement() { return Reflect.construct(HTMLElement, [], GlimmerElement); } GlimmerElement.prototype = Object.create(HTMLElement.prototype, { constructor: { value: GlimmerElement }, connectedCallback: { value: function connectedCallback(): void { // ... bring element into the DOM and do setup work // ... } } }); // finally registering the component via customElements v1 API window.customElements.define(name, GlimmerElement); }
  14. GLIMMER.JS - BUILDING WEBCOMPONENTS DEPENDENCY MANAGEMENT // glimmer-poll/src/ui/components/glimmeer-poll/component.ts import Component,

    { tracked } from "@glimmer/component"; import * as d3 from "d3"; import { fetchData, putData } from ‘./../../../utils/fetch-data'; export default class GlimmerPoll extends Component { //… } ‣ Import third-party libraries as ES6 modules / CommonJS (rollup pipeline) ‣ Organize utility functions in utils/
  15. GLIMMER.JS - BUILDING WEBCOMPONENTS TRACKING CHANGES WITH THE @TRACKED DECORATOR

    // glimmer-poll/src/ui/components/glimmer-poll/component.ts export default class GlimmerPoll extends Component { // … @tracked hasNotSubmittedYet: boolean = true; @tracked fetchedPollData: any; // … }
  16. GLIMMER.JS - BUILDING WEBCOMPONENTS CHANGING UI STATE WITH ACTIONS //

    glimmer-poll/src/ui/components/glimmer-poll/component.ts export default class GlimmerPoll extends Component { // … vote(option) { const id = this.fetchedPollData.id; putData(this.apiUrl, { id, option }).then(async (res) => { await fetchData(this.apiUrl) .then((res) => { this.fetchedPollData = res.data; this.update(); }); }); this.hasNotSubmittedYet = false; } }
  17. GLIMMER.JS - BUILDING WEBCOMPONENTS IMPORTING IT INTO EXISTING APP <!DOCTYPE

    html> <html> <head> <title>My Other App</title> <script src="/assets/webcomponentsjs/webcomponents-lite.js"></script> <link rel="stylesheet" href="/assets/glimmer-poll/app.css"></link> </head> <body> <glimmer-poll></glimmer-poll> <script src="/assets/glimmer-poll/app.js"></script> </body> </html>
  18. ROAD AHEAD - PROMISING API DEVELOPMENTS IN GLIMMER.JS HTML ATTRIBUTES

    FOR CUSTOMIZATION <glimmer-poll width="400" height="800"></glimmer-poll> <glimmer-poll fetchedPollData='{ "data": [ { "option": "VisualStudio Code", "vote": "89" }, { "option": "nano", "vote": "1" }, { "option": "Vim", "vote": "65" } ] }' > </glimmer-poll>
  19. ROAD AHEAD - PROMISING API DEVELOPMENTS IN GLIMMER.JS HTML IMPORTS

    FOR DISTRIBUTING GLIMMER COMPONENTS // in web component package: glimmer-poll/glimmer-poll.html // ... load other needed assets, e.g. fonts <script src="./assets/app.js"></script> // ... // in consuming app <link rel="import" href="../../bower_components/glimmer-poll/glimmer-poll.html"> <glimmer-poll></glimmer-poll>
  20. ROAD AHEAD - API DEVELOPMENT IN GLIMMER.JS AND MORE EMBER-CLI

    POWERED DEVELOPMENTS ‣ <slot></slot> for “yielding” component content ‣ Styles in ShadowDOM or as co-located CSS ‣ Testing Story for Glimmer.js apps glimmerjs/glimmer-blueprint - PR by robbiepitts
  21. ROAD AHEAD - API DEVELOPMENT IN GLIMMER.JS AND MORE EMBER-CLI

    POWERED DEVELOPMENTS ‣ <slot></slot> for “yielding” component content ‣ Styles in ShadowDOM or as co-located CSS ‣ Testing Story for Glimmer.js apps emberjs/rfcs - PR by rwjblue