Reputation: 17067
From the custom elements page, I see that to extend an element you do:
var XFooButtonPrototype = Object.create(HTMLButtonElement.prototype);
XFooButtonPrototype.createdCallback = function() {
this.textContent = "I'm an x-foo button!";
};
var XFooButton = document.registerElement('x-foo-button', {
prototype: XFooButtonPrototype,
extends: 'button'
});
Then later in the guide it says that you can make an element by writing either:
<x-foo></x-foo>
Or:
<button is="x-foo-button"></button>
Questions:
Why is it important to specify extends: 'button'
when the element is obviously_ inheriting from HTMLButtonElement
(since it has HTMLButtonElement.prototype
in its proto chain)
How is the link between button
and x-foo-button
established? Does x-foo-button
become a possible option of button in terms of is="x-foo-button"
thanks to that extends: 'button'
? What happens "internally", so to speak?
Why would you pick <button is="x-foo-button"></button>
over <x-foo></x-foo>
...?
[ADDENDUM]
Polymer saves us from this duplication:
MyInput = Polymer({
is: 'my-input',
extends: 'input',
created: function() {
this.style.border = '1px solid red';
}
});
If extends
is there, Polymer will put the right prototype in the chain with Object.getPrototypeOf(document.createElement(tag));
.
So, corollary question:
extends
, shouldn't the browser automatically do this?Upvotes: 1
Views: 2043
Reputation: 1112
I think its Importent to Say here:
WARNING DEPRECATED Browser API METHOD Here in this Question a .registerElement is Used it got Replaced by .defineElement and the Api has changed
current way to define a element
class AppDrawer extends HTMLElement {
constructor() {
super()
this.innerHTML = '<h1>UH</h1>'
}
}
window.customElements.define('app-drawer', AppDrawer);
// Or use an anonymous class if you don't want a named constructor in current scope.
window.customElements.define('app-drawer-noname', class extends HTMLElement {
constructor() {
super()
this.innerHTML = '<h1>UH AH</h1>'
}
});
Example - defining a mobile drawer panel, < app - drawer >:
Example usage:
<app-drawer></app-drawer>
<app-drawer-noname></app-drawer-noname>
```
Upvotes: 0
Reputation: 17067
You totally misunderstood how extending web components work.
First of all, this is how you register a new element:
var XFoo = document.registerElement('x-foo', {
prototype: Object.create(HTMLElement.prototype)
});
To create an element you can do one of these:
<x-foo></x-foo>
var xFoo = new XFoo();
document.body.appendChild(xFoo);
var xFoo = document.createElement( 'x-foo')
document.body.appendChild(xFoo);
This is how you extend an existing element:
var XFooButton = document.registerElement('x-foo-button', {
prototype: Object.create(HTMLButtonElement.prototype),
extends: 'button'
});
To create one you can do one of these:
<button is="x-foo-button"></button>
var xFooButton = new XFooButton();
document.body.appendChild(xFoo);
var xFooButton = document.createElement('button', 'x-foo-button');
document.body.appendChild(xFooButton);
Note that in case of extended custom elements, when registering them you have to specify both the prototype (set to HTMLButtonElement.prototype
rather than HTMLElement.prototype
), and the extended tag's name (extends: 'button'
).
Also, when you create an extended element using markup or createElement()
, you need to also specify the basic element (button
) and the extended one (x-foo-button
),
(Note: I am aware I am answering myself)
Upvotes: 4