web组件——template标签,影子DOM,自定义组件
template标签
innerHTML会带来安全问题,document.createElemt()又太过麻烦,template就很方便且安全
I am inside template
注意:
- 这两种添加方法效果是不一样的,importNode是克隆;而直接添加,就是把它掏空了,移走了。再想克隆/'拿'就是个空的
第一种效果:tmeplate里的内容不可展开了
第二种效果:tmeplate里的内容可展开,可见
影子DOM
放影子DOM的"容器"(标签)叫"宿主",一个宿主里只能放一个影子DOM,若不小心放多了,就是"先到先得",谁在前就放谁,后面的不管
功能:
- 普通html中为了不同的样式,要避免class名一样,而影子DOM有自己的class,即使与外界class重名了,也不影响
两个同名class,互不影响
注意:
{ mode: 'open' }中的open与closed适用于创建开放与保密的影子DOM。log(d1)打印d1的详细信息,log(d2)null,目的是为了安全,但是在"有心人"面前还是显得鸡肋
- 影子DOM会具有更高的优先级:宿主里的内容会被影子DOM的内容覆盖,除非影子DOM提供插槽
,把宿主原本的内容放在slot中保存
I am host
效果:原内容被替代
加上slot
color: red
效果:宿主的内容被放到slot里保存了下来
- 改变宿主中元素的渲染顺序
a
b
效果:先渲染了b,后a
自定义组件
html的标签名时可以自己随便起的,唯一的要求就是自定义的组件中间要有横线:-
如:
最简单的用法就是直接写在html中慢慢改style,但是它搭配template或影子DOM有更高级的用法
如此后,在html'中只需要一个,就能达到下面的效果:
template也是一样,要注意的时通过影子DOM实现自定义标签内部的样式只能在影子DOM内部写style,外部不会生效。
这样的标签也是一个组件,我们可以通过在构造函数中通过constructor()和其他JS的API监听组件的属性变化等,来实现组件的生命周期:
//1. 创建元素可以通过:
constructor() {
super()
log('beforeCreated')
this.attachShadow({ mode: 'open' })
.innerHTML = `....`
log('created')
}
//2.组件被添加进某个容器时 <=> mounted
connected
//3.组件被从某容器移除时 <=> unmounted
discounted
//4.组件属性改变时 <=> updated
attributeChanged