Commit c86d77fcef08ea67027f2defc1b1abf0f81f6a34

Authored by muei
Committed by GitHub
2 parents fb189f16 62a40f4f

Merge branch '2.0' into 2.0

.github/ISSUE_TEMPLATE.md
@@ -4,19 +4,22 @@ issue 仅用于提交 bug 或 feature 及 文档错误,其余疑问恕不作 @@ -4,19 +4,22 @@ issue 仅用于提交 bug 或 feature 及 文档错误,其余疑问恕不作
4 <!-- 4 <!--
5 我们十分感谢有价值的 issue 贡献者,所以请填写以下内容。如果提问不符要求、在文档中已有解答、已有相同 issue,我们将直接 close,感谢理解。 5 我们十分感谢有价值的 issue 贡献者,所以请填写以下内容。如果提问不符要求、在文档中已有解答、已有相同 issue,我们将直接 close,感谢理解。
6 --> 6 -->
  7 +<!--
  8 +点击 Preview 按钮预览,无误后再提交 issue
  9 +-->
7 10
8 ### iView 版本号 11 ### iView 版本号
9 -<!-- 0.9.10 --> 12 +<!-- 2.0.0-rc.5 -->
10 13
11 ### 操作系统/浏览器 版本号 14 ### 操作系统/浏览器 版本号
12 -<!-- macOS/Chrome 54 --> 15 +<!-- macOS/Chrome 56 -->
13 16
14 ### Vue 版本号 17 ### Vue 版本号
15 -<!-- 1.0.26 --> 18 +<!-- 2.2.1 -->
16 19
17 -### 能够复现问题的在线示例 20 +### 能够复现问题的在线示例(重要)
18 <!-- 使用下面的在线链接快速创建示例 --> 21 <!-- 使用下面的在线链接快速创建示例 -->
19 -<!-- https://codepen.io/anon/pen/NbEbja --> 22 +<!-- https://codepen.io/anon/pen/BWwVoy -->
20 23
21 ### 复现步骤 24 ### 复现步骤
22 25
1 The MIT License (MIT) 1 The MIT License (MIT)
2 2
3 -Copyright (c) 2016 iView 3 +Copyright (c) 2016-present iView
4 4
5 Permission is hereby granted, free of charge, to any person obtaining a copy 5 Permission is hereby granted, free of charge, to any person obtaining a copy
6 of this software and associated documentation files (the "Software"), to deal 6 of this software and associated documentation files (the "Software"), to deal
@@ -20,6 +20,29 @@ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, @@ -20,6 +20,29 @@ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 20 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 SOFTWARE. 21 SOFTWARE.
22 22
  23 +MIT LICENSE
  24 +
  25 +Copyright (c) 2015-present Alipay.com, https://www.alipay.com/
  26 +
  27 +Permission is hereby granted, free of charge, to any person obtaining
  28 +a copy of this software and associated documentation files (the
  29 +"Software"), to deal in the Software without restriction, including
  30 +without limitation the rights to use, copy, modify, merge, publish,
  31 +distribute, sublicense, and/or sell copies of the Software, and to
  32 +permit persons to whom the Software is furnished to do so, subject to
  33 +the following conditions:
  34 +
  35 +The above copyright notice and this permission notice shall be
  36 +included in all copies or substantial portions of the Software.
  37 +
  38 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  39 +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  40 +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  41 +NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
  42 +LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
  43 +OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  44 +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  45 +
