与类似文档一样,Regular 将风格指南设置为了多个优先级,分别是
- 必要的: 程序运行可能会出问题的,强制遵循
- 建议的: 不遵循程序可以运行,但会引起可维护性或性能的问题
- 谨慎使用的: 未来可能会废弃的使用方式,谨慎使用
在 config
生命周期中处理默认参数,而不是的 extend
时定义
Bad
Regular.extend({
data: {
list: [1,2,3]
}
})
Good
Regular.extend({
config( data ){
data.list = data.list || [1,2,3]
}
})
Very Good
更好的做法是一个一致的缺省参数逻辑, 比如使用util.extend
(会默认添加未定义的值)
const extend = Regular.util.extend;
Regular.extend({
config( data ){
extend(data, {
list: [ 1, 2, 3 ]
})
}
})
__ 未来 Regular 会提供统一的 default 书写方式 __(会结合入参的检验机制共同设计)。
谨记 extend 是原型继承的语法糖,所以原型上的定义都是实例公用的
参考
由于一些历史原因,Regular有一个肮脏的设计:即destory
既被定义为生命周期钩子方法,又是一个对外的public
API。
为了确保组件回收的统一逻辑,请调用 this.supr()
来引入Regular.prototype.destory
中的回收逻辑
Bad
const Component = Regular.extend({
destory(){
window.removeEventListener('scroll', this.onScroll)
}
})
Good
const Component = Regular.extend({
destory(){
this.supr()
window.removeEventListener('scroll', this.onScroll)
}
})
Good
<tr>
{#list items as item by item_index}
<td>{item.content}</td>
{/list}
</tr>
Bad
{#list items as item}
<td>{item.content}</td>
{/list}
但并非所有场景都可以使用
track by
进行控制,请参考 list语句章节
参考
Regular 本身并无强限制组件的命名方式。
建议以 大写驼峰 的方式进行组件命名,并且 类名和 name
统一
Bad
const ConfirmModal = Regular.extend({
name: 'confirm-modal'
})
Good
const ConfirmModal = Regular.extend({
name: 'ConfirmModal',
// 略
})
if语句其实可以使用在节点属性上,但已经不建议大家这么做
Bad
<input {#if required} required {/if} />
<div {#if active} on-click={this.clickMe()} {/if} ></div>
Good
相关逻辑迁移到JS
// Regular会自动转义类似required、readonly 等 Boolean 类属性
<input required={required} />
Regular.extend({
template: `
<div on-click={this.clickMe()}></div>
`,
clickMe(){
// 在js中控制
if( !this.data.active ) return;
}
})
理由
使用if语句去控制属性有几个风险
- 存在自定义指令未实现 destroy 函数的可能,进而导致 Bug
- 这种在模板里夹杂大量逻辑的写法会引起可维护性降低
- 未来可能会移除这个Feature
Bad
const Input2 = Regular.extend({
name: 'Input2',
template: `<input on-change={this.changeValue($event)} />`
changeValue(ev){
this.data.value = ev.target.value;
this.$emit('change'); // emit change event
}
})
new Regular({
template: `
<Input2 value={value} on-change={this.handleValue()} />
`,
handleValue(){
console.log(this.data.value) // 返回的仍然是上一个值
}
}).$inject('body')
这里你会发现返回的仍然是上一个值
为什么?
因为触发事件的时候,并没有进入脏检查,外层的数据其实还未被同步。
Not So Bad
const Input2 = Regular.extend({
name: 'Input2',
template: `<input on-change={this.changeValue($event)} />`
changeValue(ev){
this.data.value = ev.target.value;
setTimeout(()=>{
this.$emit('change'); //emit
},0)
}
})
当通过类似setTimeout
将其延迟到脏检查之后的时机触发,此时的结果就如预期了。
Good
@TODO: new feature required