Skip to content

Commit

Permalink
#4979 - Support for Strict mode
Browse files Browse the repository at this point in the history
  • Loading branch information
Mikhail Vialov committed Jul 5, 2024
1 parent 3b35e92 commit 88bac4d
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 27 deletions.
6 changes: 3 additions & 3 deletions example/src/App.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import 'ketcher-react/dist/index.css';

import { useState } from 'react';
import { useState, StrictMode } from 'react';
import { ButtonsConfig, Editor, InfoModal } from 'ketcher-react';
import {
Ketcher,
Expand Down Expand Up @@ -71,7 +71,7 @@ const App = () => {
<PolymerEditor togglerComponent={togglerComponent} />
</>
) : (
<>
<StrictMode>
<Editor
errorHandler={(message: string) => {
setHasError(true);
Expand Down Expand Up @@ -105,7 +105,7 @@ const App = () => {
}}
/>
)}
</>
</StrictMode>
);
};

Expand Down
53 changes: 29 additions & 24 deletions packages/ketcher-react/src/Editor.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ import {
ketcherInitEventName,
KETCHER_ROOT_NODE_CLASS_NAME,
} from './constants';
import { createRoot } from 'react-dom/client';
import { createRoot, Root } from 'react-dom/client';

const mediaSizes = {
smallWidth: 1040,
Expand All @@ -43,38 +43,43 @@ interface EditorProps extends Omit<Config, 'element' | 'appRoot'> {
onInit?: (ketcher: Ketcher) => void;
}

// This is the biggest crutch in the wild west
function Editor(props: EditorProps) {
const initPromiseRef = useRef<ReturnType<typeof init> | null>(null);
const appRootRef = useRef<Root | null>(null);

const rootElRef = useRef<HTMLDivElement>(null);
const { onInit } = props;

const { height, width } = useResizeObserver<HTMLDivElement>({
ref: rootElRef,
});

useEffect(() => {
const appRoot = createRoot(rootElRef.current as HTMLDivElement);
init({
const initKetcher = () => {
appRootRef.current = createRoot(rootElRef.current as HTMLDivElement);

initPromiseRef.current = init({
...props,
element: rootElRef.current,
appRoot,
}).then(
({
ketcher,
ketcherId,
}: {
ketcher: Ketcher | undefined;
ketcherId: string;
}) => {
if (typeof onInit === 'function' && ketcher) {
onInit(ketcher);
const ketcherInitEvent = new Event(ketcherInitEventName(ketcherId));
window.dispatchEvent(ketcherInitEvent);
}
},
);
appRoot: appRootRef.current,
});
initPromiseRef.current?.then(({ ketcher, ketcherId }) => {
if (typeof props.onInit === 'function' && ketcher) {
props.onInit(ketcher);
const ketcherInitEvent = new Event(ketcherInitEventName(ketcherId));
window.dispatchEvent(ketcherInitEvent);
}
});
};
useEffect(() => {
if (initPromiseRef.current === null) {
initKetcher();
} else {
initPromiseRef.current?.finally(() => initKetcher());
}

return () => {
// setTimeout is used to disable the warn msg from react "Attempted to synchronously unmount a root while React was already rendering"
setTimeout(() => {
appRoot.unmount();
initPromiseRef.current?.then(() => {
appRootRef.current?.unmount();
});
};
// TODO: provide the list of dependencies after implementing unsubscribe function
Expand Down

1 comment on commit 88bac4d

@hellhorse123
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

please, approve this commit. This helps everyone

Please sign in to comment.