Skip to content

Commit 474e436

Browse files
committed
Refactor ProjectDashboard and filter criteria handling
- Simplified the default dashboard setup in ProjectDashboard.jsx by removing unnecessary constants and directly defining the filters. - Enhanced WithFilterCriteria.jsx to ensure that filter properties are only updated if they exist in the new criteria object. - Updated method names in WithReviewTasks and WithReviewTaskClusters to consistently use updateReviewCriteria. - Improved PaginationControl.jsx to use pageCount instead of totalPages for better clarity. - Introduced new columns and setupColumnTypes for TaskAnalysisTable, enhancing the table's configurability and readability. - Refactored ViewTask component to use functional component syntax and integrated WithLoadedTask HOC for better task loading management. - Adjusted TasksReviewTable to consistently use updateReviewCriteria for updating review criteria state. These changes improve code clarity, maintainability, and consistency across components.
1 parent 8f495cd commit 474e436

12 files changed

Lines changed: 968 additions & 987 deletions

File tree

src/components/AdminPane/Manage/ProjectDashboard/ProjectDashboard.jsx

Lines changed: 10 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -3,10 +3,7 @@ import { Component } from "react";
33
import { FormattedMessage, injectIntl } from "react-intl";
44
import { Link } from "react-router-dom";
55
import AsManager from "../../../../interactions/User/AsManager";
6-
import {
7-
challengePassesFilters,
8-
defaultChallengeFilters,
9-
} from "../../../../services/Widget/ChallengeFilter/ChallengeFilter";
6+
import { challengePassesFilters } from "../../../../services/Widget/ChallengeFilter/ChallengeFilter";
107
import {
118
WidgetDataTarget,
129
generateWidgetId,
@@ -25,15 +22,16 @@ import messages from "./Messages";
2522
import "./ProjectDashboard.scss";
2623
import WithProjectManagement from "../../HOCs/WithProjectManagement/WithProjectManagement";
2724

28-
// The name of this dashboard.
29-
const DASHBOARD_NAME = "project";
30-
3125
export const defaultDashboardSetup = function () {
3226
return {
3327
dataModelVersion: 2,
34-
name: DASHBOARD_NAME,
28+
name: "project",
3529
label: "View Project",
36-
filters: defaultChallengeFilters(),
30+
filters: {
31+
["visible"]: false,
32+
["pinned"]: false,
33+
["archived"]: false,
34+
},
3735
widgets: [
3836
widgetDescriptor("ProjectOverviewWidget"),
3937
widgetDescriptor("CompletionProgressWidget"),
@@ -42,14 +40,8 @@ export const defaultDashboardSetup = function () {
4240
widgetDescriptor("ProjectManagersWidget"),
4341
widgetDescriptor("ChallengeListWidget"),
4442
],
45-
permanentWidgets: [
46-
// Cannot be removed from workspace
47-
"ChallengeListWidget",
48-
],
49-
conditionalWidgets: [
50-
// conditionally displayed
51-
"MetaReviewStatusMetricsWidget",
52-
],
43+
permanentWidgets: ["ChallengeListWidget"],
44+
conditionalWidgets: ["MetaReviewStatusMetricsWidget"],
5345
layout: [
5446
{ i: generateWidgetId(), x: 0, y: 0, w: 4, h: 7 },
5547
{ i: generateWidgetId(), x: 0, y: 7, w: 4, h: 7 },
@@ -227,7 +219,7 @@ const ProjectDashboard = WithProjectManagement(
227219
challengePassesFilters,
228220
),
229221
[WidgetDataTarget.project, WidgetDataTarget.challenges],
230-
DASHBOARD_NAME,
222+
"project",
231223
defaultDashboardSetup,
232224
),
233225
{

src/components/HOCs/WithFilterCriteria/WithFilterCriteria.jsx

Lines changed: 37 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -53,10 +53,22 @@ export default function WithFilterCriteria(
5353

5454
updateCriteria = (newCriteria) => {
5555
const criteria = _cloneDeep(this.state.criteria);
56-
criteria.sortCriteria = newCriteria.sortCriteria;
57-
criteria.page = newCriteria.page;
58-
criteria.filters = newCriteria.filters;
59-
criteria.includeTags = newCriteria.includeTags;
56+
57+
if (newCriteria.hasOwnProperty('sortCriteria')) {
58+
criteria.sortCriteria = newCriteria.sortCriteria;
59+
}
60+
if (newCriteria.hasOwnProperty('page')) {
61+
criteria.page = newCriteria.page;
62+
}
63+
if (newCriteria.hasOwnProperty('filters')) {
64+
criteria.filters = newCriteria.filters;
65+
}
66+
if (newCriteria.hasOwnProperty('includeTags')) {
67+
criteria.includeTags = newCriteria.includeTags;
68+
}
69+
if (newCriteria.hasOwnProperty('pageSize')) {
70+
criteria.pageSize = newCriteria.pageSize;
71+
}
6072

6173
this.setState({ criteria });
6274
if (this.props.setSearchFilters) {
@@ -73,6 +85,9 @@ export default function WithFilterCriteria(
7385

7486
updateTaskPropertyCriteria = (propertySearch) => {
7587
const criteria = _cloneDeep(this.state.criteria);
88+
if (!criteria.filters) {
89+
criteria.filters = {};
90+
}
7691
criteria.filters.taskPropertySearch = propertySearch;
7792
this.setState({ criteria });
7893
};
@@ -89,6 +104,9 @@ export default function WithFilterCriteria(
89104

90105
clearTaskPropertyCriteria = () => {
91106
const criteria = _cloneDeep(this.state.criteria);
107+
if (!criteria.filters) {
108+
criteria.filters = {};
109+
}
92110
criteria.filters.taskPropertySearch = null;
93111
this.setState({ criteria });
94112
};
@@ -125,11 +143,15 @@ export default function WithFilterCriteria(
125143
changePageSize = (pageSize) => {
126144
const typedCriteria = _cloneDeep(this.state.criteria);
127145
typedCriteria.pageSize = pageSize;
146+
typedCriteria.page = 0;
128147
this.setState({ criteria: typedCriteria });
129148
};
130149

131150
setFiltered = (column, value) => {
132151
const typedCriteria = _cloneDeep(this.state.criteria);
152+
if (!typedCriteria.filters) {
153+
typedCriteria.filters = {};
154+
}
133155
typedCriteria.filters[column] = value;
134156

135157
//Reset Page so it goes back to 0
@@ -139,6 +161,11 @@ export default function WithFilterCriteria(
139161

140162
updateIncludedFilters(props, criteria = {}) {
141163
const typedCriteria = _merge({}, criteria, _cloneDeep(this.state.criteria));
164+
165+
if (!typedCriteria.filters) {
166+
typedCriteria.filters = {};
167+
}
168+
142169
typedCriteria.filters["status"] = _keys(_pickBy(props.includeTaskStatuses, (s) => s));
143170
typedCriteria.filters["reviewStatus"] = _keys(
144171
_pickBy(props.includeTaskReviewStatuses, (r) => r),
@@ -188,8 +215,12 @@ export default function WithFilterCriteria(
188215

189216
const criteria = typedCriteria || _cloneDeep(this.state.criteria);
190217

218+
// Ensure filters object exists before setting properties
219+
if (!criteria.filters) {
220+
criteria.filters = {};
221+
}
191222
criteria.filters.archived = true;
192-
223+
193224
this.debouncedTasksFetch(challengeId, criteria, this.state.criteria.pageSize);
194225
};
195226

@@ -325,7 +356,7 @@ export default function WithFilterCriteria(
325356
typedCriteria = this.updateIncludedFilters(this.props);
326357
return;
327358
}
328-
359+
329360
if (!_isEqual(prevState.criteria, this.state.criteria)) {
330361
this.refreshTasks(typedCriteria);
331362
} else if (

src/components/HOCs/WithReviewTaskClusters/WithReviewTaskClusters.jsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ export const WithReviewTaskClusters = function (WrappedComponent) {
2626
}
2727
const criteria = _cloneDeep(this.props.reviewCriteria);
2828
criteria.boundingBox = fromLatLngBounds(bounds).join(",");
29-
this.props.updateReviewTasks(criteria);
29+
this.props.updateReviewCriteria(criteria);
3030
}
3131

3232
fetchUpdatedClusters(forceLoad = false) {

src/components/HOCs/WithReviewTasks/WithReviewTasks.jsx

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ export const WithReviewTasks = function (WrappedComponent) {
4747
}
4848

4949
refresh = () => {
50-
this.update(this.props, this.state.criteria[this.props.reviewTasksType], true);
50+
this.updateReviewCriteria(this.props, this.state.criteria[this.props.reviewTasksType], true);
5151
};
5252

5353
changePageSize = (pageSize) => {
@@ -70,10 +70,10 @@ export const WithReviewTasks = function (WrappedComponent) {
7070
!typedCriteria[this.props.reviewTasksType].invertFields[fieldName];
7171

7272
this.setState({ criteria: typedCriteria });
73-
this.update(this.props, typedCriteria[this.props.reviewTasksType]);
73+
this.updateReviewCriteria(this.props, typedCriteria[this.props.reviewTasksType]);
7474
};
7575

76-
update(props, criteria, skipURLUpdate = false) {
76+
updateReviewCriteria(props, criteria, skipURLUpdate = false) {
7777
const searchOnCriteria = _cloneDeep(criteria);
7878
const userId = props.user?.id;
7979
const pageSize =
@@ -211,7 +211,7 @@ export const WithReviewTasks = function (WrappedComponent) {
211211
prevProps.reviewTasksType !== this.props.reviewTasksType ||
212212
prevProps.reviewTasksSubType !== this.props.reviewTasksSubType
213213
) {
214-
this.update(
214+
this.updateReviewCriteria(
215215
this.props,
216216
this.state.criteria[this.props.reviewTasksType] || this.buildDefaultCriteria(this.props),
217217
true,
@@ -220,7 +220,7 @@ export const WithReviewTasks = function (WrappedComponent) {
220220
}
221221

222222
if (!_isEqual(this.props.defaultFilters, prevProps.defaultFilters)) {
223-
this.update(this.props, this.buildDefaultCriteria(this.props), true);
223+
this.updateReviewCriteria(this.props, this.buildDefaultCriteria(this.props), true);
224224
return;
225225
}
226226
}
@@ -267,7 +267,7 @@ export const WithReviewTasks = function (WrappedComponent) {
267267
return (
268268
<WrappedComponent
269269
reviewData={reviewData}
270-
updateReviewTasks={(criteria) => this.update(this.props, criteria)}
270+
updateReviewCriteria={(criteria) => this.updateReviewCriteria(this.props, criteria)}
271271
refresh={this.refresh}
272272
reviewCriteria={criteria}
273273
clearFilterCriteria={this.clearCriteria}
@@ -281,7 +281,7 @@ export const WithReviewTasks = function (WrappedComponent) {
281281
reviewChallenges={reviewChallenges}
282282
reviewProjects={this.props.currentReviewTasks.reviewProjects}
283283
invertField={this.invertField}
284-
{..._omit(this.props, ["updateReviewTasks"])}
284+
{..._omit(this.props, ["updateReviewCriteria"])}
285285
/>
286286
);
287287
}

src/components/PaginationControl/PaginationControl.jsx

Lines changed: 19 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,27 +1,30 @@
11
import { FormattedMessage, injectIntl } from "react-intl";
22
import messages from "./Messages";
33

4-
function PaginationControl({ currentPage, totalPages, pageSize, gotoPage, setPageSize, intl }) {
5-
const canPreviousPage = currentPage > 0;
6-
const canNextPage = currentPage < totalPages - 1;
7-
8-
const previousPage = () => gotoPage(Math.max(currentPage - 1, 0));
9-
const nextPage = () => gotoPage(Math.min(currentPage + 1, totalPages - 1));
10-
4+
function PaginationControl({
5+
currentPage,
6+
pageCount,
7+
pageSize,
8+
gotoPage,
9+
setPageSize,
10+
previousPage,
11+
nextPage,
12+
intl,
13+
}) {
1114
return (
1215
<div className="mr-flex mr-flex-wrap mr-justify-center mr-items-center mr-gap-2 md:mr-gap-3 mr-mt-6 mr-text-white">
1316
<button
1417
className="mr-button mr-button--small mr-mb-2"
1518
onClick={() => gotoPage(0)}
16-
disabled={!canPreviousPage}
19+
disabled={!(currentPage > 0)}
1720
>
1821
{"<< "}
1922
<FormattedMessage {...messages.first} />
2023
</button>
2124
<button
2225
className="mr-button mr-button--small mr-mb-2"
23-
onClick={() => previousPage()}
24-
disabled={!canPreviousPage}
26+
onClick={previousPage}
27+
disabled={!(currentPage > 0)}
2528
>
2629
{"< "}
2730
<FormattedMessage {...messages.previous} />
@@ -32,24 +35,24 @@ function PaginationControl({ currentPage, totalPages, pageSize, gotoPage, setPag
3235
className="mr-input mr-px-1 mr-py-0 mr-w-12 md:mr-w-16"
3336
type="number"
3437
min={1}
35-
max={totalPages}
38+
max={pageCount}
3639
value={currentPage + 1}
3740
onChange={(e) => gotoPage(e.target.value ? Number(e.target.value) - 1 : 0)}
3841
/>{" "}
39-
<FormattedMessage {...messages.of} /> {totalPages}
42+
<FormattedMessage {...messages.of} /> {pageCount}
4043
</span>
4144
<button
4245
className="mr-button mr-button--small mr-mb-2"
43-
onClick={() => nextPage()}
44-
disabled={!canNextPage}
46+
onClick={nextPage}
47+
disabled={!(currentPage < pageCount - 1)}
4548
>
4649
<FormattedMessage {...messages.next} />
4750
{" >"}
4851
</button>
4952
<button
5053
className="mr-button mr-button--small mr-mb-2"
51-
onClick={() => gotoPage(totalPages - 1)}
52-
disabled={!canNextPage}
54+
onClick={() => gotoPage(pageCount - 1)}
55+
disabled={!(currentPage < pageCount - 1)}
5356
>
5457
<FormattedMessage {...messages.last} />
5558
{" >>"}

0 commit comments

Comments
 (0)