Skip to content
This repository was archived by the owner on Dec 5, 2024. It is now read-only.

Commit 586d2b9

Browse files
committed
feat(client): use context
1 parent 291082f commit 586d2b9

17 files changed

+437
-312
lines changed
+13-54
Original file line numberDiff line numberDiff line change
@@ -1,81 +1,40 @@
11
import React, { useState, useEffect } from 'react';
22
import { MdMenu } from 'react-icons/md';
3-
import { useCurrentIndex } from '../hooks/useCurrentIndex';
4-
import { useMode } from '../hooks/useMode';
5-
import { useSlidesProps } from '../hooks/useSlides';
63
import { useContentComponent } from '../hooks/useContentComponent';
74
import { useSidebarComponent } from '../hooks/useSidebarComponent';
5+
import { useSlides, addSlides } from '../context/slides';
86

9-
const slideWrapperClassName = '.swiper-container';
10-
11-
export const AppContainer = ({ slides: originalSlides, hash }) => {
7+
export const AppContainer = ({ slidesProps }) => {
128
const [isOpenSidebar, updateOpenSidebarStatus] = useState(false);
13-
const [currentIndex, setCurrentIndex] = useCurrentIndex();
14-
const { slides, contentsList } = useSlidesProps({ originalSlides, hash, currentIndex });
15-
const [mode, setMode] = useMode();
9+
const {
10+
state: { mode, slides },
11+
dispatch,
12+
} = useSlides();
1613
const ContentComponent = useContentComponent(mode);
1714
const SidebarComponent = useSidebarComponent(mode);
1815

19-
const goTo = (num) => {
20-
let nextIndex = num;
21-
const { swiper } = document.querySelector(slideWrapperClassName);
22-
const { realIndex } = swiper;
23-
24-
if (num === '+') {
25-
nextIndex = Math.min(realIndex + 1, slides.length);
26-
} else if (num === '-') {
27-
nextIndex = Math.max(realIndex - 1, 0);
28-
}
29-
30-
swiper?.slideTo(nextIndex);
31-
setCurrentIndex(nextIndex);
32-
};
33-
34-
const runPresentationMode = (type) => {
35-
updateOpenSidebarStatus(false);
36-
setMode(type === 'start' ? 'host' : 'common');
37-
};
16+
useEffect(() => {
17+
dispatch(addSlides(slidesProps));
18+
}, [slidesProps]);
3819

3920
useEffect(() => {
40-
// TODO: add params for presentation iframe
41-
if (mode === 'common') {
42-
document.addEventListener('keydown', ({ key }) => {
43-
if (key === 'ArrowRight') {
44-
goTo('+');
45-
} else if (key === 'ArrowLeft') {
46-
goTo('-');
47-
}
48-
});
21+
if (mode !== 'common' && isOpenSidebar) {
22+
updateOpenSidebarStatus(false);
4923
}
50-
}, []);
24+
}, [mode, isOpenSidebar]);
5125

5226
return (
5327
<>
5428
{SidebarComponent && (
5529
<>
5630
<SidebarComponent
57-
goTo={goTo}
5831
isOpen={isOpenSidebar}
59-
totalSlides={slides.length}
60-
terminate={() => runPresentationMode('terminate')}
61-
contents={contentsList}
6232
onStateChange={({ isOpen }) => updateOpenSidebarStatus(isOpen)}
63-
currentIndex={currentIndex}
64-
runPresentationMode={() => runPresentationMode('start')}
6533
/>
6634
<MdMenu className="btn-sidebar" onClick={() => updateOpenSidebarStatus(true)} />
6735
</>
6836
)}
69-
{ContentComponent && (
70-
<ContentComponent
71-
hash={hash}
72-
slides={slides}
73-
isJumpPage={currentIndex !== 0}
74-
terminate={() => runPresentationMode('terminate')}
75-
currentIndex={currentIndex}
76-
onChangeSlideIndex={setCurrentIndex}
77-
/>
78-
)}
37+
{ContentComponent && <ContentComponent slides={slides} />}
7938
</>
8039
);
8140
};
Original file line numberDiff line numberDiff line change
@@ -1,33 +1,34 @@
1-
import React, { useEffect, memo } from 'react';
1+
import React, { memo, useEffect } from 'react';
2+
import { useSlides, updateCurrentIndex } from '../../context/slides';
23
import { SlideCore } from '../SlideCore';
3-
import { Prism } from '../../setup/prism';
4-
import { createVMEnv } from '../../utils/createVMEnv';
5-
import { useMermaid } from '../../hooks/useMermaid';
64

