Slide 1

Slide 1 text

ngComponent als wiederverwendbare Komponente für beliebige JavaScript Apps Swiss Angular Meetup 13.09.2018 Thomas Gassmann @gassmannT

Slide 2

Slide 2 text

Thomas Gassmann Senior Consultant, Trainer, Speaker thomasgassmann.ch @gassmannT

Slide 3

Slide 3 text

Agenda 13.09.2018 Swiss Angular Meetup - Angular Elements 3 ▪ Intro Angular Elements ▪ Web Components ▪ Getting started with Angular Elements ▪ Outlook v7

Slide 4

Slide 4 text

Angular Elements 13.09.2018 Swiss Angular Meetup - Angular Elements 4

Slide 5

Slide 5 text

13.09.2018 Swiss Angular Meetup - Angular Elements 5 «Angular is ideal for building complete applications, and our tooling, documentation and infrastructure are primarily aimed at this case.» Rob Wormald, Angular Team

Slide 6

Slide 6 text

Platform 13.09.2018 Swiss Angular Meetup - Angular Elements 6 Dependency Injection Decorators Zones Compile Binding Render Material Mobile Universal CLI Language Service Augury ngUpdate Router Animation i18n

Slide 7

Slide 7 text

13.09.2018 Swiss Angular Meetup - Angular Elements 7 «[…] but it’s quite challenging to use in scenarios that don’t fit that specific Singe Page Application model.» Rob Wormald, Angular Team

Slide 8

Slide 8 text

Use case 13.09.2018 Swiss Angular Meetup - Angular Elements 8 ▪ Enhancing existing HTML Pages ▪ Content Management Systems ▪ Use components in other environments or frameworks ▪ Microfrontends ▪ Reuse components across teams

Slide 9

Slide 9 text

13.09.2018 Swiss Angular Meetup - Angular Elements 9

Slide 10

Slide 10 text

13.09.2018 Swiss Angular Meetup - Angular Elements 10 Web Components

Slide 11

Slide 11 text

Web Components 13.09.2018 Swiss Angular Meetup - Angular Elements 11 Web Components are a set of features added by the W3C ▪ HTML Template: Template of the HTML ▪ Shadow DOM: DOM and style encapsulation ▪ HTML Imports: Imports in HTML ▪ Custom Elements: Ability to add to the HTML vocabulary

Slide 12

Slide 12 text

13.09.2018 Swiss Angular Meetup - Angular Elements 12

Slide 13

Slide 13 text

Custom Elements 13.09.2018 Swiss Angular Meetup - Angular Elements 13 Custom elements share the same API surface as native DOM objects: ▪ Attributes ▪ Properties ▪ Methods ▪ Events

Slide 14

Slide 14 text

Create and Define a Custom Element 13.09.2018 Swiss Angular Meetup - Angular Elements 14 class myElement extends HTMLElement { … } customElements.define('my-element', myElement);

Slide 15

Slide 15 text

Reactions 13.09.2018 Swiss Angular Meetup - Angular Elements 15 class myElement extends HTMLElement { connectedCallback() { ... } disconnectedCallback() { ... } }

Slide 16

Slide 16 text

