Skip to content

Commit 77f0192

Browse files
Added Learning Path detail page, Updated LearningPathCards
Updated the learning path cards to use the router parameter. Need to use the parameter in the link address on card click. Added the learning path detail page, but need to flesh it out after the link issue is resolved.
1 parent f7ca43c commit 77f0192

File tree

10 files changed

+91
-28
lines changed

10 files changed

+91
-28
lines changed

Caddyfile

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ localhost:80 {
88
access-control-allow-headers {http.request.header.access-control-request-headers}
99
access-control-allow-methods "get, post, put, options"
1010
}
11-
reverse_proxy https://play.picoctf.org {
11+
reverse_proxy "https://play.picoctf.org" {
1212
header_up host play.picoctf.org
1313
header_up origin https://play.picoctf.org
1414
header_up referer https://play.picoctf.org
@@ -22,14 +22,14 @@ localhost:80 {
2222
access-control-allow-headers {http.request.header.access-control-request-headers}
2323
access-control-allow-methods "get, options"
2424
}
25-
reverse_proxy https://play.picoctf.org {
25+
reverse_proxy "https://play.picoctf.org" {
2626
header_up host play.picoctf.org
2727
header_up origin https://play.picoctf.org
2828
header_up referer https://play.picoctf.org
2929
}
3030
}
3131

32-
reverse_proxy http://frontend:5173
32+
reverse_proxy "http://frontend:5173"
3333

