support Tabs

support Tabs
This commit is contained in:
梁灏 2017-03-03 13:38:46 +08:00
parent b2d29401f7
commit 30510c3d9e
8 changed files with 98 additions and 38 deletions

View file

@ -25,4 +25,6 @@ class 改为了 className
### Tree ### Tree
废弃 data改为 value使用 v-modelkey 更名为 name不能再 template 的prop 上使用 this 废弃 data改为 value使用 v-modelkey 更名为 name不能再 template 的prop 上使用 this
### Circle ### Circle
改名为 iCircle 改名为 iCircle
### Tabs
废弃 activeKey改用 value使用 v-modelkey 更名为 name

View file

@ -50,7 +50,7 @@
- [x] Carousel - [x] Carousel
- [x] Tree - [x] Tree
- [ ] Menu - [ ] Menu
- [ ] Tabs - [x] Tabs
- [ ] Dropdown - [ ] Dropdown
- [ ] Page - [ ] Page
- [ ] Breadcrumb - [ ] Breadcrumb

View file

@ -7,7 +7,7 @@
export default { export default {
name: 'TabPane', name: 'TabPane',
props: { props: {
key: { name: {
type: String type: String
}, },
label: { label: {
@ -29,7 +29,8 @@
data () { data () {
return { return {
prefixCls: prefixCls, prefixCls: prefixCls,
show: true show: true,
currentName: this.name
}; };
}, },
methods: { methods: {
@ -38,6 +39,10 @@
} }
}, },
watch: { watch: {
name (val) {
this.currentName = val;
this.updateNav();
},
label () { label () {
this.updateNav(); this.updateNav();
}, },
@ -48,7 +53,7 @@
this.updateNav(); this.updateNav();
} }
}, },
ready () { mounted () {
this.updateNav(); this.updateNav();
} }
}; };

View file

