GanttChart
TkGanttChart is a display-only Gantt chart component with expandable tasks, configurable view types (weekly, monthly, quarterly, yearly), two-layer headers, indicators, weekend/holiday highlighting, and customisable tooltips / task bars.
- React
- Vue
- Angular
import { TkGanttChart } from '@takeoff-ui/react'
import { TkGanttChart } from '@takeoff-ui/vue'
import { TkGanttChart } from '@takeoff-ui/angular'
Playground
Preview
Generated Code
<TkGanttChart tasks={[{"id":"1","name":"Research","startDate":"2026-04-01","endDate":"2026-04-10","progress":100},{"id":"2","name":"Design","startDate":"2026-04-08","endDate":"2026-04-18","progress":75},{"id":"3","name":"Development","startDate":"2026-04-15","endDate":"2026-05-05","progress":40},{"id":"4","name":"Testing","startDate":"2026-05-01","endDate":"2026-05-12","progress":0},{"id":"5","name":"Deployment","startDate":"2026-05-10","endDate":"2026-05-15","progress":0}]} secondaryHeaderMode="days" weekStartDay="1" rowHeight="40" panelWidth="320" highlightWeekends showTodayIndicator/><TkGanttChart :tasks="[{"id":"1","name":"Research","startDate":"2026-04-01","endDate":"2026-04-10","progress":100},{"id":"2","name":"Design","startDate":"2026-04-08","endDate":"2026-04-18","progress":75},{"id":"3","name":"Development","startDate":"2026-04-15","endDate":"2026-05-05","progress":40},{"id":"4","name":"Testing","startDate":"2026-05-01","endDate":"2026-05-12","progress":0},{"id":"5","name":"Deployment","startDate":"2026-05-10","endDate":"2026-05-15","progress":0}]" secondaryHeaderMode="days" weekStartDay="1" rowHeight="40" panelWidth="320" :highlightWeekends.prop="true" :showTodayIndicator.prop="true"/><tk-gantt-chart [tasks]="[{"id":"1","name":"Research","startDate":"2026-04-01","endDate":"2026-04-10","progress":100},{"id":"2","name":"Design","startDate":"2026-04-08","endDate":"2026-04-18","progress":75},{"id":"3","name":"Development","startDate":"2026-04-15","endDate":"2026-05-05","progress":40},{"id":"4","name":"Testing","startDate":"2026-05-01","endDate":"2026-05-12","progress":0},{"id":"5","name":"Deployment","startDate":"2026-05-10","endDate":"2026-05-15","progress":0}]" secondaryHeaderMode="days" weekStartDay="1" rowHeight="40" panelWidth="320" [highlightWeekends]="true" [showTodayIndicator]="true"/>Controls
Basic
A basic Gantt chart with simple tasks showing name, start/end dates, and progress.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
{ id: '4', name: 'Testing', startDate: '2026-05-01', endDate: '2026-05-12', progress: 0 },
{ id: '5', name: 'Deployment', startDate: '2026-05-10', endDate: '2026-05-15', progress: 0 },
];
<TkGanttChart tasks={tasks} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
{ id: '4', name: 'Testing', startDate: '2026-05-01', endDate: '2026-05-12', progress: 0 },
{ id: '5', name: 'Deployment', startDate: '2026-05-10', endDate: '2026-05-15', progress: 0 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" />
</template>
<tk-gantt-chart [tasks]="tasks"></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
{ id: '4', name: 'Testing', startDate: '2026-05-01', endDate: '2026-05-12', progress: 0 },
{ id: '5', name: 'Deployment', startDate: '2026-05-10', endDate: '2026-05-15', progress: 0 },
];
View Type
The viewType prop controls the timeline zoom level. Available options are
weekly, monthly, quarterly, and yearly. When not set, the component
auto-fits based on the task date range.
- React
- Vue
- Angular
const [viewType, setViewType] = useState('monthly');
const tasks = [
{ id: '1', name: 'Sprint Planning', startDate: '2026-04-01', endDate: '2026-04-03', progress: 100 },
{ id: '2', name: 'Development', startDate: '2026-04-04', endDate: '2026-05-15', progress: 60 },
{ id: '3', name: 'QA Testing', startDate: '2026-05-10', endDate: '2026-06-10', progress: 20 },
{ id: '4', name: 'Release', startDate: '2026-06-01', endDate: '2026-07-01', progress: 0 },
];
<TkGanttChart tasks={tasks} viewType="weekly" />
<TkGanttChart tasks={tasks} viewType="monthly" />
<TkGanttChart tasks={tasks} viewType="quarterly" />
<TkGanttChart tasks={tasks} viewType="yearly" />
<script setup>
import { ref } from 'vue'
import { TkGanttChart } from '@takeoff-ui/vue'
const viewType = ref('monthly')
const tasks = [
{ id: '1', name: 'Sprint Planning', startDate: '2026-04-01', endDate: '2026-04-03', progress: 100 },
{ id: '2', name: 'Development', startDate: '2026-04-04', endDate: '2026-05-15', progress: 60 },
{ id: '3', name: 'QA Testing', startDate: '2026-05-10', endDate: '2026-06-10', progress: 20 },
{ id: '4', name: 'Release', startDate: '2026-06-01', endDate: '2026-07-01', progress: 0 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" :view-type="viewType" />
</template>
<tk-gantt-chart [tasks]="tasks" view-type="monthly"></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Sprint Planning', startDate: '2026-04-01', endDate: '2026-04-03', progress: 100 },
{ id: '2', name: 'Development', startDate: '2026-04-04', endDate: '2026-05-15', progress: 60 },
{ id: '3', name: 'QA Testing', startDate: '2026-05-10', endDate: '2026-06-10', progress: 20 },
{ id: '4', name: 'Release', startDate: '2026-06-01', endDate: '2026-07-01', progress: 0 },
];
Nested Tasks
Tasks can have nested children to create expandable sub-task hierarchies.
Click the expand button to toggle child task visibility.
- React
- Vue
- Angular
const tasks = [
{
id: '1',
name: 'Backend',
startDate: '2026-04-01',
endDate: '2026-05-10',
progress: 60,
children: [
{ id: '1-1', name: 'API Design', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '1-2', name: 'Database Schema', startDate: '2026-04-08', endDate: '2026-04-18', progress: 80 },
{ id: '1-3', name: 'Implementation', startDate: '2026-04-15', endDate: '2026-05-10', progress: 30 },
],
},
{
id: '2',
name: 'Frontend',
startDate: '2026-04-10',
endDate: '2026-05-15',
progress: 40,
children: [
{ id: '2-1', name: 'Wireframes', startDate: '2026-04-10', endDate: '2026-04-18', progress: 100 },
{ id: '2-2', name: 'UI Development', startDate: '2026-04-18', endDate: '2026-05-08', progress: 50 },
{ id: '2-3', name: 'Integration', startDate: '2026-05-05', endDate: '2026-05-15', progress: 0 },
],
},
{ id: '3', name: 'Deployment', startDate: '2026-05-12', endDate: '2026-05-20', progress: 0 },
];
<TkGanttChart tasks={tasks} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{
id: '1',
name: 'Backend',
startDate: '2026-04-01',
endDate: '2026-05-10',
progress: 60,
children: [
{ id: '1-1', name: 'API Design', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '1-2', name: 'Database Schema', startDate: '2026-04-08', endDate: '2026-04-18', progress: 80 },
{ id: '1-3', name: 'Implementation', startDate: '2026-04-15', endDate: '2026-05-10', progress: 30 },
],
},
{
id: '2',
name: 'Frontend',
startDate: '2026-04-10',
endDate: '2026-05-15',
progress: 40,
children: [
{ id: '2-1', name: 'Wireframes', startDate: '2026-04-10', endDate: '2026-04-18', progress: 100 },
{ id: '2-2', name: 'UI Development', startDate: '2026-04-18', endDate: '2026-05-08', progress: 50 },
{ id: '2-3', name: 'Integration', startDate: '2026-05-05', endDate: '2026-05-15', progress: 0 },
],
},
{ id: '3', name: 'Deployment', startDate: '2026-05-12', endDate: '2026-05-20', progress: 0 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" />
</template>
<tk-gantt-chart [tasks]="tasks"></tk-gantt-chart>
// component.ts
tasks = [
{
id: '1',
name: 'Backend',
startDate: '2026-04-01',
endDate: '2026-05-10',
progress: 60,
children: [
{ id: '1-1', name: 'API Design', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '1-2', name: 'Database Schema', startDate: '2026-04-08', endDate: '2026-04-18', progress: 80 },
{ id: '1-3', name: 'Implementation', startDate: '2026-04-15', endDate: '2026-05-10', progress: 30 },
],
},
{
id: '2',
name: 'Frontend',
startDate: '2026-04-10',
endDate: '2026-05-15',
progress: 40,
children: [
{ id: '2-1', name: 'Wireframes', startDate: '2026-04-10', endDate: '2026-04-18', progress: 100 },
{ id: '2-2', name: 'UI Development', startDate: '2026-04-18', endDate: '2026-05-08', progress: 50 },
{ id: '2-3', name: 'Integration', startDate: '2026-05-05', endDate: '2026-05-15', progress: 0 },
],
},
{ id: '3', name: 'Deployment', startDate: '2026-05-12', endDate: '2026-05-20', progress: 0 },
];
Segments
A task can display multiple time segments on the same row using the segments
property. Each segment has its own startDate, endDate, label, and
progress.
- React
- Vue
- Angular
const tasks = [
{
id: '1',
name: 'Design Phase',
startDate: '2026-04-01',
endDate: '2026-04-30',
segments: [
{ startDate: '2026-04-01', endDate: '2026-04-10', label: 'Research', progress: 100 },
{ startDate: '2026-04-15', endDate: '2026-04-25', label: 'Prototyping', progress: 60 },
],
},
{
id: '2',
name: 'Development',
startDate: '2026-04-10',
endDate: '2026-05-20',
segments: [
{ startDate: '2026-04-10', endDate: '2026-04-22', label: 'Sprint 1', progress: 100 },
{ startDate: '2026-04-25', endDate: '2026-05-08', label: 'Sprint 2', progress: 40 },
{ startDate: '2026-05-10', endDate: '2026-05-20', label: 'Sprint 3', progress: 0 },
],
},
{ id: '3', name: 'Release', startDate: '2026-05-18', endDate: '2026-05-25', progress: 0 },
];
<TkGanttChart tasks={tasks} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{
id: '1',
name: 'Design Phase',
startDate: '2026-04-01',
endDate: '2026-04-30',
segments: [
{ startDate: '2026-04-01', endDate: '2026-04-10', label: 'Research', progress: 100 },
{ startDate: '2026-04-15', endDate: '2026-04-25', label: 'Prototyping', progress: 60 },
],
},
{
id: '2',
name: 'Development',
startDate: '2026-04-10',
endDate: '2026-05-20',
segments: [
{ startDate: '2026-04-10', endDate: '2026-04-22', label: 'Sprint 1', progress: 100 },
{ startDate: '2026-04-25', endDate: '2026-05-08', label: 'Sprint 2', progress: 40 },
{ startDate: '2026-05-10', endDate: '2026-05-20', label: 'Sprint 3', progress: 0 },
],
},
{ id: '3', name: 'Release', startDate: '2026-05-18', endDate: '2026-05-25', progress: 0 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" />
</template>
<tk-gantt-chart [tasks]="tasks"></tk-gantt-chart>
// component.ts
tasks = [
{
id: '1',
name: 'Design Phase',
startDate: '2026-04-01',
endDate: '2026-04-30',
segments: [
{ startDate: '2026-04-01', endDate: '2026-04-10', label: 'Research', progress: 100 },
{ startDate: '2026-04-15', endDate: '2026-04-25', label: 'Prototyping', progress: 60 },
],
},
{
id: '2',
name: 'Development',
startDate: '2026-04-10',
endDate: '2026-05-20',
segments: [
{ startDate: '2026-04-10', endDate: '2026-04-22', label: 'Sprint 1', progress: 100 },
{ startDate: '2026-04-25', endDate: '2026-05-08', label: 'Sprint 2', progress: 40 },
{ startDate: '2026-05-10', endDate: '2026-05-20', label: 'Sprint 3', progress: 0 },
],
},
{ id: '3', name: 'Release', startDate: '2026-05-18', endDate: '2026-05-25', progress: 0 },
];
Indicators
Use the indicators prop to render vertical lines on the timeline for important
dates like milestones or deadlines. The showTodayIndicator prop automatically
adds a today marker.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-12', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-10', endDate: '2026-04-22', progress: 50 },
{ id: '3', name: 'Development', startDate: '2026-04-20', endDate: '2026-05-10', progress: 20 },
];
const indicators = [
{ date: '2026-04-07', label: 'Kickoff', color: '#2563eb', lineStyle: 'solid' },
{ date: '2026-04-25', label: 'Milestone', color: '#f59e0b', lineStyle: 'dashed' },
{ date: '2026-05-05', label: 'Deadline', color: '#ef4444', lineStyle: 'solid' },
];
<TkGanttChart tasks={tasks} indicators={indicators} showTodayIndicator={true} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-12', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-10', endDate: '2026-04-22', progress: 50 },
{ id: '3', name: 'Development', startDate: '2026-04-20', endDate: '2026-05-10', progress: 20 },
]
const indicators = [
{ date: '2026-04-07', label: 'Kickoff', color: '#2563eb', lineStyle: 'solid' },
{ date: '2026-04-25', label: 'Milestone', color: '#f59e0b', lineStyle: 'dashed' },
{ date: '2026-05-05', label: 'Deadline', color: '#ef4444', lineStyle: 'solid' },
]
</script>
<template>
<TkGanttChart :tasks="tasks" :indicators="indicators" :show-today-indicator="true" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[indicators]="indicators"
[show-today-indicator]="true"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-12', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-10', endDate: '2026-04-22', progress: 50 },
{ id: '3', name: 'Development', startDate: '2026-04-20', endDate: '2026-05-10', progress: 20 },
];
indicators = [
{ date: '2026-04-07', label: 'Kickoff', color: '#2563eb', lineStyle: 'solid' },
{ date: '2026-04-25', label: 'Milestone', color: '#f59e0b', lineStyle: 'dashed' },
{ date: '2026-05-05', label: 'Deadline', color: '#ef4444', lineStyle: 'solid' },
];
Holidays
The holidays prop highlights specific dates on the timeline. Combined with
highlightWeekends, non-working days are visually distinguished.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Sprint 1', startDate: '2026-04-01', endDate: '2026-04-15', progress: 80 },
{ id: '2', name: 'Sprint 2', startDate: '2026-04-16', endDate: '2026-04-30', progress: 30 },
];
const holidays = [
{ date: '2026-04-10', label: 'Company Holiday' },
{ date: '2026-04-23', label: 'National Holiday' },
];
<TkGanttChart tasks={tasks} holidays={holidays} highlightWeekends={true} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Sprint 1', startDate: '2026-04-01', endDate: '2026-04-15', progress: 80 },
{ id: '2', name: 'Sprint 2', startDate: '2026-04-16', endDate: '2026-04-30', progress: 30 },
]
const holidays = [
{ date: '2026-04-10', label: 'Company Holiday' },
{ date: '2026-04-23', label: 'National Holiday' },
]
</script>
<template>
<TkGanttChart :tasks="tasks" :holidays="holidays" :highlight-weekends="true" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[holidays]="holidays"
[highlight-weekends]="true"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Sprint 1', startDate: '2026-04-01', endDate: '2026-04-15', progress: 80 },
{ id: '2', name: 'Sprint 2', startDate: '2026-04-16', endDate: '2026-04-30', progress: 30 },
];
holidays = [
{ date: '2026-04-10', label: 'Company Holiday' },
{ date: '2026-04-23', label: 'National Holiday' },
];
Columns
Customise the left-side panel columns using the columns prop. Each column
definition includes field, header, optional width, and an optional html
render function.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
];
const columns = [
{ field: 'name', header: 'Task', width: '160px' },
{ field: 'startDate', header: 'Start', width: '100px' },
{ field: 'endDate', header: 'End', width: '100px' },
{
field: 'progress',
header: 'Progress',
width: '80px',
html: (task) => `<strong>${task.progress ?? 0}%</strong>`,
},
];
<TkGanttChart tasks={tasks} columns={columns} panelWidth={440} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
]
const columns = [
{ field: 'name', header: 'Task', width: '160px' },
{ field: 'startDate', header: 'Start', width: '100px' },
{ field: 'endDate', header: 'End', width: '100px' },
{
field: 'progress',
header: 'Progress',
width: '80px',
html: (task) => `<strong>${task.progress ?? 0}%</strong>`,
},
]
</script>
<template>
<TkGanttChart :tasks="tasks" :columns="columns" :panel-width="440" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[columns]="columns"
[panel-width]="440"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
];
columns = [
{ field: 'name', header: 'Task', width: '160px' },
{ field: 'startDate', header: 'Start', width: '100px' },
{ field: 'endDate', header: 'End', width: '100px' },
{
field: 'progress',
header: 'Progress',
width: '80px',
html: (task) => `<strong>${task.progress ?? 0}%</strong>`,
},
];
Hide Panel
Set hidePanel to true to hide the left-side task list panel and show only
the timeline.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
<TkGanttChart tasks={tasks} hidePanel={true} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" :hide-panel="true" />
</template>
<tk-gantt-chart [tasks]="tasks" [hide-panel]="true"></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
Highlight Weekends
The highlightWeekends prop visually distinguishes weekends on the timeline. It
is set to true by default. This demo shows how it looks when it is set to
false.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
];
<TkGanttChart tasks={tasks} highlightWeekends={false} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" :highlight-weekends="false" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[highlightWeekends]="false"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Task A', startDate: '2026-04-01', endDate: '2026-04-14', progress: 100 },
{ id: '2', name: 'Task B', startDate: '2026-04-10', endDate: '2026-04-25', progress: 50 },
{ id: '3', name: 'Task C', startDate: '2026-04-20', endDate: '2026-05-05', progress: 20 },
];
Custom Task Bar
The taskBarHtml prop allows you to fully customize the content and style of
each task bar.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
const taskBarHtml = (task) => {
const p = task.progress ?? 0;
const bg = `linear-gradient(to right, #4caf50 ${p}%, #83d397${p}%)`;
return `<div style="display:flex;align-items:center;gap:4px;border-radius:4px;padding:0 8px;background:${bg};">
<tk-icon icon="rocket" color="#fff" size="small"></tk-icon>
<span style="font-weight:bold;color:#fff;">${task.name}</span>
</div>`;
};
<TkGanttChart tasks={tasks} taskBarHtml={taskBarHtml} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
]
const taskBarHtml = (task) => {
const p = task.progress ?? 0;
const bg = `linear-gradient(to right, #4caf50 ${p}%, #83d397 ${p}%)`;
return `<div style="display:flex;align-items:center;gap:4px;border-radius:4px;padding:0 8px;background:${bg};">
<tk-icon icon="rocket" color="#fff" size="small"></tk-icon>
<span style="font-weight:bold;color:#fff;">${task.name}</span>
</div>`;
};
</script>
<template>
<TkGanttChart :tasks="tasks" :task-bar-html="taskBarHtml" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[taskBarHtml]="taskBarHtml"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
taskBarHtml = (task: any) => {
const p = task.progress ?? 0;
const bg = `linear-gradient(to right, #4caf50 ${p}%, #83d397 ${p}%)`;
return `<div style="display:flex;align-items:center;gap:4px;border-radius:4px;padding:0 8px;background:${bg};">
<tk-icon icon="rocket" color="#fff" size="small"></tk-icon>
<span style="font-weight:bold;color:#fff;">${task.name}</span>
</div>`;
};
Custom Tooltip
With the tooltipHtml prop, you can pass custom HTML for tooltips when hovering
over tasks.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100, customDetail: 'Market analysis' },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75, customDetail: 'UI/UX mockups' },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40, customDetail: 'Frontend & Backend' },
];
const tooltipHtml = (task) =>
`<div style="padding: 4px; display: flex; flex-direction: column; gap: 6px; min-width: 180px;">
<div style="display: flex; align-items: center; gap: 6px; border-bottom: 1px solid var(--tk-color-border-subtle); padding-bottom: 6px;">
<tk-icon name="calendar" style="color: #f9fafc"></tk-icon>
<span style="font-weight: bold; font-size: 14px;">${task.name}</span>
</div>
<div style="font-size: 12px; display: flex; flex-direction: column; gap: 4px;">
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Timeline:</span>
<span>${task.startDate} / ${task.endDate}</span>
</div>
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Deliverable:</span>
<strong>${task.customDetail}</strong>
</div>
</div>
<div style="margin-top: 4px;">
<div style="display: flex; justify-content: space-between; font-size: 11px; margin-bottom: 4px;">
<span style="color: var(--tk-color-text-subtlest);">Progress</span>
<strong>${task.progress}%</strong>
</div>
<div style="background: var(--tk-color-border-subtle); border-radius: 4px; height: 6px; width: 100%; overflow: hidden;">
<div style="background: var(--tk-color-primary); width: ${task.progress}%; height: 100%;"></div>
</div>
</div>
</div>`;
<TkGanttChart tasks={tasks} tooltipHtml={tooltipHtml} />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100, customDetail: 'Market analysis' },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75, customDetail: 'UI/UX mockups' },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40, customDetail: 'Frontend & Backend' },
]
const tooltipHtml = (task) =>
`<div style="padding: 4px; display: flex; flex-direction: column; gap: 6px; min-width: 180px;">
<div style="display: flex; align-items: center; gap: 6px; border-bottom: 1px solid var(--tk-color-border-subtle); padding-bottom: 6px;">
<tk-icon name="calendar" style="color: var(--tk-color-primary)"></tk-icon>
<span style="font-weight: bold; font-size: 14px;">${task.name}</span>
</div>
<div style="font-size: 12px; display: flex; flex-direction: column; gap: 4px;">
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Timeline:</span>
<span>${task.startDate} / ${task.endDate}</span>
</div>
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Deliverable:</span>
<strong>${task.customDetail}</strong>
</div>
</div>
<div style="margin-top: 4px;">
<div style="display: flex; justify-content: space-between; font-size: 11px; margin-bottom: 4px;">
<span style="color: var(--tk-color-text-subtlest);">Progress</span>
<strong>${task.progress}%</strong>
</div>
<div style="background: var(--tk-color-border-subtle); border-radius: 4px; height: 6px; width: 100%; overflow: hidden;">
<div style="background: var(--tk-color-primary); width: ${task.progress}%; height: 100%;"></div>
</div>
</div>
</div>`;
</script>
<template>
<TkGanttChart :tasks="tasks" :tooltip-html="tooltipHtml" />
</template>
<tk-gantt-chart
[tasks]="tasks"
[tooltipHtml]="tooltipHtml"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Research', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100, customDetail: 'Market analysis' },
{ id: '2', name: 'Design', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75, customDetail: 'UI/UX mockups' },
{ id: '3', name: 'Development', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40, customDetail: 'Frontend & Backend' },
];
tooltipHtml = (task: any) =>
`<div style="padding: 4px; display: flex; flex-direction: column; gap: 6px; min-width: 180px;">
<div style="display: flex; align-items: center; gap: 6px; border-bottom: 1px solid var(--tk-color-border-subtle); padding-bottom: 6px;">
<tk-icon name="calendar" style="color: var(--tk-color-primary)"></tk-icon>
<span style="font-weight: bold; font-size: 14px;">${task.name}</span>
</div>
<div style="font-size: 12px; display: flex; flex-direction: column; gap: 4px;">
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Timeline:</span>
<span>${task.startDate} / ${task.endDate}</span>
</div>
<div style="display: flex; justify-content: space-between;">
<span style="color: var(--tk-color-text-subtlest);">Deliverable:</span>
<strong>${task.customDetail}</strong>
</div>
</div>
<div style="margin-top: 4px;">
<div style="display: flex; justify-content: space-between; font-size: 11px; margin-bottom: 4px;">
<span style="color: var(--tk-color-text-subtlest);">Progress</span>
<strong>${task.progress}%</strong>
</div>
<div style="background: var(--tk-color-border-subtle); border-radius: 4px; height: 6px; width: 100%; overflow: hidden;">
<div style="background: var(--tk-color-primary); width: ${task.progress}%; height: 100%;"></div>
</div>
</div>
</div>`;
Locale
The locale prop allows you to localize the Gantt chart content, such as months
and days. In this example, it's set to "tr-TR" with Turkish task data.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Araştırma', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Tasarım', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Geliştirme', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
<TkGanttChart tasks={tasks} locale="tr-TR" />
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Araştırma', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Tasarım', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Geliştirme', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
]
</script>
<template>
<TkGanttChart :tasks="tasks" locale="tr-TR" />
</template>
<tk-gantt-chart
[tasks]="tasks"
locale="tr-TR"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Araştırma', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Tasarım', startDate: '2026-04-08', endDate: '2026-04-18', progress: 75 },
{ id: '3', name: 'Geliştirme', startDate: '2026-04-15', endDate: '2026-05-05', progress: 40 },
];
Sizing & Layout
You can customize the structural dimensions of the Gantt chart using the
rowHeight and panelWidth props.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Phase 1 - Project Scoping', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Phase 2 - Design Concepts', startDate: '2026-04-05', endDate: '2026-04-20', progress: 60 },
{ id: '3', name: 'Phase 3 - Prototyping and Testing', startDate: '2026-04-15', endDate: '2026-04-30', progress: 10 },
];
<TkGanttChart
tasks={tasks}
rowHeight={64}
panelWidth={400}
/>
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Phase 1 - Project Scoping', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Phase 2 - Design Concepts', startDate: '2026-04-05', endDate: '2026-04-20', progress: 60 },
{ id: '3', name: 'Phase 3 - Prototyping and Testing', startDate: '2026-04-15', endDate: '2026-04-30', progress: 10 },
]
</script>
<template>
<TkGanttChart
:tasks="tasks"
:row-height="64"
:panel-width="400"
/>
</template>
<tk-gantt-chart
[tasks]="tasks"
[rowHeight]="64"
[panelWidth]="400"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Phase 1 - Project Scoping', startDate: '2026-04-01', endDate: '2026-04-10', progress: 100 },
{ id: '2', name: 'Phase 2 - Design Concepts', startDate: '2026-04-05', endDate: '2026-04-20', progress: 60 },
{ id: '3', name: 'Phase 3 - Prototyping and Testing', startDate: '2026-04-15', endDate: '2026-04-30', progress: 10 },
];
Week Start Day
By default, the Gantt chart starts the week on Monday (1). You can change this
using the weekStartDay prop. This demo shows the effect of setting it to
Sunday (0).
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Task Alpha', startDate: '2026-04-05', endDate: '2026-04-19', progress: 40 },
{ id: '2', name: 'Task Beta', startDate: '2026-04-10', endDate: '2026-04-25', progress: 15 },
];
<TkGanttChart
tasks={tasks}
viewType="weekly"
weekStartDay={0}
/>
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Task Alpha', startDate: '2026-04-05', endDate: '2026-04-19', progress: 40 },
{ id: '2', name: 'Task Beta', startDate: '2026-04-10', endDate: '2026-04-25', progress: 15 },
]
</script>
<template>
<TkGanttChart
:tasks="tasks"
view-type="weekly"
:week-start-day="0"
/>
</template>
<tk-gantt-chart
[tasks]="tasks"
viewType="weekly"
[weekStartDay]="0"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Task Alpha', startDate: '2026-04-05', endDate: '2026-04-19', progress: 40 },
{ id: '2', name: 'Task Beta', startDate: '2026-04-10', endDate: '2026-04-25', progress: 15 },
];
Secondary Header Mode
The secondaryHeaderMode prop configures the display format of the sub-header.
In this example, the timeline is set to monthly with the secondary header
showing weeks.
- React
- Vue
- Angular
const tasks = [
{ id: '1', name: 'Phase 1', startDate: '2026-04-01', endDate: '2026-04-30', progress: 80 },
{ id: '2', name: 'Phase 2', startDate: '2026-05-01', endDate: '2026-05-31', progress: 10 },
];
<TkGanttChart
tasks={tasks}
viewType="monthly"
secondaryHeaderMode="weeks"
/>
<script setup>
import { TkGanttChart } from '@takeoff-ui/vue'
const tasks = [
{ id: '1', name: 'Phase 1', startDate: '2026-04-01', endDate: '2026-04-30', progress: 80 },
{ id: '2', name: 'Phase 2', startDate: '2026-05-01', endDate: '2026-05-31', progress: 10 },
]
</script>
<template>
<TkGanttChart
:tasks="tasks"
view-type="monthly"
secondary-header-mode="weeks"
/>
</template>
<tk-gantt-chart
[tasks]="tasks"
viewType="monthly"
secondaryHeaderMode="weeks"
></tk-gantt-chart>
// component.ts
tasks = [
{ id: '1', name: 'Phase 1', startDate: '2026-04-01', endDate: '2026-04-30', progress: 80 },
{ id: '2', name: 'Phase 2', startDate: '2026-05-01', endDate: '2026-05-31', progress: 10 },
];
API
Props
| Name | Type | Default | Description |
|---|---|---|---|
IGanttColumn[] | DEFAULT_COLUMNS | Column definitions for the left-side task list panel. Columns are fed from the task data. | |
CSSStyleProperties | null | Custom CSS style applied to the root container element. | |
boolean | false | Whether to hide the left-side task list panel. | |
boolean | true | Whether to highlight weekend columns with a different background. | |
IGanttHoliday[] | [] | Array of holiday dates to highlight on the timeline. | |
IGanttIndicator[] | [] | Array of indicator lines rendered on the timeline (e.g. today, startDate, freezeDate). | |
string | 'default' | Locale string for date formatting (e.g. 'tr-TR', 'en-US'). Uses native toLocaleString under the hood. | |
number | DEFAULT_PANEL_WIDTH | Width of the left-side task list panel in pixels. | |
number | DEFAULT_ROW_HEIGHT | Row height in pixels. | |
"days", "weeks" | 'days' | Secondary header display mode. - 'days' shows individual day numbers or day names - 'weeks' shows week numbers (W1, W2 … / H1, H2 … for Turkish locale) | |
boolean | true | Whether to automatically show a today indicator line. | |
(task: IGanttTask)=>string, HTMLElement | null | Custom task bar render function. Receives the task and should return an HTMLElement or an HTML string. | |
IGanttTask[] | [] | Array of tasks to display. Each task may contain nested children for sub-tasks. | |
(task: IGanttTask)=>string, HTMLElement | null | Custom tooltip render function. Receives the hovered task and should return an HTMLElement or an HTML string. | |
"monthly", "quarterly", "weekly", "yearly" | null | Timeline view type. When not set the component auto-fits based on the task date range. | |
0, 1, 2, 3, 4, 5, 6 | DEFAULT_WEEK_START_DAY | Day the week starts on (0 = Sunday … 6 = Saturday). |
Events
| Name | Description |
|---|---|
| tk-task-click | Emitted when a task bar is clicked. Detail contains the clicked task. |
| tk-task-toggle | Emitted when a task row is expanded or collapsed. |
Slots
| Name | Description |
|---|---|
| empty | Content to show when there are no tasks |
Interfaces
IGanttTask
Represents a single task in the Gantt chart.
interface IGanttTask {
/** Unique identifier for the task */
id: string;
/** Display name of the task */
name: string;
/** Start date of the task (ISO string or Date-parseable string) */
startDate: string;
/** End date of the task (ISO string or Date-parseable string) */
endDate: string;
/** Progress percentage (0–100) */
progress?: number;
/** Nested child tasks */
children?: IGanttTask[];
/** Custom inline styles for the task bar */
style?: CSSStyleProperties;
/** Arbitrary additional data attached to the task */
additionalData?: unknown;
/**
* Multiple time segments rendered on the same row.
* When provided, the task's own startDate/endDate are used only for
* positioning reference; actual bars are drawn per segment.
*/
segments?: IGanttTaskSegment[];
}
IGanttColumn
Column definition for the left-side task-list panel.
interface IGanttColumn {
/** Property key on IGanttTask (or nested path) to read data from */
field: string;
/** Column header label */
header: string;
/** Fixed width (CSS value, e.g. '120px') */
width?: string;
/** Custom HTML render function – receives the task, returns HTML string */
html?: (task: IGanttTask) => string;
}
IGanttIndicator
An indicator line drawn on the timeline (e.g. today, freeze-date).
interface IGanttIndicator {
/** Date of the indicator (ISO string or Date-parseable string) */
date: string;
/** Label shown above the indicator line */
label?: string;
/** CSS colour for the indicator line */
color?: string;
/** Line style */
lineStyle?: 'solid' | 'dashed';
}
IGanttHoliday
Holiday entry used to highlight non-working days.
interface IGanttHoliday {
/** Date of the holiday (ISO string or Date-parseable string) */
date: string;
/** Optional display label */
label?: string;
}