23 The MIT License (MIT) 46 The MIT License (MIT)
24 47
25 Copyright (c) 2016 ElemeFE 48 Copyright (c) 2016 ElemeFE
@@ -40,4 +63,92 @@ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE @@ -40,4 +63,92 @@ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
40 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 63 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
41 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 64 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
42 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 65 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
43 -SOFTWARE.  
44 \ No newline at end of file 66 \ No newline at end of file
  67 +SOFTWARE.
  68 +
  69 +The MIT License (MIT)
  70 +
  71 +Copyright (c) 2015 Koala
  72 +
  73 +Permission is hereby granted, free of charge, to any person obtaining a copy
  74 +of this software and associated documentation files (the "Software"), to deal
  75 +in the Software without restriction, including without limitation the rights
  76 +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  77 +copies of the Software, and to permit persons to whom the Software is
  78 +furnished to do so, subject to the following conditions:
  79 +
  80 +The above copyright notice and this permission notice shall be included in all
  81 +copies or substantial portions of the Software.
  82 +
  83 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  84 +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  85 +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  86 +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  87 +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  88 +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  89 +SOFTWARE.
  90 +
  91 +The MIT License (MIT)
  92 +
  93 +Copyright (c) 2016 vue-beauty
  94 +
  95 +Permission is hereby granted, free of charge, to any person obtaining a copy
  96 +of this software and associated documentation files (the "Software"), to deal
  97 +in the Software without restriction, including without limitation the rights
  98 +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  99 +copies of the Software, and to permit persons to whom the Software is
  100 +furnished to do so, subject to the following conditions:
  101 +
  102 +The above copyright notice and this permission notice shall be included in all
  103 +copies or substantial portions of the Software.
  104 +
  105 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  106 +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  107 +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  108 +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  109 +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  110 +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  111 +SOFTWARE.
  112 +
  113 +MIT License
  114 +
  115 +Copyright (c) 2016-present, Airyland
  116 +
  117 +Permission is hereby granted, free of charge, to any person obtaining a copy
  118 +of this software and associated documentation files (the "Software"), to deal
  119 +in the Software without restriction, including without limitation the rights
  120 +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  121 +copies of the Software, and to permit persons to whom the Software is
  122 +furnished to do so, subject to the following conditions:
  123 +
  124 +The above copyright notice and this permission notice shall be included in all
  125 +copies or substantial portions of the Software.
  126 +
  127 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  128 +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  129 +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  130 +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  131 +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  132 +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  133 +SOFTWARE.
  134 +
  135 +The MIT License (MIT)
  136 +
  137 +Copyright (c) 2016 Drifty (http://drifty.com/)
  138 +
  139 +Permission is hereby granted, free of charge, to any person obtaining a copy
  140 +of this software and associated documentation files (the "Software"), to deal
  141 +in the Software without restriction, including without limitation the rights
  142 +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  143 +copies of the Software, and to permit persons to whom the Software is
  144 +furnished to do so, subject to the following conditions:
  145 +
  146 +The above copyright notice and this permission notice shall be included in
  147 +all copies or substantial portions of the Software.
  148 +
  149 +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  150 +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  151 +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  152 +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  153 +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  154 +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  155 +THE SOFTWARE.
45 \ No newline at end of file 156 \ No newline at end of file
@@ -83,10 +83,7 @@ Normal browsers and Internet Explorer 9+. @@ -83,10 +83,7 @@ Normal browsers and Internet Explorer 9+.
83 - [ionicons](https://github.com/driftyco/ionicons) 83 - [ionicons](https://github.com/driftyco/ionicons)
84 - [Ant Design](https://github.com/ant-design/ant-design) 84 - [Ant Design](https://github.com/ant-design/ant-design)
85 85
86 -## Related open source projects  
87 -In iView, Some of the components and style codes refer to the following projects:  
88 -- [AntDesign](https://github.com/ant-design/ant-design)  
89 -- [Element](https://github.com/ElemeFE/element)  
90 -- [vue-antd](https://github.com/okoala/vue-antd)  
91 -- [vue-beauty](https://github.com/FE-Driver/vue-beauty)  
92 -- [Vux](https://github.com/airyland/vux)  
93 \ No newline at end of file 86 \ No newline at end of file
  87 +## License
  88 +[MIT](http://opensource.org/licenses/MIT)
  89 +
  90 +Copyright (c) 2016-present, iView
94 \ No newline at end of file 91 \ No newline at end of file
examples/routers/carousel.vue
@@ -2,7 +2,9 @@ @@ -2,7 +2,9 @@
2 <div> 2 <div>
3 <Carousel v-model="v1" dots="inside" trigger="hover"> 3 <Carousel v-model="v1" dots="inside" trigger="hover">
4 <Carousel-item> 4 <Carousel-item>
5 - <div class="demo-carousel">1</div> 5 + <Card>
  6 + <div class="demo-carousel">1</div>
  7 + </Card>
6 </Carousel-item> 8 </Carousel-item>
7 <Carousel-item> 9 <Carousel-item>
8 <div class="demo-carousel">2</div> 10 <div class="demo-carousel">2</div>
examples/routers/checkbox.vue
@@ -27,9 +27,17 @@ @@ -27,9 +27,17 @@
27 <div @click="c">修改1</div> 27 <div @click="c">修改1</div>
28 {{ fruit }} 28 {{ fruit }}
29 <Checkbox-group v-model="fruit"> 29 <Checkbox-group v-model="fruit">
30 - <Checkbox label="香蕉"></Checkbox>  
31 - <Checkbox label="苹果"></Checkbox>  
32 - <Checkbox label="西瓜"></Checkbox> 30 + <Row>
  31 + <i-col span="8">
  32 + <Checkbox label="香蕉"></Checkbox>
  33 + </i-col>
  34 + <i-col span="8">
  35 + <Checkbox label="苹果"></Checkbox>
  36 + </i-col>
  37 + <i-col span="8">
  38 + <Checkbox label="西瓜"></Checkbox>
  39 + </i-col>
  40 + </Row>
33 </Checkbox-group> 41 </Checkbox-group>
34 <br><br> 42 <br><br>
35 <div style="border-bottom: 1px solid #e9e9e9;padding-bottom:6px;margin-bottom:6px;"> 43 <div style="border-bottom: 1px solid #e9e9e9;padding-bottom:6px;margin-bottom:6px;">
examples/routers/form.vue
@@ -11,6 +11,14 @@ @@ -11,6 +11,14 @@
11 <Form-item prop="user"> 11 <Form-item prop="user">
12 <Input v-model="formInline.user"></Input> 12 <Input v-model="formInline.user"></Input>
13 </Form-item> 13 </Form-item>
  14 + <Form-item prop="targetKeys1">
  15 + <Transfer
  16 + filterable
  17 + :data="formInline.data1"
  18 + :target-keys="formInline.targetKeys1"
  19 + :render-format="render1"
  20 + @on-change="handleChange1"></Transfer>
  21 + </Form-item>
14 <Form-item> 22 <Form-item>
15 <i-button type="primary" @click.native="handleSubmit('formInline')">登录</i-button> 23 <i-button type="primary" @click.native="handleSubmit('formInline')">登录</i-button>
16 </Form-item> 24 </Form-item>
@@ -22,6 +30,8 @@ @@ -22,6 +30,8 @@
22 data () { 30 data () {
23 return { 31 return {
24 formInline: { 32 formInline: {
  33 + data1: this.getMockData(),
  34 + targetKeys1: this.getTargetKeys(),
25 date: new Date(), 35 date: new Date(),
26 user: '', 36 user: '',
27 value2: [], 37 value2: [],
@@ -102,6 +112,15 @@ @@ -102,6 +112,15 @@
102 message: '请输入', 112 message: '请输入',
103 trigger: 'change' 113 trigger: 'change'
104 } 114 }
  115 + ],
  116 + targetKeys1: [
  117 + {
  118 + required: true,
  119 + type: 'array',
  120 + max: 2,
  121 + message: '太多了',
  122 + trigger: 'change'
  123 + }
105 ] 124 ]
106 } 125 }
107 } 126 }
@@ -118,6 +137,32 @@ @@ -118,6 +137,32 @@
118 }, 137 },
119 handleInput (val) { 138 handleInput (val) {
120 console.log(val) 139 console.log(val)
  140 + },
  141 + getMockData () {
  142 + let mockData = [];
  143 + for (let i = 1; i <= 20; i++) {
  144 + mockData.push({
  145 + key: i.toString(),
  146 + label: '内容' + i,
  147 + description: '内容' + i + '的描述信息',
  148 + disabled: Math.random() * 3 < 1
  149 + });
  150 + }
  151 + return mockData;
  152 + },
  153 + getTargetKeys () {
  154 + return this.getMockData()
  155 + .filter(() => Math.random() * 2 > 1)
  156 + .map(item => item.key);
  157 + },
  158 + render1 (item) {
  159 + return item.label;
  160 + },
  161 + handleChange1 (newTargetKeys, direction, moveKeys) {
  162 + console.log(newTargetKeys);
  163 + console.log(direction);
  164 + console.log(moveKeys);
  165 + this.formInline.targetKeys1 = newTargetKeys;
121 } 166 }
122 } 167 }
123 } 168 }
examples/routers/menu.vue
1 -<!--<template>-->  
2 - <!--<div>-->  
3 - <!--<Menu mode="horizontal" :theme="theme1" active-name="1" @on-select="s">-->  
4 - <!--<Menu-item name="1">-->  
5 - <!--<Icon type="ios-paper"></Icon>-->  
6 - <!--内容管理-->  
7 - <!--</Menu-item>-->  
8 - <!--<Menu-item name="2">-->  
9 - <!--<Icon type="ios-people"></Icon>-->  
10 - <!--用户管理-->  
11 - <!--</Menu-item>-->  
12 - <!--<Submenu name="3">-->  
13 - <!--<template slot="title">-->  
14 - <!--<Icon type="stats-bars"></Icon>-->  
15 - <!--统计分析-->  
16 - <!--</template>-->  
17 - <!--<Menu-group title="使用">-->  
18 - <!--<Menu-item name="3-1">新增和启动</Menu-item>-->  
19 - <!--<Menu-item name="3-2">活跃分析</Menu-item>-->  
20 - <!--<Menu-item name="3-3">时段分析</Menu-item>-->  
21 - <!--</Menu-group>-->  
22 - <!--<Menu-group title="留存">-->  
23 - <!--<Menu-item name="3-4">用户留存</Menu-item>-->  
24 - <!--<Menu-item name="3-5">流失用户</Menu-item>-->  
25 - <!--</Menu-group>-->  
26 - <!--</Submenu>-->  
27 - <!--<Menu-item name="4">-->  
28 - <!--<Icon type="settings"></Icon>-->  
29 - <!--综合设置-->  
30 - <!--</Menu-item>-->  
31 - <!--</Menu>-->  
32 - <!--<br>-->  
33 - <!--<p>切换主题</p>-->  
34 - <!--<Radio-group v-model="theme1">-->  
35 - <!--<Radio label="light"></Radio>-->  
36 - <!--<Radio label="dark"></Radio>-->  
37 - <!--<Radio label="primary"></Radio>-->  
38 - <!--</Radio-group>-->  
39 - <!--</div>-->  
40 -<!--</template>-->  
41 -<!--<script>-->  
42 - <!--export default {-->  
43 - <!--data () {-->  
44 - <!--return {-->  
45 - <!--theme1: 'light'-->  
46 - <!--}-->  
47 - <!--},-->  
48 - <!--methods: {-->  
49 - <!--s (s) {-->  
50 - <!--console.log(s)-->  
51 - <!--}-->  
52 - <!--}-->  
53 - <!--}-->  
54 -<!--</script>-->  
55 -  
56 -  
57 <template> 1 <template>
58 <div> 2 <div>
59 - <Row>  
60 - <i-col span="8">  
61 - <Menu :theme="theme2" @on-select="s">  
62 - <Submenu name="1">  
63 - <template slot="title">  
64 - <Icon type="ios-paper"></Icon>  
65 - 内容管理  
66 - </template>  
67 - <Menu-item name="1-1">文章管理</Menu-item>  
68 - <Menu-item name="1-2">评论管理</Menu-item>  
69 - <Menu-item name="1-3">举报管理</Menu-item>  
70 - </Submenu>  
71 - <Submenu name="2">  
72 - <template slot="title">  
73 - <Icon type="ios-people"></Icon>  
74 - 用户管理  
75 - </template>  
76 - <Menu-item name="2-1">新增用户</Menu-item>  
77 - <Menu-item name="2-2">活跃用户</Menu-item>  
78 - </Submenu>  
79 - <Submenu name="3">  
80 - <template slot="title">  
81 - <Icon type="stats-bars"></Icon>  
82 - 统计分析  
83 - </template>  
84 - <Menu-group title="使用">  
85 - <Menu-item name="3-1">新增和启动</Menu-item>  
86 - <Menu-item name="3-2">活跃分析</Menu-item>  
87 - <Menu-item name="3-3">时段分析</Menu-item>  
88 - </Menu-group>  
89 - <Menu-group title="留存">  
90 - <Menu-item name="3-4">用户留存</Menu-item>  
91 - <Menu-item name="3-5">流失用户</Menu-item>  
92 - </Menu-group>  
93 - </Submenu>  
94 - </Menu>  
95 - </i-col>  
96 - <i-col span="8">  
97 - <Menu :theme="theme2" active-name="1-2" :open-names="['1']" @on-select="s">  
98 - <Submenu name="1">  
99 - <template slot="title">  
100 - <Icon type="ios-paper"></Icon>  
101 - 内容管理  
102 - </template>  
103 - <Menu-item name="1-1">文章管理</Menu-item>  
104 - <Menu-item name="1-2">评论管理</Menu-item>  
105 - <Menu-item name="1-3">举报管理</Menu-item>  
106 - </Submenu>  
107 - <Submenu name="2">  
108 - <template slot="title">  
109 - <Icon type="ios-people"></Icon>  
110 - 用户管理  
111 - </template>  
112 - <Menu-item name="2-1">新增用户</Menu-item>  
113 - <Menu-item name="2-2">活跃用户</Menu-item>  
114 - </Submenu>  
115 - <Submenu name="3">  
116 - <template slot="title">  
117 - <Icon type="stats-bars"></Icon>  
118 - 统计分析  
119 - </template>  
120 - <Menu-group title="使用">  
121 - <Menu-item name="3-1">新增和启动</Menu-item>  
122 - <Menu-item name="3-2">活跃分析</Menu-item>  
123 - <Menu-item name="3-3">时段分析</Menu-item>  
124 - </Menu-group>  
125 - <Menu-group title="留存">  
126 - <Menu-item name="3-4">用户留存</Menu-item>  
127 - <Menu-item name="3-5">流失用户</Menu-item>  
128 - </Menu-group>  
129 - </Submenu>  
130 - </Menu>  
131 - </i-col>  
132 - <i-col span="8">  
133 - <Menu :theme="theme2" :open-names="['1']" accordion @on-select="s">  
134 - <Submenu name="1">  
135 - <template slot="title">  
136 - <Icon type="ios-paper"></Icon>  
137 - 内容管理  
138 - </template>  
139 - <Menu-item name="1-1">文章管理</Menu-item>  
140 - <Menu-item name="1-2">评论管理</Menu-item>  
141 - <Menu-item name="1-3">举报管理</Menu-item>  
142 - </Submenu>  
143 - <Submenu name="2">  
144 - <template slot="title">  
145 - <Icon type="ios-people"></Icon>  
146 - 用户管理  
147 - </template>  
148 - <Menu-item name="2-1">新增用户</Menu-item>  
149 - <Menu-item name="2-2">活跃用户</Menu-item>  
150 - </Submenu> 3 + <Menu mode="horizontal" :theme="theme1" active-name="1" @on-select="s">
  4 + <Row type="flex" justify="center" align="middle">
  5 + <i-col span="12">
  6 + <Menu-item name="1">
  7 + <Icon type="ios-paper"></Icon>
  8 + 内容管理
  9 + </Menu-item>
  10 + <Menu-item name="2">
  11 + <Icon type="ios-people"></Icon>
  12 + 用户管理
  13 + </Menu-item>
151 <Submenu name="3"> 14 <Submenu name="3">
152 <template slot="title"> 15 <template slot="title">
153 <Icon type="stats-bars"></Icon> 16 <Icon type="stats-bars"></Icon>
@@ -163,14 +26,19 @@ @@ -163,14 +26,19 @@
163 <Menu-item name="3-5">流失用户</Menu-item> 26 <Menu-item name="3-5">流失用户</Menu-item>
164 </Menu-group> 27 </Menu-group>
165 </Submenu> 28 </Submenu>
166 - </Menu>  
167 - </i-col>  
168 - </Row> 29 + <Menu-item name="4">
  30 + <Icon type="settings"></Icon>
  31 + 综合设置
  32 + </Menu-item>
  33 + </i-col>
  34 + </Row>
  35 + </Menu>
169 <br> 36 <br>
170 <p>切换主题</p> 37 <p>切换主题</p>
171 - <Radio-group v-model="theme2"> 38 + <Radio-group v-model="theme1">
172 <Radio label="light"></Radio> 39 <Radio label="light"></Radio>
173 <Radio label="dark"></Radio> 40 <Radio label="dark"></Radio>
  41 + <Radio label="primary"></Radio>
174 </Radio-group> 42 </Radio-group>
175 </div> 43 </div>
176 </template> 44 </template>
@@ -178,13 +46,149 @@ @@ -178,13 +46,149 @@
178 export default { 46 export default {
179 data () { 47 data () {
180 return { 48 return {
181 - theme2: 'light' 49 + theme1: 'light'
182 } 50 }
183 }, 51 },
184 methods: { 52 methods: {
185 s (s) { 53 s (s) {
186 - console.log(s); 54 + console.log(s)
187 } 55 }
188 } 56 }
189 } 57 }
190 </script> 58 </script>
  59 +
  60 +
  61 +<!--<template>-->
  62 + <!--<div>-->
  63 + <!--<Row>-->
  64 + <!--<i-col span="8">-->
  65 + <!--<Menu :theme="theme2" @on-select="s">-->
  66 + <!--<Submenu name="1">-->
  67 + <!--<template slot="title">-->
  68 + <!--<Icon type="ios-paper"></Icon>-->
  69 + <!--内容管理-->
  70 + <!--</template>-->
  71 + <!--<Menu-item name="1-1">文章管理</Menu-item>-->
  72 + <!--<Menu-item name="1-2">评论管理</Menu-item>-->
  73 + <!--<Menu-item name="1-3">举报管理</Menu-item>-->
  74 + <!--</Submenu>-->
  75 + <!--<Submenu name="2">-->
  76 + <!--<template slot="title">-->
  77 + <!--<Icon type="ios-people"></Icon>-->
  78 + <!--用户管理-->
  79 + <!--</template>-->
  80 + <!--<Menu-item name="2-1">新增用户</Menu-item>-->
  81 + <!--<Menu-item name="2-2">活跃用户</Menu-item>-->
  82 + <!--</Submenu>-->
  83 + <!--<Submenu name="3">-->
  84 + <!--<template slot="title">-->
  85 + <!--<Icon type="stats-bars"></Icon>-->
  86 + <!--统计分析-->
  87 + <!--</template>-->
  88 + <!--<Menu-group title="使用">-->
  89 + <!--<Menu-item name="3-1">新增和启动</Menu-item>-->
  90 + <!--<Menu-item name="3-2">活跃分析</Menu-item>-->
  91 + <!--<Menu-item name="3-3">时段分析</Menu-item>-->
  92 + <!--</Menu-group>-->
  93 + <!--<Menu-group title="留存">-->
  94 + <!--<Menu-item name="3-4">用户留存</Menu-item>-->
  95 + <!--<Menu-item name="3-5">流失用户</Menu-item>-->
  96 + <!--</Menu-group>-->
  97 + <!--</Submenu>-->
  98 + <!--</Menu>-->
  99 + <!--</i-col>-->
  100 + <!--<i-col span="8">-->
  101 + <!--<Menu :theme="theme2" active-name="1-2" :open-names="['1']" @on-select="s">-->
  102 + <!--<Submenu name="1">-->
  103 + <!--<template slot="title">-->
  104 + <!--<Icon type="ios-paper"></Icon>-->
  105 + <!--内容管理-->
  106 + <!--</template>-->
  107 + <!--<Menu-item name="1-1">文章管理</Menu-item>-->
  108 + <!--<Menu-item name="1-2">评论管理</Menu-item>-->
  109 + <!--<Menu-item name="1-3">举报管理</Menu-item>-->
  110 + <!--</Submenu>-->
  111 + <!--<Submenu name="2">-->
  112 + <!--<template slot="title">-->
  113 + <!--<Icon type="ios-people"></Icon>-->
  114 + <!--用户管理-->
  115 + <!--</template>-->
  116 + <!--<Menu-item name="2-1">新增用户</Menu-item>-->
  117 + <!--<Menu-item name="2-2">活跃用户</Menu-item>-->
  118 + <!--</Submenu>-->
  119 + <!--<Submenu name="3">-->
  120 + <!--<template slot="title">-->
  121 + <!--<Icon type="stats-bars"></Icon>-->
  122 + <!--统计分析-->
  123 + <!--</template>-->
  124 + <!--<Menu-group title="使用">-->
  125 + <!--<Menu-item name="3-1">新增和启动</Menu-item>-->
  126 + <!--<Menu-item name="3-2">活跃分析</Menu-item>-->
  127 + <!--<Menu-item name="3-3">时段分析</Menu-item>-->
  128 + <!--</Menu-group>-->
  129 + <!--<Menu-group title="留存">-->
  130 + <!--<Menu-item name="3-4">用户留存</Menu-item>-->
  131 + <!--<Menu-item name="3-5">流失用户</Menu-item>-->
  132 + <!--</Menu-group>-->
  133 + <!--</Submenu>-->
  134 + <!--</Menu>-->
  135 + <!--</i-col>-->
  136 + <!--<i-col span="8">-->
  137 + <!--<Menu :theme="theme2" :open-names="['1']" accordion @on-select="s">-->
  138 + <!--<Submenu name="1">-->
  139 + <!--<template slot="title">-->
  140 + <!--<Icon type="ios-paper"></Icon>-->
  141 + <!--内容管理-->
  142 + <!--</template>-->
  143 + <!--<Menu-item name="1-1">文章管理</Menu-item>-->
  144 + <!--<Menu-item name="1-2">评论管理</Menu-item>-->
  145 + <!--<Menu-item name="1-3">举报管理</Menu-item>-->
  146 + <!--</Submenu>-->
  147 + <!--<Submenu name="2">-->
  148 + <!--<template slot="title">-->
  149 + <!--<Icon type="ios-people"></Icon>-->
  150 + <!--用户管理-->
  151 + <!--</template>-->
  152 + <!--<Menu-item name="2-1">新增用户</Menu-item>-->
  153 + <!--<Menu-item name="2-2">活跃用户</Menu-item>-->
  154 + <!--</Submenu>-->
  155 + <!--<Submenu name="3">-->
  156 + <!--<template slot="title">-->
  157 + <!--<Icon type="stats-bars"></Icon>-->
  158 + <!--统计分析-->
  159 + <!--</template>-->
  160 + <!--<Menu-group title="使用">-->
  161 + <!--<Menu-item name="3-1">新增和启动</Menu-item>-->
  162 + <!--<Menu-item name="3-2">活跃分析</Menu-item>-->
  163 + <!--<Menu-item name="3-3">时段分析</Menu-item>-->
  164 + <!--</Menu-group>-->
  165 + <!--<Menu-group title="留存">-->
  166 + <!--<Menu-item name="3-4">用户留存</Menu-item>-->
  167 + <!--<Menu-item name="3-5">流失用户</Menu-item>-->
  168 + <!--</Menu-group>-->
  169 + <!--</Submenu>-->
  170 + <!--</Menu>-->
  171 + <!--</i-col>-->
  172 + <!--</Row>-->
  173 + <!--<br>-->
  174 + <!--<p>切换主题</p>-->
  175 + <!--<Radio-group v-model="theme2">-->
  176 + <!--<Radio label="light"></Radio>-->
  177 + <!--<Radio label="dark"></Radio>-->
  178 + <!--</Radio-group>-->
  179 + <!--</div>-->
  180 +<!--</template>-->
  181 +<!--<script>-->
  182 + <!--export default {-->
  183 + <!--data () {-->
  184 + <!--return {-->
  185 + <!--theme2: 'light'-->
  186 + <!--}-->
  187 + <!--},-->
  188 + <!--methods: {-->
  189 + <!--s (s) {-->
  190 + <!--console.log(s);-->
  191 + <!--}-->
  192 + <!--}-->
  193 + <!--}-->
  194 +<!--</script>-->
examples/routers/modal.vue
1 <template> 1 <template>
2 <div> 2 <div>
3 - <i-button @click.native="instance('info')">消息</i-button>  
4 - <i-button @click.native="instance('success')">成功</i-button>  
5 - <i-button @click.native="instance('warning')">警告</i-button>  
6 - <i-button @click.native="instance('error')">错误</i-button> 3 + <i-button @click.native="modal2 = true">自定义页头和页脚</i-button>
  4 + <Modal v-model="modal2" width="360">
  5 + <p slot="header" style="color:#f60;text-align:center">
  6 + <Icon type="information-circled"></Icon>
  7 + <span>删除确认</span>
  8 + </p>
  9 + <div style="text-align:center">
  10 + <p>此任务删除后,下游 10 个任务将无法执行。</p>
  11 + <p>是否继续删除?</p>
  12 + </div>
  13 + <div slot="footer">
  14 + <i-button type="error" size="large" long :loading="modal_loading" @click.native="del">删除</i-button>
  15 + </div>
  16 + </Modal>
7 </div> 17 </div>
8 </template> 18 </template>
9 <script> 19 <script>
10 export default { 20 export default {
  21 + data () {
  22 + return {
  23 + modal2: false,
  24 + modal_loading: false,
  25 + modal3: false,
  26 + modal4: false,
  27 + modal5: false
  28 + }
  29 + },
11 methods: { 30 methods: {
12 - instance (type) {  
13 - const title = '对话框的标题';  
14 - const content = '<p>一些对话框内容</p><p>一些对话框内容</p>';  
15 - switch (type) {  
16 - case 'info':  
17 - this.$Modal.info({  
18 - title: title,  
19 - content: content  
20 - });  
21 - break;  
22 - case 'success':  
23 - this.$Modal.success({  
24 - title: title,  
25 - content: content  
26 - });  
27 - break;  
28 - case 'warning':  
29 - this.$Modal.warning({  
30 - title: title,  
31 - content: content  
32 - });  
33 - break;  
34 - case 'error':  
35 - this.$Modal.error({  
36 - title: title,  
37 - content: content  
38 - });  
39 - break;  
40 - } 31 + del () {
  32 + this.modal_loading = true;
  33 + setTimeout(() => {
  34 + this.modal_loading = false;
  35 + this.modal2 = false;
  36 + this.$Message.success('删除成功');
  37 + }, 2000);
41 } 38 }
42 } 39 }
43 } 40 }
44 </script> 41 </script>
45 -  
46 -  
47 -<!--<template>-->  
48 - <!--<div>-->  
49 - <!--<i-button @click.native="confirm">标准</i-button>-->  
50 - <!--<i-button @click.native="custom">自定义按钮文字</i-button>-->  
51 - <!--<i-button @click.native="async">异步关闭</i-button>-->  
52 - <!--</div>-->  
53 -<!--</template>-->  
54 -<!--<script>-->  
55 - <!--export default {-->  
56 - <!--methods: {-->  
57 - <!--confirm () {-->  
58 - <!--this.$Modal.confirm({-->  
59 - <!--title: '确认对话框标题',-->  
60 - <!--content: '<p>一些对话框内容</p><p>一些对话框内容</p>',-->  
61 - <!--onOk: () => {-->  
62 - <!--console.log('确定');-->  
63 -<!--// this.$Message.info('点击了确定');-->  
64 - <!--},-->  
65 - <!--onCancel: () => {-->  
66 - <!--console.log('取消');-->  
67 -<!--// this.$Message.info('点击了取消');-->  
68 - <!--}-->  
69 - <!--});-->  
70 - <!--},-->  
71 - <!--custom () {-->  
72 - <!--this.$Modal.confirm({-->  
73 - <!--title: '确认对话框标题',-->  
74 - <!--content: '<p>一些对话框内容</p><p>一些对话框内容</p>',-->  
75 - <!--okText: 'OK',-->  
76 - <!--cancelText: 'Cancel'-->  
77 - <!--});-->  
78 - <!--},-->  
79 - <!--async () {-->  
80 - <!--this.$Modal.confirm({-->  
81 - <!--title: '确认对话框标题',-->  
82 - <!--content: '<p>对话框将在 2秒 后关闭</p>',-->  
83 - <!--loading: true,-->  
84 - <!--onOk: () => {-->  
85 - <!--setTimeout(() => {-->  
86 - <!--this.$Modal.remove();-->  
87 -<!--// this.$Message.info('异步关闭了对话框');-->  
88 - <!--}, 2000);-->  
89 - <!--}-->  
90 - <!--});-->  
91 - <!--}-->  
92 - <!--}-->  
93 - <!--}-->  
94 -<!--</script>-->  
examples/routers/radio.vue
1 <template> 1 <template>
2 <div> 2 <div>
3 - <Radio v-model="single" @on-change="c">Radio</Radio>  
4 - <Radio-group v-model="phone" type="button" @on-change="c">  
5 - <Radio label="apple">  
6 - <Icon type="social-apple"></Icon>  
7 - <span>Apple</span>  
8 - </Radio>  
9 - <Radio label="android">  
10 - <Icon type="social-android"></Icon>  
11 - <span>Android</span>  
12 - </Radio>  
13 - <Radio label="windows">  
14 - <Icon type="social-windows"></Icon>  
15 - <span>Windows</span>  
16 - </Radio> 3 + <Radio-group v-model="phone">
  4 + <Row>
  5 + <i-col span="8">
  6 + <Radio label="apple">
  7 + <Icon type="social-apple"></Icon>
  8 + <span>Apple</span>
  9 + </Radio>
  10 + </i-col>
  11 + <i-col span="8">
  12 + <Radio label="android">
  13 + <Icon type="social-android"></Icon>
  14 + <span>Android</span>
  15 + </Radio>
  16 + </i-col>
  17 + <i-col span="8">
  18 + <Radio label="windows">
  19 + <Icon type="social-windows"></Icon>
  20 + <span>Windows</span>
  21 + </Radio>
  22 + </i-col>
  23 + </Row>
17 </Radio-group> 24 </Radio-group>
18 - <Radio-group v-model="animal">  
19 - <Radio label="金斑蝶"></Radio>  
20 - <Radio label="爪哇犀牛"></Radio>  
21 - <Radio label="印度黑羚"></Radio>  
22 - </Radio-group>  
23 - {{ phone }}  
24 - <div @click="phone = 'apple'">apple</div>  
25 - <div @click="single = true"> single</div>{{ single }}  
26 </div> 25 </div>
27 </template> 26 </template>
28 <script> 27 <script>
@@ -30,13 +29,7 @@ @@ -30,13 +29,7 @@
30 data () { 29 data () {
31 return { 30 return {
32 phone: 'apple', 31 phone: 'apple',
33 - animal: '爪哇犀牛',  
34 - single: false  
35 - }  
36 - },  
37 - methods: {  
38 - c (data) {  
39 - console.log(data) 32 + animal: '爪哇犀牛'
40 } 33 }
41 } 34 }
42 } 35 }
examples/routers/slider.vue
@@ -6,8 +6,8 @@ @@ -6,8 +6,8 @@
6 {{ value1 }}{{value2}} 6 {{ value1 }}{{value2}}
7 <div @click="value1 = 13">change value1</div> 7 <div @click="value1 = 13">change value1</div>
8 <br> 8 <br>
9 - <Slider :value="value9" :tip-format="format"></Slider>  
10 - <Slider :value="value10" :tip-format="hideFormat"></Slider> 9 + <Slider v-model="value9" :tip-format="format"></Slider>
  10 + <Slider v-model="value10" :tip-format="hideFormat"></Slider>
