Skip to content

Commit

Permalink
Fix performance issue
Browse files Browse the repository at this point in the history
  • Loading branch information
spaaaacccee committed May 22, 2024
1 parent ddb9854 commit 721f103
Show file tree
Hide file tree
Showing 12 changed files with 115 additions and 62 deletions.
19 changes: 19 additions & 0 deletions client/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion client/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
"eventemitter3": "^5.0.1",
"file-select-dialog": "^1.5.4",
"graphology": "^0.25.4",
"hotscript": "^1.0.13",
"internal-renderers": "file:../internal-renderers",
"jimp": "^0.22.10",
"js-yaml": "^4.1.0",
Expand All @@ -35,6 +36,7 @@
"md5": "^2.3.0",
"memoizee": "^0.4.15",
"mobile-device-detect": "^0.4.3",
"moderndash": "^3.12.0",
"monaco-editor": "^0.43.0",
"nanoid": "^5.0.1",
"nearest-pantone": "^1.0.1",
Expand Down Expand Up @@ -90,7 +92,6 @@
]
},
"devDependencies": {
"babel-plugin-react-compiler": "^0.0.0-experimental-592953e-20240517",
"@testing-library/jest-dom": "^6.1.3",
"@testing-library/react": "^14.0.0",
"@testing-library/user-event": "^14.5.1",
Expand All @@ -108,6 +109,7 @@
"@typescript-eslint/eslint-plugin": "^6.7.5",
"@typescript-eslint/parser": "^6.7.5",
"@vitejs/plugin-react": "^4.1.0",
"babel-plugin-react-compiler": "^0.0.0-experimental-592953e-20240517",
"electron": "^26.2.4",
"electron-packager": "^17.1.2",
"eslint": "^8.51.0",
Expand Down
6 changes: 1 addition & 5 deletions client/src/components/layer-editor/LayerEditor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -100,12 +100,8 @@ function useDraft<T>(
] as const;
}

