Skip to content

Commit 22b96b9

Browse files
andrewseguinmhevery
authored andcommitted
feat(elements): add support for creating custom elements (angular#22413)
PR Close angular#22413
1 parent cedc04c commit 22b96b9

34 files changed

Lines changed: 1823 additions & 17 deletions

.pullapprove.yml

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
#
88
# alexeagle - Alex Eagle
99
# alxhub - Alex Rickabaugh
10+
# andrewseguin - Andrew Seguin
1011
# brocco - Mike Brocchi
1112
# chuckjaz - Chuck Jazdzewski
1213
# filipesilva - Filipe Silva
@@ -302,6 +303,16 @@ groups:
302303
- IgorMinar #fallback
303304
- mhevery #fallback
304305

306+
elements:
307+
conditions:
308+
files:
309+
- "packages/elements/*"
310+
users:
311+
- andrewseguin #primary
312+
- gkalpak
313+
- IgorMinar #fallback
314+
- mhevery #fallback
315+
305316
benchpress:
306317
conditions:
307318
files:

BUILD.bazel

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ filegroup(
4040
"reflect-metadata",
4141
"source-map-support",
4242
"minimist",
43+
"@webcomponents/webcomponentsjs",
4344
"tslib",
4445
] for ext in [
4546
"*.js",

CONTRIBUTING.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,7 @@ The following is the list of supported scopes:
212212
* **compiler**
213213
* **compiler-cli**
214214
* **core**
215+
* **elements**
215216
* **forms**
216217
* **http**
217218
* **language-service**

aio/content/guide/elements.md

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
# Elements
2+
3+
## Release Status
4+
5+
**Angular Labs Project** - experimental and unstable. **Breaking Changes Possible**
6+
7+
Targeted to land in the [6.x release cycle](https://github.com/angular/angular/blob/master/docs/RELEASE_SCHEDULE.md) of Angular - subject to change
8+
9+
## Overview
10+
11+
Elements provides an API that allows developers to register Angular Components as Custom Elements
12+
("Web Components"), and bridges the built-in DOM API to Angular's component interface and change
13+
detection APIs.
14+
15+
```ts
16+
//hello-world.ts
17+
import { Component, Input, NgModule } from '@angular/core';
18+
import { createNgElementConstructor, getConfigFromComponentFactory } from '@angular/elements';
19+
20+
@Component({
21+
selector: 'hello-world',
22+
template: `<h1>Hello {{name}}</h1>`
23+
})
24+
export class HelloWorld {
25+
@Input() name: string = 'World!';
26+
}
27+
28+
@NgModule({
29+
declarations: [ HelloWorld ],
30+
entryComponents: [ HelloWorld ]
31+
})
32+
export class HelloWorldModule {}
33+
```
34+
35+
```ts
36+
//app.component.ts
37+
import { Component, NgModuleRef } from '@angular/core';
38+
import { createNgElementConstructor } from '@angular/elements';
39+
40+
import { HelloWorld } from './hello-world.ngfactory';
41+
42+
@Component({
43+
selector: 'app-root',
44+
templateUrl: './app.component.html',
45+
styleUrls: ['./app.component.css']
46+
})
47+
export class AppComponent {
48+
constructor(ngModuleRef: NgModuleRef) {
49+
const ngElementConfig = getConfigFromComponentFactory(HelloWorld, injector);
50+
const NgElementConstructor = createNgElementConstructor(ngElementConfig);
51+
customElements.register('hello-world', NgElementConstructor);
52+
}
53+
}
54+
55+
```
56+
Once registered, these components can be used just like built-in HTML elements, because they *are*
57+
HTML Elements!
58+
59+
They can be used in any HTML page:
60+
61+
```html
62+
<hello-world name="Angular"></hello-world>
63+
<hello-world name="Typescript"></hello-world>
64+
```
65+
66+
Custom Elements are "self-bootstrapping" - they are automatically started when they are added to the
67+
DOM, and automatically destroyed when removed from the DOM.

aio/content/navigation.json

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -457,6 +457,11 @@
457457
}
458458
]
459459
},
460+
{
461+
"url": "guide/elements",
462+
"title": "Elements",
463+
"tooltip": "Exporting Angular Components as Web Components"
464+
},
460465
{
461466
"title": "Service Workers",
462467
"tooltip": "Angular service workers: Controlling caching of application resources.",

aio/tools/transforms/angular-api-package/index.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@ module.exports = new Package('angular-api', [basePackage, typeScriptPackage])
7373
'common/testing/index.ts',
7474
'core/index.ts',
7575
'core/testing/index.ts',
76+
'elements/index.ts',
7677
'forms/index.ts',
7778
'http/index.ts',
7879
'http/testing/index.ts',

aio/tools/transforms/authors-package/api-package.js

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,15 +11,16 @@ const { API_SOURCE_PATH } = require('../config');
1111

1212
const packageMap = {
1313
animations: ['animations/index.ts', 'animations/browser/index.ts', 'animations/browser/testing/index.ts'],
14-
common: ['common/index.ts', 'common/testing/index.ts'],
14+
common: ['common/index.ts', 'common/testing/index.ts', 'common/http/index.ts', 'common/http/testing/index.ts'],
1515
core: ['core/index.ts', 'core/testing/index.ts'],
16+
elements: ['elements/index.ts'],
1617
forms: ['forms/index.ts'],
1718
http: ['http/index.ts', 'http/testing/index.ts'],
1819
'platform-browser': ['platform-browser/index.ts', 'platform-browser/animations/index.ts', 'platform-browser/testing/index.ts'],
1920
'platform-browser-dynamic': ['platform-browser-dynamic/index.ts', 'platform-browser-dynamic/testing/index.ts'],
2021
'platform-server': ['platform-server/index.ts', 'platform-server/testing/index.ts'],
2122
'platform-webworker': ['platform-webworker/index.ts'],
22-
'platform-webworker-dynamic': 'platform-webworker-dynamic/index.ts',
23+
'platform-webworker-dynamic': ['platform-webworker-dynamic/index.ts'],
2324
router: ['router/index.ts', 'router/testing/index.ts', 'router/upgrade/index.ts'],
2425
'service-worker': ['service-worker/index.ts'],
2526
upgrade: ['upgrade/index.ts', 'upgrade/static/index.ts']

build.sh

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,8 @@ PACKAGES=(core
2424
compiler-cli
2525
language-service
2626
benchpress
27-
service-worker)
27+
service-worker
28+
elements)
2829

2930
TSC_PACKAGES=(compiler-cli
3031
language-service

karma-js.conf.js

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,15 @@ module.exports = function(config) {
4141
'test-events.js',
4242
'shims_for_IE.js',
4343
'node_modules/systemjs/dist/system.src.js',
44+
45+
// Serve polyfills necessary for testing the `elements` package.
46+
{
47+
pattern: 'node_modules/@webcomponents/custom-elements/**/*.js',
48+
included: false,
49+
watched: false
50+
},
51+
{pattern: 'node_modules/mutation-observer/index.js', included: false, watched: false},
52+
4453
{pattern: 'node_modules/rxjs/**', included: false, watched: false, served: true},
4554
'node_modules/reflect-metadata/Reflect.js',
4655
'tools/build/file2modulename.js',

package.json

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,6 +48,8 @@
4848
"@types/shelljs": "^0.7.8",
4949
"@types/source-map": "^0.5.1",
5050
"@types/systemjs": "0.19.32",
51+
"@webcomponents/custom-elements": "^1.0.4",
52+
"@webcomponents/webcomponentsjs": "^1.1.0",
5153
"angular": "npm:[email protected]",
5254
"angular-1.5": "npm:[email protected]",
5355
"angular-mocks": "npm:[email protected]",
@@ -87,6 +89,7 @@
8789
"karma-sourcemap-loader": "0.3.6",
8890
"madge": "0.5.0",
8991
"minimist": "1.2.0",
92+
"mutation-observer": "^1.0.3",
9093
"node-uuid": "1.4.8",
9194
"protractor": "5.1.2",
9295
"rewire": "2.5.2",

0 commit comments

Comments
 (0)