11 </div> 11 </div>
12 </template> 12 </template>
13 <script> 13 <script>
examples/routers/table.vue
1 -<!--<template>-->  
2 - <!--<Card>-->  
3 - <!--<Table border :content="self" :columns="columns7" :data="data6"></Table>-->  
4 - <!--</Card>-->  
5 -<!--</template>-->  
6 -<!--<script>-->  
7 - <!--export default {-->  
8 - <!--data () {-->  
9 - <!--return {-->  
10 - <!--self: this,-->  
11 - <!--columns7: [-->  
12 - <!--{-->  
13 - <!--title: '姓名',-->  
14 - <!--key: 'name',-->  
15 - <!--render (row, column, index) {-->  
16 - <!--return `<Icon type="person"></Icon> <strong>${row.name}</strong>`;-->  
17 - <!--}-->  
18 - <!--},-->  
19 - <!--{-->  
20 - <!--title: '年龄',-->  
21 - <!--key: 'age'-->  
22 - <!--},-->  
23 - <!--{-->  
24 - <!--title: '地址',-->  
25 - <!--key: 'address'-->  
26 - <!--},-->  
27 - <!--{-->  
28 - <!--title: '操作',-->  
29 - <!--key: 'action',-->  
30 - <!--width: 150,-->  
31 - <!--align: 'center',-->  
32 - <!--render (row, column, index) {-->  
33 - <!--return `<i-button type="primary" size="small" @click.native="show(${index})">查看</i-button> <i-button type="error" size="small" @click.native="remove(${index})">删除</i-button>`;-->  
34 - <!--}-->  
35 - <!--}-->  
36 - <!--],-->  
37 - <!--data6: [-->  
38 - <!--{-->  
39 - <!--name: '王小明',-->  
40 - <!--age: 18,-->  
41 - <!--address: '北京市朝阳区芍药居'-->  
42 - <!--},-->  
43 - <!--{-->  
44 - <!--name: '张小刚',-->  
45 - <!--age: 25,-->  
46 - <!--address: '北京市海淀区西二旗'-->  
47 - <!--},-->  
48 - <!--{-->  
49 - <!--name: '李小红',-->  
50 - <!--age: 30,-->  
51 - <!--address: '上海市浦东新区世纪大道'-->  
52 - <!--},-->  
53 - <!--{-->  
54 - <!--name: '周小伟',-->  
55 - <!--age: 26,-->  
56 - <!--address: '深圳市南山区深南大道'-->  
57 - <!--}-->  
58 - <!--]-->  
59 - <!--}-->  
60 - <!--},-->  
61 - <!--methods: {-->  
62 - <!--show (index) {-->  
63 - <!--console.log(`姓名:${this.data6[index].name}<br>年龄:${this.data6[index].age}<br>地址:${this.data6[index].address}`)-->  
64 - <!--},-->  
65 - <!--remove (index) {-->  
66 - <!--this.data6.splice(index, 1);-->  
67 - <!--}-->  
68 - <!--},-->  
69 - <!--mounted () {-->  
70 - <!--setTimeout(() => {-->  
71 -<!--// this.data6.splice(2, 1);-->  
72 - <!--}, 3000)-->  
73 - <!--}-->  
74 - <!--}-->  
75 -<!--</script>-->  
76 -  
77 -  
78 <template> 1 <template>
79 - <div>  
80 - <i-table border :columns="columns6" :data="data5"></i-table>  
81 - </div> 2 + <i-table border :content="self" :columns="columns7" :data="data6"></i-table>
82 </template> 3 </template>
83 <script> 4 <script>
84 export default { 5 export default {
85 data () { 6 data () {
86 return { 7 return {
87 - columns6: [  
88 - {  
89 - title: '日期',  
90 - key: 'date'  
91 - }, 8 + info: '123',
  9 + self: this,
  10 + columns7: [
92 { 11 {
93 title: '姓名', 12 title: '姓名',
94 - key: 'name' 13 + key: 'name',
  14 +// render (row, column, index) {
  15 +// return `<Icon type="person"></Icon> <strong>${row.name}</strong>`;
  16 +// }
95 }, 17 },
96 { 18 {
97 title: '年龄', 19 title: '年龄',
98 - key: 'age',  
99 - filters: [  
100 - {  
101 - label: '大于25岁',  
102 - value: 1  
103 - },  
104 - {  
105 - label: '小于25岁',  
106 - value: 2  
107 - }  
108 - ],  
109 - filterMultiple: false,  
110 - filterMethod (value, row) {  
111 - if (value === 1) {  
112 - return row.age > 25;  
113 - } else if (value === 2) {  
114 - return row.age < 25;  
115 - }  
116 - } 20 + key: 'age'
117 }, 21 },
118 { 22 {
119 title: '地址', 23 title: '地址',
120 - key: 'address',  
121 - filters: [  
122 - {  
123 - label: '北京',  
124 - value: '北京'  
125 - },  
126 - {  
127 - label: '上海',  
128 - value: '上海'  
129 - },  
130 - {  
131 - label: '深圳',  
132 - value: '深圳'  
133 - }  
134 - ],  
135 - filterMethod (value, row) {  
136 - return row.address.indexOf(value) > -1; 24 + key: 'address'
  25 + },
  26 + {
  27 + title: '操作',
  28 + key: 'action',
  29 + width: 150,
  30 + align: 'center',
  31 + render (row, column, index) {
  32 + return `<i-button type="primary" size="small" @click="show(${index})">{{ info }}查看</i-button> <i-button type="error" size="small" @click="remove(${index})">删除</i-button>`;
137 } 33 }
138 } 34 }
139 ], 35 ],
140 - data5: [ 36 + data6: [
141 { 37 {
142 name: '王小明', 38 name: '王小明',
143 age: 18, 39 age: 18,
144 - address: '北京市朝阳区芍药居',  
145 - date: '2016-10-03'  
146 - },  
147 - {  
148 - name: '张小刚',  
149 - age: 25,  
150 - address: '北京市海淀区西二旗',  
151 - date: '2016-10-01' 40 + address: '北京市朝阳区芍药居'
152 }, 41 },
153 - {  
154 - name: '李小红',  
155 - age: 30,  
156 - address: '上海市浦东新区世纪大道',  
157 - date: '2016-10-02'  
158 - },  
159 - {  
160 - name: '周小伟',  
161 - age: 26,  
162 - address: '深圳市南山区深南大道',  
163 - date: '2016-10-04'  
164 - } 42 +// {
  43 +// name: '张小刚',
  44 +// age: 25,
  45 +// address: '北京市海淀区西二旗'
  46 +// },
  47 +// {
  48 +// name: '李小红',
  49 +// age: 30,
  50 +// address: '上海市浦东新区世纪大道'
  51 +// },
  52 +// {
  53 +// name: '周小伟',
  54 +// age: 26,
  55 +// address: '深圳市南山区深南大道'
  56 +// }
165 ] 57 ]
166 } 58 }
  59 + },
  60 + computed: {
  61 + dddfff () {
  62 + return this.info
  63 + }
  64 + },
  65 + methods: {
  66 + show (index) {
  67 + this.$Modal.info({
  68 + title: '用户信息',
  69 + content: `姓名:${this.data6[index].name}<br>年龄:${this.data6[index].age}<br>地址:${this.data6[index].address}`
  70 + })
  71 + },
  72 + remove (index) {
  73 + this.data6.splice(index, 1);
  74 + }
  75 + },
  76 + mounted () {
  77 + setTimeout(() => {
  78 + this.info = '444';
  79 + }, 3000);
167 } 80 }
168 } 81 }
169 </script> 82 </script>
examples/routers/transfer.vue
1 -<!--<template>-->  
2 - <!--<div>-->  
3 - <!--<Transfer-->  
4 - <!--:data="data1"-->  
5 - <!--filterable-->  
6 - <!--:target-keys="targetKeys1"-->  
7 - <!--:render-format="render1"-->  
8 - <!--@on-change="handleChange1"></Transfer>-->  
9 - <!--</div>-->  
10 -<!--</template>-->  
11 -<!--<script>-->  
12 - <!--export default {-->  
13 - <!--data () {-->  
14 - <!--return {-->  
15 - <!--data1: this.getMockData(),-->  
16 - <!--targetKeys1: this.getTargetKeys()-->  
17 - <!--}-->  
18 - <!--},-->  
19 - <!--methods: {-->  
20 - <!--getMockData () {-->  
21 - <!--let mockData = [];-->  
22 - <!--for (let i = 1; i <= 20; i++) {-->  
23 - <!--mockData.push({-->  
24 - <!--key: i.toString(),-->  
25 - <!--label: '内容' + i,-->  
26 - <!--description: '内容' + i + '的描述信息',-->  
27 - <!--disabled: Math.random() * 3 < 1-->  
28 - <!--});-->  
29 - <!--}-->  
30 - <!--return mockData;-->  
31 - <!--},-->  
32 - <!--getTargetKeys () {-->  
33 - <!--return this.getMockData()-->  
34 - <!--.filter(() => Math.random() * 2 > 1)-->  
35 - <!--.map(item => item.key);-->  
36 - <!--},-->  
37 - <!--render1 (item) {-->  
38 - <!--return item.label;-->  
39 - <!--},-->  
40 - <!--handleChange1 (newTargetKeys, direction, moveKeys) {-->  
41 - <!--console.log(newTargetKeys);-->  
42 - <!--console.log(direction);-->  
43 - <!--console.log(moveKeys);-->  
44 - <!--this.targetKeys1 = newTargetKeys;-->  
45 - <!--}-->  
46 - <!--}-->  
47 - <!--}-->  
48 -<!--</script>-->  
49 -  
50 -  
51 <template> 1 <template>
52 - <Transfer  
53 - :data="data3"  
54 - :target-keys="targetKeys3"  
55 - :list-style="listStyle"  
56 - :render-format="render3"  
57 - :operations="['向左移动','向右移动']"  
58 - filterable  
59 - @on-change="handleChange3">  
60 - <div :style="{float: 'right', margin: '5px'}">  
61 - <Button type="ghost" size="small" @click.native="reloadMockData">刷新</Button>  
62 - </div>  
63 - </Transfer> 2 + <div>
  3 + <Transfer
  4 + :data="data1"
  5 + filterable
  6 + :target-keys="targetKeys1"
  7 + :render-format="render1"
  8 + @on-change="handleChange1"></Transfer>
  9 + </div>
