«listenable»

This is an audio-enabled presentation.

Make sure you have your volume up, your headphones on, and click that highlighted arrow in the lower-right corner after the audio has loaded.

autoplay the presentation

AD ot UE w WC

Agile Development
of the User Experience
with Web Components

You can pirate this

For more information about how you can digitally copy this and how it won't probably hurt my economy, please visit

Creative Commons Attribution-NonCommercial 4.0 International License

curtis@schlak.com

@realistschuckle

UX

ambience: look and sound

mechanics: application interaction

throughput: information presentation

ux workflows

traditional media

two teams / two goals

pure wireframing

from basic to beautiful

UX first

pretty. then, functional.

bootstrap'd

stick with bootstrap

or zurb

or pure

ಠ_ಠ

web components!

custom elements

register your custom element

var prototype = Object.create(HTMLDivElement.prototype, {
  uri: { value: undefined },
  data: { value: undefined },
  attachedCallback: function () {
    this.uri = this.getAttribute('uri');
    // Do some AJAXy stuff here...
    this.data = content;
    // Fire a data-received event
  }
});
document.registerElement('declarative-ajax', HTMLDivElement.prototype);
              
and then use it in HTML

<body>
  <declarative-ajax uri="http://example.com/api"></declarative-ajax>
</body>
              

templates

include it in your HTML

<template id="example-template">
  <img src="http://example.com/dummy.png">
  <div>Bacon ipsum dolor amet brisket boudin</div>
  <script>alert('HELLO!');</script>
</template>
              
access and use it in your script

function appendTemplate(imgSrc, content) {
  // Get the template and set the image's source
  var t = document.querySelector("template");
  t.querySelector('img').src = imgSrc;
  t.querySelector('div').innerHTML = content;

  // Clone the content and put it in the DOM
  var clone = document.importNode(t.content, true);
  document.querySelector("#template-example").appendNode(clone);
}
              

HTML imports

import html using a link tag

<link id="my-tag-link" rel="import" href="/components/my-tag.html">
              
get the content from the link's import attribute

var link = document.getElementById('my-tag-link');
var content = link.import;
var clone = content.cloneNode(true);
document.body.appendChild(clone);
              

Shadow DOM

In a document like this...

<div id="hostElement"></div>
<p>This is in the normal DOM</p>
              
...create a shadow root and add DOM to it...

var shadow = document.querySelector("#hostElement").createShadowRoot();
shadow.innerHTML = '<p id="my-paragraph">Here is some new text</p>' +
                   '<style>p { color: red };</style>';
              
...I can't get to the <p> tag in the shadow DOM...

document.getElementById('my-paragraph'); // Returns undefined
              
...and the style only applies in the shadow DOM.

Here is some new text
This is in the normal DOM

compatibility

Technology IE Chrome FF
custom elements maybe yep off
<template> in dev yep yep
HTML Imports maybe yep never
Shadow DOM maybe yep off

we can think a new way

a UX workflow with Web Components

interaction-oriented development

common tactics

  • build library of interaction metaphors
  • work one iteration ahead
  • identify cross-cutting components
  • identify one-off components
  • schedule screen/page and component creation separately

thorns

  • constant backlog prioritization change
  • old browser support
  • not building an app
  • page-centric definition of done

practical

using raw tools suxorz

polymer to the rescue

Polymer's catalog

elements.polymer-project.org

Community catalog

customelements.io

Build a Web Component

the world's dumbest button

Push me


              <dumb-button>Push me</dumb-button>
            

import polymer


<link rel="import" href="../polymer/polymer.html">
            

declare the dom-module


<dom-module id="dumb-button">
</dom-module>
            

put in the style


<style>
  :host {
    display: inline-block;
  }

  button {
    font-size: 24px;
    padding: 0.2em 0.4em;
    border: 0;
    background-color: white;
  }

  button:active {
    background-color: green;
  }
</style>
            

put in the template


<template>
  <button id="clickable"><content></content></button>
  <audio id="sound" src="./button-sound.wav"></audio>
</template>
            

put in the behavior


<script>
  Polymer({
    is: "dumb-button",

    ready: function () {
      var self = this;
      this.$.clickable.addEventListener('click', function () {
        self.$.sound.play();
      });
    }
  });
</script>
            

and you get the dumbest button. ever.

Push me

And, that's what I've got so far

contact info

curtis@schlak.com

@realistschuckle

conversation?