关于
Web Components
>Vite
为工程依赖Ts
语言开发
<!-- index.html -->
<body>
<button class="open">open</button>
<my-dialog>
<h1>wo cao nb</h1>
</my-dialog>
<script type="module" src="./src/index.ts"></script>
</body>
/* ./src/index.ts */
class MyDialog extends HTMLElement {
static componentName: string = "my-dialog";
private closeButton: HTMLButtonElement;
constructor() {
super();
const style = `
:host(:not([open])) {
display: none;
}
:host {
position: fixed;
left: 0; top: 0;
height: 100%; width: 100%;
background-color: rgba(25, 28, 34, 0.88);
z-index: 19;
display: grid;
place-items: center;
}
dialog {
position: static;
display: inherit;
}
`;
const html = `
<style>${style}</style>
<dialog>
<!-- slot 插槽 作用与 Vue 的 slot 相同-->
<slot>暂无提示信息</slot>
<p>
<button name="close">确定</button>
</p>
</dialog>
`;
// 解析html 字符串
const template = document.createRange().createContextualFragment(html);
const shadowRoot = this.attachShadow({ mode: "open" });
shadowRoot.append(template);
this.closeButton = this.shadowRoot.querySelector('button[name="close"]');
this.closeButton.addEventListener("click", this.hide.bind(this));
}
hide() {
this.toggleAttribute("open", false);
}
// 连接到 DOM
connectedCallback() {
/**
* 一种常见错误是将 connectedCallback 用做一次性的初始化事件,
* 然而实际上你每次将节点连接到 DOM 时都会被调用。
* 取而代之的,
* 在 constructor 这个 API 接口调用时做一次性初始化工作会更加合适。
*/
}
// 从 DOM 上脱离
disconnectedCallback() {
this.closeButton.removeEventListener("click", this.hide.bind(this));
}
}
window.customElements.define(MyDialog.componentName, MyDialog);
const onLoaded = () => {
const $ = {
open: document.querySelector(".open"),
dialog: document.querySelector("my-dialog"),
};
$.open.addEventListener("click", () => {
$.dialog.toggleAttribute("open", true);
});
};
window.addEventListener("load", onLoaded);