Columns in Vue Kanban component
16 Mar 202319 minutes to read
The Kanban columns represent the each stage of the process. The column definitions are used as the dataSource schema in the Kanban. The Kanban operations such as drag-and-drop, swimlane, and toggle columns are performed based on column definitions.
Single-key mapping
Kanban columns are categorized by mapping the key from the datasource using the keyField
property. The corresponding value in the datasource is mapped inside the columns keyField
. Based on this categorization, Kanban columns are split on this board.
The
keyField
property is mandatory to render the columns in the Kanban board.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings">
<e-columns>
<e-column headerText="To Do" keyField="Open"></e-column>
<e-column headerText="In Progress" keyField="InProgress"></e-column>
<e-column headerText="Testing" keyField="Testing"></e-column>
<e-column headerText="Done" keyField="Close"></e-column>
</e-columns>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
}
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
</style>
Multi-key mapping
Kanban board allows to render a single column by mapping multiple keys using keyField
property. In below sample, specified the multiple keys(Open, Validate) to a single column.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings">
<e-columns>
<e-column headerText="To Do" keyField="Open, Validate"></e-column>
<e-column headerText="In Progress" keyField="InProgress"></e-column>
<e-column headerText="Testing" keyField="Testing"></e-column>
<e-column headerText="Done" keyField="Close"></e-column>
</e-columns>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
}
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
</style>
Header text
You can provide the column header text of Kanban columns using the headerText
property. If you have not specified any header text, it will render the header without any text.
Header template
You can customize the column header with any HTML or CSS element using the template
property as shown in the following code.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings" cssClass="kanban-header-template">
<e-columns>
<e-column headerText="To Do" keyField="Open" :template="columnsTemplate"></e-column>
<e-column headerText="In Progress" keyField="InProgress" :template="columnsTemplate"></e-column>
<e-column headerText="Testing" keyField="Testing" :template="columnsTemplate"></e-column>
<e-column headerText="Done" keyField="Close" :template="columnsTemplate"></e-column>
</e-columns>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
},
columnsTemplate: function () {
return {
template: Vue.component('columnsTemplate', {
template: `<div class="header-template-wrap">
<div :class="getClassName(data)"></div>
<div class="header-text"></div>
</div>`,
data() {
return {
data: {}
};
},
methods: {
getClassName: function(data) {
return "header-icon e-icons " + data.keyField;
}
}
})
}
},
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
.kanban-header-template.e-kanban .header-template-wrap {
display: inline-flex;
font-size: 15px;
font-weight: 400;
}
.kanban-header-template.e-kanban .header-template-wrap .header-icon {
font-family: 'Kanban priority icons';
margin-top: 3px;
width: 10%;
}
.kanban-header-template.e-kanban .header-template-wrap .header-text {
margin-left: 15px;
}
.e-kanban.e-rtl .header-template-wrap .header-text {
margin-right: 15px;
}
.kanban-header-template.e-kanban .card-header {
padding-left: 12px;
}
.kanban-header-template.e-kanban .Open::before {
content: '\e700';
color: #0251cc;
font-size: 16px;
}
.kanban-header-template.e-kanban .InProgress::before {
content: '\e703';
color: #ea9713;
font-size: 16px;
}
.kanban-header-template.e-kanban .Review::before {
content: '\e701';
color: #8e4399;
font-size: 16px;
}
.kanban-header-template.e-kanban .Close::before {
content: '\e702';
color: #63ba3c;
font-size: 16px;
}
@font-face {
font-family: 'Kanban priority icons';
src:
url(data:application/x-font-ttf;charset=utf-8;base64,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) format('truetype');
font-weight: normal;
font-style: normal;
}
[class^="sf-icon-"],
[class*=" sf-icon-"] {
font-family: 'Kanban priority icons' !important;
speak: none;
font-size: 55px;
font-style: normal;
font-weight: normal;
font-variant: normal;
text-transform: none;
line-height: 1;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
</style>
Toggle columns
Kanban allows to expand or collapse its columns using allowToggle
inside the columns
property. When enable the property, it will render the expand or collapse icon to the column header.
By default, collapsed column width is set to
50px
.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings">
<e-columns>
<e-column headerText="To Do" keyField="Open" allowToggle="true"></e-column>
<e-column headerText="In Progress" keyField="InProgress" allowToggle="true"></e-column>
<e-column headerText="Testing" keyField="Testing" allowToggle="true"></e-column>
<e-column headerText="Done" keyField="Close" allowToggle="true"></e-column>
</e-columns>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
}
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
</style>
Initially collapsed column
By default, all columns are on expanded state when loading the Kanban board initially. But, you can render the columns with collapsed state using the isExpanded
property.
The
isExpanded
property only works when enabling theallowToggle
property on particular column.
In the following example, the backlog column is collapsed on initialization of Kanban board.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings">
<e-columns>
<e-column headerText="To Do" keyField="Open" allowToggle="true" isExpanded="false"></e-column>
<e-column headerText="In Progress" keyField="InProgress" allowToggle="true"></e-column>
<e-column headerText="Testing" keyField="Testing" allowToggle="true" isExpanded="false"></e-column>
<e-column headerText="Done" keyField="Close" allowToggle="true"></e-column>
</e-columns>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
}
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
</style>
Stacked headers
Stacked headers are the additional headers to column header that will group the similar columns.
Define the grouping of columns key value to the keyFields
property and provide the custom header text name to grouped columns using the text
property, which is placed inside the stackedHeaders
property.
In the following code, the kanban columns ‘InProgress, Review’ are grouped under ‘Development Phase’ category.
<template>
<div id="app">
<ejs-kanban id="kanban" keyField="Status" :dataSource="kanbanData"
:cardSettings="cardSettings">
<e-columns>
<e-column headerText="Open" keyField="Open"></e-column>
<e-column headerText="In Progress" keyField="InProgress"></e-column>
<e-column headerText="In Review" keyField="Review"></e-column>
<e-column headerText="Completed" keyField="Close"></e-column>
</e-columns>
<e-stackedHeaders>
<e-stackedHeader text= 'To Do' keyFields= 'Open'></e-stackedHeader>
<e-stackedHeader text= 'Development Phase' keyFields= 'InProgress, Review'></e-stackedHeader>
<e-stackedHeader text= 'Done' keyFields= 'Close'></e-stackedHeader>
</e-stackedHeaders>
</ejs-kanban>
</div>
</template>
<script>
import Vue from "vue";
import { KanbanPlugin } from '@syncfusion/ej2-vue-kanban';
import { extend } from '@syncfusion/ej2-base';
import { kanbanData } from './datasource.js';
Vue.use(KanbanPlugin);
export default {
data: function() {
return {
kanbanData: extend([], kanbanData, null, true),
cardSettings: {
contentField: "Summary",
headerField: "Id"
}
};
},
}
</script>
<style>
@import '../node_modules/@syncfusion/ej2-base/styles/material.css';
@import '../node_modules/@syncfusion/ej2-buttons/styles/material.css';
@import '../node_modules/@syncfusion/ej2-layouts/styles/material.css';
@import '../node_modules/@syncfusion/ej2-dropdowns/styles/material.css';
@import '../node_modules/@syncfusion/ej2-inputs/styles/material.css';
@import '../node_modules/@syncfusion/ej2-navigations/styles/material.css';
@import '../node_modules/@syncfusion/ej2-popups/styles/material.css';
@import '../node_modules/@syncfusion/ej2-vue-kanban/styles/material.css';
</style>