Skip to content

Commit d416c59

Browse files
authored
Merge pull request #1184 from topcoder-platform/PM-1502-scorecards
PM- 1502 Scorecards filtering and listing UI
2 parents a914d96 + 8e2377e commit d416c59

File tree

28 files changed

+1050
-29
lines changed

28 files changed

+1050
-29
lines changed

src/apps/admin/src/lib/components/common/Pagination/Pagination.module.scss

Lines changed: 38 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,18 +6,49 @@
66
justify-content: flex-end;
77
align-items: center;
88
padding: 16px 0;
9-
gap: $sp-4;
9+
gap: $sp-2;
10+
11+
.pageNumbers button,
12+
.previous,
13+
.disabled,
14+
.first,
15+
.last,
16+
.next {
17+
box-shadow: none;
18+
border: 1px solid #E9ECEF;
19+
border-radius: 4px;
20+
color: #0A0A0A;
21+
font-weight: 400;
22+
font-size: 14px;
23+
}
24+
25+
.previous,
26+
.first,
27+
.last,
28+
.next {
29+
padding: 7px 11px;
30+
31+
&:disabled {
32+
background-color: #E9ECEF !important;
33+
}
34+
}
35+
1036

1137
.pageNumbers {
1238
display: flex;
1339
justify-content: center;
1440
align-items: center;
15-
gap: $sp-1;
41+
gap: $sp-2;
42+
43+
button {
44+
padding: 3px 12px;
45+
}
1646

1747
button.active {
1848
color: $black-60;
1949
pointer-events: none;
20-
box-shadow: inset 0 0 0 2px #{$black-60};
50+
background-color: $teal-160;
51+
color: white;
2152
}
2253
}
2354

@@ -35,4 +66,8 @@
3566
@media (max-width: #{$mobile-max}) {
3667
justify-content: center;
3768
}
69+
70+
:global(.btn-style-secondary) {
71+
box-shadow: none !important;
72+
}
3873
}

