Skip to content

Commit

Permalink
CourseAgenda refactor
Browse files Browse the repository at this point in the history
  • Loading branch information
Haxikowy committed Aug 21, 2023
1 parent 735cc56 commit 2054074
Show file tree
Hide file tree
Showing 10 changed files with 761 additions and 806 deletions.
141 changes: 62 additions & 79 deletions src/components/organisms/CourseAgenda/CourseAgenda.md
Original file line number Diff line number Diff line change
@@ -1,115 +1,98 @@
```js
import img1 from "./CourseAgenda.png";
import { useState, useCallback, useEffect } from "react";
import { useState, useCallback, useMemo } from "react";
import { ThemeTester } from "../../../styleguide";
import { Button } from "../../../";
import data from "./mock.json";
import "../../../styleguide/i18n.ts";
import { getFlatTopics } from "../../../utils/course";

const flatTopics = data.lessons.reduce(
(acc, curr) => (Array.isArray(curr.topics) ? [...acc, ...curr.topics] : acc),
[]
);
const flatTopics = useMemo(() => getFlatTopics(data.lessons), []);

const [state, setState] = useState({
finishedTopicIds: [],
currentTopicId: flatTopics[0].id,
});

const [stateWithRandomBlockers, setStateWithRandomBlockers] = useState([]);

const randomizeState = () => {
const randomizedState = data.lessons.map((lesson) => ({
...lesson,
topics: lesson.topics.map((topic) => ({
...topic,
const getRandomizedState = (lessons) =>
lessons.map((l) => ({
...l,
lessons: getRandomizedState(l.lessons ? l.lessons : []),
topics: l.topics.map((t) => ({
...t,
can_skip: Math.random() > 0.3,
})),
}));

const [stateWithRandomBlockers, setStateWithRandomBlockers] = useState(
getRandomizedState(data.lessons)
);

const randomizeState = () => {
const randomizedState = getRandomizedState(data.lessons);

setStateWithRandomBlockers(randomizedState);
setState({
finishedTopicIds: [],
currentTopicId: flatTopics[0].id,
});
};

const onNextTopic = useCallback(() => {
let nextTopicId;
data.lessons.forEach((lesson, lIndex) => {
lesson.topics.forEach((topic, tIndex) => {
if (topic.id === state.currentTopicId) {
// try find next topic in current lesson
if (lesson.topics[tIndex + 1]) {
nextTopicId = lesson.topics[tIndex + 1];
// try find first topic in next lesson
} else if (data.lessons[lIndex + 1]) {
nextTopicId = data.lessons[lIndex + 1].topics[0];
// otherwise this is end so going back to first lesson and topic
} else {
nextTopicId = data.lessons[0].topics[0];
}
}
});
});
const changeTopicToNext = useCallback(() => {
const currentTopicIndex = flatTopics.findIndex(
(t) => t.id === state.currentTopicId
);
if (currentTopicIndex === -1) return;
const nextTopic = flatTopics[currentTopicIndex + 1];

if (!nextTopic) return;
setState((prevState) => ({
...prevState,
currentTopicId: nextTopicId.id,
currentTopicId: nextTopic.id,
}));
}, [state.currentTopicId]);
}, [flatTopics, state.currentTopicId]);

const onTopicFinished = useCallback(
(topic) => {
const markTopicFinished = useCallback(
(topic) =>
setState((prevState) => {
const s = new Set([...prevState.finishedTopicIds, topic.id]);

return {
finishedTopicIds: [...prevState.finishedTopicIds, topic.id],
currentTopicId: prevState.currentTopicId,
...prevState,
finishedTopicIds: Array.from(s),
};
});

onNextTopic();
},
[state.currentTopicId]
}),
[]
);

const onTopicChange = useCallback((topic) => {
setState((prevState) => {
return {
...prevState,
currentTopicId: topic.id,
};
});
}, []);

useEffect(() => {
randomizeState();
const changeTopic = useCallback((topic) => {
setState((prevState) => ({
...prevState,
currentTopicId: topic.id,
}));
}, []);

<React.Fragment>
<ThemeTester flexDirection="column">
<Button onClick={() => randomizeState()}>Randomize</Button>
<div style={{ width: "100%" }}>
<CourseAgenda
lessons={stateWithRandomBlockers}
finishedTopicIds={state.finishedTopicIds}
currentTopicId={state.currentTopicId}
onTopicClick={(topic) => onTopicChange(topic)}
onMarkFinished={(topic) => onTopicFinished(topic)}
onNextTopicClick={(topic) => onNextTopic(topic)}
/>
</div>
<div style={{ width: 375 }}>
<CourseAgenda
mobile
lessons={stateWithRandomBlockers}
finishedTopicIds={state.finishedTopicIds}
currentTopicId={state.currentTopicId}
onTopicClick={(topic) => onTopicChange(topic)}
onMarkFinished={(topic) => onTopicFinished(topic)}
onNextTopicClick={(topic) => onNextTopic(topic)}
/>
</div>
</ThemeTester>
</React.Fragment>;
<ThemeTester flexDirection="column">
<Button onClick={() => randomizeState()}>Randomize</Button>
<div style={{ width: "100%" }}>
<CourseAgenda
lessons={stateWithRandomBlockers}
finishedTopicIds={state.finishedTopicIds}
currentTopicId={state.currentTopicId}
onTopicClick={changeTopic}
onMarkFinished={markTopicFinished}
onNextTopicClick={changeTopicToNext}
/>
</div>
<div style={{ width: 375 }}>
<CourseAgenda
mobile
lessons={stateWithRandomBlockers}
finishedTopicIds={state.finishedTopicIds}
currentTopicId={state.currentTopicId}
onTopicClick={changeTopic}
onMarkFinished={markTopicFinished}
onNextTopicClick={changeTopicToNext}
/>
</div>
</ThemeTester>;
```
Loading

0 comments on commit 2054074

Please sign in to comment.