这是我参与「第四届青训营 」笔记创作活动的第1天
今天再次认真看了月影老师的JS课程,感觉还是非常有收获的,第一次对如何写好JS有了一些认识。特此记下笔记:
写好JS的一些原则
- 各司其职(让HTML、CSS、JS职能分离)
- 组件封装(好的UI组件具备扩展性、正确性、复用性)
- 过程抽象(应用函数式编程思想)
深夜食堂
写一段JS,控制一个网页,让它支持浅色和深色两种浏览模式。 如果是你来实现,你会怎么做?
下面是版本1:
主要的JS代码,就是通过对按钮元素添加点击事件,从而控制按钮标签的内容和css样式的改变。这也是我以前的常规做法。虽然实现了点击页面让背景颜色变化但是违背了js只负责页面动作的原则。同时这样也会存在一些问题:
- js直接修改的是行内样式,其优先级最高;如果我们想要覆盖只能让后面的规则加上!important。
- 后续想要添加更多样式的话只能在这加入更多的代码,会对后期修改造成不小的麻烦。
- 性能问题,每一次触发点击事件都会查询DOM树找到body节点,为其修改样式后触发重绘。
const btn = document.getElementById('modeBtn');
btn.addEventListener('click', (e) => {
const body = document.body;
if(e.target.innerHTML === '🌞') {
body.style.backgroundColor = 'black';
body.style.color = 'white';
e.target.innerHTML = '🌜';
} else {
body.style.backgroundColor = 'white';
body.style.color = 'black';
e.target.innerHTML = '🌞';
}
});
下面是版本2:
版本2的主要方法就是通过CSS的伪元素来对按钮里面的内容进行控制,同时对body里面写两套样式,使用类night来区分,通过JS来修改body标签的类名,从而实现样式的改变。
在这里我们将样式以及动作分开,需要的样式规则放入css文件中,而js只负责监听点击事件切换class,满足了“CSS负责页面样式,JavaScript负责页面动作”的准则;往后我们需要再添加样式则只需要在相应的css文件中修改而不需要再关注负责逻辑的js代码。
#modeBtn::after { content: '🌞'; } body.night #modeBtn::after { content: '🌜'; }
PS:伪类元素的用法
下面是版本3:
版本3的实现是纯HTML和CSS实现,点击标签的时候因为label中的for属性和input标签绑定,导致input的click事件触发,而太阳图案和月亮图案的切换则通过复选框的是否选择,从而在css中的伪类选择器:checked来判断是否选中,而实现改变.content #modeBtn::after的content。
PS:label的for属性规定了label与哪个表单元素绑定。for属性的值和表单元素的id值是一样的,即可完成label标签和该表单元素的绑点。
深夜食堂结论:
- HTML/CSS/JS 各司其责
- 应当避免不必要的由 JS 直接操作样式
- 可以用 class 来表示状态
- 纯展示类交互寻求零 JS 方案