64 </template> 10 </template>
65 <script> 11 <script>
66 export default { 12 export default {
67 data () { 13 data () {
68 return { 14 return {
69 - data3: this.getMockData(),  
70 - targetKeys3: this.getTargetKeys(),  
71 - listStyle: {  
72 - width: '250px',  
73 - height: '300px'  
74 - } 15 + data1: this.getMockData(),
  16 + targetKeys1: this.getTargetKeys()
75 } 17 }
76 }, 18 },
77 methods: { 19 methods: {
@@ -92,20 +34,78 @@ @@ -92,20 +34,78 @@
92 .filter(() => Math.random() * 2 > 1) 34 .filter(() => Math.random() * 2 > 1)
93 .map(item => item.key); 35 .map(item => item.key);
94 }, 36 },
95 - handleChange3 (newTargetKeys) {  
96 - this.targetKeys3 = newTargetKeys; 37 + render1 (item) {
  38 + return item.label;
97 }, 39 },
98 - render3 (item) {  
99 - return item.label + ' - ' + item.description;  
100 - },  
101 - reloadMockData () {  
102 - this.data3 = this.getMockData();  
103 - this.targetKeys3 = this.getTargetKeys(); 40 + handleChange1 (newTargetKeys, direction, moveKeys) {
  41 + console.log(newTargetKeys);
  42 + console.log(direction);
  43 + console.log(moveKeys);
  44 + this.targetKeys1 = newTargetKeys;
104 } 45 }
105 } 46 }
106 } 47 }
107 </script> 48 </script>
108 49
  50 +
  51 +<!--<template>-->
  52 + <!--<Transfer-->
  53 + <!--:data="data3"-->
  54 + <!--:target-keys="targetKeys3"-->
  55 + <!--:list-style="listStyle"-->
  56 + <!--:render-format="render3"-->
  57 + <!--:operations="['向左移动','向右移动']"-->
  58 + <!--filterable-->
  59 + <!--@on-change="handleChange3">-->
  60 + <!--<div :style="{float: 'right', margin: '5px'}">-->
  61 + <!--<Button type="ghost" size="small" @click.native="reloadMockData">刷新</Button>-->
  62 + <!--</div>-->
  63 + <!--</Transfer>-->
  64 +<!--</template>-->
  65 +<!--<script>-->
  66 + <!--export default {-->
  67 + <!--data () {-->
  68 + <!--return {-->
  69 + <!--data3: this.getMockData(),-->
  70 + <!--targetKeys3: this.getTargetKeys(),-->
  71 + <!--listStyle: {-->
  72 + <!--width: '250px',-->
  73 + <!--height: '300px'-->
  74 + <!--}-->
  75 + <!--}-->
  76 + <!--},-->
  77 + <!--methods: {-->
  78 + <!--getMockData () {-->
  79 + <!--let mockData = [];-->
  80 + <!--for (let i = 1; i <= 20; i++) {-->
  81 + <!--mockData.push({-->
  82 + <!--key: i.toString(),-->
  83 + <!--label: '内容' + i,-->
  84 + <!--description: '内容' + i + '的描述信息',-->
  85 + <!--disabled: Math.random() * 3 < 1-->
  86 + <!--});-->
  87 + <!--}-->
  88 + <!--return mockData;-->
  89 + <!--},-->
  90 + <!--getTargetKeys () {-->
  91 + <!--return this.getMockData()-->
  92 + <!--.filter(() => Math.random() * 2 > 1)-->
  93 + <!--.map(item => item.key);-->
  94 + <!--},-->
  95 + <!--handleChange3 (newTargetKeys) {-->
  96 + <!--this.targetKeys3 = newTargetKeys;-->
  97 + <!--},-->
  98 + <!--render3 (item) {-->
  99 + <!--return item.label + ' - ' + item.description;-->
  100 + <!--},-->
  101 + <!--reloadMockData () {-->
  102 + <!--this.data3 = this.getMockData();-->
  103 + <!--this.targetKeys3 = this.getTargetKeys();-->
  104 + <!--}-->
  105 + <!--}-->
  106 + <!--}-->
  107 +<!--</script>-->
  108 +