Attributes 13.09.2018 Swiss Angular Meetup - Angular Elements 16 class myElement extends HTMLElement { static get observedAttributes() { return ['country']; } attributeChangedCallback(name, oldValue, newValue) { if (name === 'country') { // do something with newValue } } }

Slide 17

Slide 17 text

13.09.2018 Swiss Angular Meetup - Angular Elements 17

Slide 18

Slide 18 text

Properties 13.09.2018 Swiss Angular Meetup - Angular Elements 18 class myElement extends HTMLElement { get country() { return this.getAttribute('country'); } set country(val) { this.setAttribute('country', val); } }

Slide 19

Slide 19 text

13.09.2018 Swiss Angular Meetup - Angular Elements 19 let matches = document.querySelector('app-matches-by-country’); matches.country = 'ger';

Slide 20

Slide 20 text

Custom Events 13.09.2018 Swiss Angular Meetup - Angular Elements 20 class myElement extends HTMLElement { emitCountryChange() { this.dispatchEvent( new CustomEvent('country-change', { detail: this.country })); } }

Slide 21

Slide 21 text

13.09.2018 Swiss Angular Meetup - Angular Elements 21 let matches = document.querySelector('app-matches-by-country’); matches.addEventListener('country-change', event => { ... });

Slide 22

Slide 22 text

Custom Elements in Angular 13.09.2018 Swiss Angular Meetup - Angular Elements 22 => Angular has been designed for this

Slide 23

Slide 23 text

Enter Angular Elements 13.09.2018 Swiss Angular Meetup - Angular Elements 23 Provides a bridge from angular concepts to web components. ▪ @HostBinding() => Attributes ▪ @Input() => Properties ▪ @Output() => CustomEvents ▪ Lifecycle Hooks => Reactions

Slide 24

Slide 24 text

A lot of framework exists 13.09.2018 Swiss Angular Meetup - Angular Elements 24

Slide 25

Slide 25 text

Getting started 13.09.2018 Swiss Angular Meetup - Angular Elements 25

Slide 26

Slide 26 text

Platform 13.09.2018 Swiss Angular Meetup - Angular Elements 26 Dependency Injection Decorators Zones Compile Binding Render Material Mobile Universal CLI Language Service Augury ngUpdate Router Animation i18n

Slide 27

Slide 27 text

First Steps 13.09.2018 Swiss Angular Meetup - Angular Elements 27 Update Angular CLI Update Angular CLI to > 6 ng new angularElements Create a new Angular CLI project ng add @angular/elements Add support for angular elements ng g c matchToday -v Native Generate new component

Slide 28

Slide 28 text

Component 13.09.2018 Swiss Angular Meetup - Angular Elements 28 @Component({ selector: 'app-matches-today', templateUrl: 'matches-today.component.html’, styleUrls: ['matches-today.component.css’], encapsulation: ViewEncapsulation.ShadowDom }) export class MatchesTodayComponent implements OnInit { public matches$: Observable; constructor(private matchService: MatchService) {} ngOnInit() { this.matches$ = this.matchService.getTodayMatches(); } }

Slide 29

Slide 29 text

Module 13.09.2018 Swiss Angular Meetup - Angular Elements 29 @NgModule({ imports: [BrowserModule, HttpClientModule], declarations: [AppComponent, MatchesTodayComponent], entryComponents: [MatchesTodayComponent], providers: [] }) export class AppModule { … }

Slide 30

Slide 30 text

Module 13.09.2018 Swiss Angular Meetup - Angular Elements 30 export class AppModule { constructor(private injector: Injector) {} ngDoBootstrap() { const el1 = createCustomElement( MatchesTodayComponent, { injector: this.injector }); customElements.define('app-matches-today', el1); } }

Slide 31

Slide 31 text

13.09.2018 Swiss Angular Meetup - Angular Elements 31

Slide 32

Slide 32 text

Use with Javascript 13.09.2018 Swiss Angular Meetup - Angular Elements 32 const matchesToday = document.createElement('app- matches-today'); document.body.appendChild(matchesToday); matchesToday.country = 'SUI'; matchesToday.setAttribute('country', 'GER');

Slide 33

Slide 33 text

Use with Custom Element API 13.09.2018 Swiss Angular Meetup - Angular Elements 33 const MatchToday = document.get('app-matches-today’); const matchToday = new MatchToday(); // or const matchToday = new MatchToday(differencInjector);

Slide 34

Slide 34 text

Angular Elements are the Host Element 13.09.2018 Swiss Angular Meetup - Angular Elements 34 export class TestComponent implements OnInit { constructor(el: ElementRef) { el.nativeElement // <- Angular Element } @HostListener('click’) onHostClick($event) { ... } @HostBinding('attr.selected') isActive: boolean; }

Slide 35

Slide 35 text

Dependency Injection 13.09.2018 Swiss Angular Meetup - Angular Elements 35 Plattform Injector (Renderer) Module Injector (Services) Component Injector (ElementRef)

Slide 36

Slide 36 text

Dependency Injection in Angular Elements 13.09.2018 Swiss Angular Meetup - Angular Elements 36 Plattform Injector (Renderer) Module Injector (Services) Element Injector (ElementRef) Element Injector (ElementRef)

Slide 37

Slide 37 text

Module 13.09.2018 Swiss Angular Meetup - Angular Elements 37 export class AppModule { constructor(private injector: Injector) {} ngDoBootstrap() { const el1 = createCustomElement( MatchesTodayComponent, { injector: this.injector }); customElements.define('app-matches-today', el1); } }

Slide 38

Slide 38 text

13.09.2018 Swiss Angular Meetup - Angular Elements 38 Dependency Injection works!

Slide 39

Slide 39 text

Demo 13.09.2018 Swiss Angular Meetup - Angular Elements 39

Slide 40

Slide 40 text

Content Projection 13.09.2018 Swiss Angular Meetup - Angular Elements 40 Hallo Angular Meetup @Component({ selector: 'app-test’, template: ` ` }) export class TestComponent { }

Slide 41

Slide 41 text

Shadow DOM 13.09.2018 Swiss Angular Meetup - Angular Elements 41 @Component({ … encapsulation: ViewEncapsulation.ShadowDom }) export class MatchesTodayComponent implements OnInit { … }

Slide 42

Slide 42 text

Demo 13.09.2018 Swiss Angular Meetup - Angular Elements 42

Slide 43

Slide 43 text

Angular Elements in V6 13.09.2018 Swiss Angular Meetup - Angular Elements 43 ▪ It is just the beginning ▪ Size is too big for shipping in non Angular projects ▪ Will be much better with Ivy (V7) ▪ Will be much easier with V7 ▪ Browser Support.

Slide 44

Slide 44 text

Outlook V7 13.09.2018 Swiss Angular Meetup - Angular Elements 44 @Component({ selector: 'app-test', template: '...', customElement: true }) export class TestComponent { ... }

Slide 45

Slide 45 text

13.09.2018 Swiss Angular Meetup - Angular Elements 45 How to use it today in non Angular Projects?

Slide 46

Slide 46 text

Combine bundle in a single file 13.09.2018 Swiss Angular Meetup - Angular Elements 46 npm install concat --save-dev Install package concat npm install fs-extra --save-dev Install package fs-extra "build:elements": "ng build --prod --output- hashing none && node build-elements.js" Add script command

Slide 47

Slide 47 text

build-elements.js 13.09.2018 Swiss Angular Meetup - Angular Elements 47 const fs = require('fs-extra'); const concat = require('concat'); (async function build() { const files = [ './dist/WorldCupComponent/runtime.js', './dist/WorldCupComponent/polyfills.js', './dist/WorldCupComponent/main.js' ]; await fs.ensureDir('elements’); await concat(files, 'elements/world-cup.js'); console.info('Wold Cup Element created successfully!'); })();

Slide 48

Slide 48 text

Demo 13.09.2018 Swiss Angular Meetup - Angular Elements 48

Slide 49

Slide 49 text

13.09.2018 Swiss Angular Meetup - Angular Elements 49 It is just the beginning. Stay tuned with Angular 7

Slide 50

Slide 50 text

Ressources 13.09.2018 Swiss Angular Meetup - Angular Elements 50 ▪ github.com/gassmannT/WorldCupComponent ▪ thomasgassmann.net ▪ swissangular.com ▪ m.trivadis.com/angular ▪ angular-academy.ch

Slide 51

Slide 51 text

Thank you Thomas Gassmann @gassmannT thomasgassmann.net [email protected] 13.09.2018 Swiss Angular Meetup - Angular Elements 51

Slide 52

Slide 52 text

No content