3434
@preflight {
3535
method OPTIONS

frontend/react_app/src/App.tsx

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,9 +17,10 @@ import Primer from "./pages/resources/Primer";
1717
import Community from "./pages/resources/Community";
1818
import ExternalResources from "./pages/resources/ExternalResources";
1919
import LearningGuides from "./pages/resources/LearningGuides";
20-
import LearningPathsHome from './pages/practice/learning-paths/LearningPathHome';
20+
import LearningHome from './pages/practice/learning-paths/Home';
2121
import { mockLearningPathsHome } from './mock-data/LearningPathsData';
2222
import { mockProfile } from './mock-data/ProfileData';
23+
import PathDetail from './pages/practice/learning-paths/Path';
2324

2425
declare module "@react-types/shared" {
2526
interface RouterConfig {
@@ -45,12 +46,14 @@ function App() {
4546
<Route path='practice' element={<Outlet/>}>
4647
<Route path='games' element={<Games/>}/>
4748
<Route path='gym' element={<Gym/>}/>
48-
<Route path='learning-paths' element={<LearningPathsHome paths={mockLearningPathsHome.paths}/>}/>
49+
<Route path='learning-paths' element={<Outlet/>}>
50+
<Route index={true} element={<LearningHome paths={mockLearningPathsHome.paths}/>}/>
51+
<Route path=':pathID' element={<PathDetail/>}/>
52+
</Route>
4953
</Route>
5054
<Route path='profile' element={<Profile activity={mockProfile.activity}
5155
skillDistribution={mockProfile.skillDistribution}
5256
challengeCompletion={mockProfile.challengeCompletion}
53-
badges={mockProfile.badges}
5457
userInfo={mockProfile.userInfo}/>}/>
5558
<Route path='resources' element={<Outlet/>}>
5659
<Route path='community' element={<Community/>}/>

frontend/react_app/src/components/General/PageNavbar.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,7 @@ function PageNavbar() {
4141
<NavbarItem className="hidden lg:flex">
4242
<NotificationModal/>
4343
</NavbarItem>
44-
<NavbarItem> {/* GRAPHICS_ISSUE - this item is not showing up on the webpage as of 9/23/25 */}
44+
<NavbarItem>
4545
<Button as={Link} color="default" href="/profile" variant="flat" radius="full" isIconOnly={true}>
4646
<Avatar size='sm'/>
4747
</Button>

frontend/react_app/src/components/learning-paths/LearningPathCard.tsx

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
import { Card, CardBody } from "@heroui/react";
1+
import { Card, CardBody, Link } from "@heroui/react";
2+
import { useNavigate } from "react-router-dom";
23

34
import DifficultyChip, { type DifficultyProp } from "../general/DifficultyChip";
45
import IconCard from "../general/IconCard";
@@ -18,6 +19,7 @@ export interface LearningPathCardProps {
1819
}
1920

2021
function getBottomContent(hasProgress: boolean, numCompletedChallenges: number, numSolves: number, numTotalChallenges: number) {
22+
2123
if(hasProgress) {
2224
return (
2325
<ProgressWithTextDiv color="primary" ariaLabel={"Amount Completed"} value={numCompletedChallenges/numTotalChallenges*100} endingText={numCompletedChallenges + "/" + numTotalChallenges + " challenges"}/>
@@ -44,15 +46,15 @@ function getBottomContent(hasProgress: boolean, numCompletedChallenges: number,
4446
);
4547
}
4648

47-
const LearningPathCard: React.FC<LearningPathCardProps> = ({ description, difficulty, hasProgress, link, name, numCompletedChallenges, numSolves, numTotalChallenges }) => {
49+
const LearningPathCard: React.FC<LearningPathCardProps> = ({ description, difficulty, hasProgress, id, name, numCompletedChallenges, numSolves, numTotalChallenges }) => {
4850

4951
return (
5052
/* API_NEEDED - Get the link to the learning path and navigate there on press */
51-
<Card className="flex w-full min-w-[384px] max-w-[400px] h-[288px] border-small border-default-300 p-6 bg-content1-base" radius="md" shadow="none" isPressable isHoverable /*onPress={() => onLearningPathCardPress()}*/>
53+
<Card as={Link} className="flex w-full min-w-[384px] max-w-[400px] h-[288px] border-small border-default-300 p-6 bg-content1-base" radius="md" shadow="none" href={"/" + id} isPressable isHoverable>
5254
<CardBody className="flex flex-col w-full h-full justify-between p-0 m-0">
5355
<div className="flex flex-col w-full h-fit gap-6">
5456
<div className="flex flex-row w-full justify-between">
55-
<IconCard background={"primary"} icon={"book"}/>
57+
<IconCard background={"primary"} icon={"book"} size={"sm"}/>
5658
<DifficultyChip difficultyLvl={difficulty["difficultyLvl"]}/>
5759
</div>
5860
<div className="flex flex-col w-full h-fit items-start gap-2">

frontend/react_app/src/components/profile/UserStudiesCard.tsx

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -20,23 +20,23 @@ const UserStudiesCard: React.FC<UserStudiesCardProps> = ({ }) => {
2020
Researchers facilitating this study may...
2121
</p>
2222
<Accordion className="p-0 m-0">
23-
<AccordionItem key="1" aria-label="View platform activity data. Click to expand." title="View platform activity data">
24-
Placeholder Text
23+
<AccordionItem key="1" aria-label="View platform activity data" title="View platform activity data">
24+
Researchers may view data related to your platform usage, such as flag submissions, playlist progress, and classroom memberships.
2525
</AccordionItem>
26-
<AccordionItem key="2" aria-label="View email address. Click to expand." title="View email addresses">
27-
Placeholder Text
26+
<AccordionItem key="2" aria-label="View email address" title="View email addresses">
27+
Researchers may view your email address. You may be contacted directly regarding surveys or other follow-up questions.
2828
</AccordionItem>
29-
<AccordionItem key="3" aria-label="View basic demographic data. Click to expand." title="View basic demographic data">
30-
Placeholder Text
29+
<AccordionItem key="3" aria-label="View basic demographic data" title="View basic demographic data">
30+
Researchers may view basic demographic data, such as your player type and grade.
3131
</AccordionItem>
32-
<AccordionItem key="4" aria-label="View locational demographic data. Click to expand." title="View locational demographic data">
33-
Placeholder Text
32+
<AccordionItem key="4" aria-label="View locational demographic data" title="View locational demographic data">
33+
Researchers may view demographic data regarding your geographical location, such as your country, postal code, and school name.
3434
</AccordionItem>
35-
<AccordionItem key="5" aria-label="View personal demographic data. Click to expand." title="View personal demographic data">
36-
Placeholder Text
35+
<AccordionItem key="5" aria-label="View personal demographic data" title="View personal demographic data">
36+
Researchers may view your selected gender and race/ethnicity self-identifications.
3737
</AccordionItem>
38-
<AccordionItem key="6" aria-label="View webshell logs. Click to expand." title="View webshell logs">
39-
Placeholder Text
38+
<AccordionItem key="6" aria-label="View webshell logs" title="View webshell logs">
39+
Researchers may view logs of your webshell sessions.
4040
</AccordionItem>
4141
</Accordion>
4242
</CardBody>

frontend/react_app/src/mock-data/LearningPathsData.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import type { LearningPathsHomeProps } from "../pages/practice/learning-paths/LearningPathHome";
1+
import type { LearningPathsHomeProps } from "../pages/practice/learning-paths/Home";
22

33
export const mockLearningPathsHome: LearningPathsHomeProps = {
44
paths: [

frontend/react_app/src/pages/practice/learning-paths/LearningPathHome.tsx renamed to frontend/react_app/src/pages/practice/learning-paths/Home.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ export interface LearningPathsHomeProps {
77
paths: LearningPathCardProps[];
88
}
99

10-
const LearningPathsHome: React.FC<LearningPathsHomeProps> = ({ paths }) => {
10+
const Home: React.FC<LearningPathsHomeProps> = ({ paths }) => {
1111

1212
let continuingPaths: LearningPathCardProps[] = [];
1313

@@ -58,4 +58,4 @@ const LearningPathsHome: React.FC<LearningPathsHomeProps> = ({ paths }) => {
5858
);
5959
}
6060

61-
export default LearningPathsHome;
61+
export default Home;
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
import "../../Page.css";
2+
import Header from "../../../components/General/PageNavbar";
3+
import { useParams } from "react-router";
4+
import { BreadcrumbItem, Breadcrumbs } from "@heroui/react";
5+
import LearningPathsContentListCard from "../../../components/learning-paths/LearningPathsAccordion";
6+
import LearningPathOverviewDiv from "../../../components/learning-paths/LearningPathOverviewDiv";
7+
8+
export interface PathDetailProps {
9+
}
10+
11+
const PathDetail: React.FC<PathDetailProps> = ({ }) => {
12+
13+
// API_NEEDED - Get the path detail information using the path's ID
14+
let params = useParams();
15+
const id = params.pathID;
16+
17+
return (
18+
<div className="Page">
19+
<Header/>
20+
<div className="flex flex-col w-full px-32 py-10 gap-6 items-center">
21+
<Breadcrumbs>
22+
<BreadcrumbItem href="/practice/learning-paths">Practice</BreadcrumbItem>
23+
<BreadcrumbItem href="/practice/learning-paths">Learning Paths</BreadcrumbItem>
24+
<BreadcrumbItem href="/practice/learning-paths/page">Learning Path Page</BreadcrumbItem>
25+
</Breadcrumbs>
26+
27+
<div className="flex flex-row w-full h-fit gap-64">
28+
<LearningPathOverviewDiv
29+
difficulty={"Easy"}
30+
name={"My Path"}
31+
numChallenges={0}
32+
numSolves={0}
33+
prereqs={[]}
34+
skills={[]}
35+
/>
36+
<LearningPathsContentListCard
37+
name={"My Path"}
38+
progress={{
39+
color:"primary",
40+
ariaLabel:"temp",
41+
value: 0.5,
42+
endingText: "50%"
43+
}}
44+
list={[
45+
{
46+
item: {},
47+
itemProgress: {},
48+
children: []
49+
}
50+
]}
51+
/>
52+
</div>
53+
</div>
54+
</div>
55+
);
56+
}
57+
58+
export default PathDetail;

frontend/react_app/src/stories/learning-paths/LearningPathOverviewDiv.stories.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ type Story = StoryObj<typeof meta>;
2727

2828
export const Default: Story = {
2929
args: {
30-
difficulty: {Enum: 1},
30+
difficulty: "Easy",
3131
name: "Learning Path Name",
3232
numChallenges: 15,
3333
numSolves: 1347,

frontend/react_app/src/stories/pages/practice/learning-paths/LearningPathHome.stories.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import type { Meta, StoryObj } from '@storybook/react-vite';
2-
import LearningPathsHome from '../../../../pages/practice/learning-paths/LearningPathHome';
2+
import LearningPathsHome from '../../../../pages/practice/learning-paths/Home';
33

44
const meta = {
55
title: 'Pages/Practice/Learning Paths/Home',

0 commit comments

Comments
 (0)