src/apps/admin/src/lib/components/common/Pagination/Pagination.tsx

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,6 @@ const Pagination: FC<PaginationProps> = (props: PaginationProps) => {
7474
size='md'
7575
icon={IconOutline.ChevronDoubleLeftIcon}
7676
iconToLeft
77-
label='FIRST'
7877
disabled={props.page === 1 || props.disabled}
7978
className={styles.first}
8079
/>
@@ -84,7 +83,6 @@ const Pagination: FC<PaginationProps> = (props: PaginationProps) => {
8483
size='md'
8584
icon={IconOutline.ChevronLeftIcon}
8685
iconToLeft
87-
label='PREVIOUS'
8886
disabled={props.page === 1 || props.disabled}
8987
className={styles.previous}
9088
/>
@@ -93,7 +91,6 @@ const Pagination: FC<PaginationProps> = (props: PaginationProps) => {
9391
<Button
9492
key={`page-${i}`}
9593
secondary
96-
variant='round'
9794
label={`${i}`}
9895
onClick={createHandlePageClick(i)}
9996
className={i === props.page ? styles.active : ''}
@@ -107,7 +104,6 @@ const Pagination: FC<PaginationProps> = (props: PaginationProps) => {
107104
size='md'
108105
icon={IconOutline.ChevronRightIcon}
109106
iconToRight
110-
label='NEXT'
111107
disabled={props.page === totalPages || props.disabled}
112108
className={styles.next}
113109
/>
@@ -118,7 +114,6 @@ const Pagination: FC<PaginationProps> = (props: PaginationProps) => {
118114
size='md'
119115
icon={IconOutline.ChevronDoubleRightIcon}
120116
iconToRight
121-
label='LAST'
122117
disabled={props.page === totalPages || props.disabled}
123118
className={styles.last}
124119
/>

src/apps/review/src/config/routes.config.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,5 @@ export const activeReviewAssigmentsRouteId = 'active-review-assigments'
1212
export const openOpportunitiesRouteId = 'open-opportunities'
1313
export const pastReviewAssignmentsRouteId = 'past-review-assignments'
1414
export const challengeDetailRouteId = ':challengeId'
15+
export const scorecardRouteId = 'scorecard'
16+
export const viewScorecardRouteId = ':scorecardId'

src/apps/review/src/lib/components/NavTabs/NavTabs.tsx

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@ import {
33
FC,
44
SetStateAction,
55
useCallback,
6+
useContext,
7+
useEffect,
68
useMemo,
79
useRef,
810
useState,
@@ -13,23 +15,35 @@ import classNames from 'classnames'
1315

1416
import { useClickOutside } from '~/libs/shared/lib/hooks'
1517

16-
import { getTabIdFromPathName, TabsConfig } from './config'
18+
import { ReviewAppContext } from '../../contexts'
19+
import { ReviewAppContextModel } from '../../models'
20+
21+
import { getTabIdFromPathName, getTabsConfig } from './config'
1722
import styles from './NavTabs.module.scss'
1823

1924
const NavTabs: FC = () => {
2025
const navigate: NavigateFunction = useNavigate()
2126
const [isOpen, setIsOpen] = useState<boolean>(false)
2227
const triggerRef = useRef<HTMLDivElement>(null)
2328
const { pathname }: { pathname: string } = useLocation()
29+
30+
const { loginUserInfo }: ReviewAppContextModel = useContext(ReviewAppContext)
31+
const userRoles = useMemo(() => loginUserInfo?.roles || [], [loginUserInfo?.roles])
32+
const tabs = useMemo(() => getTabsConfig(userRoles), [userRoles])
33+
2434
const activeTabPathName: string = useMemo<string>(
25-
() => getTabIdFromPathName(pathname),
26-
[pathname],
35+
() => getTabIdFromPathName(pathname, userRoles),
36+
[pathname, userRoles],
2737
)
2838
const [activeTab, setActiveTab]: [
2939
string,
3040
Dispatch<SetStateAction<string>>
3141
] = useState<string>(activeTabPathName)
3242

43+
useEffect(() => {
44+
setActiveTab(activeTabPathName)
45+
}, [activeTabPathName])
46+
3347
const handleTabChange = useCallback(
3448
(tabId: string) => {
3549
setActiveTab(tabId)
@@ -58,7 +72,7 @@ const NavTabs: FC = () => {
5872
Review
5973
</div>
6074
<ul className={styles.tab}>
61-
{TabsConfig.map(tab => (
75+
{tabs.map(tab => (
6276
<li
6377
key={tab.id}
6478
className={

src/apps/review/src/lib/components/NavTabs/config/tabs-config.ts

Lines changed: 28 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -5,25 +5,37 @@ import {
55
activeReviewAssigmentsRouteId,
66
openOpportunitiesRouteId,
77
pastReviewAssignmentsRouteId,
8+
scorecardRouteId,
89
} from '~/apps/review/src/config/routes.config'
910

10-
export const TabsConfig: TabsNavItem[] = [
11-
{
12-
id: activeReviewAssigmentsRouteId,
13-
title: 'Active Review Assignments',
14-
},
15-
{
16-
id: openOpportunitiesRouteId,
17-
title: 'Open Opportunities',
18-
},
19-
{
20-
id: pastReviewAssignmentsRouteId,
21-
title: 'Past Review Assignments',
22-
},
23-
]
11+
export function getTabsConfig(userRoles: string[]): TabsNavItem[] {
12+
const tabs: TabsNavItem[] = [
13+
{
14+
id: activeReviewAssigmentsRouteId,
15+
title: 'Active Review Assignments',
16+
},
17+
{
18+
id: openOpportunitiesRouteId,
19+
title: 'Open Opportunities',
20+
},
21+
{
22+
id: pastReviewAssignmentsRouteId,
23+
title: 'Past Review Assignments',
24+
},
25+
]
2426

25-
export function getTabIdFromPathName(pathname: string): string {
26-
const matchItem = _.find(TabsConfig, item => pathname.includes(`/${item.id}`))
27+
if (userRoles.includes('administrator')) {
28+
tabs.push({
29+
id: scorecardRouteId,
30+
title: 'Scorecards',
31+
})
32+
}
33+
34+
return tabs
35+
}
36+
37+
export function getTabIdFromPathName(pathname: string, userRoles: string[]): string {
38+
const matchItem = _.find(getTabsConfig(userRoles), item => pathname.includes(`/${item.id}`))
2739

2840
if (matchItem) {
2941
return matchItem.id
Lines changed: 176 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,176 @@
1+
@import '@libs/ui/styles/includes';
2+
3+
.filtersContainer {
4+
display: flex;
5+
flex-wrap: wrap;
6+
gap: 1rem;
7+
margin-top: 32px;
8+
align-items: flex-end;
9+
padding: 20px;
10+
background-color: #E0E4E84D;
11+
justify-content: center;
12+
align-items: center;
13+
14+
.inputWrapper {
15+
gap: $sp-1;
16+
flex: 5;
17+
min-width: 355px;
18+
width: 100%;
19+
margin-bottom: 0;
20+
justify-content: end;
21+
22+
label {
23+
flex-direction: row;
24+
align-items: center;
25+
justify-content: space-between;
26+
}
27+
}
28+
29+
.inputText {
30+
color: $black-60;
31+
box-sizing: border-box;
32+
border: 0;
33+
width: 100%;
34+
padding: 0;
35+
margin: 0;
36+
height: auto;
37+
border-radius: 0;
38+
39+
&:focus {
40+
box-shadow: none;
41+
border: none;
42+
outline: none;
43+
color: $black-100;
44+
}
45+
46+
&::placeholder {
47+
color: $black-60;
48+
opacity: 1;
49+
text-transform: none;
50+
}
51+
}
52+
53+
.inputIcon {
54+
color: $black-60;
55+
}
56+
57+
58+
59+
.searchInput {
60+
flex: 5;
61+
min-width: 355px;
62+
width: 100%;
63+
margin-bottom: 0;
64+
65+
}
66+
67+
.typeSelect {
68+
flex: 2;
69+
margin-bottom: 0;
70+
71+
> div:first-child {
72+
padding: 3px 16px 4px 16px;
73+
}
74+
}
75+
76+
.projectTypeSelect {
77+
flex: 1.5;
78+
margin-bottom: 0;
79+
80+
> div:first-child {
81+
padding: 3px 16px 4px 16px;
82+
}
83+
}
84+
85+
.categorySelect {
86+
flex: 1.5;
87+
margin-bottom: 0;
88+
89+
> div:first-child {
90+
padding: 3px 16px 4px 16px;
91+
}
92+
}
93+
94+
.statusSelect {
95+
flex: 1;
96+
margin-bottom: 0;
97+
98+
> div:first-child {
99+
padding: 3px 16px 4px 16px;
100+
}
101+
}
102+
103+
.clearButton {
104+
flex: 0.5;
105+
color: #767676;
106+
text-transform: capitalize;
107+
border-radius: 4px;
108+
border: 1px #A8A8A8 solid;
109+
box-shadow: none;
110+
font-weight: 700;
111+
}
112+
113+
}
114+
115+
@media (max-width: 768px) {
116+
.filtersContainer {
117+
flex-wrap: wrap;
118+
justify-content: center;
119+
gap: 1rem;
120+
121+
.inputWrapper {
122+
flex: 1 1 100%;
123+
min-width: 0 !important;
124+
}
125+
126+
// Two filters per row
127+
.typeSelect,
128+
.projectTypeSelect,
129+
.categorySelect,
130+
.statusSelect,
131+
.clearButton {
132+
flex: 1 1 calc(50% - 0.5rem);
133+
min-width: 0;
134+
}
135+
}
136+
}
137+
138+
@media (max-width: 1285px) and (min-width: 769px) {
139+
140+
.filtersContainer {
141+
142+
.typeSelect,
143+
.projectTypeSelect,
144+
.categorySelect,
145+
.statusSelect {
146+
flex: 1 1 20%;
147+
min-width: 0;
148+
149+
> div:first-child {
150+
white-space: normal;
151+
min-width: 0;
152+
}
153+
}
154+
}
155+
}
156+
157+
158+
@media (max-width: 500px) {
159+
.filtersContainer > * {
160+
flex: 1 1 100%;
161+
}
162+
}
163+
164+
:global(.input-el) {
165+
margin-bottom: 0;
166+
padding: 3px 16px 3px 16px;
167+
}
168+
169+
:global(.input-wrapper) {
170+
height: 38px;
171+
}
172+
173+
:global(.btn-size-lg) {
174+
padding: 6px 24px;
175+
}
176+

0 commit comments

Comments
 (0)