在 TypeScript 中实例化新的 HTMLElement

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/26220243/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-09 06:31:56  来源:igfitidea点击:

Instantiating new HTMLElement in TypeScript

typescript

提问by daniel.sedlacek

I am trying to instantiate new HTMLDivElement in TypeScript

我正在尝试在 TypeScript 中实例化新的 HTMLDivElement

var elem = new HTMLDivElement();

but the browser throws

但浏览器抛出

Uncaught TypeError: Illegal constructor.

The workaround seems to be to use

解决方法似乎是使用

var elem = document.createElement('div');

but I find this suboptimal for various reasons.

但由于各种原因,我发现这不是最理想的。

Why can't I instantiate DOM elements directly when there is a newkeyword for in in the lib.d.ts?

lib.d.ts 中有一个关键字 for in时,为什么我不能直接实例化 DOM 元素?

declare var HTMLDivElement: {
    prototype: HTMLDivElement;
    new (): HTMLDivElement;
}

回答by Ryan Cavanaugh

Note that the error you get here is "Illegal constructor". This is different from the error "object is not a function" that you would get if you were to write new {}(), for example.

请注意,您在这里得到的错误是“非法构造函数”。例如,这与您在编写时会得到的错误“对象不是函数”不同new {}()

So, technically, HTMLDivElementdoeshave a constructor. It's just that this particular constructor throws an exception rather than creating an object.

所以,从技术上讲,HTMLDivElement确实有一个构造函数。只是这个特定的构造函数抛出异常而不是创建一个对象。

Normally lib.d.tswould just exclude such useless signatures, but TypeScript requires that the right-hand side of the instanceofoperator have a constructor. In other words, it's legal to write foo instanceof HTMLElement, but not foo instanceof [], and the difference is determined by the fact that HTMLElementhas a constructor.

通常lib.d.ts只会排除这种无用的签名,但 TypeScript 要求instanceof运算符的右侧有一个构造函数。换句话说,写合法foo instanceof HTMLElement,但不合法,foo instanceof []区别在于HTMLElement是否有构造函数。

There were basically three choices on the table here:

这里的桌子上基本上有三个选择:

  1. Remove the construct signature from the DOM elements and remove the restriction on instanceof's right operand. This is undesirable because you'd really prefer to catch errors where someone accidentally writes code like x instanceof fooinstead of x instanceof Foo(where foois an instance of Foo).
  2. Remove the construct signature from DOM elements, but keep the instanceofcheck in place. This is bad because foo instanceof HTMLElementis a very reasonable thing to write.
  3. The current situation, where the constructors exist but you have to know not to call them.
  1. 从 DOM 元素中移除构造签名并移除对instanceof右操作数的限制。这是不可取的,因为您真的更喜欢捕获某人意外编写代码的错误,x instanceof foo而不是x instanceof Foo(其中foo是 的实例Foo)。
  2. 从 DOM 元素中删除构造签名,但保留instanceof检查位置。这很糟糕,因为这foo instanceof HTMLElement是一个非常合理的写法。
  3. 当前情况,构造函数存在但您必须知道不要调用它们。

You can't construct DOM elements using normal constructors because you're supposed to go through document.createElement. This is basically for technical reasons relating to how browsers implement these objects.

您不能使用普通构造函数构造 DOM 元素,因为您应该通过document.createElement. 这基本上是出于与浏览器如何实现这些对象有关的技术原因。

回答by Mostafa Khodakarami

You have mistaken typescript syntax with c# syntax.

您使用 c# 语法错误地使用了 typescript 语法。

Just replace

只需更换

var elem = new HTMLDivElement();

with one of the following

具有以下之一

var elem = document.createElement('div');

or

或者

var elem = <HTMLDivElement>(document.createElement('div'));

or

或者

let elem = document.createElement('div') as HTMLDivElement

(if you need to use HTMLDivElement attributes)

(如果你需要使用 HTMLDivElement 属性)

回答by Nick Mitchell

If you extend HTMLElementor any subclass like HTMLDivElement

如果您扩展HTMLElement或任何子类,如HTMLDivElement

You also need to register the custom element

您还需要注册自定义元素


class SampleDiv extends HTMLDivElement{
    constructor(){
       super();
    }
}
customElements.define('sample-div', SampleDiv, { extends: 'div' });

See more here: https://javascript.info/custom-elements

在此处查看更多信息:https: //javascript.info/custom-elements