## 组件
组件(Component)是UOkay三大核心之一(Okay,Action)。组件可以扩展HTML元素,封装可重用的代码。UOkay组件的定义如下:
~~~
组件是视图结构和数据结构的定义,并拥有相应行为的对象。
~~~
### 使用组件
#### 全局注册
我们可以使用静态函数`Okay.component`定义全局组件:
~~~
<div id = "app">
<ucomponent></ucomponent>
</div>
~~~
~~~
Okay.component("ucomponent",{
template: "<div>{{ message }}</div>",
data: function () {
return {
message: 'Hello World'
}
}
})
var app = new Okay({
ele:'app',
})
~~~
全局注册的组件将在任何Okay实例中有效。
#### 局部注册
局部注册时在Okay配置参数中配置components属性:
~~~
<div id = "app">
<ucomponent></ucomponent>
</div>
~~~
~~~
var app = new Okay({
ele:'app',
components: {
ucomponent: {
template: "<div>{{ message }}</div>",
data: function () {
return {
message: 'Hello World'
}
}
}
}
})
~~~
局部注册的组件仅在定义该组件的Okay实例中可见。
#### 子组件注册
子组件注册是在组件中配置中配置components属性:
~~~
<div id = "app">
<ucomponent></ucomponent>
</div>
~~~
~~~
let Child = {
template: `<div>{{message}}</div>`,
name: 'child',
data() {
return {
message: 'Hello Child'
}
}
}
Okay.component("ucomponent",{
template: `<div>{{ message }}</div>
<child></child>`,
data: function () {
return {
message: 'Hello World'
}
},
components: {
child: Child
}
})
var app = new Okay({
ele:'app',
})
~~~
在上例中,组件ucomponent中定义了子组件child,输出结果如下:
~~~
<ucomponent>
<div>Hello World</div>
<child>
<div>Hello Child</div>
</child>
</ucomponent>
~~~
### 组件继承
与其他框架不同的是,我们并不期待组件的复用,UOkay主张组合编程的模式,即多个子组件组合成大组件,不断的组合形成一个应用。所以子组件应该可以访问父组件的数据,而对于兄弟组件透明,即子组件继承父组件的数据与行为。
~~~
<div id = "app">
<ucomponent></ucomponent>
</div>
~~~
~~~
let Child = {
template: `<div>{{message}}</div>`,
name: 'child',
}
Okay.component("ucomponent",{
template: `<div>{{ message }}</div>
<child></child>`,
data: function () {
return {
message: 'Hello World'
}
},
components: {
child: Child
}
})
var app = new Okay({
ele:'app',
})
~~~
上例中Child组件中使用父组件ucomponent组件中的message值,输出结果:
~~~
<ucomponent>
<div>Hello World</div>
<child>
<div>Hello World</div>
</child>
</ucomponent>
~~~
### 行为状态继承
在UOkay中我们可以继承行为的状态,但并不能继承行为函数,这是因为行为在父组件中拥有的行为,子组件不一定拥有,但行为的状态是描述父组件的状态,理应该对组件开放,即子组件能访问父组件的状态。
~~~
<div id = "app">
<ucomponent></ucomponent>
</div>
~~~
~~~
class TestAction extends Action{
__initial__() {
this.message = "Hello Test"
}
}
let Child = {
template: `<div>{{test.message}}</div>`,
name: 'child',
}
Okay.component("ucomponent",{
template: `<div>{{ message }}</div>
<child></child>`,
data: function () {
return {
message: 'Hello World'
}
},
action_classes: {
test: TestAction
},
components: {
child: Child
}
})
var app = new Okay({
ele:'app',
})
~~~
上例中,ucomponent组件中定义了行为test,子组件Child中使用test.message访问父组件ucomponent中的行为test。
### 规模化
我们提供了一个简单的Webpack Loader:okay-loader,我们可以利用okay-loader编写UOkay组件。
#### 新建文件:Test.okay
~~~
<template>
<div>{{message}}</div>
</template>
<script>
export default {
name: "test",
data() {
return {
message: 'Hello World'
}
}
}
</script>
~~~
需要注意的是,export default必须顶格,否则okay-loader将无法正常加载okay文件
#### 在需要Test组件的地方引入组件Test
~~~
import Test from './components/Test.okay'
var app = new Okay({
ele:'app',
components: {
test: Test
}
})
~~~
#### 编写页面
~~~
<div id = "app">
<test></test>
</div>
~~~
#### 编译结果
~~~
<div id = "app">
<test>
<div>Hello World</div>
</test>
</div>
~~~