refactoring(player): separating Screen and MessageManager; renamings
This commit is contained in:
parent
af6fd085e2
commit
daf35a2dfa
52 changed files with 91 additions and 134 deletions
|
|
@ -1,9 +1,9 @@
|
|||
import WebPlayer from './_web/WebPlayer';
|
||||
import WebPlayer from './web/WebPlayer';
|
||||
import reduxStore, {update, cleanStore} from './_store';
|
||||
|
||||
import type { State as MMState } from './_web/MessageManager'
|
||||
import type { State as MMState } from './web/MessageManager'
|
||||
import type { State as PState } from './player/Player'
|
||||
import type { Store } from './player/types'
|
||||
import type { Store } from './common/types'
|
||||
|
||||
|
||||
const myStore: Store<PState & MMState> = {
|
||||
|
|
|
|||
|
|
@ -1,15 +1,11 @@
|
|||
import { applyChange, revertChange } from 'deep-diff';
|
||||
|
||||
import { INITIAL_STATE as MM_INITIAL_STATE } from '../_web/MessageManager'
|
||||
import Player from '../player/Player'
|
||||
import WebPlayer from '../web/WebPlayer'
|
||||
|
||||
const UPDATE = 'player/UPDATE';
|
||||
const CLEAN = 'player/CLEAN';
|
||||
const REDUX = 'player/REDUX';
|
||||
|
||||
const resetState = {
|
||||
...MM_INITIAL_STATE,
|
||||
...Player.INITIAL_STATE,
|
||||
...WebPlayer.INITIAL_STATE,
|
||||
initialized: false,
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
// export * from './connector';
|
||||
// export * from './store';
|
||||
// export * from './selectors';
|
||||
// export { default } from './store';
|
||||
export * from './connector';
|
||||
export * from './store';
|
||||
export * from './selectors';
|
||||
export { default } from './store';
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
import type { Timed } from '../_web/messages/timed';
|
||||
import type { Timed } from './types';
|
||||
|
||||
export default class ListWalker<T extends Timed> {
|
||||
private p = 0
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
import type { Timed } from '../_web/messages/timed';
|
||||
import type { Timed } from './types';
|
||||
import ListWalker from './ListWalker'
|
||||
|
||||
|
||||
|
|
@ -1,5 +1,4 @@
|
|||
|
||||
import { Store } from '../player/types'
|
||||
import { Store } from './types'
|
||||
|
||||
// (not a type)
|
||||
export default class SimpleSore<G, S=G> implements Store<G, S> {
|
||||
|
|
@ -1,3 +1,6 @@
|
|||
export interface Timed {
|
||||
time: number
|
||||
}
|
||||
|
||||
export interface Moveable {
|
||||
move(time: number): void
|
||||
|
|
@ -18,4 +21,3 @@ export interface Store<G extends Object, S extends Object = G> {
|
|||
update(state: Partial<S>): void
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
import SimpleStore from './_common/SimpleStore'
|
||||
import type { Store } from './player/types'
|
||||
import SimpleStore from './common/SimpleStore'
|
||||
import type { Store } from './common/types'
|
||||
|
||||
import WebPlayer from './_web/WebPlayer'
|
||||
import WebPlayer from './web/WebPlayer'
|
||||
|
||||
type WebState = typeof WebPlayer.INITIAL_STATE //?
|
||||
type WebPlayerStore = Store<WebState>
|
||||
|
|
|
|||
|
|
@ -1,9 +1,9 @@
|
|||
export * from './_web/assist/AssistManager';
|
||||
export * from './_web/assist/LocalStream';
|
||||
export * from './_web/WebPlayer';
|
||||
export * from './web/assist/AssistManager';
|
||||
export * from './web/assist/LocalStream';
|
||||
export * from './web/WebPlayer';
|
||||
export * from './create';
|
||||
|
||||
export type { MarkedTarget } from './_web/TargetMarker'
|
||||
export type { MarkedTarget } from './web/TargetMarker'
|
||||
|
||||
//export * from './_store';
|
||||
//export * from './_singletone';
|
||||
export * from './_store';
|
||||
export * from './_singletone';
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
import type { Store, Moveable, Interval } from './types';
|
||||
import type { Store, Moveable, Interval } from '../common/types';
|
||||
import * as localStorage from './localStorage';
|
||||
|
||||
const fps = 60
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
import * as typedLocalStorage from './localStorage';
|
||||
|
||||
import type { Moveable, Cleanable, Store } from './types';
|
||||
import type { Moveable, Cleanable, Store } from '../common/types';
|
||||
import Animator from './Animator';
|
||||
import type { GetState as AnimatorGetState, SetState as AnimatorSetState } from './Animator';
|
||||
|
||||
|
|
@ -57,8 +57,6 @@ export default class Player extends Animator {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* === TODO: incapsulate in LSCache === */
|
||||
|
||||
toggleAutoplay() {
|
||||
|
|
@ -67,14 +65,14 @@ export default class Player extends Animator {
|
|||
this.pState.update({ autoplay })
|
||||
}
|
||||
|
||||
// Shouldn't it be in the react part as a fully (with localStorage-cache react hook)?
|
||||
//TODO: move to react part (with localStorage-cache react hook)?
|
||||
toggleEvents() {
|
||||
const showEvents = !this.pState.get().showEvents
|
||||
localStorage.setItem(SHOW_EVENTS_STORAGE_KEY, `${showEvents}`);
|
||||
this.pState.update({ showEvents })
|
||||
}
|
||||
|
||||
// move to React part?
|
||||
// TODO: move to React part
|
||||
toggleSkipToIssue() {
|
||||
const skipToIssue = !this.pState.get().skipToIssue
|
||||
localStorage.setItem(SKIP_TO_ISSUE_STORAGE_KEY, `${skipToIssue}`);
|
||||
|
|
@ -107,15 +105,6 @@ export default class Player extends Animator {
|
|||
}
|
||||
/* === === */
|
||||
|
||||
// TODO: move theese to React hooks
|
||||
// injectNotes(notes: Note[]) {
|
||||
// update({ notes })
|
||||
// }
|
||||
// filterOutNote(noteId: number) {
|
||||
// const { notes } = getState()
|
||||
// update({ notes: notes.filter((note: Note) => note.noteId !== noteId) })
|
||||
// }
|
||||
|
||||
|
||||
clean() {
|
||||
this.pause()
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import ListWalker from '../_common/ListWalker';
|
||||
import ListWalkerWithMarks from '../_common/ListWalkerWithMarks';
|
||||
import ListWalker from '../common/ListWalker';
|
||||
import ListWalkerWithMarks from '../common/ListWalkerWithMarks';
|
||||
|
||||
import type { Message } from './messages'
|
||||
|
||||
|
|
@ -8,10 +8,8 @@ import Log from 'Types/session/log';
|
|||
|
||||
import { toast } from 'react-toastify';
|
||||
|
||||
import type { Store } from '../player/types';
|
||||
import ListWalker from '../_common/ListWalker';
|
||||
|
||||
import Screen from './Screen/Screen';
|
||||
import type { Store } from '../common/types';
|
||||
import ListWalker from '../common/ListWalker';
|
||||
|
||||
import PagesManager from './managers/PagesManager';
|
||||
import MouseMoveManager from './managers/MouseMoveManager';
|
||||
|
|
@ -24,15 +22,19 @@ import MFileReader from './messages/MFileReader';
|
|||
import { loadFiles, requestEFSDom, requestEFSDevtools } from './network/loadFiles';
|
||||
import { decryptSessionBytes } from './network/crypto';
|
||||
|
||||
import { INITIAL_STATE as SCREEN_INITIAL_STATE, State as SuperState } from './Screen/Screen';
|
||||
import Lists, { INITIAL_STATE as LISTS_INITIAL_STATE } from './Lists';
|
||||
|
||||
import Screen, {
|
||||
INITIAL_STATE as SCREEN_INITIAL_STATE,
|
||||
State as ScreenState,
|
||||
} from './Screen/Screen';
|
||||
|
||||
import type { InitialLists } from './Lists'
|
||||
import type { PerformanceChartPoint } from './managers/PerformanceTrackManager';
|
||||
import type { SkipInterval } from './managers/ActivityManager';
|
||||
|
||||
|
||||
export interface State extends SuperState {
|
||||
export interface State extends ScreenState {
|
||||
performanceChartData: PerformanceChartPoint[],
|
||||
skipIntervals: SkipInterval[],
|
||||
connType?: string,
|
||||
|
|
@ -73,7 +75,7 @@ const visualChanges = [
|
|||
"set_viewport_scroll",
|
||||
]
|
||||
|
||||
export default class MessageManager extends Screen {
|
||||
export default class MessageManager {
|
||||
static INITIAL_STATE: State = {
|
||||
...SCREEN_INITIAL_STATE,
|
||||
...LISTS_INITIAL_STATE,
|
||||
|
|
@ -116,12 +118,12 @@ export default class MessageManager extends Screen {
|
|||
|
||||
constructor(
|
||||
private readonly session: any /*Session*/,
|
||||
private readonly state: Store<State>,
|
||||
private readonly state: Store<State>,
|
||||
private readonly screen: Screen,
|
||||
initialLists?: Partial<InitialLists>
|
||||
) {
|
||||
super();
|
||||
this.pagesManager = new PagesManager(this, this.session.isMobile)
|
||||
this.mouseMoveManager = new MouseMoveManager(this)
|
||||
this.pagesManager = new PagesManager(screen, this.session.isMobile, this)
|
||||
this.mouseMoveManager = new MouseMoveManager(screen)
|
||||
|
||||
this.sessionStart = this.session.startedAt
|
||||
|
||||
|
|
@ -281,8 +283,8 @@ export default class MessageManager extends Screen {
|
|||
|
||||
this.performanceTrackManager = new PerformanceTrackManager()
|
||||
this.windowNodeCounter = new WindowNodeCounter();
|
||||
this.pagesManager = new PagesManager(this, this.session.isMobile)
|
||||
this.mouseMoveManager = new MouseMoveManager(this);
|
||||
this.pagesManager = new PagesManager(this.screen, this.session.isMobile, this)
|
||||
this.mouseMoveManager = new MouseMoveManager(this.screen);
|
||||
this.activityManager = new ActivityManager(this.session.duration.milliseconds);
|
||||
}
|
||||
|
||||
|
|
@ -339,14 +341,14 @@ export default class MessageManager extends Screen {
|
|||
this.pagesManager.moveReady(t).then(() => {
|
||||
|
||||
const lastScroll = this.scrollManager.moveGetLast(t, index);
|
||||
if (!!lastScroll && this.window) {
|
||||
this.window.scrollTo(lastScroll.x, lastScroll.y);
|
||||
if (!!lastScroll && this.screen.window) {
|
||||
this.screen.window.scrollTo(lastScroll.x, lastScroll.y);
|
||||
}
|
||||
// Moving mouse and setting :hover classes on ready view
|
||||
this.mouseMoveManager.move(t);
|
||||
const lastClick = this.clickManager.moveGetLast(t);
|
||||
if (!!lastClick && t - lastClick.time < 600) { // happend during last 600ms
|
||||
this.cursor.click();
|
||||
this.screen.cursor.click();
|
||||
}
|
||||
// After all changes - redraw the marker
|
||||
//this.marker.redraw();
|
||||
|
|
@ -514,17 +516,17 @@ export default class MessageManager extends Screen {
|
|||
}
|
||||
|
||||
setMessagesLoading(messagesLoading: boolean) {
|
||||
this.display(!messagesLoading);
|
||||
this.screen.display(!messagesLoading);
|
||||
this.state.update({ messagesLoading });
|
||||
}
|
||||
|
||||
setCSSLoading(cssLoading: boolean) {
|
||||
this.displayFrame(!cssLoading);
|
||||
this.screen.displayFrame(!cssLoading);
|
||||
this.state.update({ cssLoading });
|
||||
}
|
||||
|
||||
private setSize({ height, width }: { height: number, width: number }) {
|
||||
this.scale({ height, width });
|
||||
this.screen.scale({ height, width });
|
||||
this.state.update({ width, height });
|
||||
|
||||
//this.updateMarketTargets()
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
import type Screen from './Screen/Screen'
|
||||
import type { Point } from './Screen/types'
|
||||
import type { Store } from '../player/types'
|
||||
import type { Store } from '../common/types'
|
||||
|
||||
|
||||
function getOffset(el: Element, innerWindow: Window) {
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
import type { Store } from '../player/types'
|
||||
import type { Store } from '../common/types'
|
||||
import Player, { State as PlayerState } from '../player/Player'
|
||||
|
||||
import MessageManager from './MessageManager'
|
||||
|
|
@ -39,17 +39,13 @@ export default class WebPlayer extends Player {
|
|||
exceptions: session.errors,
|
||||
} : {}
|
||||
|
||||
// TODO: separate screen from manager
|
||||
const screen = new MessageManager(session, wpState, initialLists)
|
||||
super(wpState, screen)
|
||||
const screen = new Screen()
|
||||
const messageManager = new MessageManager(session, wpState, screen, initialLists)
|
||||
super(wpState, messageManager)
|
||||
this.screen = screen
|
||||
this.messageManager = screen
|
||||
|
||||
// TODO: separate LiveWebPlayer
|
||||
this.assistManager = new AssistManager(session, this.messageManager, config, wpState)
|
||||
this.messageManager = messageManager
|
||||
|
||||
this.targetMarker = new TargetMarker(this.screen, wpState)
|
||||
|
||||
this.inspectorController = new InspectorController(screen)
|
||||
|
||||
|
||||
|
|
@ -65,6 +61,8 @@ export default class WebPlayer extends Player {
|
|||
endTime, // : 0, //TODO: through initialState
|
||||
})
|
||||
|
||||
// TODO: separate LiveWebPlayer
|
||||
this.assistManager = new AssistManager(session, this.messageManager, config, wpState)
|
||||
if (live) {
|
||||
this.assistManager.connect(session.agentToken)
|
||||
}
|
||||
|
|
@ -123,6 +121,15 @@ export default class WebPlayer extends Player {
|
|||
}
|
||||
}
|
||||
|
||||
// TODO: restore notes functionality
|
||||
// injectNotes(notes: Note[]) {
|
||||
// update({ notes })
|
||||
// }
|
||||
// filterOutNote(noteId: number) {
|
||||
// const { notes } = getState()
|
||||
// update({ notes: notes.filter((note: Note) => note.noteId !== noteId) })
|
||||
// }
|
||||
|
||||
toggleUserName(name?: string) {
|
||||
this.screen.cursor.showTag(name)
|
||||
}
|
||||
|
|
@ -1,4 +1,4 @@
|
|||
import ListWalker from '../../_common/ListWalker';
|
||||
import ListWalker from '../../common/ListWalker';
|
||||
|
||||
|
||||
class SkipIntervalCls {
|
||||
|
|
@ -1,9 +1,11 @@
|
|||
import logger from 'App/logger';
|
||||
|
||||
import type Screen from '../../Screen/Screen';
|
||||
import type MessageManager from '../../MessageManager';
|
||||
|
||||
import type { Message, SetNodeScroll, CreateElementNode } from '../../messages';
|
||||
|
||||
import ListWalker from '../../../_common/ListWalker';
|
||||
import ListWalker from '../../../common/ListWalker';
|
||||
import StylesManager, { rewriteNodeStyleSheet } from './StylesManager';
|
||||
import FocusManager from './FocusManager';
|
||||
import {
|
||||
|
|
@ -51,12 +53,13 @@ export default class DOMManager extends ListWalker<Message> {
|
|||
|
||||
|
||||
constructor(
|
||||
private readonly screen: MessageManager,
|
||||
private readonly screen: Screen,
|
||||
private readonly isMobile: boolean,
|
||||
public readonly time: number
|
||||
public readonly time: number,
|
||||
mm: MessageManager,
|
||||
) {
|
||||
super()
|
||||
this.stylesManager = new StylesManager(screen)
|
||||
this.stylesManager = new StylesManager(screen, mm)
|
||||
}
|
||||
|
||||
append(m: Message): void {
|
||||
|
|
@ -1,7 +1,7 @@
|
|||
import logger from 'App/logger';
|
||||
import type { SetNodeFocus } from '../../messages';
|
||||
import type { VElement } from './VirtualDOM';
|
||||
import ListWalker from '../../../_common/ListWalker';
|
||||
import ListWalker from '../../../common/ListWalker';
|
||||
|
||||
|
||||
const FOCUS_CLASS = "-openreplay-focus"
|
||||
|
|
@ -1,11 +1,9 @@
|
|||
import type MessageManager from '../../MessageManager';
|
||||
import type Screen from '../../Screen/Screen';
|
||||
import type MessageManager from '../../MessageManager'
|
||||
import type { CssInsertRule, CssDeleteRule } from '../../messages';
|
||||
|
||||
type CSSRuleMessage = CssInsertRule | CssDeleteRule;
|
||||
|
||||
import ListWalker from '../../../_common/ListWalker';
|
||||
|
||||
|
||||
const HOVER_CN = "-openreplay-hover";
|
||||
const HOVER_SELECTOR = `.${HOVER_CN}`;
|
||||
|
||||
|
|
@ -21,17 +19,14 @@ export function rewriteNodeStyleSheet(doc: Document, node: HTMLLinkElement | HTM
|
|||
}
|
||||
}
|
||||
|
||||
export default class StylesManager extends ListWalker<CSSRuleMessage> {
|
||||
export default class StylesManager {
|
||||
private linkLoadingCount: number = 0;
|
||||
private linkLoadPromises: Array<Promise<void>> = [];
|
||||
private skipCSSLinks: Array<string> = []; // should be common for all pages
|
||||
|
||||
constructor(private readonly screen: MessageManager) {
|
||||
super();
|
||||
}
|
||||
constructor(private readonly screen: Screen, private readonly mm: MessageManager) {}
|
||||
|
||||
reset():void {
|
||||
super.reset();
|
||||
this.linkLoadingCount = 0;
|
||||
this.linkLoadPromises = [];
|
||||
|
||||
|
|
@ -43,7 +38,7 @@ export default class StylesManager extends ListWalker<CSSRuleMessage> {
|
|||
const promise = new Promise<void>((resolve) => {
|
||||
if (this.skipCSSLinks.includes(value)) resolve();
|
||||
this.linkLoadingCount++;
|
||||
this.screen.setCSSLoading(true);
|
||||
this.mm.setCSSLoading(true);
|
||||
const addSkipAndResolve = () => {
|
||||
this.skipCSSLinks.push(value); // watch out
|
||||
resolve()
|
||||
|
|
@ -62,44 +57,13 @@ export default class StylesManager extends ListWalker<CSSRuleMessage> {
|
|||
clearTimeout(timeoutId);
|
||||
this.linkLoadingCount--;
|
||||
if (this.linkLoadingCount === 0) {
|
||||
this.screen.setCSSLoading(false);
|
||||
this.mm.setCSSLoading(false);
|
||||
}
|
||||
});
|
||||
this.linkLoadPromises.push(promise);
|
||||
}
|
||||
|
||||
private manageRule = (msg: CSSRuleMessage):void => {
|
||||
// if (msg.tp === "css_insert_rule") {
|
||||
// let styleSheet = this.#screen.document.styleSheets[ msg.stylesheetID ];
|
||||
// if (!styleSheet) {
|
||||
// logger.log("No stylesheet with corresponding ID found: ", msg)
|
||||
// styleSheet = this.#screen.document.styleSheets[0];
|
||||
// if (!styleSheet) {
|
||||
// return;
|
||||
// }
|
||||
// }
|
||||
// try {
|
||||
// styleSheet.insertRule(msg.rule, msg.index);
|
||||
// } catch (e) {
|
||||
// logger.log(e, msg)
|
||||
// //const index = Math.min(msg.index, styleSheet.cssRules.length);
|
||||
// styleSheet.insertRule(msg.rule, styleSheet.cssRules.length);
|
||||
// //styleSheet.ownerNode.innerHTML += msg.rule;
|
||||
// }
|
||||
// }
|
||||
// if (msg.tp === "css_delete_rule") {
|
||||
// // console.warn('Warning: STYLESHEET_DELETE_RULE msg')
|
||||
// const styleSheet = this.#screen.document.styleSheets[msg.stylesheetID];
|
||||
// if (!styleSheet) {
|
||||
// logger.log("No stylesheet with corresponding ID found: ", msg)
|
||||
// return;
|
||||
// }
|
||||
// styleSheet.deleteRule(msg.index);
|
||||
// }
|
||||
}
|
||||
|
||||
moveReady(t: number): Promise<void> {
|
||||
moveReady(t: number): Promise<void[]> {
|
||||
return Promise.all(this.linkLoadPromises)
|
||||
.then(() => this.moveApply(t, this.manageRule));
|
||||
}
|
||||
}
|
||||
|
|
@ -2,7 +2,7 @@ import type Screen from '../Screen/Screen'
|
|||
import type { Point } from '../Screen/types'
|
||||
import type { MouseMove } from '../messages'
|
||||
|
||||
import ListWalker from '../../_common/ListWalker'
|
||||
import ListWalker from '../../common/ListWalker'
|
||||
|
||||
const HOVER_CLASS = "-openreplay-hover";
|
||||
const HOVER_CLASS_DEPR = "-asayer-hover";
|
||||
|
|
@ -1,28 +1,23 @@
|
|||
import type Screen from '../Screen/Screen';
|
||||
import type { Message } from '../messages';
|
||||
import type MessageManager from '../MessageManager';
|
||||
|
||||
import ListWalker from '../../_common/ListWalker';
|
||||
|
||||
import ListWalker from '../../common/ListWalker';
|
||||
import DOMManager from './DOM/DOMManager';
|
||||
|
||||
|
||||
export default class PagesManager extends ListWalker<DOMManager> {
|
||||
private currentPage: DOMManager | null = null
|
||||
|
||||
private isMobile: boolean;
|
||||
private screen: Screen;
|
||||
|
||||
constructor(screen: Screen, isMobile: boolean) {
|
||||
super()
|
||||
this.screen = screen
|
||||
this.isMobile = isMobile
|
||||
}
|
||||
constructor(private screen: Screen, private isMobile: boolean, private mm: MessageManager) { super() }
|
||||
|
||||
/*
|
||||
Assumed that messages added in a correct time sequence.
|
||||
*/
|
||||
appendMessage(m: Message): void {
|
||||
if (m.tp === "create_document") {
|
||||
super.append(new DOMManager(this.screen, this.isMobile, m.time))
|
||||
super.append(new DOMManager(this.screen, this.isMobile, m.time, this.mm))
|
||||
}
|
||||
if (this.last === null) {
|
||||
// Log wrong
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
import type { PerformanceTrack, SetPageVisibility } from '../messages';
|
||||
|
||||
import ListWalker from '../../_common/ListWalker';
|
||||
import ListWalker from '../../common/ListWalker';
|
||||
|
||||
export type PerformanceChartPoint = {
|
||||
time: number,
|
||||
Loading…
Add table
Reference in a new issue