function Component(
{ value, onValueChange: onChange }: LayerEditorProps,
_ref: ForwardedRef<HTMLElement>
) {
function Component({ value, onValueChange: onChange }: LayerEditorProps) {
const paper = usePaper();
const acrylic = useAcrylic();
const [draft, setDraft] = useDraft(value, onChange, 300, [
"name",
"source.type",
Expand Down
37 changes: 16 additions & 21 deletions client/src/components/title-bar/ExportWorkspaceModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,19 @@ import { Button } from "components/generic/Button";
import Modal, { ModalAppBar } from "components/generic/Modal";
import { useSnackbar } from "components/generic/Snackbar";
import download from "downloadjs";
import { useEffectWhen } from "hooks/useEffectWhen";
import { useDebouncedState2 } from "hooks/useDebouncedState";
import { useWorkspace } from "hooks/useWorkspace";
import { ceil, delay, entries, kebabCase, omit, reduce } from "lodash";
import { ceil, entries, kebabCase, reduce } from "lodash";
import { nanoid as id } from "nanoid";
import { producify } from "produce";
import { map } from "promise-tools";
import { ComponentProps, useMemo } from "react";
import { useMap } from "react-use";
import { WorkspaceMeta, useUIState } from "slices/UIState";
import { useLoadingState } from "slices/loading";
import { textFieldProps, usePaper } from "theme";
import { Jimp } from "utils/Jimp";
import { set } from "utils/set";
import { Gallery } from "./Gallery";
import { nanoid as id } from "nanoid";

const replacements = {
"*": "star",
Expand Down Expand Up @@ -58,20 +59,14 @@ async function resizeImage(s: string) {

export function A() {
const paper = usePaper();
const [{ workspaceMeta }, setUIState] = useUIState();
const [fields, { set }] = useMap<WorkspaceMeta>(
omit(workspaceMeta, "screenshots", "size")
);
useEffectWhen(
() => {
const timeout = delay(() => {
setUIState((prev) => ({ ...prev, workspaceMeta: fields }));
}, 300);
return () => clearTimeout(timeout);
},
[fields, setUIState],
[fields]
const [_uiState, _setUIState] = useUIState();
const [{ workspaceMeta: fields }, setUIState] = useDebouncedState2(
_uiState,
_setUIState
);
function set2(k: keyof WorkspaceMeta, v: any) {
setUIState(producify((prev) => set(prev, `workspaceMeta.${k}`, v)));
}
const { save, estimateWorkspaceSize } = useWorkspace();
const usingLoadingState = useLoadingState("general");
const notify = useSnackbar();
Expand All @@ -90,13 +85,13 @@ export function A() {
return (
<>
<Box>
<Gallery onChange={(v) => set("screenshots", v)} />
<Gallery onChange={(v) => set2("screenshots", v)} />
</Box>
<Stack p={2} gap={2}>
<TextField
{...textFieldProps}
defaultValue={fields.name}
onChange={(e) => set("name", e.target.value)}
onChange={(e) => set2("name", e.target.value)}
label="Name"
fullWidth
/>
Expand All @@ -105,7 +100,7 @@ export function A() {
minRows={3}
defaultValue={fields.description}
size="small"
onChange={(e) => set("description", e.target.value)}
onChange={(e) => set2("description", e.target.value)}
label="Description"
fullWidth
multiline
Expand All @@ -114,7 +109,7 @@ export function A() {
{...textFieldProps}
defaultValue={fields.author}
size="small"
onChange={(e) => set("author", e.target.value)}
onChange={(e) => set2("author", e.target.value)}
label="Author"
fullWidth
multiline
Expand Down
31 changes: 27 additions & 4 deletions client/src/hooks/useDebouncedState.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import { delay, noop, now } from "lodash";
import { noop, now } from "lodash";
import { useRef, useState } from "react";
import { useEffectWhen } from "./useEffectWhen";

export function useDebouncedState<T>(
defaultValue: T,
Expand All @@ -11,7 +10,7 @@ export function useDebouncedState<T>(
const head = useRef(now());
return [
state,
(a: any) => {
(a: T) => {
const commit = now();
requestIdleCallback(
() => {
Expand All @@ -20,9 +19,33 @@ export function useDebouncedState<T>(
head.current = commit;
}
},
{ timeout: 300 }
{ timeout: wait }
);
setState(a);
},
] as const;
}
export function useDebouncedState2<T>(
defaultValue: T,
onChange: (v: (prev: T) => T) => void = noop,
wait: number = 300
) {
const [state, setState] = useState(defaultValue);
const head = useRef(now());
return [
state,
(a: (prev: T) => T) => {
const commit = now();
requestIdleCallback(
() => {
if (commit > head.current) {
onChange?.(a);
head.current = commit;
}
},
{ timeout: wait }
);
setState(a(state));
},
] as const;
}
23 changes: 9 additions & 14 deletions client/src/layers/trace/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,6 @@ import { useTraceParser } from "components/renderer/parser-v140/parseTrace";
import { parseProperty as parsePropertyLegacy } from "components/renderer/parser/parseProperty";
import { ParseTraceWorkerReturnType } from "components/renderer/parser/parseTraceSlave.worker";
import { DebugLayerData } from "hooks/useBreakpoints";
import { useEffectWhen } from "hooks/useEffectWhen";
import { useTraceContent } from "hooks/useTraceContent";
import { dump } from "js-yaml";
import { LayerController, inferLayerName } from "layers";
Expand All @@ -60,8 +59,8 @@ import { nanoid as id } from "nanoid";
import { produce, withProduce } from "produce";
import { TraceEvent, Trace as TraceLegacy } from "protocol";
import { Trace } from "protocol/Trace-v140";
import { useDeferredValue, useEffect, useMemo } from "react";
import { useThrottle } from "react-use";
import { useEffect, useMemo } from "react";
import { useAsync, useThrottle } from "react-use";
import { UploadedTrace } from "slices/UIState";
import { Layer, useLayer } from "slices/layers";
import { AccentColor, accentColors, getShade } from "theme";
Expand Down Expand Up @@ -264,17 +263,13 @@ export const controller = {
return set(l, "source.playbackTo", trace?.content?.events?.length ?? 0);
});
}, [trace?.key, trace?.lastModified]);
useEffectWhen(
async () => {
const parsedTrace = await parseTrace();
produce((l) => {
set(l, "source.parsedTrace", parsedTrace);
set(l, "viewKey", id());
});
},
[parseTrace],
[trace?.key, palette.mode]
);
useAsync(async () => {
const parsedTrace = await parseTrace();
produce((l) => {
set(l, "source.parsedTrace", parsedTrace);
set(l, "viewKey", id());
});
}, [trace?.key, palette.mode]);
return (
<>
<PlaybackService value={value} />
Expand Down
4 changes: 2 additions & 2 deletions client/src/produce.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ export function transaction<T, U>(obj: T, f: (obj: T) => U) {
export const producify =
<T>(f: (obj: T) => void) =>
(obj: T) => {
const b = structuredClone(obj);
const b = clone(obj);
f(b);
return b;
};
Expand All @@ -30,6 +30,6 @@ export function withProduce<T>(
return (props: EditorSetterProps<T>) =>
createElement(component, {
...props,
produce: (f) => props?.onChange?.((prev) => produce(prev, f)),
produce: (f) => props?.onChange?.(producify(f)),
});
}
26 changes: 11 additions & 15 deletions client/src/services/SyncService.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -57,19 +57,15 @@ export function SyncService() {
};
}, [c1, c2, setSettings, setLayers, participants]);
// Broadcast
useEffectWhen(
() => {
if (peers.length) {
sysend.broadcast<SyncedData>("settings", {
initiator: instance,
state: { settings },
commit: c1,
});
}
},
[settings, c1, peers.length],
[c1, peers.length]
);
useEffect(() => {
if (peers.length) {
sysend.broadcast<SyncedData>("settings", {
initiator: instance,
state: { settings },
commit: c1,
});
}
}, [c1, peers.length]);
const previous = usePrevious(c2);
const broadCastLayers = useMemo(
() =>
Expand All @@ -91,7 +87,7 @@ export function SyncService() {
});
}
},
[layers, c2, participants.length],
[c2, participants.length],
[previous, c2]
);
// Primary broadcasts to new
Expand All @@ -105,7 +101,7 @@ export function SyncService() {
});
}
},
[layers, c2, participants.length, isOnly, isPrimary],
[c2, participants.length, isOnly, isPrimary],
[participants.length]
);

Expand Down
2 changes: 2 additions & 0 deletions client/src/slices/UIState.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ export type UploadedTrace = FeatureDescriptor & {
source?: string;
/**
* Uniquely identifies a trace.
* The difference between this and `id` is that `key` changes whenever
* the contents of the trace change, but `id` stays the same.
*/
key?: string;
};
Expand Down
1 change: 1 addition & 0 deletions client/src/slices/createSlice.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,7 @@ export function createSlice<T, U = T>(
const [commit, reduceCommit] = useReducer(() => nanoid(), nanoid());
const reduceSlice = useCallback(
(n: (prev: T) => U, c?: boolean) => {
// console.log(n);
const next = reduce(get(), n(get()));
effect?.({ prev: get(), next });
if (!c) reduceCommit?.();
Expand Down
21 changes: 21 additions & 0 deletions client/src/utils/set.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { set as moderndashSet } from "moderndash";
import type { Call, Objects, Strings, Booleans } from "hotscript";
import type { PlainObject } from "moderndash";

export function set<
TObj extends PlainObject,
TPath extends Call<Objects.AllPaths, TObj>
>(obj: TObj, path: TPath, value: Call<Objects.Get<TPath>, TObj>): TObj {
return moderndashSet(obj, path, value);
}
declare global {
interface String {
// typesafe 's-t-r-i-n-g'.split('-'): ['s', 't', 'r', 'i', 'n', 'g']
split<S extends string, D extends string>(
this: S,
separator: D
): Call<Booleans.Equals<S, string>> extends true
? string[]
: Call<Strings.Split<D>, S>;
}
}
3 changes: 3 additions & 0 deletions protocol/FeatureQuery.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@ import { Method, Namespace, Response } from "./Message";
import { Trace } from "./Trace";

export interface FeatureDescriptor {
/**
* Uniquely identifies this entity.
*/
id: string;
name?: string;
description?: string;
Expand Down

0 comments on commit 721f103

Please sign in to comment.