Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Customizeable Reports #1791

Merged
merged 72 commits into from
Nov 16, 2023
Merged
Show file tree
Hide file tree
Changes from 69 commits
Commits
Show all changes
72 commits
Select commit Hold shift + click to select a range
e196a34
Reorganize and add graphs
carkom Sep 8, 2023
ed576f0
Merge remote-tracking branch 'upstream/master' into reportsOrganization
carkom Oct 12, 2023
0ea6036
Create Customizable Chart
carkom Oct 13, 2023
29cdc84
Notes
carkom Oct 13, 2023
b90ccc9
Hide Menu update Donut
carkom Oct 13, 2023
758f91b
lint fixes
carkom Oct 13, 2023
7a50264
Organize Menus
carkom Oct 13, 2023
a57f362
Change Title
carkom Oct 13, 2023
e032d66
UI changes
carkom Oct 14, 2023
0709edd
Merge branch 'master' into reportsOrganization
carkom Oct 14, 2023
8a1465e
Merge remote-tracking branch 'upstream/master' into reportsOrganization
carkom Oct 14, 2023
94dd8df
Merge branch 'reportsOrganization' of https://github.com/carkom/actua…
carkom Oct 14, 2023
9b64c00
UI updates
carkom Oct 14, 2023
014d4ea
Add Data Table
carkom Oct 16, 2023
1c83854
Functionality additions and Privacy Filters
carkom Oct 16, 2023
c6d4ebc
Merge branch 'master' into reportsOrganization
carkom Oct 16, 2023
175d88f
Date filters working and formatting changes
carkom Oct 17, 2023
2877942
Fix default spreadsheet and add tableGraph
carkom Oct 18, 2023
6a5d4f3
Integrate Summary Data and Split Legend
carkom Oct 18, 2023
a08df24
started adding functionality on charts
carkom Oct 19, 2023
6aa596b
Merge branch 'master' into reportsOrganization
carkom Oct 19, 2023
9518f5d
list fix
carkom Oct 19, 2023
a3eaf1e
Enabling more graphs, fixing errors
carkom Oct 20, 2023
053c419
Legend, interactions, Empty Rows Filter
carkom Oct 20, 2023
b2d14d7
fixes for EmptyRows/interactions/legends
carkom Oct 21, 2023
318f016
formatting UI and filtering data
carkom Oct 21, 2023
578d2de
format date
carkom Oct 21, 2023
f87255e
Merge branch 'master' into reportsOrganization
carkom Oct 21, 2023
15448b3
fix errors
carkom Oct 21, 2023
b40ba7b
Fix Legend Order
carkom Oct 22, 2023
47557d9
lint fixes
carkom Oct 22, 2023
f5fbbce
Add tooltips
carkom Oct 22, 2023
cde6193
Feature Flag
carkom Oct 22, 2023
a432aae
Merge branch 'master' into reportsOrganization
carkom Oct 24, 2023
7d99b30
fix overview card, fix offbudget checkbox
carkom Oct 24, 2023
4de4996
Revamped dataType, added scrollBars
carkom Oct 25, 2023
2d492e1
data display adjustments
carkom Oct 26, 2023
47058b1
data spreadsheet updates/groups added to matrix
carkom Oct 27, 2023
80d08c6
Add Category Selector
carkom Oct 28, 2023
6953a0d
Add Labels Button
carkom Oct 28, 2023
69db103
formatting fixes
carkom Oct 28, 2023
a9e414d
Add Averages to dataTable
carkom Oct 28, 2023
d367884
data bug fix
carkom Oct 28, 2023
54f8cf2
Added all type back in with exceptions
carkom Oct 29, 2023
de892a4
formatting
carkom Oct 29, 2023
443fce0
Merge branch 'master' into reportsOrganization
carkom Oct 31, 2023
d887a44
split assets/debts, add Uncategorized
carkom Oct 31, 2023
f2dd6d8
bug fixes and UI updates
carkom Oct 31, 2023
8df59c0
add scrollbars to table
carkom Oct 31, 2023
7790fd6
Merge branch 'master' into reportsOrganization
carkom Oct 31, 2023
e698f1c
formatting dataTable
carkom Nov 1, 2023
e7093aa
tooltips, navigation and graph labels
carkom Nov 3, 2023
c0cc2e9
Merge branch 'master' into reportsOrganization
carkom Nov 5, 2023
5d05239
Merge branch 'master' into reportsOrganization
carkom Nov 6, 2023
f7b1cc9
Code clean-up and re-org
carkom Nov 6, 2023
a20d18a
revert color change
carkom Nov 6, 2023
0df6f8e
Change labels name
carkom Nov 7, 2023
3fa193a
organize files
carkom Nov 11, 2023
a8ffc0d
Merge branch 'master' into reportsOrganization
carkom Nov 11, 2023
2dde53d
code cleanup
carkom Nov 13, 2023
aa7ac72
Tooltip Colors
carkom Nov 13, 2023
4728537
Descoping legend for future PR
carkom Nov 13, 2023
9e3364f
descope legend & rename split
carkom Nov 14, 2023
8699335
rename type variable to be more descriptive
carkom Nov 14, 2023
32da839
Merge remote-tracking branch 'upstream/master' into reportsOrganization
carkom Nov 14, 2023
4d3bb9f
adjustments for sankey and eslint merges
carkom Nov 14, 2023
6d42ece
notes update
carkom Nov 14, 2023
3f82ccb
code review fixes
carkom Nov 15, 2023
64d672f
Merge branch 'master' into reportsOrganization
carkom Nov 15, 2023
20301a0
code fixes
carkom Nov 16, 2023
7df30ac
Merge branch 'master' into reportsOrganization
carkom Nov 16, 2023
62ac0c3
fix date selections
carkom Nov 16, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion packages/desktop-client/src/components/accounts/Header.js
Original file line number Diff line number Diff line change
Expand Up @@ -239,7 +239,7 @@ export function AccountHeader({
</Button>
)}
<View style={{ flexShrink: 0 }}>
<FilterButton onApply={onApplyFilter} />
<FilterButton onApply={onApplyFilter} type="accounts" />
</View>
<View style={{ flex: 1 }} />
<Search
Expand Down
31 changes: 24 additions & 7 deletions packages/desktop-client/src/components/filters/FiltersMenu.js
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import {
import { titleFirst } from 'loot-core/src/shared/util';

import DeleteIcon from '../../icons/v0/Delete';
import Filter from '../../icons/v1/Filter';
import SettingsSliderAlternate from '../../icons/v2/SettingsSliderAlternate';
import { theme } from '../../style';
import Button from '../common/Button';
Expand Down Expand Up @@ -335,7 +336,28 @@ function ConfigureField({
);
}

export function FilterButton({ onApply }) {
function ButtonType({ type, dispatch }) {
return (
<Button
type="bare"
onClick={() => dispatch({ type: 'select-field' })}
title={type && 'Filters'}
>
{type === 'reports' ? (
<Filter width={15} height={15} />
) : (
<>
<SettingsSliderAlternate
style={{ width: 16, height: 16, marginRight: 5 }}
/>{' '}
Filter
</>
)}
</Button>
);
}

export function FilterButton({ onApply, type }) {
let filters = useFilters();

let { dateFormat } = useSelector(state => {
Expand Down Expand Up @@ -418,12 +440,7 @@ export function FilterButton({ onApply }) {

return (
<View>
<Button type="bare" onClick={() => dispatch({ type: 'select-field' })}>
<SettingsSliderAlternate
style={{ width: 16, height: 16, marginRight: 5 }}
/>{' '}
Filter
</Button>
<ButtonType type={type} dispatch={dispatch} />
{state.fieldsOpen && (
<Tooltip
position="bottom-left"
Expand Down
138 changes: 138 additions & 0 deletions packages/desktop-client/src/components/reports/ChooseGraph.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
import React from 'react';

import View from '../common/View';

import AreaGraph from './graphs/AreaGraph';
import BarGraph from './graphs/BarGraph';
import BarLineGraph from './graphs/BarLineGraph';
import DonutGraph from './graphs/DonutGraph';
import LineGraph from './graphs/LineGraph';
import StackedBarGraph from './graphs/StackedBarGraph';
import { ReportOptions } from './ReportOptions';
import ReportTable from './ReportTable';
import ReportTableHeader from './ReportTableHeader';
import ReportTableList from './ReportTableList';
import ReportTableTotals from './ReportTableTotals';

export function ChooseGraph({
start,
end,
data,
mode,
graphType,
balanceType,
groupBy,
empty,
scrollWidth,
setScrollWidth,
months,
}) {
function saveScrollWidth(parent, child) {
let width = parent > 0 && child > 0 && parent - child;

setScrollWidth(!width ? 0 : width);
}

if (graphType === 'AreaGraph') {
return (
<AreaGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
data={data}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
/>
);
}
if (graphType === 'BarGraph') {
return (
<BarGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
data={data}
groupBy={groupBy}
empty={empty}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
/>
);
}
if (graphType === 'BarLineGraph') {
return (
<BarLineGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
graphData={data.graphData}
/>
);
}
if (graphType === 'DonutGraph') {
return (
<DonutGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
data={data}
groupBy={groupBy}
empty={empty}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
/>
);
}
if (graphType === 'LineGraph') {
return (
<LineGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
graphData={data.graphData}
/>
);
}
if (graphType === 'StackedBarGraph') {
return (
<StackedBarGraph
style={{ flexGrow: 1 }}
start={start}
end={end}
data={data}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
/>
);
}
if (graphType === 'TableGraph') {
return (
<View
style={{
overflow: 'auto',
}}
>
<ReportTableHeader
interval={mode === 'time' && months}
scrollWidth={scrollWidth}
groupBy={groupBy}
balanceType={balanceType}
/>
<ReportTable saveScrollWidth={saveScrollWidth}>
<ReportTableList
data={data}
empty={empty}
monthsCount={months.length}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
mode={mode}
groupBy={groupBy}
/>
<ReportTableTotals
scrollWidth={scrollWidth}
data={data}
mode={mode}
balanceTypeOp={ReportOptions.balanceTypeMap.get(balanceType)}
monthsCount={months.length}
balanceType={balanceType}
/>
</ReportTable>
</View>
);
}
}
127 changes: 71 additions & 56 deletions packages/desktop-client/src/components/reports/Header.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import { useLocation } from 'react-router-dom';

import * as monthUtils from 'loot-core/src/shared/months';

import ArrowLeft from '../../icons/v1/ArrowLeft';
Expand All @@ -8,15 +10,15 @@ import Select from '../common/Select';
import View from '../common/View';
import { FilterButton, AppliedFilters } from '../filters/FiltersMenu';

function validateStart(allMonths, start, end) {
export function validateStart(allMonths, start, end) {
const earliest = allMonths[allMonths.length - 1].name;
if (end < start) {
end = monthUtils.addMonths(start, 6);
}
return boundedRange(earliest, start, end);
}

function validateEnd(allMonths, start, end) {
export function validateEnd(allMonths, start, end) {
const earliest = allMonths[allMonths.length - 1].name;
if (start > end) {
start = monthUtils.subMonths(end, 6);
Expand All @@ -35,13 +37,13 @@ function boundedRange(earliest, start, end) {
return [start, end];
}

function getLatestRange(offset) {
export function getLatestRange(offset) {
const end = monthUtils.currentMonth();
const start = monthUtils.subMonths(end, offset);
return [start, end];
}

function getFullRange(allMonths) {
export function getFullRange(allMonths) {
const start = allMonths[allMonths.length - 1].name;
const end = monthUtils.currentMonth();
return [start, end];
Expand All @@ -61,7 +63,11 @@ function Header({
onDeleteFilter,
onCondOpChange,
headerPrefixItems,
selectGraph,
}) {
let location = useLocation();
let path = location.pathname;

return (
<View
style={{
Expand All @@ -79,70 +85,79 @@ function Header({
</ButtonLink>
<View style={styles.veryLargeText}>{title}</View>

<View
style={{
flexDirection: 'row',
alignItems: 'center',
marginTop: 15,
gap: 15,
}}
>
{headerPrefixItems}

{path !== '/reports/custom-report' && (
<View
style={{
flexDirection: 'row',
alignItems: 'center',
gap: 5,
marginTop: 15,
gap: 15,
}}
>
<Select
onChange={newValue =>
onChangeDates(...validateStart(allMonths, newValue, end))
}
value={start}
defaultLabel={monthUtils.format(start, 'MMMM, yyyy')}
options={allMonths.map(({ name, pretty }) => [name, pretty])}
/>
<View>to</View>
<Select
onChange={newValue =>
onChangeDates(...validateEnd(allMonths, start, newValue))
}
value={end}
options={allMonths.map(({ name, pretty }) => [name, pretty])}
/>
</View>
{headerPrefixItems}

{filters && <FilterButton onApply={onApply} />}
<View
style={{
flexDirection: 'row',
alignItems: 'center',
gap: 5,
}}
>
<Select
onChange={newValue =>
onChangeDates(...validateStart(allMonths, newValue, end))
}
value={start}
defaultLabel={monthUtils.format(start, 'MMMM, yyyy')}
options={allMonths.map(({ name, pretty }) => [name, pretty])}
/>
<View>to</View>
<Select
onChange={newValue =>
onChangeDates(...validateEnd(allMonths, start, newValue))
}
value={end}
options={allMonths.map(({ name, pretty }) => [name, pretty])}
/>
</View>

{filters && <FilterButton onApply={onApply} type="accounts" />}

{show1Month && (
{show1Month && (
<Button
type="bare"
onClick={() => onChangeDates(...getLatestRange(1))}
>
1 month
</Button>
)}
<Button
type="bare"
onClick={() => onChangeDates(...getLatestRange(1))}
onClick={() => onChangeDates(...getLatestRange(2))}
>
1 month
3 months
</Button>
)}
<Button type="bare" onClick={() => onChangeDates(...getLatestRange(2))}>
3 months
</Button>
<Button type="bare" onClick={() => onChangeDates(...getLatestRange(5))}>
6 months
</Button>
<Button
type="bare"
onClick={() => onChangeDates(...getLatestRange(11))}
>
1 Year
</Button>
<Button
type="bare"
onClick={() => onChangeDates(...getFullRange(allMonths))}
>
All Time
</Button>
</View>
<Button
type="bare"
onClick={() => onChangeDates(...getLatestRange(5))}
>
6 months
</Button>
<Button
type="bare"
onClick={() => onChangeDates(...getLatestRange(11))}
>
1 Year
</Button>
<Button
type="bare"
onClick={() => onChangeDates(...getFullRange(allMonths))}
>
All Time
</Button>
<View style={{ flex: 1 }} />
</View>
)}
{filters && filters.length > 0 && (
<View
style={{ marginTop: 5 }}
Expand Down
Loading