@ -4,12 +4,12 @@
<div :class="[prefixCls + '-nav-container']"> <div :class="[prefixCls + '-nav-container']">
<div :class="[prefixCls + '-nav-wrap']"> <div :class="[prefixCls + '-nav-wrap']">
<div :class="[prefixCls + '-nav-scroll']"> <div :class="[prefixCls + '-nav-scroll']">
<div :class="[prefixCls + '-nav']" v-el:nav> <div :class="[prefixCls + '-nav']" ref="nav">
<div :class="barClasses" :style="barStyle"></div> <div :class="barClasses" :style="barStyle"></div>
<div :class="tabCls(item)" v-for="item in navList" @click="handleChange($index)"> <div :class="tabCls(item)" v-for="(item, index) in navList" @click="handleChange(index)">
<Icon v-if="item.icon !== ''" :type="item.icon"></Icon> <Icon v-if="item.icon !== ''" :type="item.icon"></Icon>
{{ item.label }} {{ item.label }}
<Icon v-if="showClose(item)" type="ios-close-empty" @click.stop="handleRemove($index)"></Icon> <Icon v-if="showClose(item)" type="ios-close-empty" @click.native.stop="handleRemove(index)"></Icon>
</div> </div>
</div> </div>
</div> </div>
@ -26,9 +26,10 @@
const prefixCls = 'ivu-tabs'; const prefixCls = 'ivu-tabs';
export default { export default {
name: 'Tabs',
components: { Icon }, components: { Icon },
props: { props: {
activeKey: { value: {
type: [String, Number] type: [String, Number]
}, },
type: { type: {
@ -57,7 +58,8 @@
prefixCls: prefixCls, prefixCls: prefixCls,
navList: [], navList: [],
barWidth: 0, barWidth: 0,
barOffset: 0 barOffset: 0,
activeKey: this.value
}; };
}, },
computed: { computed: {
@ -88,7 +90,7 @@
]; ];
}, },
contentStyle () { contentStyle () {
const x = this.navList.findIndex((nav) => nav.key === this.activeKey); const x = this.navList.findIndex((nav) => nav.name === this.activeKey);
const p = x === 0 ? '0%' : `-${x}00%`; const p = x === 0 ? '0%' : `-${x}00%`;
let style = {}; let style = {};
@ -124,13 +126,13 @@
this.navList.push({ this.navList.push({
label: pane.label, label: pane.label,
icon: pane.icon || '', icon: pane.icon || '',
key: pane.key || index, name: pane.currentName || index,
disabled: pane.disabled, disabled: pane.disabled,
closable: pane.closable closable: pane.closable
}); });
if (!pane.key) pane.key = index; if (!pane.currentName) pane.currentName = index;
if (index === 0) { if (index === 0) {
if (!this.activeKey) this.activeKey = pane.key || index; if (!this.activeKey) this.activeKey = pane.currentName || index;
} }
}); });
this.updateStatus(); this.updateStatus();
@ -138,8 +140,8 @@
}, },
updateBar () { updateBar () {
this.$nextTick(() => { this.$nextTick(() => {
const index = this.navList.findIndex((nav) => nav.key === this.activeKey); const index = this.navList.findIndex((nav) => nav.name === this.activeKey);
const prevTabs = this.$els.nav.querySelectorAll(`.${prefixCls}-tab`); const prevTabs = this.$refs.nav.querySelectorAll(`.${prefixCls}-tab`);
const tab = prevTabs[index]; const tab = prevTabs[index];
this.barWidth = parseFloat(getStyle(tab, 'width')); this.barWidth = parseFloat(getStyle(tab, 'width'));
@ -158,29 +160,30 @@
}, },
updateStatus () { updateStatus () {
const tabs = this.getTabs(); const tabs = this.getTabs();
tabs.forEach(tab => tab.show = (tab.key === this.activeKey) || this.animated); tabs.forEach(tab => tab.show = (tab.currentName === this.activeKey) || this.animated);
}, },
tabCls (item) { tabCls (item) {
return [ return [
`${prefixCls}-tab`, `${prefixCls}-tab`,
{ {
[`${prefixCls}-tab-disabled`]: item.disabled, [`${prefixCls}-tab-disabled`]: item.disabled,
[`${prefixCls}-tab-active`]: item.key === this.activeKey [`${prefixCls}-tab-active`]: item.name === this.activeKey
} }
]; ];
}, },
handleChange (index) { handleChange (index) {
const nav = this.navList[index]; const nav = this.navList[index];
if (nav.disabled) return; if (nav.disabled) return;
this.activeKey = nav.key; this.activeKey = nav.name;
this.$emit('on-click', nav.key); this.$emit('input', nav.name);
this.$emit('on-click', nav.name);
}, },
handleRemove (index) { handleRemove (index) {
const tabs = this.getTabs(); const tabs = this.getTabs();
const tab = tabs[index]; const tab = tabs[index];
tab.$destroy(true); tab.$destroy(true);
if (tab.key === this.activeKey) { if (tab.currentName === this.activeKey) {
const newTabs = this.getTabs(); const newTabs = this.getTabs();
let activeKey = -1; let activeKey = -1;
@ -189,16 +192,16 @@
const rightNoDisabledTabs = tabs.filter((item, itemIndex) => !item.disabled && itemIndex > index); const rightNoDisabledTabs = tabs.filter((item, itemIndex) => !item.disabled && itemIndex > index);
if (rightNoDisabledTabs.length) { if (rightNoDisabledTabs.length) {
activeKey = rightNoDisabledTabs[0].key; activeKey = rightNoDisabledTabs[0].currentName;
} else if (leftNoDisabledTabs.length) { } else if (leftNoDisabledTabs.length) {
activeKey = leftNoDisabledTabs[leftNoDisabledTabs.length - 1].key; activeKey = leftNoDisabledTabs[leftNoDisabledTabs.length - 1].currentName;
} else { } else {
activeKey = newTabs[0].key; activeKey = newTabs[0].currentName;
} }
} }
this.activeKey = activeKey; this.activeKey = activeKey;
} }
this.$emit('on-tab-remove', tab.key); this.$emit('on-tab-remove', tab.currentName);
this.updateNav(); this.updateNav();
}, },
showClose (item) { showClose (item) {
@ -214,6 +217,9 @@
} }
}, },
watch: { watch: {
value (val) {
this.activeKey = val;
},
activeKey () { activeKey () {
this.updateBar(); this.updateBar();
this.updateStatus(); this.updateStatus();

View file

@ -34,7 +34,7 @@ import Rate from './components/rate';
import Steps from './components/steps'; import Steps from './components/steps';
import Switch from './components/switch'; import Switch from './components/switch';
// import Table from './components/table'; // import Table from './components/table';
// import Tabs from './components/tabs'; import Tabs from './components/tabs';
import Tag from './components/tag'; import Tag from './components/tag';
import Timeline from './components/timeline'; import Timeline from './components/timeline';
// import TimePicker from './components/time-picker'; // import TimePicker from './components/time-picker';
@ -100,8 +100,8 @@ const iview = {
Steps, Steps,
iSwitch: Switch, iSwitch: Switch,
// iTable: Table, // iTable: Table,
// Tabs: Tabs, Tabs: Tabs,
// TabPane: Tabs.Pane, TabPane: Tabs.Pane,
Tag, Tag,
Timeline, Timeline,
TimelineItem: Timeline.Item, TimelineItem: Timeline.Item,

View file

@ -34,6 +34,7 @@ li + li { border-left: solid 1px #bbb; padding-left: 10px; margin-left: 10px; }
<li><router-link to="/tree">Tree</router-link></li> <li><router-link to="/tree">Tree</router-link></li>
<li><router-link to="/rate">Rate</router-link></li> <li><router-link to="/rate">Rate</router-link></li>
<li><router-link to="/circle">Circle</router-link></li> <li><router-link to="/circle">Circle</router-link></li>
<li><router-link to="/tabs">Tabs</router-link></li>
</ul> </ul>
</nav> </nav>
<router-view></router-view> <router-view></router-view>

View file

@ -100,6 +100,10 @@ const router = new VueRouter({
{ {
path: '/circle', path: '/circle',
component: require('./routers/circle.vue') component: require('./routers/circle.vue')
},
{
path: '/tabs',
component: require('./routers/tabs.vue')
} }
] ]
}); });

View file

@ -1,14 +1,56 @@
<style>
.demo-tabs-style1 > .ivu-tabs-card > .ivu-tabs-content {
height: 120px;
margin-top: -16px;
}
.demo-tabs-style1 > .ivu-tabs-card > .ivu-tabs-content > .ivu-tabs-tabpane {
background: #fff;
padding: 16px;
}
.demo-tabs-style1 > .ivu-tabs.ivu-tabs-card > .ivu-tabs-bar .ivu-tabs-tab {
border-color: transparent;
}
.demo-tabs-style1 > .ivu-tabs-card > .ivu-tabs-bar .ivu-tabs-tab-active {
border-color: #fff;
}
.demo-tabs-style2 > .ivu-tabs.ivu-tabs-card > .ivu-tabs-bar .ivu-tabs-tab{
border-radius: 0;
background: #fff;
}
.demo-tabs-style2 > .ivu-tabs.ivu-tabs-card > .ivu-tabs-bar .ivu-tabs-tab-active{
border-top: 1px solid #3399ff;
}
.demo-tabs-style2 > .ivu-tabs.ivu-tabs-card > .ivu-tabs-bar .ivu-tabs-tab-active:before{
content: '';
display: block;
width: 100%;
height: 1px;
background: #3399ff;
position: absolute;
top: 0;
left: 0;
}
</style>
<template> <template>
<Tabs active-key="key1"> <Row :gutter="32">
<Tab-pane label="标签一" key="key1">标签一的内容</Tab-pane> <i-col span="12" class="demo-tabs-style1" style="background: #e3e8ee;padding:16px;">
<Tab-pane label="标签二" key="key2">标签二的内容</Tab-pane> <Tabs type="card">
<Tab-pane label="标签三" key="key3">标签三的内容</Tab-pane> <Tab-pane label="标签一">标签一的内容</Tab-pane>
</Tabs> <Tab-pane label="标签二">标签二的内容</Tab-pane>
<Tabs type="card" > <Tab-pane label="标签三">标签三的内容</Tab-pane>
<Tab-pane label="标签一">标签一的内容</Tab-pane> </Tabs>
<Tab-pane label="标签二" :closable="true">标签二的内容</Tab-pane> </i-col>
<Tab-pane label="标签三">标签三的内容</Tab-pane> <i-col span="12" class="demo-tabs-style2">
</Tabs> <Tabs type="card">
<Tab-pane label="标签一">标签一的内容</Tab-pane>
<Tab-pane label="标签二">标签二的内容</Tab-pane>
<Tab-pane label="标签三">标签三的内容</Tab-pane>
</Tabs>
</i-col>
</Row>
</template> </template>
<script> <script>
export default { export default {