7-
export const Base = memo(
8-
({ slides, onChangeSlideIndex, hash }) => {
9-
const [mermaid] = useMermaid();
5+
export const Base = memo(() => {
6+
const {
7+
state: { currentIndex },
8+
dispatch,
9+
} = useSlides();
1010

11-
if (import.meta.webpackHot) {
12-
useEffect(() => {
13-
if (process.env.CHART) {
14-
mermaid?.reload();
15-
}
11+
useEffect(() => {
12+
// TODO: swiper should be gone to context
13+
const { swiper } = document.querySelector('.swiper-container');
14+
swiper?.slideTo(currentIndex);
15+
}, [currentIndex]);
1616

17-
Prism.highlightAll();
18-
}, [hash]);
19-
}
20-
21-
useEffect(() => {
22-
if (slides.some(({ fusumaProps }) => !!fusumaProps.hasExecutableCode)) {
23-
createVMEnv();
24-
}
25-
if (process.env.CHART) {
26-
mermaid?.reload();
17+
useEffect(() => {
18+
const keyboardListener = ({ key }) => {
19+
if (key === 'ArrowRight') {
20+
dispatch(updateCurrentIndex('+'));
21+
} else if (key === 'ArrowLeft') {
22+
dispatch(updateCurrentIndex('-'));
2723
}
28-
}, []);
24+
};
25+
26+
document.addEventListener('keydown', keyboardListener);
27+
28+
return () => {
29+
document.removeEventListener('keydown', keyboardListener);
30+
};
31+
}, []);
2932

30-
return <SlideCore slides={slides} onChangeSlideIndex={onChangeSlideIndex} />;
31-
},
32-
(prevProps, nextProps) => prevProps.hash === nextProps.hash
33-
);
33+
return <SlideCore />;
34+
});

packages/client/src/components/ContentView/Host.js

+65-58
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,17 @@
1-
/**
2-
* Host for Presentation mode
3-
*/
4-
51
import React, { memo, useState, useEffect } from 'react';
62
import Modal from 'react-modal';
73
import {
84
FaTimes,
95
FaHistory,
106
FaCaretDown,
11-
FaCaretRight,
7+
// FaCaretRight,
128
FaCaretUp,
139
FaMicrophoneAlt,
1410
FaMicrophoneAltSlash,
1511
} from 'react-icons/fa';
1612
import { MdZoomOutMap } from 'react-icons/md';
13+
import { useSlides, setMode } from '../../context/slides';
14+
import { PresenterProvider, usePresenter, updateCurrentIndex } from '../../context/presenter';
1715
import { Controller as PresentationController } from '../../presentationMode/Controller'; // common and host
1816
import { Canvas, emitCanvasEvent } from '../Canvas';
1917
import { Timer } from '../Timer';
@@ -40,11 +38,21 @@ let recordedTimeline = [];
4038
let recordedStartedTime = 0;
4139
let audioUrl = null;
4240

43-
const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
41+
const Host = () => {
42+
const {
43+
state: { slides },
44+
dispatch: dispatchSlides,
45+
} = useSlides();
46+
const {
47+
state: { currentIndex },
48+
dispatch: dispatchPresenter,
49+
} = usePresenter();
50+
4451
if (!presentationController) {
4552
const { origin, pathname } = new URL(window.location);
4653

4754
slideUrl = `${origin}${pathname}?sidebar=false&reference=false#slide-`;
55+
4856
presentationController = new PresentationController();
4957
}
5058

@@ -54,39 +62,38 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
5462
const [isEmptyRecordedTimeline, updateEmptyRecordedTimelineStatus] = useState(true);
5563
const [isOpenZoomSlide, updateOpenZoomSlideStatus] = useState(false);
5664

57-
const _terminate = () => {
65+
const terminate = () => {
5866
try {
59-
terminate();
60-
6167
if (presentationController) {
6268
presentationController.terminate();
6369
presentationController = null;
6470
}
6571
} catch (e) {
6672
console.error(e);
73+
} finally {
74+
dispatchSlides(setMode('common'));
6775
}
6876
};
6977

70-
const changeCurrentSlide = (num) => {
71-
if (status === 'start') {
72-
const time = new Date().getTime() - recordedStartedTime;
73-
const prevItem = recordedTimeline.slice(-1)[0];
74-
75-
recordedTimeline.push({
76-
slideNum: num + 1,
77-
time,
78-
timeStr: `${formatTime(time)} (+${formatTime(time - prevItem.time)})`,
79-
event: 'changed',
80-
title: `Moved to the ${num + 1} slide from the ${num} slide.`,
81-
Slide: slides[num].slide,
82-
color: '#3498db',
83-
Icon: <FaCaretRight size="22" />,
84-
});
85-
}
86-
87-
onChangeSlideIndex(num);
88-
presentationController.changePage(num);
89-
};
78+
// const changeCurrentSlide = (num) => {
79+
// if (status === 'start') {
80+
// const time = new Date().getTime() - recordedStartedTime;
81+
// const prevItem = recordedTimeline.slice(-1)[0];
82+
83+
// recordedTimeline.push({
84+
// slideNum: num + 1,
85+
// time,
86+
// timeStr: `${formatTime(time)} (+${formatTime(time - prevItem.time)})`,
87+
// event: 'changed',
88+
// title: `Moved to the ${num + 1} slide from the ${num} slide.`,
89+
// Slide: slides[num].slide,
90+
// color: '#3498db',
91+
// Icon: <FaCaretRight size="22" />,
92+
// });
93+
// }
94+
95+
// presentationController.changePage(num);
96+
// };
9097

9198
const start = () => {
9299
if (recordedTimeline.length === 0) {
@@ -143,14 +150,6 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
143150
updateEmptyRecordedTimelineStatus(true);
144151
};
145152

146-
const openTimeline = () => {
147-
updateOpenTimelineStatus(true);
148-
};
149-
150-
const closeTimeline = () => {
151-
updateOpenTimelineStatus(false);
152-
};
153-
154153
const setupRecording = () => {
155154
if (!webrtc) {
156155
try {
@@ -183,7 +182,7 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
183182
};
184183

185184
useEffect(() => {
186-
async function openView() {
185+
(async () => {
187186
try {
188187
if (!presentationController) {
189188
throw new Error('Not found PresenterController.');
@@ -192,30 +191,32 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
192191
} catch (e) {
193192
console.error(e);
194193
}
195-
}
194+
})();
196195

197-
openView();
196+
const keyboardListener = ({ key }) => {
197+
const slideLength = slides.length;
198198

199-
return () => {
200-
document.onkeyup = null;
199+
if (key === 'ArrowLeft') {
200+
dispatchPresenter(updateCurrentIndex({ index: '-', slideLength }));
201+
} else if (key === 'ArrowRight') {
202+
dispatchPresenter(updateCurrentIndex({ index: '+', slideLength }));
203+
204+
// TODO: fix here
205+
// presentationController.changePage(3);
206+
}
207+
};
208+
document.addEventListener('keydown', keyboardListener, false);
201209

210+
return () => {
202211
if (presentationController) {
203-
_terminate();
212+
terminate();
204213
}
205214

206215
disposeRecording();
207-
};
208-
}, []);
209216

210-
useEffect(() => {
211-
document.onkeyup = (e) => {
212-
if (e.key === 'ArrowLeft') {
213-
changeCurrentSlide(Math.max(0, currentIndex - 1));
214-
} else if (e.key === 'ArrowRight') {
215-
changeCurrentSlide(Math.min(slides.length - 1, currentIndex + 1));
216-
}
217+
document.removeEventListener('keydown', keyboardListener);
217218
};
218-
});
219+
}, []);
219220

220221
// prohibit below actions
221222
// usedAudio && status === 'start'
@@ -226,7 +227,7 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
226227
// mic
227228
return (
228229
<div className="host-container">
229-
<Modal isOpen={isOpenTimeline} onRequestClose={closeTimeline}>
230+
<Modal isOpen={isOpenTimeline} onRequestClose={() => updateOpenTimelineStatus(false)}>
230231
<Timeline items={recordedTimeline} url={audioUrl} />
231232
</Modal>
232233
<div className="host-left-box">
@@ -260,7 +261,7 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
260261
</div>
261262
</div>
262263
<div className="host-bottom-box">
263-
<FaTimes onClick={_terminate} className="terminate-button" />
264+
<FaTimes onClick={terminate} className="terminate-button" />
264265
<div className="host-bottom-box-info">
265266
<Timer
266267
start={start}
@@ -275,7 +276,7 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
275276
{`${currentIndex + 1}`.padStart(2, '0')} / {`${slides.length}`.padStart(2, '0')}
276277
</span>
277278
<FaHistory
278-
onClick={openTimeline}
279+
onClick={() => updateOpenTimelineStatus(true)}
279280
size={18}
280281
className={
281282
(status === 'start' && usedAudio) || isEmptyRecordedTimeline ? 'disabled' : undefined
@@ -299,6 +300,12 @@ const Host = memo(({ slides, currentIndex, terminate, onChangeSlideIndex }) => {
299300
</div>
300301
</div>
301302
);
302-
});
303+
};
304+
305+
const Presenter = memo(() => (
306+
<PresenterProvider>
307+
<Host />
308+
</PresenterProvider>
309+
));
303310

304-
export default Host;
311+
export default Presenter;

0 commit comments

Comments
 (0)