mirror of
https://github.com/mayswind/ezbookkeeping.git
synced 2026-05-20 01:34:24 +08:00
support creating transaction from template
This commit is contained in:
@@ -41,7 +41,18 @@
|
|||||||
</v-btn>
|
</v-btn>
|
||||||
<span>{{ $t('Transaction List') }}</span>
|
<span>{{ $t('Transaction List') }}</span>
|
||||||
<v-btn class="ml-3" color="default" variant="outlined"
|
<v-btn class="ml-3" color="default" variant="outlined"
|
||||||
:disabled="loading || !canAddTransaction" @click="add">{{ $t('Add') }}</v-btn>
|
:disabled="loading || !canAddTransaction" @click="add">
|
||||||
|
{{ $t('Add') }}
|
||||||
|
<v-menu activator="parent" :open-on-hover="true" v-if="allTransactionTemplates && allTransactionTemplates.length">
|
||||||
|
<v-list>
|
||||||
|
<v-list-item :title="template.name"
|
||||||
|
:prepend-icon="icons.templates"
|
||||||
|
:key="template.id"
|
||||||
|
v-for="template in allTransactionTemplates"
|
||||||
|
@click="add(template)"></v-list-item>
|
||||||
|
</v-list>
|
||||||
|
</v-menu>
|
||||||
|
</v-btn>
|
||||||
<v-btn density="compact" color="default" variant="text" size="24"
|
<v-btn density="compact" color="default" variant="text" size="24"
|
||||||
class="ml-2" :icon="true" :loading="loading" @click="reload">
|
class="ml-2" :icon="true" :loading="loading" @click="reload">
|
||||||
<template #loader>
|
<template #loader>
|
||||||
@@ -516,11 +527,13 @@ import { useAccountsStore } from '@/stores/account.js';
|
|||||||
import { useTransactionCategoriesStore } from '@/stores/transactionCategory.js';
|
import { useTransactionCategoriesStore } from '@/stores/transactionCategory.js';
|
||||||
import { useTransactionTagsStore } from '@/stores/transactionTag.js';
|
import { useTransactionTagsStore } from '@/stores/transactionTag.js';
|
||||||
import { useTransactionsStore } from '@/stores/transaction.js';
|
import { useTransactionsStore } from '@/stores/transaction.js';
|
||||||
|
import { useTransactionTemplatesStore } from '@/stores/transactionTemplate.js';
|
||||||
|
|
||||||
import numeralConstants from '@/consts/numeral.js';
|
import numeralConstants from '@/consts/numeral.js';
|
||||||
import datetimeConstants from '@/consts/datetime.js';
|
import datetimeConstants from '@/consts/datetime.js';
|
||||||
import accountConstants from '@/consts/account.js';
|
import accountConstants from '@/consts/account.js';
|
||||||
import transactionConstants from '@/consts/transaction.js';
|
import transactionConstants from '@/consts/transaction.js';
|
||||||
|
import templateConstants from '@/consts/template.js';
|
||||||
import { isString, getNameByKeyValue } from '@/lib/common.js';
|
import { isString, getNameByKeyValue } from '@/lib/common.js';
|
||||||
import logger from '@/lib/logger.js';
|
import logger from '@/lib/logger.js';
|
||||||
import {
|
import {
|
||||||
@@ -562,6 +575,7 @@ import {
|
|||||||
mdiArrowLeft,
|
mdiArrowLeft,
|
||||||
mdiArrowRight,
|
mdiArrowRight,
|
||||||
mdiPound,
|
mdiPound,
|
||||||
|
mdiTextBoxOutline,
|
||||||
mdiDotsVertical
|
mdiDotsVertical
|
||||||
} from '@mdi/js';
|
} from '@mdi/js';
|
||||||
|
|
||||||
@@ -621,12 +635,13 @@ export default {
|
|||||||
arrowLeft: mdiArrowLeft,
|
arrowLeft: mdiArrowLeft,
|
||||||
arrowRight: mdiArrowRight,
|
arrowRight: mdiArrowRight,
|
||||||
tag: mdiPound,
|
tag: mdiPound,
|
||||||
|
templates: mdiTextBoxOutline,
|
||||||
more: mdiDotsVertical
|
more: mdiDotsVertical
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
...mapStores(useSettingsStore, useUserStore, useAccountsStore, useTransactionCategoriesStore, useTransactionTagsStore, useTransactionsStore),
|
...mapStores(useSettingsStore, useUserStore, useAccountsStore, useTransactionCategoriesStore, useTransactionTagsStore, useTransactionsStore, useTransactionTemplatesStore),
|
||||||
defaultCurrency() {
|
defaultCurrency() {
|
||||||
return getUnifiedSelectedAccountsCurrencyOrDefaultCurrency(this.allAccounts, this.queryAllFilterAccountIds, this.userStore.currentUserDefaultCurrency);
|
return getUnifiedSelectedAccountsCurrencyOrDefaultCurrency(this.allAccounts, this.queryAllFilterAccountIds, this.userStore.currentUserDefaultCurrency);
|
||||||
},
|
},
|
||||||
@@ -907,6 +922,10 @@ export default {
|
|||||||
allAvailableTagsCount() {
|
allAvailableTagsCount() {
|
||||||
return this.transactionTagsStore.allAvailableTagsCount;
|
return this.transactionTagsStore.allAvailableTagsCount;
|
||||||
},
|
},
|
||||||
|
allTransactionTemplates() {
|
||||||
|
const allVisibleTemplates = this.transactionTemplatesStore.allVisibleTemplates;
|
||||||
|
return allVisibleTemplates[templateConstants.allTemplateTypes.Normal] || [];
|
||||||
|
},
|
||||||
recentMonthDateRanges() {
|
recentMonthDateRanges() {
|
||||||
return this.$locale.getAllRecentMonthDateRanges(this.userStore, true, true);
|
return this.$locale.getAllRecentMonthDateRanges(this.userStore, true, true);
|
||||||
},
|
},
|
||||||
@@ -992,6 +1011,11 @@ export default {
|
|||||||
|
|
||||||
this.currentPage = 1;
|
this.currentPage = 1;
|
||||||
this.reload(false);
|
this.reload(false);
|
||||||
|
|
||||||
|
this.transactionTemplatesStore.loadAllTemplates({
|
||||||
|
templateType: templateConstants.allTemplateTypes.Normal,
|
||||||
|
force: false
|
||||||
|
});
|
||||||
},
|
},
|
||||||
reload(force) {
|
reload(force) {
|
||||||
const self = this;
|
const self = this;
|
||||||
@@ -1307,14 +1331,15 @@ export default {
|
|||||||
this.$router.push(this.getFilterLinkUrl());
|
this.$router.push(this.getFilterLinkUrl());
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
add() {
|
add(template) {
|
||||||
const self = this;
|
const self = this;
|
||||||
|
|
||||||
self.$refs.editDialog.open({
|
self.$refs.editDialog.open({
|
||||||
type: self.query.type,
|
type: self.query.type,
|
||||||
categoryId: self.queryAllFilterCategoryIdsCount === 1 ? self.query.categoryIds : '',
|
categoryId: self.queryAllFilterCategoryIdsCount === 1 ? self.query.categoryIds : '',
|
||||||
accountId: self.queryAllFilterAccountIdsCount === 1 ? self.query.accountIds : '',
|
accountId: self.queryAllFilterAccountIdsCount === 1 ? self.query.accountIds : '',
|
||||||
tagIds: self.query.tagIds || ''
|
tagIds: self.query.tagIds || '',
|
||||||
|
template: template
|
||||||
}).then(result => {
|
}).then(result => {
|
||||||
if (result && result.message) {
|
if (result && result.message) {
|
||||||
self.$refs.snackbar.showMessage(result.message);
|
self.$refs.snackbar.showMessage(result.message);
|
||||||
|
|||||||
@@ -669,6 +669,10 @@ export default {
|
|||||||
self.mode = 'add';
|
self.mode = 'add';
|
||||||
self.editId = null;
|
self.editId = null;
|
||||||
|
|
||||||
|
if (options.template) {
|
||||||
|
self.setTransaction(options.template, options, false, false);
|
||||||
|
}
|
||||||
|
|
||||||
if (self.settingsStore.appSettings.autoGetCurrentGeoLocation
|
if (self.settingsStore.appSettings.autoGetCurrentGeoLocation
|
||||||
&& !self.geoLocationStatus && !self.transaction.geoLocation) {
|
&& !self.geoLocationStatus && !self.transaction.geoLocation) {
|
||||||
self.updateGeoLocation(false);
|
self.updateGeoLocation(false);
|
||||||
|
|||||||
@@ -172,7 +172,7 @@
|
|||||||
<f7-icon f7="creditcard"></f7-icon>
|
<f7-icon f7="creditcard"></f7-icon>
|
||||||
<span class="tabbar-label">{{ $t('Accounts') }}</span>
|
<span class="tabbar-label">{{ $t('Accounts') }}</span>
|
||||||
</f7-link>
|
</f7-link>
|
||||||
<f7-link class="link" href="/transaction/add">
|
<f7-link id="homepage-add-button" class="link" href="/transaction/add" @taphold="openTransactionTemplatePopover">
|
||||||
<f7-icon f7="plus_square" class="ebk-tarbar-big-icon"></f7-icon>
|
<f7-icon f7="plus_square" class="ebk-tarbar-big-icon"></f7-icon>
|
||||||
</f7-link>
|
</f7-link>
|
||||||
<f7-link class="link" href="/statistic/transaction">
|
<f7-link class="link" href="/statistic/transaction">
|
||||||
@@ -184,6 +184,19 @@
|
|||||||
<span class="tabbar-label">{{ $t('Settings') }}</span>
|
<span class="tabbar-label">{{ $t('Settings') }}</span>
|
||||||
</f7-link>
|
</f7-link>
|
||||||
</f7-toolbar>
|
</f7-toolbar>
|
||||||
|
|
||||||
|
<f7-popover class="template-popover-menu" target-el="#homepage-add-button"
|
||||||
|
v-model:opened="showTransactionTemplatePopover">
|
||||||
|
<f7-list dividers v-if="allTransactionTemplates">
|
||||||
|
<f7-list-item :title="template.name" :key="template.id"
|
||||||
|
v-for="template in allTransactionTemplates"
|
||||||
|
@click="addTransaction(template)">
|
||||||
|
<template #media>
|
||||||
|
<f7-icon f7="doc_plaintext"></f7-icon>
|
||||||
|
</template>
|
||||||
|
</f7-list-item>
|
||||||
|
</f7-list>
|
||||||
|
</f7-popover>
|
||||||
</f7-page>
|
</f7-page>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
@@ -191,19 +204,25 @@
|
|||||||
import { mapStores } from 'pinia';
|
import { mapStores } from 'pinia';
|
||||||
import { useSettingsStore } from '@/stores/setting.js';
|
import { useSettingsStore } from '@/stores/setting.js';
|
||||||
import { useUserStore } from '@/stores/user.js';
|
import { useUserStore } from '@/stores/user.js';
|
||||||
|
import { useTransactionTemplatesStore } from '@/stores/transactionTemplate.js';
|
||||||
import { useOverviewStore } from '@/stores/overview.js';
|
import { useOverviewStore } from '@/stores/overview.js';
|
||||||
|
|
||||||
import datetimeConstants from '@/consts/datetime.js';
|
import datetimeConstants from '@/consts/datetime.js';
|
||||||
|
import templateConstants from '@/consts/template.js';
|
||||||
import { formatUnixTime } from '@/lib/datetime.js';
|
import { formatUnixTime } from '@/lib/datetime.js';
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
|
props: [
|
||||||
|
'f7router'
|
||||||
|
],
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
loading: true
|
loading: true,
|
||||||
|
showTransactionTemplatePopover: false
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
...mapStores(useSettingsStore, useUserStore, useOverviewStore),
|
...mapStores(useSettingsStore, useUserStore, useTransactionTemplatesStore, useOverviewStore),
|
||||||
showAmountInHomePage: {
|
showAmountInHomePage: {
|
||||||
get: function() {
|
get: function() {
|
||||||
return this.settingsStore.appSettings.showAmountInHomePage;
|
return this.settingsStore.appSettings.showAmountInHomePage;
|
||||||
@@ -215,6 +234,10 @@ export default {
|
|||||||
defaultCurrency() {
|
defaultCurrency() {
|
||||||
return this.userStore.currentUserDefaultCurrency;
|
return this.userStore.currentUserDefaultCurrency;
|
||||||
},
|
},
|
||||||
|
allTransactionTemplates() {
|
||||||
|
const allTemplates = this.transactionTemplatesStore.allVisibleTemplates;
|
||||||
|
return allTemplates[templateConstants.allTemplateTypes.Normal] || [];
|
||||||
|
},
|
||||||
allDateRanges() {
|
allDateRanges() {
|
||||||
return datetimeConstants.allDateRanges;
|
return datetimeConstants.allDateRanges;
|
||||||
},
|
},
|
||||||
@@ -260,6 +283,11 @@ export default {
|
|||||||
self.$toast(error.message || error);
|
self.$toast(error.message || error);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
self.transactionTemplatesStore.loadAllTemplates({
|
||||||
|
templateType: templateConstants.allTemplateTypes.Normal,
|
||||||
|
force: false
|
||||||
|
});
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
methods: {
|
methods: {
|
||||||
@@ -292,6 +320,16 @@ export default {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
addTransaction(template) {
|
||||||
|
if (template && template.id) {
|
||||||
|
this.f7router.navigate('/transaction/add?templateId=' + template.id);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
openTransactionTemplatePopover() {
|
||||||
|
if (this.allTransactionTemplates && this.allTransactionTemplates.length) {
|
||||||
|
this.showTransactionTemplatePopover = true;
|
||||||
|
}
|
||||||
|
},
|
||||||
getDisplayCurrency(value, currencyCode) {
|
getDisplayCurrency(value, currencyCode) {
|
||||||
return this.$locale.formatAmountWithCurrency(this.settingsStore, this.userStore, value, currencyCode);
|
return this.$locale.formatAmountWithCurrency(this.settingsStore, this.userStore, value, currencyCode);
|
||||||
},
|
},
|
||||||
@@ -387,4 +425,9 @@ export default {
|
|||||||
height: var(--ebk-big-icon-button-size);
|
height: var(--ebk-big-icon-button-size);
|
||||||
line-height: var(--ebk-big-icon-button-size);
|
line-height: var(--ebk-big-icon-button-size);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.template-popover-menu .popover-inner{
|
||||||
|
max-height: 400px;
|
||||||
|
overflow-y: auto;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
@@ -355,10 +355,12 @@ import { useAccountsStore } from '@/stores/account.js';
|
|||||||
import { useTransactionCategoriesStore } from '@/stores/transactionCategory.js';
|
import { useTransactionCategoriesStore } from '@/stores/transactionCategory.js';
|
||||||
import { useTransactionTagsStore } from '@/stores/transactionTag.js';
|
import { useTransactionTagsStore } from '@/stores/transactionTag.js';
|
||||||
import { useTransactionsStore } from '@/stores/transaction.js';
|
import { useTransactionsStore } from '@/stores/transaction.js';
|
||||||
|
import { useTransactionTemplatesStore } from '@/stores/transactionTemplate.js';
|
||||||
import { useExchangeRatesStore } from '@/stores/exchangeRates.js';
|
import { useExchangeRatesStore } from '@/stores/exchangeRates.js';
|
||||||
|
|
||||||
import categoryConstants from '@/consts/category.js';
|
import categoryConstants from '@/consts/category.js';
|
||||||
import transactionConstants from '@/consts/transaction.js';
|
import transactionConstants from '@/consts/transaction.js';
|
||||||
|
import templateConstants from '@/consts/template.js';
|
||||||
import logger from '@/lib/logger.js';
|
import logger from '@/lib/logger.js';
|
||||||
import {
|
import {
|
||||||
getNameByKeyValue
|
getNameByKeyValue
|
||||||
@@ -413,7 +415,7 @@ export default {
|
|||||||
};
|
};
|
||||||
},
|
},
|
||||||
computed: {
|
computed: {
|
||||||
...mapStores(useSettingsStore, useUserStore, useAccountsStore, useTransactionCategoriesStore, useTransactionTagsStore, useTransactionsStore, useExchangeRatesStore),
|
...mapStores(useSettingsStore, useUserStore, useAccountsStore, useTransactionCategoriesStore, useTransactionTagsStore, useTransactionsStore, useTransactionTemplatesStore, useExchangeRatesStore),
|
||||||
title() {
|
title() {
|
||||||
if (this.mode === 'add') {
|
if (this.mode === 'add') {
|
||||||
return 'Add Transaction';
|
return 'Add Transaction';
|
||||||
@@ -654,7 +656,8 @@ export default {
|
|||||||
const promises = [
|
const promises = [
|
||||||
self.accountsStore.loadAllAccounts({ force: false }),
|
self.accountsStore.loadAllAccounts({ force: false }),
|
||||||
self.transactionCategoriesStore.loadAllCategories({ force: false }),
|
self.transactionCategoriesStore.loadAllCategories({ force: false }),
|
||||||
self.transactionTagsStore.loadAllTags({ force: false })
|
self.transactionTagsStore.loadAllTags({ force: false }),
|
||||||
|
self.transactionTemplatesStore.loadAllTemplates({ force: false, templateType: templateConstants.allTemplateTypes.Normal })
|
||||||
];
|
];
|
||||||
|
|
||||||
if (query.id) {
|
if (query.id) {
|
||||||
@@ -676,15 +679,23 @@ export default {
|
|||||||
}
|
}
|
||||||
|
|
||||||
Promise.all(promises).then(function (responses) {
|
Promise.all(promises).then(function (responses) {
|
||||||
if (query.id && !responses[3]) {
|
if (query.id && !responses[4]) {
|
||||||
self.$toast('Unable to retrieve transaction');
|
self.$toast('Unable to retrieve transaction');
|
||||||
self.loadingError = 'Unable to retrieve transaction';
|
self.loadingError = 'Unable to retrieve transaction';
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let fromTransaction = null;
|
||||||
|
|
||||||
|
if (query.id) {
|
||||||
|
fromTransaction = responses[4];
|
||||||
|
} else if (query.templateId && self.transactionTemplatesStore.allTransactionTemplatesMap && self.transactionTemplatesStore.allTransactionTemplatesMap[templateConstants.allTemplateTypes.Normal]) {
|
||||||
|
fromTransaction = self.transactionTemplatesStore.allTransactionTemplatesMap[templateConstants.allTemplateTypes.Normal][query.templateId];
|
||||||
|
}
|
||||||
|
|
||||||
setTransactionModelByTransaction(
|
setTransactionModelByTransaction(
|
||||||
self.transaction,
|
self.transaction,
|
||||||
query.id ? responses[3] : null,
|
fromTransaction,
|
||||||
self.allCategories,
|
self.allCategories,
|
||||||
self.allCategoriesMap,
|
self.allCategoriesMap,
|
||||||
self.allVisibleAccounts,
|
self.allVisibleAccounts,
|
||||||
|
|||||||
Reference in New Issue
Block a user