mirror of
https://github.com/DCsunset/taskwarrior-webui.git
synced 2025-08-19 06:53:06 +02:00
Added dialog to hide columns
This commit is contained in:
parent
3f5a9d6dd7
commit
4eb20b8160
4 changed files with 118 additions and 4 deletions
76
frontend/components/ColumnDialog.vue
Normal file
76
frontend/components/ColumnDialog.vue
Normal file
|
@ -0,0 +1,76 @@
|
||||||
|
<template>
|
||||||
|
<v-dialog v-model="showDialog" max-width="400px" @keydown.esc="closeDialog">
|
||||||
|
<v-card>
|
||||||
|
<v-card-title> Visible Columns </v-card-title>
|
||||||
|
<v-card-text>
|
||||||
|
<v-form ref="formRef">
|
||||||
|
<v-list-item v-for="c in activeColumns" :key="c.value">
|
||||||
|
<v-list-item-content>
|
||||||
|
<v-list-item-title> {{ c.text }} </v-list-item-title>
|
||||||
|
</v-list-item-content>
|
||||||
|
<v-list-item-action>
|
||||||
|
<v-checkbox
|
||||||
|
:value="!hiddenColumns.includes(c.value)"
|
||||||
|
@change="handleChange(c.value)"
|
||||||
|
/>
|
||||||
|
</v-list-item-action>
|
||||||
|
</v-list-item>
|
||||||
|
</v-form>
|
||||||
|
</v-card-text>
|
||||||
|
</v-card>
|
||||||
|
</v-dialog>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script lang="ts">
|
||||||
|
import {
|
||||||
|
watch,
|
||||||
|
defineComponent,
|
||||||
|
useStore,
|
||||||
|
computed,
|
||||||
|
ref,
|
||||||
|
reactive,
|
||||||
|
PropType,
|
||||||
|
} from "@nuxtjs/composition-api";
|
||||||
|
import { accessorType } from "../store";
|
||||||
|
|
||||||
|
export default defineComponent({
|
||||||
|
props: {
|
||||||
|
value: Boolean,
|
||||||
|
activeColumns: Array as PropType<Array<{ text: String; value: String }>>,
|
||||||
|
},
|
||||||
|
|
||||||
|
setup(props, ctx) {
|
||||||
|
const store = useStore<typeof accessorType>();
|
||||||
|
|
||||||
|
const showDialog = computed({
|
||||||
|
get: () => props.value,
|
||||||
|
set: (val) => ctx.emit("input", val),
|
||||||
|
});
|
||||||
|
|
||||||
|
const closeDialog = () => {
|
||||||
|
showDialog.value = false;
|
||||||
|
};
|
||||||
|
|
||||||
|
const handleChange = (value: string) => {
|
||||||
|
if (store.state.hiddenColumns.includes(value)) {
|
||||||
|
store.commit(
|
||||||
|
"setHiddenColumns",
|
||||||
|
store.state.hiddenColumns.filter((v) => v !== value)
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
store.dispatch("updateHiddenColumns", [
|
||||||
|
...store.state.hiddenColumns,
|
||||||
|
value,
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
return {
|
||||||
|
showDialog,
|
||||||
|
closeDialog,
|
||||||
|
hiddenColumns: store.state.hiddenColumns,
|
||||||
|
handleChange,
|
||||||
|
};
|
||||||
|
},
|
||||||
|
});
|
||||||
|
</script>
|
|
@ -7,7 +7,7 @@
|
||||||
@yes="confirmation.handler"
|
@yes="confirmation.handler"
|
||||||
/>
|
/>
|
||||||
<TaskDialog v-model="showTaskDialog" :task="currentTask || undefined" />
|
<TaskDialog v-model="showTaskDialog" :task="currentTask || undefined" />
|
||||||
|
<ColumnDialog v-model="showColumnDialog" :active-columns="headers"/>
|
||||||
<v-row class="px-4 pt-4">
|
<v-row class="px-4 pt-4">
|
||||||
<v-btn-toggle v-model="status" mandatory background-color="rgba(0, 0, 0, 0)">
|
<v-btn-toggle v-model="status" mandatory background-color="rgba(0, 0, 0, 0)">
|
||||||
<v-row class="pa-3">
|
<v-row class="pa-3">
|
||||||
|
@ -40,7 +40,7 @@
|
||||||
<v-row class="px-4 pt-4">
|
<v-row class="px-4 pt-4">
|
||||||
<v-data-table
|
<v-data-table
|
||||||
:items="classifiedTasks[status]"
|
:items="classifiedTasks[status]"
|
||||||
:headers="headers"
|
:headers="filteredHeaders"
|
||||||
show-select
|
show-select
|
||||||
item-key="uuid"
|
item-key="uuid"
|
||||||
:item-class="rowClass"
|
:item-class="rowClass"
|
||||||
|
@ -110,6 +110,16 @@
|
||||||
>
|
>
|
||||||
<v-icon>mdi-plus</v-icon>
|
<v-icon>mdi-plus</v-icon>
|
||||||
</v-btn>
|
</v-btn>
|
||||||
|
<v-btn
|
||||||
|
class="primary ml-1"
|
||||||
|
fab
|
||||||
|
dark
|
||||||
|
small
|
||||||
|
title="Configure Columns"
|
||||||
|
@click="showColumnDialog = true"
|
||||||
|
>
|
||||||
|
<v-icon>mdi-cogs</v-icon>
|
||||||
|
</v-btn>
|
||||||
</div>
|
</div>
|
||||||
</v-row>
|
</v-row>
|
||||||
</template>
|
</template>
|
||||||
|
@ -193,6 +203,7 @@ import { Task } from 'taskwarrior-lib';
|
||||||
import _ from 'lodash';
|
import _ from 'lodash';
|
||||||
import TaskDialog from '../components/TaskDialog.vue';
|
import TaskDialog from '../components/TaskDialog.vue';
|
||||||
import ConfirmationDialog from '../components/ConfirmationDialog.vue';
|
import ConfirmationDialog from '../components/ConfirmationDialog.vue';
|
||||||
|
import ColumnDialog from '../components/ColumnDialog.vue';
|
||||||
import moment from 'moment';
|
import moment from 'moment';
|
||||||
import urlRegex from 'url-regex-safe';
|
import urlRegex from 'url-regex-safe';
|
||||||
import normalizeUrl from 'normalize-url';
|
import normalizeUrl from 'normalize-url';
|
||||||
|
@ -293,6 +304,12 @@ export default defineComponent({
|
||||||
{ text: 'Actions', value: 'actions', sortable: false }
|
{ text: 'Actions', value: 'actions', sortable: false }
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
const filteredHeaders = computed(()=>
|
||||||
|
headers.value.filter((v)=> !store.state.hiddenColumns.includes(v.value))
|
||||||
|
)
|
||||||
|
|
||||||
|
const showColumnDialog = ref(false);
|
||||||
|
|
||||||
const tempTasks: { [key: string]: ComputedRef<Task[]> } = {};
|
const tempTasks: { [key: string]: ComputedRef<Task[]> } = {};
|
||||||
for (const status of allStatus) {
|
for (const status of allStatus) {
|
||||||
tempTasks[status] = computed((): Task[] => props.tasks?.filter(task => {
|
tempTasks[status] = computed((): Task[] => props.tasks?.filter(task => {
|
||||||
|
@ -393,6 +410,7 @@ export default defineComponent({
|
||||||
linkify,
|
linkify,
|
||||||
refresh,
|
refresh,
|
||||||
headers,
|
headers,
|
||||||
|
filteredHeaders,
|
||||||
classifiedTasks,
|
classifiedTasks,
|
||||||
status,
|
status,
|
||||||
allStatus,
|
allStatus,
|
||||||
|
@ -406,12 +424,14 @@ export default defineComponent({
|
||||||
restoreTasks,
|
restoreTasks,
|
||||||
showTaskDialog,
|
showTaskDialog,
|
||||||
showConfirmationDialog,
|
showConfirmationDialog,
|
||||||
|
showColumnDialog,
|
||||||
confirmation,
|
confirmation,
|
||||||
displayDate,
|
displayDate,
|
||||||
rowClass,
|
rowClass,
|
||||||
|
|
||||||
TaskDialog,
|
TaskDialog,
|
||||||
ConfirmationDialog
|
ConfirmationDialog,
|
||||||
|
ColumnDialog,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
@ -60,6 +60,7 @@ export default defineComponent({
|
||||||
const context = useContext();
|
const context = useContext();
|
||||||
const store = useStore<typeof accessorType>();
|
const store = useStore<typeof accessorType>();
|
||||||
store.dispatch('fetchSettings');
|
store.dispatch('fetchSettings');
|
||||||
|
store.dispatch('fetchHiddenColumns');
|
||||||
|
|
||||||
context.$vuetify.theme.dark = store.state.settings.dark;
|
context.$vuetify.theme.dark = store.state.settings.dark;
|
||||||
|
|
||||||
|
|
|
@ -13,7 +13,8 @@ export const state = () => ({
|
||||||
dark: false,
|
dark: false,
|
||||||
autoRefresh: '5', // in minutes
|
autoRefresh: '5', // in minutes
|
||||||
autoSync: '0' // in minutes
|
autoSync: '0' // in minutes
|
||||||
}
|
},
|
||||||
|
hiddenColumns: [] as string[]
|
||||||
});
|
});
|
||||||
|
|
||||||
export type RootState = ReturnType<typeof state>;
|
export type RootState = ReturnType<typeof state>;
|
||||||
|
@ -34,6 +35,10 @@ export const mutations: MutationTree<RootState> = {
|
||||||
state.tasks = tasks;
|
state.tasks = tasks;
|
||||||
},
|
},
|
||||||
|
|
||||||
|
setHiddenColumns(state, hiddenColumns) {
|
||||||
|
state.hiddenColumns = hiddenColumns
|
||||||
|
},
|
||||||
|
|
||||||
setNotification(state, notification) {
|
setNotification(state, notification) {
|
||||||
state.notification = notification;
|
state.notification = notification;
|
||||||
// Show notification
|
// Show notification
|
||||||
|
@ -58,6 +63,18 @@ export const actions: ActionTree<RootState, RootState> = {
|
||||||
localStorage.setItem('settings', JSON.stringify(settings));
|
localStorage.setItem('settings', JSON.stringify(settings));
|
||||||
},
|
},
|
||||||
|
|
||||||
|
fetchHiddenColumns(context) {
|
||||||
|
const columns = localStorage.getItem('hiddenColumns');
|
||||||
|
if (columns) {
|
||||||
|
context.commit('setHiddenColumns', JSON.parse(columns));
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
updateHiddenColumns(context, columns) {
|
||||||
|
context.commit('setHiddenColumns', columns);
|
||||||
|
localStorage.setItem('hiddenColumns', JSON.stringify(columns));
|
||||||
|
},
|
||||||
|
|
||||||
async fetchTasks(context) {
|
async fetchTasks(context) {
|
||||||
const tasks: Task[] = await this.$axios.$get('/api/tasks');
|
const tasks: Task[] = await this.$axios.$get('/api/tasks');
|
||||||
context.commit('setTasks', tasks);
|
context.commit('setTasks', tasks);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue