“是”的重点是什么?扩展Web组件中的元素时的语法? [英] What is the point of the "is" syntax when extending elements in web components?

查看:84
本文介绍了“是”的重点是什么?扩展Web组件中的元素时的语法?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Web组件中,要注册一个元素,只需键入:

In web components, to register an element you simply type:

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 all fine and dandy. The issues start when you are talking about extending existing elements.

var XFooButton = document.registerElement('x-foo-button', {
  prototype: Object.create(HTMLButtonElement.prototype),
  extends: 'button'
});

问题1 :为什么重复?在这里,'button'应该足够了(特别是因为它很容易用 Object.getPrototypeOf(document.createElement(tag))来计算元素的原型;

Question 1: Why the duplication? Here, 'button' should suffice (especially since it's easy enough to work out the element's prototype with Object.getPrototypeOf(document.createElement(tag));

问题2 :该信息如何在内部使用?如果发生了什么?例如,您有原型:Object.create(HTMLFormElement.prototype extends:'button'(其中的内容是 extends 与传递的原型不匹配)

Question 2: How is that information used internally? What happens if you for example have prototype: Object.create(HTMLFormElement.prototype and extends: 'button' (where what's after extends doesn't match the prototype passed)

要创建一个,您可以执行以下操作之一:

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);

问题3 :因为它是清除 x-foo-button 扩展按钮,wh当我们使用 document.createElement()时,我们是否必须指定它们?我怀疑是因为 document.createElement()只是创建一个语法为< button is =x-foo-button>< / button> ,这让我想到下一个问题:

Question 3: since it's clear that x-foo-button extends button, why do we have to specify both of them when we use document.createElement()? I suspect that's because document.createElement() simply creates a tag with syntax <button is="x-foo-button"></button>, which brings me to the next question:

问题4 :<重点是什么? code>是语法?这样做的实际区别是什么:

Question 4: What's the point of the is syntax? What is the actual difference between doing this:

var XFooButton = document.registerElement('x-foo-button', {
  prototype: Object.create(HTMLButtonElement.prototype),
  extends: 'button'
});

这个:

var XFooButton = document.registerElement('x-foo-button', {
  prototype: Object.create(HTMLButtonElement.prototype),
});

除了1)第一种语法需要< button is = x-foo-button>< / button> 在文档中创建实例2)第二种语法可用于任何元素,而不仅仅是扩展名自定义的?

Other than 1) The first syntax will need <button is="x-foo-button"></button> to create an instance in the document 2) The second syntax can be used on any element, not just an extension of the custom ones?

推荐答案

答案1
明显的重复是因为你的例子非常简单。在真正的虚拟生活中,你会提供一个不同的原型 registerElement

带有自定义按钮的示例单击时显示弹出窗口:

Example with a custom button that will display a popup when clicked:

//Custom method
function callback ()
{
    console.log( this + " {created}" )
    this.onclick = function ( event )
    {
        alert( this.id + " " + this.value )
    } 
}

//Type Extension
var newProto = Object.create( HTMLButtonElement.prototype )
newProto.createdCallback = callback
var XFooButtonExt = document.registerElement( 'x-foo-button', {
    prototype: newProto,
    extends: 'button'
} )

newProto 不同HTMLButtonElement 's prototype

使用以下HTML代码:

With the following HTML code:

<button is="x-foo-button" id="Hello" value="World"> Hello </button>

单击它会在弹出窗口中显示Hello World。

A click on it will display "Hello World" in a popup.

回答2
扩展:'button'是一个语义指示,告诉浏览器提供的新原型实现了 HTMLButtonElement 接口。这就是为什么从一个继承自 HTMLButtonElement 的对象开始更容易的原因。相反,您可以从 HTMLFormElement 原型开始,但您必须重新实现 HTMLButtonElement 界面的所有属性和方法。