109 <!--<template>--> 109 <!--<template>-->
110 <!--<Transfer--> 110 <!--<Transfer-->
111 <!--:data="data4"--> 111 <!--:data="data4"-->
examples/routers/upload.vue
  1 +<!--<template>-->
  2 + <!--<div>-->
  3 + <!--<div class="demo-upload-list" v-for="item in uploadList">-->
  4 + <!--<template v-if="item.status === 'finished'">-->
  5 + <!--<img :src="item.url">-->
  6 + <!--<div class="demo-upload-list-cover">-->
  7 + <!--<Icon type="ios-eye-outline" @click.native="handleView(item.name)"></Icon>-->
  8 + <!--<Icon type="ios-trash-outline" @click.native="handleRemove(item)"></Icon>-->
  9 + <!--</div>-->
  10 + <!--</template>-->
  11 + <!--<template v-else>-->
  12 + <!--<i-progress v-if="item.showProgress" :percent="item.percentage" hide-info></i-progress>-->
  13 + <!--</template>-->
  14 + <!--</div>-->
  15 + <!--<Upload-->
  16 + <!--ref="upload"-->
  17 + <!--:show-upload-list="false"-->
  18 + <!--:default-file-list="defaultList"-->
  19 + <!--:on-success="handleSuccess"-->
  20 + <!--:format="['jpg','jpeg','png']"-->
  21 + <!--:max-size="2048"-->
  22 + <!--:on-format-error="handleFormatError"-->
  23 + <!--:on-exceeded-size="handleMaxSize"-->
  24 + <!--@on-progress="handleProgress"-->
  25 + <!--:before-upload="handleBeforeUpload"-->
  26 + <!--multiple-->
  27 + <!--type="drag"-->
  28 + <!--action="//jsonplaceholder.typicode.com/posts/"-->
  29 + <!--style="display: inline-block;width:58px;">-->
  30 + <!--<div style="width: 58px;height:58px;line-height: 58px;">-->
  31 + <!--<Icon type="camera" size="20"></Icon>-->
  32 + <!--</div>-->
  33 + <!--</Upload>-->
  34 + <!--{{ visible }}-->
  35 + <!--</div>-->
  36 +<!--</template>-->
  37 +<!--<script>-->
  38 + <!--export default {-->
  39 + <!--data () {-->
  40 + <!--return {-->
  41 + <!--defaultList: [-->
  42 + <!--{-->
  43 + <!--'name': 'a42bdcc1178e62b4694c830f028db5c0',-->
  44 + <!--'url': 'https://o5wwk8baw.qnssl.com/a42bdcc1178e62b4694c830f028db5c0/avatar'-->
  45 + <!--},-->
  46 + <!--{-->
  47 + <!--'name': 'bc7521e033abdd1e92222d733590f104',-->
  48 + <!--'url': 'https://o5wwk8baw.qnssl.com/bc7521e033abdd1e92222d733590f104/avatar'-->
  49 + <!--}-->
  50 + <!--],-->
  51 + <!--imgName: '',-->
  52 + <!--visible: false,-->
  53 + <!--uploadList: []-->
  54 + <!--}-->
  55 + <!--},-->
  56 + <!--computed: {-->
  57 +<!--// uploadList () {-->
  58 +<!--// return this.$refs.upload ? this.$refs.upload.fileList : [];-->
  59 +<!--// }-->
  60 + <!--},-->
  61 + <!--watch: {-->
  62 +
  63 + <!--},-->
  64 + <!--mounted () {-->
  65 + <!--this.uploadList = this.$refs.upload.fileList;-->
  66 +<!--// console.log(this.$refs.upload.fileList)-->
  67 + <!--},-->
  68 + <!--methods: {-->
  69 + <!--handleView (name) {-->
  70 + <!--this.imgName = name;-->
  71 + <!--this.visible = true;-->
  72 + <!--},-->
  73 + <!--handleRemove (file) {-->
  74 + <!--// 从 upload 实例删除数据-->
  75 + <!--const fileList = this.$refs.upload.fileList;-->
  76 + <!--this.$refs.upload.fileList.splice(fileList.indexOf(file), 1);-->
  77 + <!--},-->
  78 + <!--handleSuccess (res, file) {-->
  79 + <!--// 因为上传过程为实例,这里模拟添加 url-->
  80 + <!--file.url = 'https://o5wwk8baw.qnssl.com/7eb99afb9d5f317c912f08b5212fd69a/avatar';-->
  81 + <!--file.name = '7eb99afb9d5f317c912f08b5212fd69a';-->
  82 + <!--},-->
  83 + <!--handleFormatError (file) {-->
  84 + <!--this.$Notice.warning({-->
  85 + <!--title: '文件格式不正确',-->
  86 + <!--desc: '文件 ' + file.name + ' 格式不正确,请上传 jpg 或 png 格式的图片。'-->
  87 + <!--});-->
  88 + <!--},-->
  89 + <!--handleMaxSize (file) {-->
  90 + <!--this.$Notice.warning({-->
  91 + <!--title: '超出文件大小限制',-->
  92 + <!--desc: '文件 ' + file.name + ' 太大,不能超过 2M。'-->
  93 + <!--});-->
  94 + <!--},-->
  95 + <!--handleBeforeUpload () {-->
  96 + <!--const check = this.uploadList.length < 5;-->
  97 + <!--if (!check) {-->
  98 + <!--this.$Notice.warning({-->
  99 + <!--title: '最多只能上传 5 张图片。'-->
  100 + <!--});-->
  101 + <!--}-->
  102 + <!--return check;-->
  103 + <!--},-->
  104 + <!--handleProgress (s) {-->
  105 + <!--console.log(s)-->
  106 + <!--}-->
  107 + <!--}-->
  108 + <!--}-->
  109 +<!--</script>-->
  110 +<!--<style>-->
  111 + <!--.demo-upload-list{-->
  112 + <!--display: inline-block;-->
  113 + <!--width: 60px;-->
  114 + <!--height: 60px;-->
  115 + <!--text-align: center;-->
  116 + <!--line-height: 60px;-->
  117 + <!--border: 1px solid transparent;-->
  118 + <!--border-radius: 4px;-->
  119 + <!--overflow: hidden;-->
  120 + <!--background: #fff;-->
  121 + <!--position: relative;-->
  122 + <!--box-shadow: 0 1px 1px rgba(0,0,0,.2);-->
  123 + <!--margin-right: 4px;-->
  124 + <!--}-->
  125 + <!--.demo-upload-list img{-->
  126 + <!--width: 100%;-->
  127 + <!--height: 100%;-->
  128 + <!--}-->
  129 + <!--.demo-upload-list-cover{-->
  130 + <!--display: none;-->
  131 + <!--position: absolute;-->
  132 + <!--top: 0;-->
  133 + <!--bottom: 0;-->
  134 + <!--left: 0;-->
  135 + <!--right: 0;-->
  136 + <!--background: rgba(0,0,0,.6);-->
  137 + <!--}-->
  138 + <!--.demo-upload-list:hover .demo-upload-list-cover{-->
  139 + <!--display: block;-->
  140 + <!--}-->
  141 + <!--.demo-upload-list-cover i{-->
  142 + <!--color: #fff;-->
  143 + <!--font-size: 20px;-->
  144 + <!--cursor: pointer;-->
  145 + <!--margin: 0 2px;-->
  146 + <!--}-->
  147 +<!--</style>-->
  148 +
  149 +
