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

Multi-device apps with Web Components

Rob Dodson
September 13, 2014

Multi-device apps with Web Components

Building a multi-device app is extremely challenging, unless you're an expert developer. It's time for the web to get its own collection of fast, beautiful, and responsive by default components. In this talk, we'll look at how you can use readily available Web Components to quickly build apps that look gorgeous on phones, tablets, and desktops. With these new tools we can greatly simplify the process of supporting multiple screen sizes, while also keeping our code sane and readable.

Rob Dodson

September 13, 2014
Tweet

More Decks by Rob Dodson

Other Decks in Technology

Transcript

  1. <paper-tabs selected=“1”> <paper-tab>Tab 1</paper-tab> <paper-tab>Tab 2</paper-tab> <paper-tab>Tab 3</paper-tab> </paper-tabs> declarative,

    readable meaningful HTML common way to extend Custom Elements define new HTML @polymer @rob_dodson #jqcon
  2. declarative, readable meaningful HTML common way to extend Custom Elements

    define new HTML var tabs = document.querySelector('paper-tabs'); tabs.addEventListener('core-activate', function() { console.log(this.selected); }); @polymer @rob_dodson #jqcon
  3. Custom Elements Create new HTML elements and extend existing ones

    Templates Native templating in the browser Shadow DOM Scoped CSS!!! + encapsulated markup HTML Imports Load custom element definitions and resources
  4. USE

  5. USE

  6. vanilla polymer usage document.registerElement(‘paper-tabs’, { prototype: Object.create( HTMLElement.prototype ) });

    <polymer-element name=“paper-tabs”> … </polymer-element> <paper-tabs>…</paper-tabs> // document.createElement(‘paper-tabs’);
  7. vanilla polymer usage document.registerElement(‘paper-tabs’, { prototype: Object.create( HTMLElement.prototype ) });

    <polymer-element name=“paper-tabs”> … </polymer-element> <paper-tabs>…</paper-tabs> // document.createElement(‘paper-tabs’);
  8. vanilla polymer usage document.registerElement(‘paper-tabs’, { prototype: Object.create( HTMLElement.prototype ) });

    <polymer-element name=“paper-tabs”> … </polymer-element> <paper-tabs>…</paper-tabs> // document.createElement(‘paper-tabs’);
  9. vanilla polymer usage document.registerElement(‘paper-tabs’, { prototype: Object.create( HTMLElement.prototype ) });

    <polymer-element name=“paper-tabs”> … </polymer-element> <paper-tabs>…</paper-tabs> // document.createElement(‘paper-tabs’);
  10. var shadow = el.createShadowRoot(); shadow.innerHTML = “<h2>I’m a profile-card</h2>”; vanilla

    polymer <polymer-element name=“profile-card” noscript> <template> <link rel=“stylesheet” href=“styles.css”> <h2>I’m a profile-card</h2> </template> </polymer-element>
  11. var shadow = el.createShadowRoot(); shadow.innerHTML = “<h2>I’m a profile-card</h2>”; vanilla

    polymer <polymer-element name=“profile-card” noscript> <template> <link rel=“stylesheet” href=“styles.css”> <h2>I’m a profile-card</h2> </template> </polymer-element>
  12. var shadow = el.createShadowRoot(); shadow.innerHTML = “<h2>I’m a profile-card</h2>”; vanilla

    polymer <polymer-element name=“profile-card” noscript> <template> <link rel=“stylesheet” href=“styles.css”> <h2>I’m a profile-card</h2> </template> </polymer-element>
  13. MY APP <core-toolbar> A container for controls like tabs or

    buttons <link rel=“import” href=“core-toolbar.html”> @polymer @rob_dodson #jqcon
  14. MY APP <core-toolbar> A container for controls like tabs or

    buttons <core-toolbar> <div>MY APP</div> </core-toolbar> <link rel=“import” href=“core-toolbar.html”> @polymer @rob_dodson #jqcon
  15. <core-toolbar> MY APP A container for controls like tabs or

    buttons <core-toolbar> <core-icon-button icon=“menu”> </core-icon-button> <div>MY APP</div> </core-toolbar> <link rel=“import” href=“core-toolbar.html”> @polymer @rob_dodson #jqcon
  16. A simple container with a header section and a content

    section <core-header-panel> <core-header-panel flex> <core-toolbar> <core-icon-button icon=“menu"> </core-icon-button> <div>MY APP</div> </core-toolbar> <div class=“content”>…</div> </core-header-panel> MY APP @polymer @rob_dodson #jqcon
  17. MY APP <core-header-panel flex> <core-toolbar> <core-icon-button icon=“menu"> </core-icon-button> <div>MY APP</div>

    </core-toolbar> <div class=“content”>…</div> </core-header-panel> A simple container with a header section and a content section <core-header-panel> @polymer @rob_dodson #jqcon
  18. MY APP <core-header-panel flex> <core-toolbar> <core-icon-button icon=“menu"> </core-icon-button> <div>MY APP</div>

    </core-toolbar> <div class=“content”>…</div> </core-header-panel> A simple container with a header section and a content section <core-header-panel> @polymer @rob_dodson #jqcon
  19. MY APP <core-header-panel flex> <core-toolbar> <core-icon-button icon=“menu"> </core-icon-button> <div>MY APP</div>

    </core-toolbar> <div class=“content”>…</div> </core-header-panel> A simple container with a header section and a content section <core-header-panel> @polymer @rob_dodson #jqcon
  20. A responsive container that combines a left- or right-side drawer

    panel and a main content area. <core-drawer-panel> <core-drawer-panel> <div drawer> Drawer panel... </div> <div main> Main panel... </div> </core-drawer-panel> @polymer @rob_dodson #jqcon
  21. A responsive container that combines a left- or right-side drawer

    panel and a main content area. <core-drawer-panel> <core-drawer-panel> <div drawer> Drawer panel... </div> <div main> Main panel... </div> </core-drawer-panel> @polymer @rob_dodson #jqcon
  22. A responsive container that combines a left- or right-side drawer

    panel and a main content area. <core-drawer-panel> <core-drawer-panel> <div drawer> Drawer panel... </div> <div main> Main panel... </div> </core-drawer-panel> @polymer @rob_dodson #jqcon
  23. <app-router> github.com/erikringsmuth/app-router my-site.com/order/:id <app-router> <!-- matches an exact path -->

    <app-route path="/home" import=“/pages/home-page.html"> </app-route> ! <!-- matches using a path variable --> <app-route path="/order/:id" import=“/pages/order-page.html”> </app-route>
  24. <page-er> github.com/addyosmani/page-er <page-er perpage="5" previous=“<< Previous" next=“Next >>”> </page-er> !

    var pager = document.querySelector("page-er"); document.addEventListener("polymer-ready", function() {
  25. <ajax-form> github.com/garstasio/ajax-form Full Name Country City Join newsletter <form is="ajax-form"

    action="my/action"> <label>Full Name <input type="text" name=“full_name"> </label> … </form> √
  26. <style> #map { height: 400px; } </style> ! <div id="map"></div>

    ! <script src=“http://maps.googleapis.com/maps/api/js?callback=mapReady"> </script> <script> var marker = null; function getCurrentLocation(callback) { navigator.geolocation.watchPosition(callback); } ! function addMarker(opts, info) { var marker = new google.maps.Marker(opts); ! var infoWindow = new google.maps.InfoWindow({content: info}); ! google.maps.event.addListener(marker, 'click', function() { infoWindow.open(opts.map, marker); }); ! return marker; } ! function mapReady() { var container = document.querySelector('#map'); var map = new google.maps.Map(container, { zoom: 14, disableDefaultUI: true }); getCurrentLocation(function(pos) { var current = new google.maps.LatLng(pos.coords.latitude, pos.coords.longitude); map.setCenter(current); ! // Re-position marker or create new one. if (marker) { marker.setPosition(map.getCenter()); } else { marker = addMarker({ position: current, map: map, title: 'Your location' }, '<b>Your location</b>'); } }); } </script> So much code for one map marker!
  27. { "name": "my-element", "version": "0.0.0", "description": "My awesome Custom Element",

    "license": "MIT", "keywords": [ "web-components" ], "ignore": [ "**/.*", "node_modules", "bower_components" ] } bower.json