Answer 2 The extends: 'button' is a semantic indication that tells the browser that the new prototype provided implements the HTMLButtonElement interface. That's why it's easier to start with an object that inherits from HTMLButtonElement. Instead you could start with an HTMLFormElement prototype but you would have to reimplement all the properties and methods of the HTMLButtonElement interface.

如果不是,元素行为将不正确。在上面的示例中,如果您将行替换为:

If not, the element behaviour will be incorrect. In the above example, if you replace a line by:

var newProto = Object.create( HTMLFormElement.prototype )

...点击它将失败,因为属性未在< form> 元素中实现。

... the click on it will fail because the property value is not implemented in a <form> element.

属性 id 总是正确的,因为它是由 HTMLElement 接口,由每个元素实现(包括< form> )。

The property id is always correct because it is provided by the HTMLElement interface, implemented by every elements (including <form>).

请注意,你可以添加缺少的属性,并将它们链接到 attributeChangedCallback 方法中的属性。

Note that you could add the missing properties, and link them to their attribute in the attributeChangedCallback method.

回答3
你是对的。这保持了与旧浏览器的向后兼容性,这些浏览器将忽略第二个参数,仍然能够创建普通元素(标准< button> in你的例子。)

Answer 3 You are correct. This maintains backward compatibility with old browsers that will ignore the second argument, still being able to create a normal element (a standard <button> in your example).

答案4
背后有两个不同的概念自定义元素范例:


  1. 类型扩展程序自定义内置元素)如果要扩展标准HTML元素。

  2. 自定义标记自主自定义元素),如果您想使用新名称定义自定义元素。

  1. Type Extensions (Customized Built-in Elements) if you want to extend a standard HTML element.
  2. Custom Tag (Autonomous Custom Elements) if you want to define custom elements with new names.

两者都使用相同的方法定义 registerElement extends / 选项允许您选择其中一个。

Both are defined with the same method registerElement. The extends/is option permits you to choose one of them.

语法仅适用于 Type Extensions ,因此始终与 extends 选项。

The is syntax works only with Type Extensions and is therefore always associated with the extends option.

使用 Type Extensions ,您可以保留元素的所有语义你扩展:CSS样式,内置行为(接口),辅助功能。向后兼容性是此语法的另一个好处。

With Type Extensions, you keep all the semantics of the element you extend: CSS styles, built-in behaviour (interfaces), accessibility features. Backward compatibility is another benefit of this syntax.

使用自定义标记,您将失去语义,并且您的自定义元素只能实现 HTMLElement 界面,没有内置风格或行为。

With Custom Tags, you loose the semantics and your custom element is expected to implement only the HTMLElement interface, with no built-in style or behavior.

更新:下一个示例(适用于Chrome和Opera)说明了类型扩展程序自定义标记之间的区别。

Update: the next example (for Chrome and Opera) illustrates the difference between Type Extension and Custom Tag.

//Method
function callback() {
  this.textContent = this //Get the HTML semantics
  this.onclick = function(event) {
    try {
      var output = this.id + " "
      output += this.name        //works only with <button is=...>
    } 
    catch (e) {
      output += "a generic element"
    }
    alert(output)
  }
}

//Type Extension
var newProto = Object.create(HTMLButtonElement.prototype)
newProto.createdCallback = callback

var XFooButtonExt = document.registerElement('x-foo-button', {
  prototype: newProto,
  extends: 'button'
})

//Custom Tag
var newProto2 = Object.create(HTMLButtonElement.prototype)
newProto2.createdCallback = callback

var XFooButtonCust = document.registerElement('x-foo-button-2', {
  prototype: newProto2,
})

<!DOCTYPE html>
<html>

<head>
  <meta charset="utf-8" />
  <title>Custom Elements</title>
</head>

<body>
  <h3>Type Extension</h3>
  <button is="x-foo-button" id="I'm" name="a button">Type Extension</button>
  <h3>Custom Tag</h3>
  <x-foo-button-2 id="I'm" name="a button">Custom Tag</x-foo-button-2>
</body>

</html>

这篇关于“是”的重点是什么?扩展Web组件中的元素时的语法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