1 <template> 150 <template>
2 <div> 151 <div>
3 - <div class="demo-upload-list" v-for="item in uploadList">  
4 - <template v-if="item.status === 'finished'">  
5 - <img :src="item.url">  
6 - <div class="demo-upload-list-cover">  
7 - <Icon type="ios-eye-outline" @click.native="handleView(item.name)"></Icon>  
8 - <Icon type="ios-trash-outline" @click.native="handleRemove(item)"></Icon>  
9 - </div>  
10 - </template>  
11 - <template v-else>  
12 - <i-progress v-if="item.showProgress" :percent="item.percentage" hide-info></i-progress>  
13 - </template>  
14 - </div>  
15 - <Upload  
16 - ref="upload"  
17 - :show-upload-list="false"  
18 - :default-file-list="defaultList"  
19 - :on-success="handleSuccess"  
20 - :format="['jpg','jpeg','png']"  
21 - :max-size="2048"  
22 - :on-format-error="handleFormatError"  
23 - :on-exceeded-size="handleMaxSize"  
24 - @on-progress="handleProgress"  
25 - :before-upload="handleBeforeUpload"  
26 - multiple  
27 - type="drag"  
28 - action="//jsonplaceholder.typicode.com/posts/"  
29 - style="display: inline-block;width:58px;">  
30 - <div style="width: 58px;height:58px;line-height: 58px;">  
31 - <Icon type="camera" size="20"></Icon>  
32 - </div> 152 + <Upload action="//jsonplaceholder.typicode.com/posts/" :before-upload="handleBeforeUpload" ref="file">
  153 + <i-button type="ghost" icon="ios-cloud-upload-outline">选择文件</i-button>
33 </Upload> 154 </Upload>
34 - {{ visible }} 155 + <i-button @click.native="handleUpload">上传</i-button>
35 </div> 156 </div>
36 </template> 157 </template>
37 <script> 158 <script>
38 export default { 159 export default {
39 data () { 160 data () {
40 return { 161 return {
41 - defaultList: [  
42 - {  
43 - 'name': 'a42bdcc1178e62b4694c830f028db5c0',  
44 - 'url': 'https://o5wwk8baw.qnssl.com/a42bdcc1178e62b4694c830f028db5c0/avatar'  
45 - },  
46 - {  
47 - 'name': 'bc7521e033abdd1e92222d733590f104',  
48 - 'url': 'https://o5wwk8baw.qnssl.com/bc7521e033abdd1e92222d733590f104/avatar'  
49 - }  
50 - ],  
51 - imgName: '',  
52 - visible: false,  
53 - uploadList: [] 162 + file: null
54 } 163 }
55 }, 164 },
56 - computed: {  
57 -// uploadList () {  
58 -// return this.$refs.upload ? this.$refs.upload.fileList : [];  
59 -// }  
60 - },  
61 - watch: {  
62 -  
63 - },  
64 - mounted () {  
65 - this.uploadList = this.$refs.upload.fileList;  
66 -// console.log(this.$refs.upload.fileList)  
67 - },  
68 methods: { 165 methods: {
69 - handleView (name) {  
70 - this.imgName = name;  
71 - this.visible = true;  
72 - },  
73 - handleRemove (file) {  
74 - // 从 upload 实例删除数据  
75 - const fileList = this.$refs.upload.fileList;  
76 - this.$refs.upload.fileList.splice(fileList.indexOf(file), 1);  
77 - },  
78 - handleSuccess (res, file) {  
79 - // 因为上传过程为实例,这里模拟添加 url  
80 - file.url = 'https://o5wwk8baw.qnssl.com/7eb99afb9d5f317c912f08b5212fd69a/avatar';  
81 - file.name = '7eb99afb9d5f317c912f08b5212fd69a'; 166 + handleBeforeUpload (file) {
  167 + this.file = file;
  168 + return false;
82 }, 169 },
83 - handleFormatError (file) {  
84 - this.$Notice.warning({  
85 - title: '文件格式不正确',  
86 - desc: '文件 ' + file.name + ' 格式不正确,请上传 jpg 或 png 格式的图片。'  
87 - });  
88 - },  
89 - handleMaxSize (file) {  
90 - this.$Notice.warning({  
91 - title: '超出文件大小限制',  
92 - desc: '文件 ' + file.name + ' 太大,不能超过 2M。'  
93 - });  
94 - },  
95 - handleBeforeUpload () {  
96 - const check = this.uploadList.length < 5;  
97 - if (!check) {  
98 - this.$Notice.warning({  
99 - title: '最多只能上传 5 张图片。'  
100 - });  
101 - }  
102 - return check;  
103 - },  
104 - handleProgress (s) {  
105 - console.log(s) 170 + handleUpload () {
  171 + this.$refs.file.post(this.file);
106 } 172 }
107 } 173 }
108 } 174 }
109 </script> 175 </script>
110 -<style>  
111 - .demo-upload-list{  
112 - display: inline-block;  
113 - width: 60px;  
114 - height: 60px;  
115 - text-align: center;  
116 - line-height: 60px;  
117 - border: 1px solid transparent;  
118 - border-radius: 4px;  
119 - overflow: hidden;  
120 - background: #fff;  
121 - position: relative;  
122 - box-shadow: 0 1px 1px rgba(0,0,0,.2);  
123 - margin-right: 4px;  
124 - }  
125 - .demo-upload-list img{  
126 - width: 100%;  
127 - height: 100%;  
128 - }  
129 - .demo-upload-list-cover{  
130 - display: none;  
131 - position: absolute;  
132 - top: 0;  
133 - bottom: 0;  
134 - left: 0;  
135 - right: 0;  
136 - background: rgba(0,0,0,.6);  
137 - }  
138 - .demo-upload-list:hover .demo-upload-list-cover{  
139 - display: block;  
140 - }  
141 - .demo-upload-list-cover i{  
142 - color: #fff;  
143 - font-size: 20px;  
144 - cursor: pointer;  
145 - margin: 0 2px;  
146 - }  
147 -</style>  
1 { 1 {
2 "name": "iview", 2 "name": "iview",
3 - "version": "2.0.0-rc.4", 3 + "version": "2.0.0-rc.5",
4 "title": "iView", 4 "title": "iView",
5 "description": "A high quality UI components Library with Vue.js", 5 "description": "A high quality UI components Library with Vue.js",
6 "homepage": "http://www.iviewui.com", 6 "homepage": "http://www.iviewui.com",
src/components/button/button.vue
1 <template> 1 <template>
2 - <button :type="htmlType" :class="classes" :disabled="disabled"> 2 + <button :type="htmlType" :class="classes" :disabled="disabled" @click="handleClick">
3 <Icon class="ivu-load-loop" type="load-c" v-if="loading"></Icon> 3 <Icon class="ivu-load-loop" type="load-c" v-if="loading"></Icon>
4 <Icon :type="icon" v-if="icon && !loading"></Icon> 4 <Icon :type="icon" v-if="icon && !loading"></Icon>
5 <span v-if="showSlot" ref="slot"><slot></slot></span> 5 <span v-if="showSlot" ref="slot"><slot></slot></span>
@@ -64,8 +64,13 @@ @@ -64,8 +64,13 @@
64 ]; 64 ];
65 } 65 }
66 }, 66 },
  67 + methods: {
  68 + handleClick (event) {
  69 + this.$emit('click', event);
  70 + }
  71 + },
67 mounted () { 72 mounted () {
68 - this.showSlot = this.$refs.slot.innerHTML.replace(/\n/g, '').replace(/<!--[\w\W\r\n]*?-->/gmi, '') !== ''; 73 + this.showSlot = this.$slots.default !== undefined;
69 } 74 }
70 }; 75 };
71 </script> 76 </script>
src/components/carousel/carousel-item.vue
@@ -25,11 +25,9 @@ @@ -25,11 +25,9 @@
25 } 25 }
26 }, 26 },
27 mounted () { 27 mounted () {
28 - // todo while  
29 this.$parent.slotChange(); 28 this.$parent.slotChange();
30 }, 29 },
31 beforeDestroy () { 30 beforeDestroy () {
32 - // todo while  
33 this.$parent.slotChange(); 31 this.$parent.slotChange();
34 } 32 }
35 }; 33 };
src/components/checkbox/checkbox-group.vue
@@ -4,6 +4,7 @@ @@ -4,6 +4,7 @@
4 </div> 4 </div>
5 </template> 5 </template>
6 <script> 6 <script>
  7 + import { findComponentsDownward } from '../../utils/assist';
