diff --git a/packages/desktop-client/src/components/reports/ChooseGraph.tsx b/packages/desktop-client/src/components/reports/ChooseGraph.tsx index c8afbdd50a3655f927d6d4b09e4ed6496ae07d56..0e19a7c146762803fd0261c266c25e05ac688b71 100644 --- a/packages/desktop-client/src/components/reports/ChooseGraph.tsx +++ b/packages/desktop-client/src/components/reports/ChooseGraph.tsx @@ -1,7 +1,7 @@ // @ts-strict-ignore import React, { useRef } from 'react'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { type CSSProperties } from '../../style'; @@ -20,7 +20,7 @@ import { ReportTableTotals } from './graphs/tableGraph/ReportTableTotals'; import { ReportOptions } from './ReportOptions'; type ChooseGraphProps = { - data: GroupedEntity; + data: DataEntity; filters?: RuleConditionEntity[]; mode: string; graphType: string; @@ -160,13 +160,14 @@ export function ChooseGraph({ <ReportTableHeader headerScrollRef={headerScrollRef} handleScroll={handleScroll} - data={mode === 'time' && data.intervalData} + data={data.intervalData} groupBy={groupBy} interval={interval} balanceType={balanceType} compact={compact} style={rowStyle} compactStyle={compactStyle} + mode={mode} /> <ReportTable saveScrollWidth={saveScrollWidth} diff --git a/packages/desktop-client/src/components/reports/ReportSummary.tsx b/packages/desktop-client/src/components/reports/ReportSummary.tsx index 790f52193ac515d04451d0db13a0985898a6ba49..9e25d548cfe5bd6361695548f05067442c8b21f5 100644 --- a/packages/desktop-client/src/components/reports/ReportSummary.tsx +++ b/packages/desktop-client/src/components/reports/ReportSummary.tsx @@ -1,4 +1,3 @@ -// @ts-strict-ignore import React from 'react'; import * as monthUtils from 'loot-core/src/shared/months'; @@ -7,7 +6,7 @@ import { integerToCurrency, amountToInteger, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { theme, styles } from '../../style'; import { Text } from '../common/Text'; @@ -19,8 +18,8 @@ import { ReportOptions } from './ReportOptions'; type ReportSummaryProps = { startDate: string; endDate: string; - data: GroupedEntity; - balanceTypeOp: string; + data: DataEntity; + balanceTypeOp: 'totalDebts' | 'totalAssets' | 'totalTotals'; interval: string; intervalsCount: number; }; @@ -63,20 +62,20 @@ export function ReportSummary({ > {monthUtils.format( startDate, - ReportOptions.intervalFormat.get(interval), + ReportOptions.intervalFormat.get(interval) || '', )} {monthUtils.format( startDate, - ReportOptions.intervalFormat.get(interval), + ReportOptions.intervalFormat.get(interval) || '', ) !== monthUtils.format( endDate, - ReportOptions.intervalFormat.get(interval), + ReportOptions.intervalFormat.get(interval) || '', ) && ' to ' + monthUtils.format( endDate, - ReportOptions.intervalFormat.get(interval), + ReportOptions.intervalFormat.get(interval) || '', )} </Text> </View> @@ -153,7 +152,7 @@ export function ReportSummary({ </PrivacyFilter> </Text> <Text style={{ fontWeight: 600 }}> - Per {ReportOptions.intervalMap.get(interval).toLowerCase()} + Per {(ReportOptions.intervalMap.get(interval) || '').toLowerCase()} </Text> </View> </View> diff --git a/packages/desktop-client/src/components/reports/graphs/AreaGraph.tsx b/packages/desktop-client/src/components/reports/graphs/AreaGraph.tsx index ed21a78200dacd4afbe25947dbd5151c316b684d..860d2c7fcdfe0881548982a162a999385307628f 100644 --- a/packages/desktop-client/src/components/reports/graphs/AreaGraph.tsx +++ b/packages/desktop-client/src/components/reports/graphs/AreaGraph.tsx @@ -17,7 +17,7 @@ import { amountToCurrency, amountToCurrencyNoDecimal, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { usePrivacyMode } from '../../../hooks/usePrivacyMode'; import { useResponsive } from '../../../ResponsiveProvider'; @@ -105,14 +105,14 @@ const customLabel = (props, width, end) => { const textAnchor = props.index === 0 ? 'left' : 'middle'; const display = props.value !== 0 && `${amountToCurrencyNoDecimal(props.value)}`; - const textSize = adjustTextSize(width, 'area'); + const textSize = adjustTextSize({ sized: width, type: 'area' }); return renderCustomLabel(calcX, calcY, textAnchor, display, textSize); }; type AreaGraphProps = { style?: CSSProperties; - data: GroupedEntity; + data: DataEntity; balanceTypeOp: string; compact?: boolean; viewLabels: boolean; diff --git a/packages/desktop-client/src/components/reports/graphs/BarGraph.tsx b/packages/desktop-client/src/components/reports/graphs/BarGraph.tsx index a01984afae5cd5046073afcec169685efc3e5b41..e8d1eb26b7acff209191cbdd3b2ae16e65f27f7a 100644 --- a/packages/desktop-client/src/components/reports/graphs/BarGraph.tsx +++ b/packages/desktop-client/src/components/reports/graphs/BarGraph.tsx @@ -19,7 +19,7 @@ import { amountToCurrency, amountToCurrencyNoDecimal, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../hooks/useAccounts'; @@ -122,18 +122,18 @@ const customLabel = (props, typeOp) => { const textAnchor = 'middle'; const display = props.value !== 0 && `${amountToCurrencyNoDecimal(props.value)}`; - const textSize = adjustTextSize( - props.width, - typeOp === 'totalTotals' ? 'default' : 'variable', - props.value, - ); + const textSize = adjustTextSize({ + sized: props.width, + type: typeOp === 'totalTotals' ? 'default' : 'variable', + values: props.value, + }); return renderCustomLabel(calcX, calcY, textAnchor, display, textSize); }; type BarGraphProps = { style?: CSSProperties; - data: GroupedEntity; + data: DataEntity; filters: RuleConditionEntity[]; groupBy: string; balanceTypeOp: string; diff --git a/packages/desktop-client/src/components/reports/graphs/DonutGraph.tsx b/packages/desktop-client/src/components/reports/graphs/DonutGraph.tsx index e6cfeffa5ed6cceb56ba15cee53a1090dc2dfbae..c1f50df27a39acbcbcf482fda153013ebc98eba7 100644 --- a/packages/desktop-client/src/components/reports/graphs/DonutGraph.tsx +++ b/packages/desktop-client/src/components/reports/graphs/DonutGraph.tsx @@ -4,7 +4,7 @@ import React, { useState } from 'react'; import { PieChart, Pie, Cell, Sector, ResponsiveContainer } from 'recharts'; import { amountToCurrency } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../hooks/useAccounts'; @@ -158,7 +158,7 @@ const customLabel = props => { const calcY = props.cy + radius * Math.sin(-props.midAngle * RADIAN); const textAnchor = calcX > props.cx ? 'start' : 'end'; const display = props.value !== 0 && `${(props.percent * 100).toFixed(0)}%`; - const textSize = adjustTextSize(size, 'donut'); + const textSize = adjustTextSize({ sized: size, type: 'donut' }); const showLabel = props.percent; const showLabelThreshold = 0.05; const fill = theme.reportsInnerLabel; @@ -177,7 +177,7 @@ const customLabel = props => { type DonutGraphProps = { style?: CSSProperties; - data: GroupedEntity; + data: DataEntity; filters: RuleConditionEntity[]; groupBy: string; balanceTypeOp: string; diff --git a/packages/desktop-client/src/components/reports/graphs/LineGraph.tsx b/packages/desktop-client/src/components/reports/graphs/LineGraph.tsx index e7b1174246b3d637c3817b193976cb794203c7a0..3cb78f3d4df614816a410875bb2b20600598c4cd 100644 --- a/packages/desktop-client/src/components/reports/graphs/LineGraph.tsx +++ b/packages/desktop-client/src/components/reports/graphs/LineGraph.tsx @@ -16,7 +16,7 @@ import { amountToCurrency, amountToCurrencyNoDecimal, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/types/models/reports'; +import { type DataEntity } from 'loot-core/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../hooks/useAccounts'; @@ -109,7 +109,7 @@ const CustomTooltip = ({ type LineGraphProps = { style?: CSSProperties; - data: GroupedEntity; + data: DataEntity; filters: RuleConditionEntity[]; groupBy: string; compact?: boolean; diff --git a/packages/desktop-client/src/components/reports/graphs/StackedBarGraph.tsx b/packages/desktop-client/src/components/reports/graphs/StackedBarGraph.tsx index 3712c10a6ba50ddd9ea9f5b4dabfea42fcae8f66..2df89692dac74ab44ae0039f5c83e3440d9e780f 100644 --- a/packages/desktop-client/src/components/reports/graphs/StackedBarGraph.tsx +++ b/packages/desktop-client/src/components/reports/graphs/StackedBarGraph.tsx @@ -17,7 +17,7 @@ import { amountToCurrency, amountToCurrencyNoDecimal, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../hooks/useAccounts'; @@ -138,7 +138,7 @@ const customLabel = props => { type StackedBarGraphProps = { style?: CSSProperties; - data: GroupedEntity; + data: DataEntity; filters: RuleConditionEntity[]; groupBy: string; compact?: boolean; diff --git a/packages/desktop-client/src/components/reports/graphs/adjustTextSize.ts b/packages/desktop-client/src/components/reports/graphs/adjustTextSize.ts index b8e4824140fc15d4a3f5cf9e349233ca439f3508..f1b9116ef606343b962d2a6935eb5c12fa353a6f 100644 --- a/packages/desktop-client/src/components/reports/graphs/adjustTextSize.ts +++ b/packages/desktop-client/src/components/reports/graphs/adjustTextSize.ts @@ -1,13 +1,23 @@ -// @ts-strict-ignore -export const adjustTextSize = ( - sized: number, - type: string, - values?: number, -): `${number}px` => { - let source; +export const adjustTextSize = ({ + sized, + type, + values = 0, +}: { + sized: number; + type: string; + values?: number; +}): `${number}px` => { + let source: { + size: number; + font: number; + }[] = [{ size: -1, font: -1 }]; switch (type) { case 'variable': - source = variableLookup.find(({ value }) => values >= value).arr; + const findLookup = variableLookup.find(({ value }) => values >= value); + if (!findLookup) { + break; + } + source = findLookup.arr; break; case 'donut': source = donutLookup; @@ -15,8 +25,12 @@ export const adjustTextSize = ( default: source = defaultLookup; } - const lookup = source.find(({ size }) => sized >= size); - return `${lookup.font}px`; + const findSource = source.find(({ size }) => sized >= size); + if (!findSource) { + return '13px'; + } + + return `${findSource.font}px`; }; const defaultLookup = [ diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/RenderTableRow.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/RenderTableRow.tsx new file mode 100644 index 0000000000000000000000000000000000000000..aad73c34239433d51a360eaa91c45a95b1f28737 --- /dev/null +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/RenderTableRow.tsx @@ -0,0 +1,55 @@ +import React, { type ReactNode } from 'react'; + +import { type GroupedEntity } from 'loot-core/src/types/models/reports'; + +import { type CSSProperties } from '../../../../style'; +import { View } from '../../../common/View'; + +import { type renderRowProps } from './ReportTable'; + +type RenderTableRowProps = { + index: number; + parent_index?: number; + compact: boolean; + renderRow: (arg: renderRowProps) => ReactNode; + intervalsCount: number; + mode: string; + metadata: GroupedEntity[]; + style?: CSSProperties; + compactStyle?: CSSProperties; +}; + +export function RenderTableRow({ + index, + parent_index, + compact, + renderRow, + intervalsCount, + mode, + metadata, + style, + compactStyle, +}: RenderTableRowProps) { + const child = metadata[index]; + const parent = + parent_index !== undefined ? metadata[parent_index] : ({} as GroupedEntity); + + const item = + parent_index === undefined + ? child + : (parent.categories && parent.categories[index]) || + ({} as GroupedEntity); + + return ( + <View> + {renderRow({ + item, + mode, + intervalsCount, + compact, + style, + compactStyle, + })} + </View> + ); +} diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTable.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTable.tsx index 9987321dbdaf0f0995d9e43425c36d0978130338..c45be017ec6a23fd3a2971dae84d63360ea531a0 100644 --- a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTable.tsx +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTable.tsx @@ -1,13 +1,15 @@ -// @ts-strict-ignore import React, { + type RefObject, useCallback, useLayoutEffect, useRef, type UIEventHandler, } from 'react'; -import { type RefProp } from 'react-spring'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { + type GroupedEntity, + type DataEntity, +} from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { type CSSProperties } from '../../../../style'; @@ -19,11 +21,11 @@ import { ReportTableRow } from './ReportTableRow'; type ReportTableProps = { saveScrollWidth: (value: number) => void; - listScrollRef: RefProp<HTMLDivElement>; + listScrollRef: RefObject<HTMLDivElement>; handleScroll: UIEventHandler<HTMLDivElement>; groupBy: string; balanceTypeOp: 'totalDebts' | 'totalTotals' | 'totalAssets'; - data: GroupedEntity; + data: DataEntity; filters?: RuleConditionEntity[]; mode: string; intervalsCount: number; @@ -34,6 +36,15 @@ type ReportTableProps = { showOffBudget?: boolean; }; +export type renderRowProps = { + item: GroupedEntity; + mode: string; + intervalsCount: number; + compact: boolean; + style?: CSSProperties; + compactStyle?: CSSProperties; +}; + export function ReportTable({ saveScrollWidth, listScrollRef, @@ -58,8 +69,15 @@ export function ReportTable({ } }); - const renderItem = useCallback( - ({ item, mode, intervalsCount, compact, style, compactStyle }) => { + const renderRow = useCallback( + ({ + item, + mode, + intervalsCount, + compact, + style, + compactStyle, + }: renderRowProps) => { return ( <ReportTableRow item={item} @@ -109,7 +127,7 @@ export function ReportTable({ intervalsCount={intervalsCount} mode={mode} groupBy={groupBy} - renderItem={renderItem} + renderRow={renderRow} compact={compact} style={style} compactStyle={compactStyle} diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableHeader.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableHeader.tsx index 2246e4b1263a15aeaaaa3dc200f263742291bd1c..4543fda453981c08099116464231992b59152307 100644 --- a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableHeader.tsx +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableHeader.tsx @@ -1,8 +1,6 @@ -// @ts-strict-ignore -import React, { type UIEventHandler } from 'react'; -import { type RefProp } from 'react-spring'; +import React, { type RefObject, type UIEventHandler } from 'react'; -import { type DataEntity } from 'loot-core/src/types/models/reports'; +import { type IntervalEntity } from 'loot-core/src/types/models/reports'; import { theme } from '../../../../style'; import { type CSSProperties } from '../../../../style/types'; @@ -12,14 +10,15 @@ import { ReportOptions } from '../../ReportOptions'; type ReportTableHeaderProps = { groupBy: string; - interval?: string; - data?: DataEntity[]; + interval: string; + data: IntervalEntity[]; balanceType: string; - headerScrollRef: RefProp<HTMLDivElement>; + headerScrollRef: RefObject<HTMLDivElement>; handleScroll: UIEventHandler<HTMLDivElement>; compact: boolean; - style?: CSSProperties; - compactStyle?: CSSProperties; + style: CSSProperties; + compactStyle: CSSProperties; + mode: string; }; export function ReportTableHeader({ @@ -32,6 +31,7 @@ export function ReportTableHeader({ compact, style, compactStyle, + mode, }: ReportTableHeaderProps) { return ( <Row @@ -70,7 +70,7 @@ export function ReportTableHeader({ : groupBy } /> - {data + {mode === 'time' ? data.map((header, index) => { return ( <Cell diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableList.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableList.tsx index e619d4e0b3f1b3f9cf43065870ab3e7d7a0f9230..f2076605a79f2be8dcfdc339defab83c866f8618 100644 --- a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableList.tsx +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableList.tsx @@ -1,18 +1,23 @@ -// @ts-strict-ignore -import React from 'react'; +import React, { type ReactNode } from 'react'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { + type GroupedEntity, + type DataEntity, +} from 'loot-core/src/types/models/reports'; import { type CSSProperties, theme } from '../../../../style'; import { View } from '../../../common/View'; import { Row } from '../../../table'; +import { RenderTableRow } from './RenderTableRow'; +import { type renderRowProps } from './ReportTable'; + type ReportTableListProps = { - data: GroupedEntity; - mode?: string; - intervalsCount?: number; + data: DataEntity; + mode: string; + intervalsCount: number; groupBy: string; - renderItem; + renderRow: (arg: renderRowProps) => ReactNode; compact: boolean; style?: CSSProperties; compactStyle?: CSSProperties; @@ -23,47 +28,28 @@ export function ReportTableList({ intervalsCount, mode, groupBy, - renderItem, + renderRow, compact, style, compactStyle, }: ReportTableListProps) { - const groupByData = + const metadata: GroupedEntity[] | undefined = groupBy === 'Category' - ? 'groupedData' + ? data.groupedData || [] : groupBy === 'Interval' - ? 'intervalData' - : 'data'; - const metadata = data[groupByData]; - - type RenderRowProps = { - index: number; - parent_index?: number; - compact: boolean; - style?: CSSProperties; - compactStyle?: CSSProperties; - }; - function RenderRow({ - index, - parent_index, - compact, - style, - compactStyle, - }: RenderRowProps) { - const item = - parent_index === undefined - ? metadata[index] - : metadata[parent_index].categories[index]; - - return renderItem({ - item, - mode, - intervalsCount, - compact, - style, - compactStyle, - }); - } + ? data.intervalData.map(interval => { + return { + id: '', + name: '', + date: interval.date, + totalAssets: interval.totalAssets, + totalDebts: interval.totalDebts, + totalTotals: interval.totalTotals, + intervalData: [], + categories: [], + }; + }) + : data.data; return ( <View> @@ -71,10 +57,14 @@ export function ReportTableList({ <View> {metadata.map((item, index) => { return ( - <View key={item.id}> - <RenderRow + <View key={index}> + <RenderTableRow index={index} compact={compact} + renderRow={renderRow} + intervalsCount={intervalsCount} + mode={mode} + metadata={metadata} style={{ ...(item.categories && { color: theme.tableRowHeaderText, @@ -88,18 +78,24 @@ export function ReportTableList({ {item.categories && ( <> <View> - {item.categories.map((category, i) => { - return ( - <RenderRow - key={category.id} - index={i} - compact={compact} - parent_index={index} - style={style} - compactStyle={compactStyle} - /> - ); - })} + {item.categories.map( + (category: GroupedEntity, i: number) => { + return ( + <RenderTableRow + key={category.id} + index={i} + compact={compact} + renderRow={renderRow} + intervalsCount={intervalsCount} + mode={mode} + metadata={metadata} + parent_index={index} + style={style} + compactStyle={compactStyle} + /> + ); + }, + )} </View> <Row height={20} /> </> diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableRow.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableRow.tsx index 54c1c650f549efc14e1c7c1e9501bd235d0b8272..d759a90d78c15e116b162c081afad4c269d3cd41 100644 --- a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableRow.tsx +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableRow.tsx @@ -5,7 +5,7 @@ import { amountToInteger, integerToCurrency, } from 'loot-core/src/shared/util'; -import { type DataEntity } from 'loot-core/src/types/models/reports'; +import { type GroupedEntity } from 'loot-core/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../../hooks/useAccounts'; @@ -17,7 +17,7 @@ import { Row, Cell } from '../../../table'; import { showActivity } from '../showActivity'; type ReportTableRowProps = { - item: DataEntity; + item: GroupedEntity; balanceTypeOp: 'totalAssets' | 'totalDebts' | 'totalTotals'; groupBy: string; mode: string; diff --git a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableTotals.tsx b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableTotals.tsx index 48b16e581e855fff89a59bb2bdb338bfdd2c35ff..f9f01a6df62221106c893f35247a23aa4b6399be 100644 --- a/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableTotals.tsx +++ b/packages/desktop-client/src/components/reports/graphs/tableGraph/ReportTableTotals.tsx @@ -1,13 +1,16 @@ -// @ts-strict-ignore -import React, { type UIEventHandler, useLayoutEffect, useState } from 'react'; -import { type RefProp } from 'react-spring'; +import React, { + type UIEventHandler, + useLayoutEffect, + useState, + type RefObject, +} from 'react'; import { amountToCurrency, amountToInteger, integerToCurrency, } from 'loot-core/src/shared/util'; -import { type GroupedEntity } from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; import { useAccounts } from '../../../../hooks/useAccounts'; @@ -22,11 +25,11 @@ import { Row, Cell } from '../../../table'; import { showActivity } from '../showActivity'; type ReportTableTotalsProps = { - data: GroupedEntity; - balanceTypeOp: string; + data: DataEntity; + balanceTypeOp: 'totalAssets' | 'totalDebts' | 'totalTotals'; mode: string; intervalsCount: number; - totalScrollRef: RefProp<HTMLDivElement>; + totalScrollRef: RefObject<HTMLDivElement>; handleScroll: UIEventHandler<HTMLDivElement>; compact: boolean; style?: CSSProperties; @@ -58,11 +61,13 @@ export function ReportTableTotals({ if (totalScrollRef.current) { const [parent, child] = [ totalScrollRef.current.offsetParent - ? totalScrollRef.current.parentElement.scrollHeight || 0 + ? (totalScrollRef.current.parentElement + ? totalScrollRef.current.parentElement.scrollHeight + : 0) || 0 : 0, totalScrollRef.current ? totalScrollRef.current.scrollHeight : 0, ]; - setScrollWidthTotals(parent > 0 && child > 0 && parent - child); + setScrollWidthTotals(parent > 0 && child > 0 ? parent - child : 0); } }); const average = amountToInteger(data[balanceTypeOp]) / intervalsCount; diff --git a/packages/desktop-client/src/components/reports/reports/CustomReport.tsx b/packages/desktop-client/src/components/reports/reports/CustomReport.tsx index 53320dd83fb5121f16a97aee84b271314528712c..0f0738b7f00bc39fccdd0599fc13af801e1d27b6 100644 --- a/packages/desktop-client/src/components/reports/reports/CustomReport.tsx +++ b/packages/desktop-client/src/components/reports/reports/CustomReport.tsx @@ -8,8 +8,8 @@ import * as monthUtils from 'loot-core/src/shared/months'; import { amountToCurrency } from 'loot-core/src/shared/util'; import { type CategoryEntity } from 'loot-core/types/models/category'; import { - type GroupedEntity, type CustomReportEntity, + type DataEntity, } from 'loot-core/types/models/reports'; import { type RuleConditionEntity } from 'loot-core/types/models/rule'; @@ -240,7 +240,7 @@ export function CustomReport() { } }, [interval, startDate, endDate, firstDayOfWeekIdx]); - const balanceTypeOp = + const balanceTypeOp: 'totalAssets' | 'totalDebts' | 'totalTotals' = ReportOptions.balanceTypeMap.get(balanceType) || 'totalDebts'; const payees = usePayees(); const accounts = useAccounts(); @@ -321,7 +321,7 @@ export function CustomReport() { const graphData = useReport('default', getGraphData); const groupedData = useReport('grouped', getGroupData); - const data: GroupedEntity = { ...graphData, groupedData } as GroupedEntity; + const data: DataEntity = { ...graphData, groupedData } as DataEntity; const customReportItems: CustomReportEntity = { id: '', diff --git a/packages/desktop-client/src/components/reports/spreadsheets/calculateLegend.ts b/packages/desktop-client/src/components/reports/spreadsheets/calculateLegend.ts index f19bc69049cba4e6791065ce019368ab08845470..de1ed8675851b25f6767834417151d360f6ac92e 100644 --- a/packages/desktop-client/src/components/reports/spreadsheets/calculateLegend.ts +++ b/packages/desktop-client/src/components/reports/spreadsheets/calculateLegend.ts @@ -1,18 +1,19 @@ import { - type IntervalData, - type ItemEntity, + type LegendEntity, + type IntervalEntity, + type GroupedEntity, } from 'loot-core/src/types/models/reports'; import { theme } from '../../../style'; import { getColorScale } from '../chart-theme'; export function calculateLegend( - intervalData: IntervalData[], - calcDataFiltered: ItemEntity[], + intervalData: IntervalEntity[], + calcDataFiltered: GroupedEntity[], groupBy: string, - graphType: string, - balanceTypeOp: string, -) { + graphType?: string, + balanceTypeOp?: keyof GroupedEntity, +): LegendEntity[] { const colorScale = getColorScale('qualitative'); const chooseData = groupBy === 'Interval' @@ -22,10 +23,11 @@ export function calculateLegend( : calcDataFiltered.map(c => { return { name: c.name, id: c.id }; }); - return chooseData.map((item, index) => { + + const legend: LegendEntity[] = chooseData.map((item, index) => { return { - id: item.id, - name: item.name, + id: item.id || '', + name: item.name || '', color: graphType === 'DonutGraph' ? colorScale[index % colorScale.length] @@ -36,4 +38,5 @@ export function calculateLegend( : colorScale[index % colorScale.length], }; }); + return legend; } diff --git a/packages/desktop-client/src/components/reports/spreadsheets/custom-spreadsheet.ts b/packages/desktop-client/src/components/reports/spreadsheets/custom-spreadsheet.ts index 5251bafc1abedcd1de638b78eb69f9d6d51aee1f..149c5678577d372931f49aed3d5cf1e04e75c3a5 100644 --- a/packages/desktop-client/src/components/reports/spreadsheets/custom-spreadsheet.ts +++ b/packages/desktop-client/src/components/reports/spreadsheets/custom-spreadsheet.ts @@ -13,10 +13,7 @@ import { type RuleConditionEntity, type CategoryGroupEntity, } from 'loot-core/src/types/models'; -import { - type DataEntity, - type GroupedEntity, -} from 'loot-core/src/types/models/reports'; +import { type DataEntity } from 'loot-core/src/types/models/reports'; import { type LocalPrefs } from 'loot-core/types/prefs'; import { @@ -44,7 +41,7 @@ export type createCustomSpreadsheetProps = { showHiddenCategories: boolean; showUncategorized: boolean; groupBy?: string; - balanceTypeOp?: keyof DataEntity; + balanceTypeOp?: 'totalAssets' | 'totalDebts' | 'totalTotals'; payees?: PayeeEntity[]; accounts?: AccountEntity[]; graphType?: string; @@ -65,7 +62,7 @@ export function createCustomSpreadsheet({ showHiddenCategories, showUncategorized, groupBy, - balanceTypeOp, + balanceTypeOp = 'totalDebts', payees, accounts, graphType, @@ -92,7 +89,7 @@ export function createCustomSpreadsheet({ return async ( spreadsheet: ReturnType<typeof useSpreadsheet>, - setData: (data: GroupedEntity) => void, + setData: (data: DataEntity) => void, ) => { if (groupByList.length === 0) { return; diff --git a/packages/desktop-client/src/components/reports/spreadsheets/grouped-spreadsheet.ts b/packages/desktop-client/src/components/reports/spreadsheets/grouped-spreadsheet.ts index b273ccf07f66b397f23d1dc19d694eb025ecd7dd..9bd7b45d9aacf5e0a3774dfe70e8207650622271 100644 --- a/packages/desktop-client/src/components/reports/spreadsheets/grouped-spreadsheet.ts +++ b/packages/desktop-client/src/components/reports/spreadsheets/grouped-spreadsheet.ts @@ -4,7 +4,7 @@ import { type useSpreadsheet } from 'loot-core/src/client/SpreadsheetProvider'; import { send } from 'loot-core/src/platform/client/fetch'; import * as monthUtils from 'loot-core/src/shared/months'; import { integerToAmount } from 'loot-core/src/shared/util'; -import { type DataEntity } from 'loot-core/src/types/models/reports'; +import { type GroupedEntity } from 'loot-core/src/types/models/reports'; import { categoryLists, ReportOptions } from '../ReportOptions'; @@ -41,7 +41,7 @@ export function createGroupedSpreadsheet({ return async ( spreadsheet: ReturnType<typeof useSpreadsheet>, - setData: (data: DataEntity[]) => void, + setData: (data: GroupedEntity[]) => void, ) => { if (categoryList.length === 0) { return; @@ -100,7 +100,7 @@ export function createGroupedSpreadsheet({ endDate, ); - const groupedData: DataEntity[] = categoryGroup.map( + const groupedData: GroupedEntity[] = categoryGroup.map( group => { let totalAssets = 0; let totalDebts = 0; diff --git a/packages/loot-core/src/types/models/reports.d.ts b/packages/loot-core/src/types/models/reports.d.ts index f1c01d6ab0a8a654ea0dc6957f4e881e14056fda..563de0b1f44f6b51ef09650b66e9d399364092ce 100644 --- a/packages/loot-core/src/types/models/reports.d.ts +++ b/packages/loot-core/src/types/models/reports.d.ts @@ -57,10 +57,10 @@ export interface SpendingEntity { totalTotals: number; } -export interface GroupedEntity { - data?: DataEntity[]; - intervalData: DataEntity[]; - groupedData?: DataEntity[] | null; +export interface DataEntity { + data?: GroupedEntity[]; + intervalData: IntervalEntity[]; + groupedData?: GroupedEntity[] | null; legend?: LegendEntity[]; startDate?: string; endDate?: string; @@ -75,33 +75,25 @@ type LegendEntity = { color: string; }; -export type ItemEntity = { - id: string; - name: string; - intervalData: IntervalData[]; - totalAssets: number; - totalDebts: number; - totalTotals: number; -}; - -export type IntervalData = { - date: string; - dateLookup: string; +export type IntervalEntity = { + date?: string; + dateStart?: string; + change?: number; + dateLookup?: string; totalAssets: number; totalDebts: number; totalTotals: number; }; -export interface DataEntity { +export interface GroupedEntity { id: string; name: string; date?: string; - dateStart?: string; - intervalData: IntervalData[]; - categories?: ItemEntity[]; + intervalData: IntervalEntity[]; totalAssets: number; totalDebts: number; totalTotals: number; + categories?: GroupedEntity[]; } export type Interval = { diff --git a/upcoming-release-notes/2726.md b/upcoming-release-notes/2726.md new file mode 100644 index 0000000000000000000000000000000000000000..b6fffc3da21b9f5dfa4c8e2db812e4cd564c07f8 --- /dev/null +++ b/upcoming-release-notes/2726.md @@ -0,0 +1,6 @@ +--- +category: Maintenance +authors: [carkom] +--- + +Making files in custom reports to comply with TS strict - stage #1.