code refactor

This commit is contained in:
MaysWind
2025-08-30 00:38:45 +08:00
parent 32cf41a7a0
commit 4d0e376568
16 changed files with 126 additions and 120 deletions
+20 -19
View File
@@ -1,8 +1,9 @@
import { computed } from 'vue'; import { computed } from 'vue';
import type { ColorValue } from '@/core/color.ts'; import type {ColorStyleValue, ColorValue} from '@/core/color.ts';
import { ALL_ACCOUNT_ICONS, DEFAULT_ACCOUNT_ICON, ALL_CATEGORY_ICONS, DEFAULT_CATEGORY_ICON } from '@/consts/icon.ts'; import { ALL_ACCOUNT_ICONS, DEFAULT_ACCOUNT_ICON, ALL_CATEGORY_ICONS, DEFAULT_CATEGORY_ICON } from '@/consts/icon.ts';
import { DEFAULT_ICON_COLOR, DEFAULT_ACCOUNT_COLOR, DEFAULT_CATEGORY_COLOR } from '@/consts/color.ts'; import { DEFAULT_ICON_COLOR, DEFAULT_ACCOUNT_COLOR, DEFAULT_CATEGORY_COLOR, DEFAULT_COLOR_STYLE_VARIABLE } from '@/consts/color.ts';
import { isNumber } from '@/lib/common.ts'; import { isNumber } from '@/lib/common.ts';
type IconItemStyleName = string; type IconItemStyleName = string;
@@ -14,14 +15,14 @@ export interface CommonIconProps {
iconType: CommonIconItemType | MobileIconItemType; iconType: CommonIconItemType | MobileIconItemType;
iconId: string | number; iconId: string | number;
color?: ColorValue; color?: ColorValue;
defaultColor?: ColorValue; defaultColor?: ColorStyleValue;
additionalColorAttr?: string; additionalColorAttr?: string;
size?: string | number; size?: string | number;
} }
export function useItemIconBase(props: CommonIconProps) { export function useItemIconBase(props: CommonIconProps) {
const style = computed<Record<IconItemStyleName, IconItemStyleValue>>(() => { const style = computed<Record<IconItemStyleName, IconItemStyleValue>>(() => {
let defaultColor = 'var(--default-icon-color)'; let defaultColor: ColorStyleValue = DEFAULT_COLOR_STYLE_VARIABLE;
if (props.defaultColor) { if (props.defaultColor) {
defaultColor = props.defaultColor; defaultColor = props.defaultColor;
@@ -60,15 +61,15 @@ export function useItemIconBase(props: CommonIconProps) {
return ALL_CATEGORY_ICONS[iconId].icon; return ALL_CATEGORY_ICONS[iconId].icon;
} }
function getAccountIconStyle(color?: ColorValue | string, defaultColor?: ColorValue | string, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> { function getAccountIconStyle(color?: ColorValue, defaultColor?: ColorStyleValue, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> {
let displayColor: ColorStyleValue | undefined = defaultColor;
if (color && color !== DEFAULT_ACCOUNT_COLOR) { if (color && color !== DEFAULT_ACCOUNT_COLOR) {
color = '#' + color; displayColor = `#${color}`;
} else {
color = defaultColor;
} }
const ret: Record<IconItemStyleName, IconItemStyleValue> = { const ret: Record<IconItemStyleName, IconItemStyleValue> = {
color: color color: displayColor
}; };
if (additionalColorAttr) { if (additionalColorAttr) {
@@ -82,15 +83,15 @@ export function useItemIconBase(props: CommonIconProps) {
return ret; return ret;
} }
function getCategoryIconStyle(color?: ColorValue | string, defaultColor?: ColorValue | string, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> { function getCategoryIconStyle(color?: ColorValue, defaultColor?: ColorStyleValue, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> {
let displayColor: ColorStyleValue | undefined = defaultColor;
if (color && color !== DEFAULT_CATEGORY_COLOR) { if (color && color !== DEFAULT_CATEGORY_COLOR) {
color = '#' + color; displayColor = `#${color}`;
} else {
color = defaultColor;
} }
const ret: Record<IconItemStyleName, IconItemStyleValue> = { const ret: Record<IconItemStyleName, IconItemStyleValue> = {
color: color color: displayColor
}; };
if (additionalColorAttr) { if (additionalColorAttr) {
@@ -104,15 +105,15 @@ export function useItemIconBase(props: CommonIconProps) {
return ret; return ret;
} }
function getDefaultIconStyle(color?: ColorValue | string, defaultColor?: ColorValue | string, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> { function getDefaultIconStyle(color?: ColorValue, defaultColor?: ColorStyleValue, additionalColorAttr?: string): Record<IconItemStyleName, IconItemStyleValue> {
let displayColor: ColorStyleValue | undefined = defaultColor;
if (color && color !== DEFAULT_ICON_COLOR) { if (color && color !== DEFAULT_ICON_COLOR) {
color = '#' + color; displayColor = `#${color}`;
} else {
color = defaultColor;
} }
const ret: Record<IconItemStyleName, IconItemStyleValue> = { const ret: Record<IconItemStyleName, IconItemStyleValue> = {
color: color color: displayColor
}; };
if (additionalColorAttr) { if (additionalColorAttr) {
+1 -12
View File
@@ -11,8 +11,6 @@ import type {
YearMonthUnixTime YearMonthUnixTime
} from '@/core/datetime.ts'; } from '@/core/datetime.ts';
import type { FiscalYearUnixTime } from '@/core/fiscalyear.ts'; import type { FiscalYearUnixTime } from '@/core/fiscalyear.ts';
import type { ColorValue } from '@/core/color.ts';
import { DEFAULT_ICON_COLOR } from '@/consts/color.ts';
import type { YearMonthItems } from '@/models/transaction.ts'; import type { YearMonthItems } from '@/models/transaction.ts';
import { getAllDateRangesFromItems } from '@/lib/statistics.ts'; import { getAllDateRangesFromItems } from '@/lib/statistics.ts';
@@ -49,19 +47,10 @@ export function useMonthlyTrendsChartBase<T extends Year1BasedMonth>(props: Comm
return props.translateName ? tt(name) : name; return props.translateName ? tt(name) : name;
} }
function getColor(color: string): ColorValue {
if (color && color !== DEFAULT_ICON_COLOR) {
color = '#' + color;
}
return color;
}
return { return {
// computed states // computed states
allDateRanges, allDateRanges,
// functions // functions
getItemName, getItemName
getColor
} }
} }
+4 -2
View File
@@ -2,9 +2,11 @@ import { ref, computed, watch } from 'vue';
import { useI18n } from '@/locales/helpers.ts'; import { useI18n } from '@/locales/helpers.ts';
import type { ColorValue, ColorStyleValue } from '@/core/color.ts';
import { DEFAULT_CHART_COLORS } from '@/consts/color.ts'; import { DEFAULT_CHART_COLORS } from '@/consts/color.ts';
import { isNumber } from '@/lib/common.ts'; import { isNumber } from '@/lib/common.ts';
import { getDisplayColor } from '@/lib/color.ts';
export interface CommonPieChartDataItem { export interface CommonPieChartDataItem {
id: string; id: string;
@@ -13,7 +15,7 @@ export interface CommonPieChartDataItem {
value: number; value: number;
percent: number; percent: number;
actualPercent: number; actualPercent: number;
color: string; color: ColorStyleValue;
sourceItem: Record<string, unknown>; sourceItem: Record<string, unknown>;
displayPercent?: string; displayPercent?: string;
displayValue?: string; displayValue?: string;
@@ -68,7 +70,7 @@ export function usePieChartBase(props: CommonPieChartProps) {
value: value, value: value,
percent: (isNumber(percent) && percent >= 0) ? percent : (value / totalValidValue * 100), percent: (isNumber(percent) && percent >= 0) ? percent : (value / totalValidValue * 100),
actualPercent: value / totalValidValue, actualPercent: value / totalValidValue,
color: (props.colorField && item[props.colorField]) ? item[props.colorField] as string : DEFAULT_CHART_COLORS[validItems.length % DEFAULT_CHART_COLORS.length], color: getDisplayColor((props.colorField && item[props.colorField]) ? item[props.colorField] as ColorValue : DEFAULT_CHART_COLORS[validItems.length % DEFAULT_CHART_COLORS.length]),
sourceItem: item sourceItem: item
}; };
@@ -14,7 +14,7 @@ import { useUserStore } from '@/stores/user.ts';
import type { NameValue } from '@/core/base.ts'; import type { NameValue } from '@/core/base.ts';
import { TextDirection } from '@/core/text.ts'; import { TextDirection } from '@/core/text.ts';
import type { ColorValue } from '@/core/color.ts'; import type { ColorStyleValue } from '@/core/color.ts';
import { ThemeType } from '@/core/theme.ts'; import { ThemeType } from '@/core/theme.ts';
import { AccountBalanceTrendChartType } from '@/core/statistics.ts'; import { AccountBalanceTrendChartType } from '@/core/statistics.ts';
import { DEFAULT_CHART_COLORS } from '@/consts/color.ts'; import { DEFAULT_CHART_COLORS } from '@/consts/color.ts';
@@ -32,10 +32,10 @@ interface AccountBalanceTrendsChartDataItem {
id: string; id: string;
name: string; name: string;
itemStyle: { itemStyle: {
color: ColorValue; color: ColorStyleValue;
color0?: string; color0?: ColorStyleValue;
borderColor?: string; borderColor?: ColorStyleValue;
borderColor0?: string; borderColor0?: ColorStyleValue;
}; };
selected: boolean; selected: boolean;
type: string; type: string;
+5 -13
View File
@@ -11,7 +11,7 @@
> >
<template #selection="{ item }"> <template #selection="{ item }">
<v-label class="cursor-pointer" style="padding-top: 3px"> <v-label class="cursor-pointer" style="padding-top: 3px">
<v-icon size="28" :icon="mdiSquareRounded" :color="getFinalColor(item.raw)"/> <v-icon size="28" :icon="mdiSquareRounded" :color="getDisplayColor(item.raw)"/>
</v-label> </v-label>
</template> </template>
@@ -23,14 +23,14 @@
<div class="text-center" :key="colorInfo.color" v-for="colorInfo in row"> <div class="text-center" :key="colorInfo.color" v-for="colorInfo in row">
<div class="cursor-pointer" @click="color = colorInfo.color"> <div class="cursor-pointer" @click="color = colorInfo.color">
<v-icon class="ma-2" size="28" <v-icon class="ma-2" size="28"
:icon="mdiSquareRounded" :color="getFinalColor(colorInfo.color)" :icon="mdiSquareRounded" :color="getDisplayColor(colorInfo.color)"
v-if="!modelValue || modelValue !== colorInfo.color" /> v-if="!modelValue || modelValue !== colorInfo.color" />
<v-badge class="right-bottom-icon" color="primary" <v-badge class="right-bottom-icon" color="primary"
offset-x="8" offset-y="8" offset-x="8" offset-y="8"
:location="`bottom ${textDirection === TextDirection.LTR ? 'right' : 'left'}`" :location="`bottom ${textDirection === TextDirection.LTR ? 'right' : 'left'}`"
:icon="mdiCheck" :icon="mdiCheck"
v-if="modelValue && modelValue === colorInfo.color"> v-if="modelValue && modelValue === colorInfo.color">
<v-icon class="ma-2" size="28" :icon="mdiSquareRounded" :color="getFinalColor(colorInfo.color)" /> <v-icon class="ma-2" size="28" :icon="mdiSquareRounded" :color="getDisplayColor(colorInfo.color)" />
</v-badge> </v-badge>
</div> </div>
</div> </div>
@@ -47,9 +47,9 @@ import { useI18n } from '@/locales/helpers.ts';
import { TextDirection } from '@/core/text.ts'; import { TextDirection } from '@/core/text.ts';
import type { ColorValue, ColorInfo } from '@/core/color.ts'; import type { ColorValue, ColorInfo } from '@/core/color.ts';
import { DEFAULT_ICON_COLOR } from '@/consts/color.ts';
import { arrayContainsFieldValue } from '@/lib/common.ts'; import { arrayContainsFieldValue } from '@/lib/common.ts';
import { getColorsInRows } from '@/lib/color.ts'; import { getColorsInRows, getDisplayColor } from '@/lib/color.ts';
import { scrollToSelectedItem } from '@/lib/ui/desktop.ts'; import { scrollToSelectedItem } from '@/lib/ui/desktop.ts';
import { import {
@@ -86,14 +86,6 @@ function hasSelectedIcon(row: ColorInfo[]): boolean {
return arrayContainsFieldValue(row, 'id', props.modelValue); return arrayContainsFieldValue(row, 'id', props.modelValue);
} }
function getFinalColor(color: ColorValue): string {
if (color && color !== DEFAULT_ICON_COLOR) {
return '#' + color;
} else {
return 'var(--default-icon-color)';
}
}
function onMenuStateChanged(state: boolean): void { function onMenuStateChanged(state: boolean): void {
if (state) { if (state) {
nextTick(() => { nextTick(() => {
@@ -16,10 +16,12 @@ import { useUserStore } from '@/stores/user.ts';
import { TextDirection } from '@/core/text.ts'; import { TextDirection } from '@/core/text.ts';
import { type Year1BasedMonth, DateRangeScene } from '@/core/datetime.ts'; import { type Year1BasedMonth, DateRangeScene } from '@/core/datetime.ts';
import type { ColorValue } from '@/core/color.ts'; import type { ColorStyleValue } from '@/core/color.ts';
import { ThemeType } from '@/core/theme.ts'; import { ThemeType } from '@/core/theme.ts';
import { TrendChartType, ChartDateAggregationType } from '@/core/statistics.ts'; import { TrendChartType, ChartDateAggregationType } from '@/core/statistics.ts';
import { DEFAULT_CHART_COLORS } from '@/consts/color.ts'; import { DEFAULT_CHART_COLORS } from '@/consts/color.ts';
import type { YearMonthDataItem, SortableTransactionStatisticDataItem } from '@/models/transaction.ts'; import type { YearMonthDataItem, SortableTransactionStatisticDataItem } from '@/models/transaction.ts';
import { import {
@@ -32,6 +34,9 @@ import {
getDateTypeByDateRange, getDateTypeByDateRange,
getFiscalYearFromUnixTime getFiscalYearFromUnixTime
} from '@/lib/datetime.ts'; } from '@/lib/datetime.ts';
import {
getDisplayColor
} from '@/lib/color.ts';
import { import {
sortStatisticsItems sortStatisticsItems
} from '@/lib/statistics.ts'; } from '@/lib/statistics.ts';
@@ -47,7 +52,7 @@ interface MonthlyTrendsChartDataItem {
id: string; id: string;
name: string; name: string;
itemStyle: { itemStyle: {
color: ColorValue; color: ColorStyleValue;
}; };
selected: boolean; selected: boolean;
type: string; type: string;
@@ -83,7 +88,7 @@ const {
formatAmountToLocalizedNumeralsWithCurrency formatAmountToLocalizedNumeralsWithCurrency
} = useI18n(); } = useI18n();
const { allDateRanges, getItemName, getColor } = useMonthlyTrendsChartBase(props); const { allDateRanges, getItemName } = useMonthlyTrendsChartBase(props);
const userStore = useUserStore(); const userStore = useUserStore();
@@ -218,7 +223,7 @@ const allSeries = computed<MonthlyTrendsChartDataItem[]>(() => {
id: (props.idField && item[props.idField]) ? item[props.idField] as string : getItemName(item[props.nameField] as string), id: (props.idField && item[props.idField]) ? item[props.idField] as string : getItemName(item[props.nameField] as string),
name: (props.idField && item[props.idField]) ? item[props.idField] as string : getItemName(item[props.nameField] as string), name: (props.idField && item[props.idField]) ? item[props.idField] as string : getItemName(item[props.nameField] as string),
itemStyle: { itemStyle: {
color: getColor(props.colorField && item[props.colorField] ? item[props.colorField] as string : DEFAULT_CHART_COLORS[i % DEFAULT_CHART_COLORS.length]), color: getDisplayColor(props.colorField && item[props.colorField] ? item[props.colorField] as string : DEFAULT_CHART_COLORS[i % DEFAULT_CHART_COLORS.length]),
}, },
selected: true, selected: true,
type: 'line', type: 'line',
+3 -12
View File
@@ -13,13 +13,12 @@ import type { CallbackDataParams } from 'echarts/types/dist/shared';
import { useI18n } from '@/locales/helpers.ts'; import { useI18n } from '@/locales/helpers.ts';
import { type CommonPieChartDataItem, type CommonPieChartProps, usePieChartBase } from '@/components/base/PieChartBase.ts' import { type CommonPieChartDataItem, type CommonPieChartProps, usePieChartBase } from '@/components/base/PieChartBase.ts'
import type { ColorValue } from '@/core/color.ts'; import type { ColorStyleValue } from '@/core/color.ts';
import { ThemeType } from '@/core/theme.ts'; import { ThemeType } from '@/core/theme.ts';
import { DEFAULT_ICON_COLOR } from '@/consts/color.ts';
interface DesktopPieChartDataItem extends CommonPieChartDataItem { interface DesktopPieChartDataItem extends CommonPieChartDataItem {
itemStyle: { itemStyle: {
color: ColorValue; color: ColorStyleValue;
}; };
selected: boolean; selected: boolean;
} }
@@ -66,7 +65,7 @@ const seriesData = computed<DesktopPieChartDataItem[]>(() => {
ret.push({ ret.push({
...item, ...item,
itemStyle: { itemStyle: {
color: getColor(item.color), color: item.color,
}, },
selected: true selected: true
}); });
@@ -214,14 +213,6 @@ const chartOptions = computed<object>(() => {
}; };
}); });
function getColor(color: string): ColorValue {
if (color && color !== DEFAULT_ICON_COLOR) {
color = '#' + color;
}
return color;
}
function clickItem(e: ECElementEvent): void { function clickItem(e: ECElementEvent): void {
if (!props.enableClickItem || e.componentType !== 'series' || e.seriesType !=='pie') { if (!props.enableClickItem || e.componentType !== 'series' || e.seriesType !=='pie') {
return; return;
@@ -37,7 +37,7 @@
<template #inner> <template #inner>
<div class="display-flex padding-top-half"> <div class="display-flex padding-top-half">
<div class="statistics-percent-line width-100 no-margin-horizontal"> <div class="statistics-percent-line width-100 no-margin-horizontal">
<f7-progressbar :progress="item.percent >= 0 ? item.percent : 0" :style="{ '--f7-progressbar-progress-color': (item.color ? '#' + item.color : '') } "></f7-progressbar> <f7-progressbar :progress="item.percent >= 0 ? item.percent : 0" :style="{ '--f7-progressbar-progress-color': item.color } "></f7-progressbar>
</div> </div>
</div> </div>
</template> </template>
@@ -56,13 +56,13 @@ import {
useAccountBalanceTrendsChartBase useAccountBalanceTrendsChartBase
} from '@/components/base/AccountBalanceTrendsChartBase.ts' } from '@/components/base/AccountBalanceTrendsChartBase.ts'
import type { ColorValue } from '@/core/color.ts'; import type { ColorStyleValue } from '@/core/color.ts';
import { DEFAULT_CHART_COLORS } from '@/consts/color.ts'; import { DEFAULT_CHART_COLORS } from '@/consts/color.ts';
interface MobileAccountBalanceTrendsChartItem extends AccountBalanceTrendsChartItem { interface MobileAccountBalanceTrendsChartItem extends AccountBalanceTrendsChartItem {
index: number; index: number;
percent: number; percent: number;
color: ColorValue; color: ColorStyleValue;
} }
interface MobileAccountBalanceTrendsChartProps extends CommonAccountBalanceTrendsChartProps { interface MobileAccountBalanceTrendsChartProps extends CommonAccountBalanceTrendsChartProps {
@@ -104,7 +104,7 @@ const allVirtualListItems = computed<MobileAccountBalanceTrendsChartItem[]>(() =
averageBalance: dataItem.averageBalance, averageBalance: dataItem.averageBalance,
minimumBalance: dataItem.minimumBalance, minimumBalance: dataItem.minimumBalance,
maximumBalance: dataItem.maximumBalance, maximumBalance: dataItem.maximumBalance,
color: DEFAULT_CHART_COLORS[0], color: `#${DEFAULT_CHART_COLORS[0]}`,
percent: 0.0 percent: 0.0
}; };
@@ -96,8 +96,11 @@ import { type CommonMonthlyTrendsChartProps, type MonthlyTrendsBarChartClickEven
import { useUserStore } from '@/stores/user.ts'; import { useUserStore } from '@/stores/user.ts';
import { type Year1BasedMonth, type UnixTimeRange, DateRangeScene } from '@/core/datetime.ts'; import { type Year1BasedMonth, type UnixTimeRange, DateRangeScene } from '@/core/datetime.ts';
import type { ColorStyleValue } from '@/core/color.ts';
import { ChartDateAggregationType } from '@/core/statistics.ts'; import { ChartDateAggregationType } from '@/core/statistics.ts';
import { DEFAULT_CHART_COLORS } from '@/consts/color.ts'; import { DEFAULT_CHART_COLORS } from '@/consts/color.ts';
import type { YearMonthDataItem, SortableTransactionStatisticDataItem } from '@/models/transaction.ts'; import type { YearMonthDataItem, SortableTransactionStatisticDataItem } from '@/models/transaction.ts';
import { import {
@@ -109,6 +112,9 @@ import {
getDateTypeByDateRange, getDateTypeByDateRange,
getFiscalYearFromUnixTime getFiscalYearFromUnixTime
} from '@/lib/datetime.ts'; } from '@/lib/datetime.ts';
import {
getDisplayColor
} from '@/lib/color.ts';
import { import {
sortStatisticsItems sortStatisticsItems
} from '@/lib/statistics.ts'; } from '@/lib/statistics.ts';
@@ -116,7 +122,7 @@ import {
interface TrendsBarChartLegend { interface TrendsBarChartLegend {
readonly id: string; readonly id: string;
readonly name: string; readonly name: string;
readonly color: string; readonly color: ColorStyleValue;
readonly displayOrders: number[]; readonly displayOrders: number[];
} }
@@ -157,7 +163,7 @@ const {
formatAmountToLocalizedNumeralsWithCurrency formatAmountToLocalizedNumeralsWithCurrency
} = useI18n(); } = useI18n();
const { allDateRanges, getItemName, getColor } = useMonthlyTrendsChartBase(props); const { allDateRanges, getItemName } = useMonthlyTrendsChartBase(props);
const userStore = useUserStore(); const userStore = useUserStore();
@@ -179,7 +185,7 @@ const allDisplayDataItems = computed<MonthlyTrendsBarChartData>(() => {
const legend: TrendsBarChartLegend = { const legend: TrendsBarChartLegend = {
id: id, id: id,
name: (props.nameField && item[props.nameField]) ? getItemName(item[props.nameField] as string) : id, name: (props.nameField && item[props.nameField]) ? getItemName(item[props.nameField] as string) : id,
color: getColor(props.colorField && item[props.colorField] ? item[props.colorField] as string : DEFAULT_CHART_COLORS[i % DEFAULT_CHART_COLORS.length]), color: getDisplayColor(props.colorField && item[props.colorField] ? item[props.colorField] as string : DEFAULT_CHART_COLORS[i % DEFAULT_CHART_COLORS.length]),
displayOrders: (props.displayOrdersField && item[props.displayOrdersField]) ? item[props.displayOrdersField] as number[] : [0] displayOrders: (props.displayOrdersField && item[props.displayOrdersField]) ? item[props.displayOrdersField] as number[] : [0]
}; };
+8 -21
View File
@@ -7,7 +7,7 @@
fill="transparent" fill="transparent"
cx="0" cy="0" cx="0" cy="0"
:r="diameter / 2" :r="diameter / 2"
:stroke="getColor(item.color)" :stroke="item.color"
:stroke-width="diameter" :stroke-width="diameter"
:stroke-dasharray="getItemStrokeDash(item)" :stroke-dasharray="getItemStrokeDash(item)"
:stroke-dashoffset="getItemDashOffset(item, validItems, itemCommonDashOffset)" :stroke-dashoffset="getItemDashOffset(item, validItems, itemCommonDashOffset)"
@@ -50,7 +50,7 @@
</f7-chip> </f7-chip>
<f7-chip outline <f7-chip outline
:text="selectedItem.displayPercent" :text="selectedItem.displayPercent"
:style="getColorStyle(selectedItem ? selectedItem.color : '', '--f7-chip-outline-border-color')" :style="getColorStyle(selectedItem?.color, '--f7-chip-outline-border-color')"
v-else-if="!skeleton"></f7-chip> v-else-if="!skeleton"></f7-chip>
</p> </p>
<p v-else-if="!validItems || !validItems.length"> <p v-else-if="!validItems || !validItems.length">
@@ -60,7 +60,7 @@
<span class="skeleton-text" v-if="skeleton">Name</span> <span class="skeleton-text" v-if="skeleton">Name</span>
<span v-else-if="!skeleton && selectedItem.displayName">{{ selectedItem.displayName }}</span> <span v-else-if="!skeleton && selectedItem.displayName">{{ selectedItem.displayName }}</span>
<span class="skeleton-text" v-if="skeleton">Value</span> <span class="skeleton-text" v-if="skeleton">Value</span>
<span v-else-if="!skeleton && showValue" :style="getColorStyle(selectedItem ? selectedItem.color : '')">{{ selectedItem.displayValue }}</span> <span v-else-if="!skeleton && showValue" :style="getColorStyle(selectedItem?.color)">{{ selectedItem.displayValue }}</span>
<f7-icon class="item-navigate-icon icon-with-direction" f7="chevron_right" v-if="enableClickItem"></f7-icon> <f7-icon class="item-navigate-icon icon-with-direction" f7="chevron_right" v-if="enableClickItem"></f7-icon>
</f7-link> </f7-link>
<f7-link :no-link-class="true" v-else-if="!validItems || !validItems.length"> <f7-link :no-link-class="true" v-else-if="!validItems || !validItems.length">
@@ -82,13 +82,12 @@ import { computed } from 'vue';
import { useI18n } from '@/locales/helpers.ts'; import { useI18n } from '@/locales/helpers.ts';
import { type CommonPieChartDataItem, type CommonPieChartProps, usePieChartBase } from '@/components/base/PieChartBase.ts' import { type CommonPieChartDataItem, type CommonPieChartProps, usePieChartBase } from '@/components/base/PieChartBase.ts'
import type { ColorValue } from '@/core/color.ts'; import type { ColorStyleValue } from '@/core/color.ts';
import { DEFAULT_ICON_COLOR } from '@/consts/color.ts';
interface MobilePieChartProps extends CommonPieChartProps { interface MobilePieChartProps extends CommonPieChartProps {
showCenterText?: boolean; showCenterText?: boolean;
showSelectedItemInfo?: boolean; showSelectedItemInfo?: boolean;
centerTextBackground?: ColorValue; centerTextBackground?: ColorStyleValue;
} }
const props = defineProps<MobilePieChartProps>(); const props = defineProps<MobilePieChartProps>();
@@ -135,25 +134,13 @@ const itemCommonDashOffset = computed<number>(() => {
return offset; return offset;
}); });
function getColor(color: ColorValue): ColorValue { function getColorStyle(color: ColorStyleValue, additionalFieldName?: string): Record<string, string> {
if (color && color !== DEFAULT_ICON_COLOR) {
color = '#' + color;
} else {
color = 'var(--default-icon-color)';
}
return color;
}
function getColorStyle(color: ColorValue, additionalFieldName?: string): Record<string, string> {
const finalColor = getColor(color);
const ret: Record<string, string> = { const ret: Record<string, string> = {
color: finalColor color: color
}; };
if (additionalFieldName) { if (additionalFieldName) {
ret[additionalFieldName] = finalColor; ret[additionalFieldName] = color;
} }
return ret; return ret;
+3 -1
View File
@@ -1,4 +1,4 @@
import type { ColorValue } from '@/core/color.ts'; import type { ColorValue, ColorStyleValue } from '@/core/color.ts';
const defaultColor: ColorValue = '000000'; const defaultColor: ColorValue = '000000';
@@ -6,6 +6,8 @@ export const DEFAULT_ICON_COLOR: ColorValue = defaultColor;
export const DEFAULT_ACCOUNT_COLOR: ColorValue = defaultColor; export const DEFAULT_ACCOUNT_COLOR: ColorValue = defaultColor;
export const DEFAULT_CATEGORY_COLOR: ColorValue = defaultColor; export const DEFAULT_CATEGORY_COLOR: ColorValue = defaultColor;
export const DEFAULT_COLOR_STYLE_VARIABLE: ColorStyleValue = 'var(--default-icon-color)';
const allAvailableColors: ColorValue[] = [ const allAvailableColors: ColorValue[] = [
'000000', // black '000000', // black
'8e8e93', // gray '8e8e93', // gray
+7 -5
View File
@@ -2,13 +2,15 @@ import type { TypeAndName } from './base.ts';
export type ColorValue = string; export type ColorValue = string;
export type ColorStyleValue = `#${ColorValue}` | 'var(--default-icon-color)';
export interface ColorInfo extends Record<string, unknown> { export interface ColorInfo extends Record<string, unknown> {
readonly color: ColorValue; readonly color: ColorValue;
} }
export interface AmountColor { export interface AmountColor {
readonly expenseAmountColor: ColorValue; readonly expenseAmountColor: ColorStyleValue;
readonly incomeAmountColor: ColorValue; readonly incomeAmountColor: ColorStyleValue;
} }
export class PresetAmountColor implements TypeAndName { export class PresetAmountColor implements TypeAndName {
@@ -26,12 +28,12 @@ export class PresetAmountColor implements TypeAndName {
public readonly type: number; public readonly type: number;
public readonly name: string; public readonly name: string;
public readonly lightThemeColor: string; public readonly lightThemeColor: ColorStyleValue;
public readonly darkThemeColor: string; public readonly darkThemeColor: ColorStyleValue;
public readonly expenseClassName: string; public readonly expenseClassName: string;
public readonly incomeClassName: string; public readonly incomeClassName: string;
private constructor(type: number, name: string, lightThemeColor: string, darkThemeColor: string, expenseClassName: string, incomeClassName: string) { private constructor(type: number, name: string, lightThemeColor: ColorStyleValue, darkThemeColor: ColorStyleValue, expenseClassName: string, incomeClassName: string) {
this.type = type; this.type = type;
this.name = name; this.name = name;
this.lightThemeColor = lightThemeColor; this.lightThemeColor = lightThemeColor;
+35 -1
View File
@@ -1,4 +1,15 @@
import type { ColorValue, ColorInfo } from '@/core/color.ts'; import type {
ColorValue,
ColorStyleValue,
ColorInfo
} from '@/core/color.ts';
import {
DEFAULT_ICON_COLOR,
DEFAULT_ACCOUNT_COLOR,
DEFAULT_CATEGORY_COLOR,
DEFAULT_COLOR_STYLE_VARIABLE
} from '@/consts/color.ts';
export function getColorsInRows(allColorValues: ColorValue[], itemPerRow: number): ColorInfo[][] { export function getColorsInRows(allColorValues: ColorValue[], itemPerRow: number): ColorInfo[][] {
const ret: ColorInfo[][] = []; const ret: ColorInfo[][] = [];
@@ -16,3 +27,26 @@ export function getColorsInRows(allColorValues: ColorValue[], itemPerRow: number
return ret; return ret;
} }
export function getDisplayColor(color?: ColorValue): ColorStyleValue {
if (color && color !== DEFAULT_ICON_COLOR) {
return `#${color}`;
} else {
return DEFAULT_COLOR_STYLE_VARIABLE;
}
}
export function getCategoryDisplayColor(color?: ColorValue): ColorStyleValue {
if (color && color !== DEFAULT_CATEGORY_COLOR) {
return `#${color}`;
} else {
return DEFAULT_COLOR_STYLE_VARIABLE;
}
}
export function getAccountDisplayColor(color?: ColorValue): ColorStyleValue {
if (color && color !== DEFAULT_ACCOUNT_COLOR) {
return `#${color}`;
} else {
return DEFAULT_COLOR_STYLE_VARIABLE;
}
}
@@ -8,9 +8,11 @@ import { type TransactionStatisticsFilter, useStatisticsStore } from '@/stores/s
import type { TypeAndDisplayName } from '@/core/base.ts'; import type { TypeAndDisplayName } from '@/core/base.ts';
import { type LocalizedDateRange, type WeekDayValue, DateRangeScene, DateRange } from '@/core/datetime.ts'; import { type LocalizedDateRange, type WeekDayValue, DateRangeScene, DateRange } from '@/core/datetime.ts';
import type { ColorStyleValue } from '@/core/color.ts';
import { StatisticsAnalysisType, ChartDataType, ChartSortingType, ChartDateAggregationType } from '@/core/statistics.ts'; import { StatisticsAnalysisType, ChartDataType, ChartSortingType, ChartDateAggregationType } from '@/core/statistics.ts';
import { DEFAULT_ACCOUNT_COLOR, DEFAULT_CATEGORY_COLOR } from '@/consts/color.ts';
import { DISPLAY_HIDDEN_AMOUNT } from '@/consts/numeral.ts'; import { DISPLAY_HIDDEN_AMOUNT } from '@/consts/numeral.ts';
import type { import type {
TransactionCategoricalAnalysisData, TransactionCategoricalAnalysisData,
TransactionCategoricalAnalysisDataItem, TransactionCategoricalAnalysisDataItem,
@@ -19,6 +21,7 @@ import type {
import { limitText, findNameByType, findDisplayNameByType } from '@/lib/common.ts'; import { limitText, findNameByType, findDisplayNameByType } from '@/lib/common.ts';
import { getYearMonthFirstUnixTime, getYearMonthLastUnixTime } from '@/lib/datetime.ts'; import { getYearMonthFirstUnixTime, getYearMonthLastUnixTime } from '@/lib/datetime.ts';
import { getDisplayColor, getCategoryDisplayColor, getAccountDisplayColor } from '@/lib/color.ts';
export function useStatisticsTransactionPageBase() { export function useStatisticsTransactionPageBase() {
const { const {
@@ -205,21 +208,13 @@ export function useStatisticsTransactionPageBase() {
} }
} }
function getTransactionCategoricalAnalysisDataItemColor(item: TransactionCategoricalAnalysisDataItem): string { function getTransactionCategoricalAnalysisDataItemDisplayColor(item: TransactionCategoricalAnalysisDataItem): ColorStyleValue {
if (item.type === 'category') { if (item.type === 'category') {
if (item.color === DEFAULT_CATEGORY_COLOR) { return getCategoryDisplayColor(item.color);
return 'var(--default-icon-color)';
} else {
return '#' + item.color;
}
} else if (item.type === 'account') { } else if (item.type === 'account') {
if (item.color === DEFAULT_ACCOUNT_COLOR) { return getAccountDisplayColor(item.color);
return 'var(--default-icon-color)';
} else {
return '#' + item.color;
}
} else { } else {
return item.color; return getDisplayColor(item.color);
} }
} }
@@ -272,7 +267,7 @@ export function useStatisticsTransactionPageBase() {
trendsAnalysisData, trendsAnalysisData,
// functions // functions
canShowCustomDateRange, canShowCustomDateRange,
getTransactionCategoricalAnalysisDataItemColor, getTransactionCategoricalAnalysisDataItemDisplayColor,
getDisplayAmount getDisplayAmount
}; };
} }
@@ -244,7 +244,7 @@
<span class="statistics-amount">{{ getDisplayAmount(item.totalAmount, defaultCurrency) }}</span> <span class="statistics-amount">{{ getDisplayAmount(item.totalAmount, defaultCurrency) }}</span>
</div> </div>
<div> <div>
<v-progress-linear :color="item.color ? getTransactionCategoricalAnalysisDataItemColor(item) : 'primary'" <v-progress-linear :color="item.color ? getTransactionCategoricalAnalysisDataItemDisplayColor(item) : 'primary'"
:bg-color="isDarkMode ? '#444444' : '#f8f8f8'" :bg-opacity="1" :bg-color="isDarkMode ? '#444444' : '#f8f8f8'" :bg-opacity="1"
:model-value="item.percent >= 0 ? item.percent : 0" :model-value="item.percent >= 0 ? item.percent : 0"
:height="4"></v-progress-linear> :height="4"></v-progress-linear>
@@ -458,7 +458,7 @@ const {
categoricalAnalysisData, categoricalAnalysisData,
trendsAnalysisData, trendsAnalysisData,
canShowCustomDateRange, canShowCustomDateRange,
getTransactionCategoricalAnalysisDataItemColor, getTransactionCategoricalAnalysisDataItemDisplayColor,
getDisplayAmount getDisplayAmount
} = useStatisticsTransactionPageBase(); } = useStatisticsTransactionPageBase();
@@ -182,7 +182,7 @@
<template #inner-end> <template #inner-end>
<div class="statistics-item-end"> <div class="statistics-item-end">
<div class="statistics-percent-line"> <div class="statistics-percent-line">
<f7-progressbar :progress="item.percent >= 0 ? item.percent : 0" :style="{ '--f7-progressbar-progress-color': (item.color ? getTransactionCategoricalAnalysisDataItemColor(item) : '') } "></f7-progressbar> <f7-progressbar :progress="item.percent >= 0 ? item.percent : 0" :style="{ '--f7-progressbar-progress-color': (item.color ? getTransactionCategoricalAnalysisDataItemDisplayColor(item) : '') } "></f7-progressbar>
</div> </div>
</div> </div>
</template> </template>
@@ -404,7 +404,7 @@ const {
categoricalAnalysisData, categoricalAnalysisData,
trendsAnalysisData, trendsAnalysisData,
canShowCustomDateRange, canShowCustomDateRange,
getTransactionCategoricalAnalysisDataItemColor, getTransactionCategoricalAnalysisDataItemDisplayColor,
getDisplayAmount getDisplayAmount
} = useStatisticsTransactionPageBase(); } = useStatisticsTransactionPageBase();