7 import Emitter from '../../mixins/emitter'; 8 import Emitter from '../../mixins/emitter';
8 const prefixCls = 'ivu-checkbox-group'; 9 const prefixCls = 'ivu-checkbox-group';
9 10
@@ -20,7 +21,8 @@ @@ -20,7 +21,8 @@
20 }, 21 },
21 data () { 22 data () {
22 return { 23 return {
23 - currentValue: this.value 24 + currentValue: this.value,
  25 + childrens: []
24 }; 26 };
25 }, 27 },
26 computed: { 28 computed: {
@@ -34,15 +36,18 @@ @@ -34,15 +36,18 @@
34 methods: { 36 methods: {
35 updateModel (update) { 37 updateModel (update) {
36 const value = this.value; 38 const value = this.value;
  39 + this.childrens = findComponentsDownward(this, 'Checkbox');
37 40
38 - this.$children.forEach((child) => {  
39 - child.model = value; 41 + if (this.childrens) {
  42 + this.childrens.forEach(child => {
  43 + child.model = value;
40 44
41 - if (update) {  
42 - child.currentValue = value.indexOf(child.label) >= 0;  
43 - child.group = true;  
44 - }  
45 - }); 45 + if (update) {
  46 + child.currentValue = value.indexOf(child.label) >= 0;
  47 + child.group = true;
  48 + }
  49 + });
  50 + }
46 }, 51 },
47 change (data) { 52 change (data) {
48 this.currentValue = data; 53 this.currentValue = data;
src/components/checkbox/checkbox.vue
@@ -18,10 +18,11 @@ @@ -18,10 +18,11 @@
18 :checked="currentValue" 18 :checked="currentValue"
19 @change="change"> 19 @change="change">
20 </span> 20 </span>
21 - <slot v-if="showSlot"><span ref="slot">{{ label }}</span></slot> 21 + <slot><span v-if="showSlot">{{ label }}</span></slot>
22 </label> 22 </label>
23 </template> 23 </template>
24 <script> 24 <script>
  25 + import { findComponentUpward } from '../../utils/assist';
25 import Emitter from '../../mixins/emitter'; 26 import Emitter from '../../mixins/emitter';
26 27
27 const prefixCls = 'ivu-checkbox'; 28 const prefixCls = 'ivu-checkbox';
@@ -51,7 +52,8 @@ @@ -51,7 +52,8 @@
51 model: [], 52 model: [],
52 currentValue: this.value, 53 currentValue: this.value,
53 group: false, 54 group: false,
54 - showSlot: true 55 + showSlot: true,
  56 + parent: findComponentUpward(this, 'CheckboxGroup')
55 }; 57 };
56 }, 58 },
57 computed: { 59 computed: {
@@ -83,16 +85,11 @@ @@ -83,16 +85,11 @@
83 } 85 }
84 }, 86 },
85 mounted () { 87 mounted () {
86 - // todo 使用 while向上查找  
87 - if (this.$parent && this.$parent.$options.name === 'CheckboxGroup') this.group = true; 88 + this.parent = findComponentUpward(this, 'CheckboxGroup');
  89 + if (this.parent) this.group = true;
88 if (!this.group) { 90 if (!this.group) {
89 this.updateModel(); 91 this.updateModel();
90 -// if (this.$refs.slot && this.$refs.slot.innerHTML === '') {  
91 -// this.showSlot = false;  
92 -// }  
93 - if (this.$slots.default === undefined) {  
94 - this.showSlot = false;  
95 - } 92 + this.showSlot = this.$slots.default !== undefined;
96 } 93 }
97 }, 94 },
98 methods: { 95 methods: {
src/components/collapse/panel.vue
@@ -48,7 +48,6 @@ @@ -48,7 +48,6 @@
48 }, 48 },
49 methods: { 49 methods: {
50 toggle () { 50 toggle () {
51 - // todo while向上查找  
52 this.$parent.toggle({ 51 this.$parent.toggle({
53 name: this.name || this.index, 52 name: this.name || this.index,
54 isActive: this.isActive 53 isActive: this.isActive
src/components/input/input.vue
@@ -151,8 +151,8 @@ @@ -151,8 +151,8 @@
151 this.$emit('on-focus', event); 151 this.$emit('on-focus', event);
152 }, 152 },
153 handleBlur (event) { 153 handleBlur (event) {
154 - this.$emit('on-blur', event);  
155 - if (!findComponentUpward(this, ['DatePicker', 'TimePicker', 'Cascader'])) { 154 + this.$emit('on-blur', envent);
  155 + if (!findComponentUpward(this, ['DatePicker', 'TimePicker', 'Cascader', 'Search'])) {
156 this.dispatch('FormItem', 'on-form-blur', this.currentValue); 156 this.dispatch('FormItem', 'on-form-blur', this.currentValue);
157 } 157 }
158 }, 158 },
@@ -171,7 +171,7 @@ @@ -171,7 +171,7 @@
171 this.resizeTextarea(); 171 this.resizeTextarea();
172 }); 172 });
173 this.currentValue = value; 173 this.currentValue = value;
174 - if (!findComponentUpward(this, ['DatePicker', 'TimePicker', 'Cascader'])) { 174 + if (!findComponentUpward(this, ['DatePicker', 'TimePicker', 'Cascader', 'Search'])) {
175 this.dispatch('FormItem', 'on-form-change', value); 175 this.dispatch('FormItem', 'on-form-change', value);
176 } 176 }
177 }, 177 },
src/components/menu/menu.vue
@@ -2,7 +2,7 @@ @@ -2,7 +2,7 @@
2 <ul :class="classes" :style="styles"><slot></slot></ul> 2 <ul :class="classes" :style="styles"><slot></slot></ul>
3 </template> 3 </template>
4 <script> 4 <script>
5 - import { oneOf } from '../../utils/assist'; 5 + import { oneOf, findComponentsDownward } from '../../utils/assist';
6 import Emitter from '../../mixins/emitter'; 6 import Emitter from '../../mixins/emitter';
7 7
8 const prefixCls = 'ivu-menu'; 8 const prefixCls = 'ivu-menu';
@@ -84,11 +84,13 @@ @@ -84,11 +84,13 @@
84 } 84 }
85 }, 85 },
86 updateOpened () { 86 updateOpened () {
87 - this.$children.forEach(item => {  
88 - if (item.$options.name === 'Submenu') { 87 + const items = findComponentsDownward(this, 'Submenu');
  88 +
  89 + if (items.length) {
  90 + items.forEach(item => {
89 if (this.openNames.indexOf(item.name) > -1) item.opened = true; 91 if (this.openNames.indexOf(item.name) > -1) item.opened = true;
90 - }  
91 - }); 92 + });
  93 + }
92 } 94 }
93 }, 95 },
94 mounted () { 96 mounted () {
src/components/menu/submenu.vue
@@ -17,7 +17,7 @@ @@ -17,7 +17,7 @@
17 <script> 17 <script>
18 import Drop from '../select/dropdown.vue'; 18 import Drop from '../select/dropdown.vue';
19 import Icon from '../icon/icon.vue'; 19 import Icon from '../icon/icon.vue';
20 - import { getStyle } from '../../utils/assist'; 20 + import { getStyle, findComponentUpward } from '../../utils/assist';
21 import Emitter from '../../mixins/emitter'; 21 import Emitter from '../../mixins/emitter';
22 22
23 const prefixCls = 'ivu-menu'; 23 const prefixCls = 'ivu-menu';
@@ -41,7 +41,8 @@ @@ -41,7 +41,8 @@
41 prefixCls: prefixCls, 41 prefixCls: prefixCls,
42 active: false, 42 active: false,
43 opened: false, 43 opened: false,
44 - dropWidth: parseFloat(getStyle(this.$el, 'width')) 44 + dropWidth: parseFloat(getStyle(this.$el, 'width')),
  45 + parent: findComponentUpward(this, 'Menu')
45 }; 46 };
46 }, 47 },
47 computed: { 48 computed: {
@@ -56,12 +57,10 @@ @@ -56,12 +57,10 @@
56 ]; 57 ];
57 }, 58 },
58 mode () { 59 mode () {
59 - // todo while  
60 - return this.$parent.mode; 60 + return this.parent.mode;
61 }, 61 },
62 accordion () { 62 accordion () {
63 - // todo while  
64 - return this.$parent.accordion; 63 + return this.parent.accordion;
65 }, 64 },
66 dropStyle () { 65 dropStyle () {
67 let style = {}; 66 let style = {};
@@ -77,8 +76,7 @@ @@ -77,8 +76,7 @@
77 76
78 clearTimeout(this.timeout); 77 clearTimeout(this.timeout);
79 this.timeout = setTimeout(() => { 78 this.timeout = setTimeout(() => {
80 - // todo while  
81 - this.$parent.updateOpenKeys(this.name); 79 + this.parent.updateOpenKeys(this.name);
82 this.opened = true; 80 this.opened = true;
83 }, 250); 81 }, 250);
84 }, 82 },
@@ -88,8 +86,7 @@ @@ -88,8 +86,7 @@
88 86
89 clearTimeout(this.timeout); 87 clearTimeout(this.timeout);
90 this.timeout = setTimeout(() => { 88 this.timeout = setTimeout(() => {
91 - // todo while  
92 - this.$parent.updateOpenKeys(this.name); 89 + this.parent.updateOpenKeys(this.name);
93 this.opened = false; 90 this.opened = false;
94 }, 150); 91 }, 150);
95 }, 92 },
@@ -98,14 +95,12 @@ @@ -98,14 +95,12 @@
98 if (this.mode === 'horizontal') return; 95 if (this.mode === 'horizontal') return;
99 const opened = this.opened; 96 const opened = this.opened;
100 if (this.accordion) { 97 if (this.accordion) {
101 - // todo while  
102 - this.$parent.$children.forEach(item => { 98 + this.parent.$children.forEach(item => {
103 if (item.$options.name === 'Submenu') item.opened = false; 99 if (item.$options.name === 'Submenu') item.opened = false;
104 }); 100 });
105 } 101 }
106 this.opened = !opened; 102 this.opened = !opened;
107 - // todo while  
108 - this.$parent.updateOpenKeys(this.name); 103 + this.parent.updateOpenKeys(this.name);
109 } 104 }
110 }, 105 },
111 watch: { 106 watch: {
src/components/modal/modal.vue
@@ -198,7 +198,7 @@ @@ -198,7 +198,7 @@
198 198
199 let showHead = true; 199 let showHead = true;
200 200
201 - if (this.$slots.head === undefined && !this.title) { 201 + if (this.$slots.header === undefined && !this.title) {
202 showHead = false; 202 showHead = false;
203 } 203 }
204 204
src/components/radio/radio-group.vue
@@ -4,7 +4,7 @@ @@ -4,7 +4,7 @@
4 </div> 4 </div>
5 </template> 5 </template>
6 <script> 6 <script>
7 - import { oneOf } from '../../utils/assist'; 7 + import { oneOf, findComponentsDownward } from '../../utils/assist';
8 import Emitter from '../../mixins/emitter'; 8 import Emitter from '../../mixins/emitter';
9 9
10 const prefixCls = 'ivu-radio-group'; 10 const prefixCls = 'ivu-radio-group';
@@ -34,7 +34,8 @@ @@ -34,7 +34,8 @@
34 }, 34 },
35 data () { 35 data () {
36 return { 36 return {
37 - currentValue: this.value 37 + currentValue: this.value,
  38 + childrens: []
38 }; 39 };
39 }, 40 },
40 computed: { 41 computed: {
@@ -55,10 +56,14 @@ @@ -55,10 +56,14 @@
55 methods: { 56 methods: {
56 updateValue () { 57 updateValue () {
57 const value = this.value; 58 const value = this.value;
58 - this.$children.forEach((child) => {  
59 - child.currentValue = value == child.label;  
60 - child.group = true;  
61 - }); 59 + this.childrens = findComponentsDownward(this, 'Radio');
  60 +
  61 + if (this.childrens) {
  62 + this.childrens.forEach(child => {
  63 + child.currentValue = value == child.label;
  64 + child.group = true;
  65 + });
  66 + }
62 }, 67 },
63 change (data) { 68 change (data) {
64 this.currentValue = data.value; 69 this.currentValue = data.value;
src/components/radio/radio.vue
@@ -12,6 +12,7 @@ @@ -12,6 +12,7 @@
12 </label> 12 </label>
13 </template> 13 </template>
14 <script> 14 <script>
  15 + import { findComponentUpward } from '../../utils/assist';
15 import Emitter from '../../mixins/emitter'; 16 import Emitter from '../../mixins/emitter';
16 17
17 const prefixCls = 'ivu-radio'; 18 const prefixCls = 'ivu-radio';
@@ -35,7 +36,8 @@ @@ -35,7 +36,8 @@
35 data () { 36 data () {
36 return { 37 return {
37 currentValue: this.value, 38 currentValue: this.value,
38 - group: false 39 + group: false,
  40 + parent: findComponentUpward(this, 'RadioGroup')
39 }; 41 };
40 }, 42 },
41 computed: { 43 computed: {
@@ -66,8 +68,7 @@ @@ -66,8 +68,7 @@
66 } 68 }
67 }, 69 },
68 mounted () { 70 mounted () {
69 - // todo 使用 while向上查找  
70 - if (this.$parent && this.$parent.$options.name === 'RadioGroup') this.group = true; 71 + if (this.parent) this.group = true;
71 if (!this.group) { 72 if (!this.group) {
72 this.updateValue(); 73 this.updateValue();
73 } 74 }
@@ -83,7 +84,7 @@ @@ -83,7 +84,7 @@
83 this.$emit('input', checked); 84 this.$emit('input', checked);
84 85
85 if (this.group && this.label) { 86 if (this.group && this.label) {
86 - this.$parent.change({ 87 + this.parent.change({
87 value: this.label, 88 value: this.label,
88 checked: this.value 89 checked: this.value
89 }); 90 });
src/components/table/cell.vue
@@ -52,36 +52,32 @@ @@ -52,36 +52,32 @@
52 const template = this.column.render(this.row, this.column, this.index); 52 const template = this.column.render(this.row, this.column, this.index);
53 const cell = document.createElement('div'); 53 const cell = document.createElement('div');
54 cell.innerHTML = template; 54 cell.innerHTML = template;
55 -// const _oldParentChildLen = $parent.$children.length;  
56 -// const _newParentChildLen = $parent.$children.length;  
57 -// if (_oldParentChildLen !== _newParentChildLen) { // if render normal html node, do not tag  
58 -// this.uid = $parent.$children[$parent.$children.length - 1]._uid; // tag it, and delete when data or columns update  
59 -// } 55 +
60 this.$el.innerHTML = ''; 56 this.$el.innerHTML = '';
61 let methods = {}; 57 let methods = {};
62 Object.keys($parent).forEach(key => { 58 Object.keys($parent).forEach(key => {
63 - const func = $parent[`${key}`]; 59 + const func = $parent[key];
64 if (typeof(func) === 'function' && func.name === 'boundFn') { 60 if (typeof(func) === 'function' && func.name === 'boundFn') {
65 - methods[`${key}`] = func; 61 + methods[key] = func;
66 } 62 }
67 }); 63 });
68 const res = Vue.compile(cell.outerHTML); 64 const res = Vue.compile(cell.outerHTML);
  65 + // todo 临时解决方案
69 const component = new Vue({ 66 const component = new Vue({
70 render: res.render, 67 render: res.render,
71 staticRenderFns: res.staticRenderFns, 68 staticRenderFns: res.staticRenderFns,
72 - methods: methods 69 + methods: methods,
  70 + data () {
  71 + return $parent._data;
  72 + }
73 }); 73 });
  74 +
74 const Cell = component.$mount(); 75 const Cell = component.$mount();
75 this.$refs.cell.appendChild(Cell.$el); 76 this.$refs.cell.appendChild(Cell.$el);
76 } 77 }
77 }, 78 },
78 destroy () { 79 destroy () {
79 - const $parent = this.content;  
80 - for (let i = 0; i < $parent.$children.length; i++) {  
81 - if ($parent.$children[i]._uid === this.uid) {  
82 - $parent.$children[i].$destroy();  
83 - }  
84 - } 80 +
85 }, 81 },
86 toggleSelect () { 82 toggleSelect () {
87 this.$parent.$parent.toggleSelect(this.index); 83 this.$parent.$parent.toggleSelect(this.index);
src/components/table/table.vue
@@ -173,7 +173,8 @@ @@ -173,7 +173,8 @@
173 bodyHeight: 0, 173 bodyHeight: 0,
174 bodyRealHeight: 0, 174 bodyRealHeight: 0,
175 scrollBarWidth: getScrollBarSize(), 175 scrollBarWidth: getScrollBarSize(),
176 - currentContent: this.content 176 + currentContent: this.content,
  177 + cloneData: deepCopy(this.data) // when Cell has a button to delete row data, clickCurrentRow will throw an error, so clone a data
177 }; 178 };
178 }, 179 },
179 computed: { 180 computed: {
@@ -357,16 +358,16 @@ @@ -357,16 +358,16 @@
357 } 358 }
358 } 359 }
359 this.objData[_index]._isHighlight = true; 360 this.objData[_index]._isHighlight = true;
360 - const oldData = oldIndex < 0 ? null : JSON.parse(JSON.stringify(this.data[oldIndex]));  
361 - this.$emit('on-current-change', JSON.parse(JSON.stringify(this.data[_index])), oldData); 361 + const oldData = oldIndex < 0 ? null : JSON.parse(JSON.stringify(this.cloneData[oldIndex]));
  362 + this.$emit('on-current-change', JSON.parse(JSON.stringify(this.cloneData[_index])), oldData);
362 }, 363 },
363 clickCurrentRow (_index) { 364 clickCurrentRow (_index) {
364 this.highlightCurrentRow (_index); 365 this.highlightCurrentRow (_index);
365 - this.$emit('on-row-click', JSON.parse(JSON.stringify(this.data[_index]))); 366 + this.$emit('on-row-click', JSON.parse(JSON.stringify(this.cloneData[_index])));
366 }, 367 },
367 dblclickCurrentRow (_index) { 368 dblclickCurrentRow (_index) {
368 this.highlightCurrentRow (_index); 369 this.highlightCurrentRow (_index);
369 - this.$emit('on-row-dblclick', JSON.parse(JSON.stringify(this.data[_index]))); 370 + this.$emit('on-row-dblclick', JSON.parse(JSON.stringify(this.cloneData[_index])));
370 }, 371 },
371 getSelection () { 372 getSelection () {
372 let selectionIndexes = []; 373 let selectionIndexes = [];
@@ -663,6 +664,10 @@ @@ -663,6 +664,10 @@
663 this.objData = this.makeObjData(); 664 this.objData = this.makeObjData();
664 this.rebuildData = this.makeDataWithSortAndFilter(); 665 this.rebuildData = this.makeDataWithSortAndFilter();
665 this.handleResize(); 666 this.handleResize();
  667 + // here will trigger before clickCurrentRow, so use async
  668 + setTimeout(() => {
  669 + this.cloneData = deepCopy(this.data);
  670 + }, 0);
666 }, 671 },
667 deep: true 672 deep: true
668 }, 673 },
src/components/transfer/search.vue
@@ -44,14 +44,5 @@ @@ -44,14 +44,5 @@
44 this.$emit('on-query-clear'); 44 this.$emit('on-query-clear');
45 } 45 }
46 } 46 }
47 - // todo 事件  
48 -// events: {  
49 -// 'on-form-blur' () {  
50 -// return false;  
51 -// },  
52 -// 'on-form-change' () {  
53 -// return false;  
54 -// }  
55 -// }  
56 }; 47 };
57 </script> 48 </script>
src/components/transfer/transfer.vue
@@ -67,8 +67,8 @@ @@ -67,8 +67,8 @@
67 return cloned; 67 return cloned;
68 } 68 }
69 69
70 - const vNodes = this.$slots.default;  
71 - const clonedVNodes = vNodes.map(vnode => cloneVNode(vnode)); 70 + const vNodes = this.$slots.default === undefined ? [] : this.$slots.default;
  71 + const clonedVNodes = this.$slots.default === undefined ? [] : vNodes.map(vnode => cloneVNode(vnode));
72 72
73 return createElement('div', { 73 return createElement('div', {
74 'class': this.classes 74 'class': this.classes
@@ -120,7 +120,7 @@ @@ -120,7 +120,7 @@
120 on: { 120 on: {
121 'on-checked-keys-change': this.handleRightCheckedKeysChange 121 'on-checked-keys-change': this.handleRightCheckedKeysChange
122 } 122 }
123 - }, clonedVNodes), 123 + }, clonedVNodes)
124 ]); 124 ]);
125 }, 125 },
126 126
src/styles/components/input.less
@@ -58,6 +58,14 @@ @@ -58,6 +58,14 @@
58 .@{input-prefix-cls}-group{ 58 .@{input-prefix-cls}-group{
59 .input-group-error; 59 .input-group-error;
60 } 60 }
  61 + .@{transfer-prefix-cls} {
  62 + .@{input-prefix-cls} {
  63 + .input;
  64 + &-icon{
  65 + color: @subsidiary-color;
  66 + }
  67 + }
  68 + }
61 } 69 }
62 .@{form-item-prefix-cls}-validating{ 70 .@{form-item-prefix-cls}-validating{
63 .@{input-prefix-cls}{ 71 .@{input-prefix-cls}{
src/utils/assist.js
@@ -185,9 +185,9 @@ function findComponentUpward (content, componentName, componentNames) { @@ -185,9 +185,9 @@ function findComponentUpward (content, componentName, componentNames) {
185 } 185 }
186 export {findComponentUpward}; 186 export {findComponentUpward};
187 187
188 -// Find components downward 188 +// Find component downward
189 function findComponentDownward (content, componentName) { 189 function findComponentDownward (content, componentName) {
190 - let childrens = content.$children; 190 + const childrens = content.$children;
191 let children = null; 191 let children = null;
192 192
193 if (childrens.length) { 193 if (childrens.length) {
@@ -212,4 +212,24 @@ function findComponentDownward (content, componentName) { @@ -212,4 +212,24 @@ function findComponentDownward (content, componentName) {
212 } 212 }
213 return children; 213 return children;
214 } 214 }
215 -export {findComponentDownward};  
216 \ No newline at end of file 215 \ No newline at end of file
  216 +export {findComponentDownward};
  217 +
  218 +// Find components downward
  219 +function findComponentsDownward (content, componentName, components = []) {
  220 + const childrens = content.$children;
  221 +
  222 + if (childrens.length) {
  223 + childrens.forEach(child => {
  224 + const name = child.$options.name;
  225 + const childs = child.$children;
  226 +
  227 + if (name === componentName) components.push(child);
  228 + if (childs.length) {
  229 + const findChilds = findComponentsDownward(child, componentName, components);
  230 + if (findChilds) components.concat(findChilds);
  231 + }
  232 + });
  233 + }
  234 + return components;
  235 +}
  236 +export {findComponentsDownward};
217 \ No newline at end of file 237 \ No newline at end of file