docusaurus-live-brython 3.0.0-beta.8 → 3.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.devcontainer/devcontainer.json +38 -0
- package/.prettierignore +17 -0
- package/.prettierrc +9 -8
- package/CHANGELOG.md +5 -0
- package/README.md +7 -4
- package/lib/assets/py_back_trace.py +2 -1
- package/lib/index.d.ts +1 -7
- package/lib/index.d.ts.map +1 -0
- package/lib/index.js +94 -16
- package/lib/options.d.ts +1 -0
- package/lib/options.d.ts.map +1 -0
- package/lib/options.js +2 -2
- package/lib/theme/CodeBlock/index.d.ts +3 -3
- package/lib/theme/CodeBlock/index.d.ts.map +1 -0
- package/lib/theme/CodeBlock/index.jsx +24 -14
- package/lib/theme/CodeEditor/Actions/DownloadCode.d.ts +1 -0
- package/lib/theme/CodeEditor/Actions/DownloadCode.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Actions/DownloadCode.jsx +8 -8
- package/lib/theme/CodeEditor/Actions/Reset.d.ts +1 -0
- package/lib/theme/CodeEditor/Actions/Reset.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Actions/Reset.jsx +5 -5
- package/lib/theme/CodeEditor/Actions/RunCode.d.ts +2 -1
- package/lib/theme/CodeEditor/Actions/RunCode.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Actions/RunCode.jsx +4 -4
- package/lib/theme/CodeEditor/Actions/ShowRaw.d.ts +1 -0
- package/lib/theme/CodeEditor/Actions/ShowRaw.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Actions/ShowRaw.jsx +13 -7
- package/lib/theme/CodeEditor/Actions/ShowSyncStatus.d.ts +1 -0
- package/lib/theme/CodeEditor/Actions/ShowSyncStatus.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Actions/ShowSyncStatus.jsx +21 -16
- package/lib/theme/CodeEditor/Actions/styles.module.css +2 -3
- package/lib/theme/CodeEditor/BrythonCommunicator.d.ts +2 -1
- package/lib/theme/CodeEditor/BrythonCommunicator.d.ts.map +1 -0
- package/lib/theme/CodeEditor/BrythonCommunicator.jsx +13 -9
- package/lib/theme/CodeEditor/Button/index.d.ts +3 -2
- package/lib/theme/CodeEditor/Button/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Button/index.jsx +1 -1
- package/lib/theme/CodeEditor/Button/styles.module.css +1 -1
- package/lib/theme/CodeEditor/CodeHistory/index.d.ts +1 -0
- package/lib/theme/CodeEditor/CodeHistory/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/CodeHistory/index.jsx +26 -15
- package/lib/theme/CodeEditor/CodeHistory/styles.module.css +31 -31
- package/lib/theme/CodeEditor/ContextEditor/index.d.ts +22 -0
- package/lib/theme/CodeEditor/ContextEditor/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/ContextEditor/index.jsx +36 -0
- package/lib/theme/CodeEditor/Editor/EditorAce.d.ts +2 -1
- package/lib/theme/CodeEditor/Editor/EditorAce.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/EditorAce.jsx +17 -14
- package/lib/theme/CodeEditor/Editor/Header/index.d.ts +2 -1
- package/lib/theme/CodeEditor/Editor/Header/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/Header/index.jsx +12 -12
- package/lib/theme/CodeEditor/Editor/Header/styles.module.css +7 -7
- package/lib/theme/CodeEditor/Editor/HiddenCode/index.d.ts +8 -0
- package/lib/theme/CodeEditor/Editor/HiddenCode/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/HiddenCode/index.jsx +27 -0
- package/lib/theme/CodeEditor/Editor/HiddenCode/styles.module.css +52 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Canvas.d.ts +1 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Canvas.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Canvas.jsx +8 -9
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Turtle.d.ts +1 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Turtle.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/Turtle.jsx +11 -11
- package/lib/theme/CodeEditor/Editor/Result/Graphics/index.d.ts +4 -3
- package/lib/theme/CodeEditor/Editor/Result/Graphics/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/Result/Graphics/index.jsx +12 -10
- package/lib/theme/CodeEditor/Editor/Result/Graphics/styles.module.css +2 -2
- package/lib/theme/CodeEditor/Editor/Result/index.d.ts +2 -3
- package/lib/theme/CodeEditor/Editor/Result/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/Result/index.jsx +6 -9
- package/lib/theme/CodeEditor/Editor/Result/styles.module.css +15 -10
- package/lib/theme/CodeEditor/Editor/index.d.ts +6 -3
- package/lib/theme/CodeEditor/Editor/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/index.jsx +34 -28
- package/lib/theme/CodeEditor/Editor/styles.module.css +15 -7
- package/lib/theme/CodeEditor/Editor/utils/checkForButtonClick.d.ts +1 -0
- package/lib/theme/CodeEditor/Editor/utils/checkForButtonClick.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/utils/saveSvg.d.ts +1 -0
- package/lib/theme/CodeEditor/Editor/utils/saveSvg.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/utils/saveSvg.js +19 -8
- package/lib/theme/CodeEditor/Editor/utils/svgWithoutAnimations.d.ts +1 -0
- package/lib/theme/CodeEditor/Editor/utils/svgWithoutAnimations.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Editor/utils/svgWithoutAnimations.js +43 -49
- package/lib/theme/CodeEditor/Icon/icons.d.ts +4 -1
- package/lib/theme/CodeEditor/Icon/icons.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Icon/icons.js +3 -1
- package/lib/theme/CodeEditor/Icon/index.d.ts +4 -2
- package/lib/theme/CodeEditor/Icon/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/Icon/index.jsx +10 -3
- package/lib/theme/CodeEditor/Icon/styles.module.css +1 -1
- package/lib/theme/CodeEditor/WithScript/ScriptContext.d.ts +8 -0
- package/lib/theme/CodeEditor/WithScript/ScriptContext.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/ScriptContext.jsx +27 -0
- package/lib/theme/CodeEditor/WithScript/Storage.d.ts +2 -1
- package/lib/theme/CodeEditor/WithScript/Storage.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/Types.d.ts +12 -4
- package/lib/theme/CodeEditor/WithScript/Types.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/bryRunner.d.ts +3 -0
- package/lib/theme/CodeEditor/WithScript/bryRunner.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/bryRunner.js +29 -0
- package/lib/theme/CodeEditor/WithScript/createStore.d.ts +4 -0
- package/lib/theme/CodeEditor/WithScript/createStore.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/{Store.jsx → createStore.js} +62 -74
- package/lib/theme/CodeEditor/WithScript/helpers.d.ts +1 -4
- package/lib/theme/CodeEditor/WithScript/helpers.d.ts.map +1 -0
- package/lib/theme/CodeEditor/WithScript/helpers.js +4 -14
- package/lib/theme/CodeEditor/constants.d.ts +1 -0
- package/lib/theme/CodeEditor/constants.d.ts.map +1 -0
- package/lib/theme/CodeEditor/hooks/index.d.ts +3 -0
- package/lib/theme/CodeEditor/hooks/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/hooks/index.js +2 -0
- package/lib/theme/CodeEditor/hooks/useScript.d.ts +3 -0
- package/lib/theme/CodeEditor/hooks/useScript.d.ts.map +1 -0
- package/lib/theme/CodeEditor/hooks/useScript.js +4 -0
- package/lib/theme/CodeEditor/hooks/useStore.d.ts +3 -0
- package/lib/theme/CodeEditor/hooks/useStore.d.ts.map +1 -0
- package/lib/theme/CodeEditor/hooks/useStore.js +10 -0
- package/lib/theme/CodeEditor/index.d.ts +24 -5
- package/lib/theme/CodeEditor/index.d.ts.map +1 -0
- package/lib/theme/CodeEditor/index.jsx +17 -16
- package/lib/theme/CodeEditor/styles.module.css +28 -30
- package/og-image.md +23 -0
- package/package.json +39 -20
- package/src/assets/py_back_trace.py +2 -1
- package/src/index.ts +96 -25
- package/src/options.ts +12 -12
- package/src/theme/CodeBlock/index.tsx +44 -68
- package/src/theme/CodeEditor/Actions/DownloadCode.tsx +23 -22
- package/src/theme/CodeEditor/Actions/Reset.tsx +14 -12
- package/src/theme/CodeEditor/Actions/RunCode.tsx +14 -11
- package/src/theme/CodeEditor/Actions/ShowRaw.tsx +17 -11
- package/src/theme/CodeEditor/Actions/ShowSyncStatus.tsx +32 -27
- package/src/theme/CodeEditor/Actions/styles.module.css +2 -3
- package/src/theme/CodeEditor/BrythonCommunicator.tsx +16 -19
- package/src/theme/CodeEditor/Button/index.tsx +17 -13
- package/src/theme/CodeEditor/Button/styles.module.css +1 -1
- package/src/theme/CodeEditor/CodeHistory/index.tsx +32 -20
- package/src/theme/CodeEditor/CodeHistory/styles.module.css +31 -31
- package/src/theme/CodeEditor/ContextEditor/index.tsx +74 -0
- package/src/theme/CodeEditor/Editor/EditorAce.tsx +20 -16
- package/src/theme/CodeEditor/Editor/Header/index.tsx +13 -19
- package/src/theme/CodeEditor/Editor/Header/styles.module.css +7 -7
- package/src/theme/CodeEditor/Editor/HiddenCode/index.tsx +49 -0
- package/src/theme/CodeEditor/Editor/HiddenCode/styles.module.css +52 -0
- package/src/theme/CodeEditor/Editor/Result/Graphics/Canvas.tsx +25 -22
- package/src/theme/CodeEditor/Editor/Result/Graphics/Turtle.tsx +23 -19
- package/src/theme/CodeEditor/Editor/Result/Graphics/index.tsx +16 -16
- package/src/theme/CodeEditor/Editor/Result/Graphics/styles.module.css +2 -2
- package/src/theme/CodeEditor/Editor/Result/index.tsx +7 -13
- package/src/theme/CodeEditor/Editor/Result/styles.module.css +15 -10
- package/src/theme/CodeEditor/Editor/index.tsx +67 -65
- package/src/theme/CodeEditor/Editor/styles.module.css +15 -7
- package/src/theme/CodeEditor/Editor/utils/checkForButtonClick.ts +5 -5
- package/src/theme/CodeEditor/Editor/utils/saveSvg.ts +63 -53
- package/src/theme/CodeEditor/Editor/utils/svgWithoutAnimations.ts +182 -201
- package/src/theme/CodeEditor/Icon/icons.ts +27 -13
- package/src/theme/CodeEditor/Icon/index.tsx +31 -11
- package/src/theme/CodeEditor/Icon/styles.module.css +1 -1
- package/src/theme/CodeEditor/WithScript/ScriptContext.tsx +36 -0
- package/src/theme/CodeEditor/WithScript/Storage.ts +3 -3
- package/src/theme/CodeEditor/WithScript/Types.ts +17 -11
- package/src/theme/CodeEditor/WithScript/bryRunner.ts +39 -0
- package/src/theme/CodeEditor/WithScript/createStore.ts +276 -0
- package/src/theme/CodeEditor/WithScript/helpers.ts +16 -26
- package/src/theme/CodeEditor/constants.ts +9 -11
- package/src/theme/CodeEditor/hooks/index.ts +2 -0
- package/src/theme/CodeEditor/hooks/useScript.ts +9 -0
- package/src/theme/CodeEditor/hooks/useStore.ts +15 -0
- package/src/theme/CodeEditor/index.tsx +45 -31
- package/src/theme/CodeEditor/styles.module.css +28 -30
- package/src/typings.d.ts +11 -0
- package/lib/theme/CodeEditor/WithScript/Store.d.ts +0 -15
- package/lib/types.d.ts +0 -28
- package/lib/types.js +0 -1
- package/src/theme/CodeEditor/WithScript/Store.tsx +0 -294
- package/src/types.ts +0 -29
|
@@ -1,16 +1,31 @@
|
|
|
1
1
|
import * as React from 'react';
|
|
2
2
|
import styles from './styles.module.css';
|
|
3
|
-
import Editor from '
|
|
4
|
-
import BrythonCommunicator from '
|
|
3
|
+
import Editor from '@theme/CodeEditor/Editor';
|
|
4
|
+
import BrythonCommunicator from '@theme/CodeEditor/BrythonCommunicator';
|
|
5
5
|
import clsx from 'clsx';
|
|
6
|
-
import {
|
|
6
|
+
import { useStore, useScript } from '@theme/CodeEditor/hooks';
|
|
7
7
|
import BrowserOnly from '@docusaurus/BrowserOnly';
|
|
8
|
-
import CodeHistory from '
|
|
8
|
+
import CodeHistory from '@theme/CodeEditor/CodeHistory';
|
|
9
|
+
import CodeBlock from '@theme/CodeBlock';
|
|
9
10
|
|
|
10
|
-
interface
|
|
11
|
+
export interface MetaProps {
|
|
12
|
+
reference?: boolean;
|
|
13
|
+
live_jsx?: boolean;
|
|
14
|
+
live_py?: boolean;
|
|
15
|
+
id?: string;
|
|
16
|
+
slim?: boolean;
|
|
17
|
+
readonly?: boolean;
|
|
18
|
+
noReset?: boolean;
|
|
19
|
+
noDownload?: boolean;
|
|
20
|
+
versioned?: boolean;
|
|
21
|
+
noHistory?: boolean;
|
|
22
|
+
noCompare?: boolean;
|
|
23
|
+
maxLines?: string;
|
|
24
|
+
title?: string;
|
|
25
|
+
}
|
|
26
|
+
export interface Props {
|
|
11
27
|
slim: boolean;
|
|
12
28
|
readonly: boolean;
|
|
13
|
-
children: React.ReactNode;
|
|
14
29
|
noCompare: boolean;
|
|
15
30
|
title: string;
|
|
16
31
|
versioned: boolean;
|
|
@@ -18,40 +33,39 @@ interface Props {
|
|
|
18
33
|
download: boolean;
|
|
19
34
|
showLineNumbers: boolean;
|
|
20
35
|
lang: string;
|
|
21
|
-
|
|
36
|
+
preCode: string;
|
|
37
|
+
postCode: string;
|
|
38
|
+
code: string;
|
|
22
39
|
maxLines?: number;
|
|
23
40
|
noHistory: boolean;
|
|
41
|
+
className?: string;
|
|
42
|
+
onChange?: (code: string) => void;
|
|
24
43
|
}
|
|
25
44
|
|
|
26
|
-
const
|
|
27
|
-
const
|
|
28
|
-
const lang =
|
|
45
|
+
const CodeEditor = (props: Props) => {
|
|
46
|
+
const store = useStore();
|
|
47
|
+
const lang = useScript(store, 'lang');
|
|
29
48
|
return (
|
|
30
|
-
<BrowserOnly
|
|
31
|
-
fallback={<div>Loading...</div>}
|
|
32
|
-
>
|
|
49
|
+
<BrowserOnly fallback={<CodeBlock language={props.lang}>{props.code}</CodeBlock>}>
|
|
33
50
|
{() => {
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
<CodeHistory />
|
|
46
|
-
)}
|
|
47
|
-
</div>
|
|
48
|
-
{lang === 'python' && <BrythonCommunicator />}
|
|
51
|
+
return (
|
|
52
|
+
<div className={clsx(styles.wrapper, 'notranslate', props.className)}>
|
|
53
|
+
<div
|
|
54
|
+
className={clsx(
|
|
55
|
+
styles.playgroundContainer,
|
|
56
|
+
props.slim ? styles.containerSlim : styles.containerBig,
|
|
57
|
+
'live_py'
|
|
58
|
+
)}
|
|
59
|
+
>
|
|
60
|
+
<Editor {...props} />
|
|
61
|
+
{!props.noHistory && <CodeHistory />}
|
|
49
62
|
</div>
|
|
50
|
-
|
|
63
|
+
{lang === 'python' && <BrythonCommunicator />}
|
|
64
|
+
</div>
|
|
65
|
+
);
|
|
51
66
|
}}
|
|
52
67
|
</BrowserOnly>
|
|
53
68
|
);
|
|
54
69
|
};
|
|
55
70
|
|
|
56
|
-
export default
|
|
57
|
-
|
|
71
|
+
export default CodeEditor;
|
|
@@ -1,43 +1,41 @@
|
|
|
1
1
|
.containerBig {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
2
|
+
display: grid;
|
|
3
|
+
flex-grow: 1;
|
|
4
|
+
flex-shrink: 1;
|
|
5
|
+
flex-basis: 250px;
|
|
6
|
+
grid-template-columns: 100%;
|
|
7
|
+
grid-template-rows: min-content 1fr min-content;
|
|
8
|
+
gap: 0px 0px;
|
|
9
|
+
grid-auto-flow: row;
|
|
10
|
+
grid-template-areas: 'controls' 'editor' 'result';
|
|
11
11
|
}
|
|
12
12
|
|
|
13
13
|
.containerSlim {
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
14
|
+
display: grid;
|
|
15
|
+
grid-template-columns: 1fr min-content;
|
|
16
|
+
grid-template-rows: 1fr min-content;
|
|
17
|
+
gap: 0px 0px;
|
|
18
|
+
grid-auto-flow: row;
|
|
19
|
+
grid-template-areas: 'editor controls' 'result result';
|
|
20
20
|
}
|
|
21
21
|
|
|
22
|
-
|
|
23
22
|
.containerSlim .headerButton {
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
23
|
+
z-index: calc(var(--ifm-z-index-fixed) - 2);
|
|
24
|
+
height: 100%;
|
|
25
|
+
border-radius: 0px;
|
|
26
|
+
padding: 2px 6px;
|
|
27
|
+
margin: 0px;
|
|
29
28
|
}
|
|
30
29
|
|
|
31
|
-
|
|
32
30
|
.wrapper:last-child .playgroundContainer {
|
|
33
|
-
|
|
31
|
+
margin-bottom: inherit;
|
|
34
32
|
}
|
|
35
33
|
|
|
36
34
|
.playgroundContainer {
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
}
|
|
35
|
+
margin-bottom: var(--ifm-leading);
|
|
36
|
+
border-radius: var(--ifm-global-radius);
|
|
37
|
+
box-shadow: var(--ifm-global-shadow-lw);
|
|
38
|
+
overflow: hidden;
|
|
39
|
+
flex-grow: 1;
|
|
40
|
+
flex-shrink: 1;
|
|
41
|
+
}
|
package/src/typings.d.ts
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/// <reference types="@docusaurus/module-type-aliases" />
|
|
2
|
+
|
|
3
|
+
declare module '@theme/Details' {
|
|
4
|
+
import { ReactNode } from 'react';
|
|
5
|
+
export interface Props {
|
|
6
|
+
readonly summary: ReactNode;
|
|
7
|
+
readonly children: ReactNode;
|
|
8
|
+
[key: string]: any;
|
|
9
|
+
}
|
|
10
|
+
export default function Details(props: Props): React.ReactNode;
|
|
11
|
+
}
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
import React from "react";
|
|
2
|
-
import { type InitState, type Store } from "./Types";
|
|
3
|
-
export declare const createStore: (props: InitState, libDir: string, syncMaxOnceEvery: number) => Store;
|
|
4
|
-
type Selector<T, R> = (state: T) => R;
|
|
5
|
-
export declare const useStore: <T, R>(store: Store<T>, selector: Selector<T, R>) => R;
|
|
6
|
-
export declare const Context: React.Context<{
|
|
7
|
-
store: Store;
|
|
8
|
-
}>;
|
|
9
|
-
declare const ScriptContext: (props: InitState & {
|
|
10
|
-
children: React.ReactNode;
|
|
11
|
-
}) => React.JSX.Element;
|
|
12
|
-
export declare function useScript(): {
|
|
13
|
-
store: Store;
|
|
14
|
-
};
|
|
15
|
-
export default ScriptContext;
|
package/lib/types.d.ts
DELETED
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
export type ThemeOptions = {
|
|
2
|
-
/**
|
|
3
|
-
* The path to the brython source file.
|
|
4
|
-
* @default 'https://raw.githack.com/brython-dev/brython/master/www/src/brython.js
|
|
5
|
-
*/
|
|
6
|
-
brython_src?: string;
|
|
7
|
-
/**
|
|
8
|
-
* The path to the brython standard library source file.
|
|
9
|
-
* @default 'https://raw.githack.com/brython-dev/brython/master/www/src/brython_stdlib.js'
|
|
10
|
-
*/
|
|
11
|
-
brython_stdlib_src?: string;
|
|
12
|
-
/**
|
|
13
|
-
* The folder path to brython specific libraries.
|
|
14
|
-
* When a python file imports a module, the module is searched in the libDir directory.
|
|
15
|
-
* By default, the libDir is created in the static folder and the needed python files are copied there.
|
|
16
|
-
* This can be changed by setting skipCopyAssetsToLibDir to true and setting libDir to a custom path.
|
|
17
|
-
* Make sure to copy the needed python files to the custom libDir.
|
|
18
|
-
* @default '/bry-libs/'
|
|
19
|
-
*/
|
|
20
|
-
libDir?: string;
|
|
21
|
-
/**
|
|
22
|
-
* Skip copying the brython specific libraries to the libDir.
|
|
23
|
-
* Make sure to copy the needed python files to the custom libDir yourself.
|
|
24
|
-
* @ref [needed python files](https://github.com/lebalz/docusaurus-live-brython/tree/main/src/assets)
|
|
25
|
-
* @default false
|
|
26
|
-
*/
|
|
27
|
-
skipCopyAssetsToLibDir?: boolean;
|
|
28
|
-
};
|
package/lib/types.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1,294 +0,0 @@
|
|
|
1
|
-
import React, { useCallback } from "react";
|
|
2
|
-
import { useSyncExternalStore } from "react";
|
|
3
|
-
import { v4 as uuidv4 } from 'uuid';
|
|
4
|
-
import { checkCanvasOutput, checkGraphicsOutput, checkTurtleOutput, getPreCode, sanitizePyScript } from "docusaurus-live-brython/theme/CodeEditor/WithScript/helpers";
|
|
5
|
-
import { ReactContextError, createStorageSlot } from "@docusaurus/theme-common";
|
|
6
|
-
import { usePluginData } from "@docusaurus/useGlobalData";
|
|
7
|
-
import { DOM_ELEMENT_IDS } from "docusaurus-live-brython/theme/CodeEditor/constants";
|
|
8
|
-
import throttle from 'lodash/throttle';
|
|
9
|
-
import { getStorageScript, syncStorageScript } from "docusaurus-live-brython/theme/CodeEditor/WithScript/Storage";
|
|
10
|
-
import { type InitState, type LogMessage, type Script, Status, type Store, type StoredScript, type Version } from "./Types";
|
|
11
|
-
export const createStore = (props: InitState, libDir: string, syncMaxOnceEvery: number): Store => {
|
|
12
|
-
const canSave = !!props.id;
|
|
13
|
-
const id = props.id || uuidv4();
|
|
14
|
-
const codeId = `code.${props.title || props.lang}.${id}`.replace(/(-|\.)/g, '_');
|
|
15
|
-
const createdAt = new Date();
|
|
16
|
-
const storageKey = `code.${props.title || 'code_block'}.${id}`;
|
|
17
|
-
const storage = createStorageSlot(storageKey);
|
|
18
|
-
storage.listen((e) => {
|
|
19
|
-
if (e.key === storageKey) {
|
|
20
|
-
try {
|
|
21
|
-
if (e.newValue) {
|
|
22
|
-
const script = JSON.parse(e.newValue) as StoredScript;
|
|
23
|
-
if (new Date(script.updatedAt) > state.updatedAt) {
|
|
24
|
-
loadData(storage);
|
|
25
|
-
}
|
|
26
|
-
}
|
|
27
|
-
} catch (err) {
|
|
28
|
-
console.warn(err);
|
|
29
|
-
}
|
|
30
|
-
}
|
|
31
|
-
});
|
|
32
|
-
|
|
33
|
-
const loadData = (store) => {
|
|
34
|
-
setState((s) => ({...s, status: canSave ? Status.SYNCING : s.status}));
|
|
35
|
-
const script = getStorageScript(store);
|
|
36
|
-
const loadedCode = script?.code ? prepareCode(script.code, { codeOnly: true }) : {};
|
|
37
|
-
addVersion.cancel();
|
|
38
|
-
if (!state.isLoaded) {
|
|
39
|
-
setState((s) => ({
|
|
40
|
-
...s,
|
|
41
|
-
isLoaded: true,
|
|
42
|
-
...(script || {}),
|
|
43
|
-
...loadedCode,
|
|
44
|
-
versions: script?.versions || [],
|
|
45
|
-
versionsLoaded: true,
|
|
46
|
-
status: canSave ? Status.SUCCESS : s.status
|
|
47
|
-
}));
|
|
48
|
-
return Status.SUCCESS;
|
|
49
|
-
}
|
|
50
|
-
if (script) {
|
|
51
|
-
setState((s) => ({...s, ...script, ...loadedCode, status: canSave ? Status.SUCCESS : s.status, versionsLoaded: true}));
|
|
52
|
-
return Status.SUCCESS;
|
|
53
|
-
}
|
|
54
|
-
setState((s) => ({...s, status: canSave ? Status.ERROR : s.status}));
|
|
55
|
-
return Status.ERROR;
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
const prepareCode = (raw: string, config: { codeOnly?: boolean, stateNotInitialized?: boolean } = {}) => {
|
|
60
|
-
const { pre, code } = config.codeOnly
|
|
61
|
-
? { pre: getPreCode(state.pristineCode).pre, code: raw }
|
|
62
|
-
: getPreCode(raw);
|
|
63
|
-
const hasEdits = code !== (config.stateNotInitialized ? getPreCode(props.raw).code : state.pristineCode);
|
|
64
|
-
const updatedAt = new Date();
|
|
65
|
-
const hasCanvasOutput = checkCanvasOutput(raw);
|
|
66
|
-
const hasTurtleOutput = checkTurtleOutput(raw);
|
|
67
|
-
const hasGraphicsOutput = checkGraphicsOutput(raw);
|
|
68
|
-
if (props.versioned && !config.stateNotInitialized) {
|
|
69
|
-
addVersion({code: code, createdAt: updatedAt, version: state.versions.length + 1});
|
|
70
|
-
}
|
|
71
|
-
return {
|
|
72
|
-
code: code,
|
|
73
|
-
preCode: pre,
|
|
74
|
-
hasCanvasOutput: hasCanvasOutput,
|
|
75
|
-
hasTurtleOutput: hasTurtleOutput,
|
|
76
|
-
hasGraphicsOutput: hasGraphicsOutput,
|
|
77
|
-
hasEdits: hasEdits,
|
|
78
|
-
updatedAt: updatedAt
|
|
79
|
-
};
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
const setCode = (raw: string, action?: 'insert' | 'remove' | string) => {
|
|
83
|
-
if (state.isPasted && action === 'remove') {
|
|
84
|
-
return;
|
|
85
|
-
}
|
|
86
|
-
const data = prepareCode(raw);
|
|
87
|
-
setState(
|
|
88
|
-
(state) => ({
|
|
89
|
-
...state,
|
|
90
|
-
...data
|
|
91
|
-
})
|
|
92
|
-
);
|
|
93
|
-
if (props.id) {
|
|
94
|
-
const toStore: StoredScript = {code: data.code, createdAt: state.createdAt, updatedAt: data.updatedAt, versions: state.versions};
|
|
95
|
-
if (state.isPasted) {
|
|
96
|
-
addVersion.flush();
|
|
97
|
-
if (toStore.versions.length > 0) {
|
|
98
|
-
toStore.versions[toStore.versions.length - 1].pasted = true;
|
|
99
|
-
}
|
|
100
|
-
set(toStore);
|
|
101
|
-
set.flush();
|
|
102
|
-
state.isPasted = false;
|
|
103
|
-
} else {
|
|
104
|
-
set(toStore);
|
|
105
|
-
}
|
|
106
|
-
}
|
|
107
|
-
};
|
|
108
|
-
|
|
109
|
-
const execScript = () => {
|
|
110
|
-
const toExec = `${state.code}`;
|
|
111
|
-
const lineShift = state.preCode.split(/\n/).length;
|
|
112
|
-
const src = `from brython_runner import run
|
|
113
|
-
run("""${sanitizePyScript(toExec || '')}""", '${codeId}', ${lineShift})
|
|
114
|
-
`;
|
|
115
|
-
if (!(window as any).__BRYTHON__) {
|
|
116
|
-
alert('Brython not loaded');
|
|
117
|
-
return;
|
|
118
|
-
}
|
|
119
|
-
setState((s) => ({...s, isExecuting: true, isGraphicsmodalOpen: state.hasGraphicsOutput}));
|
|
120
|
-
const active = document.getElementById(DOM_ELEMENT_IDS.communicator(state.codeId));
|
|
121
|
-
active.setAttribute('data--start-time', `${Date.now()}`);
|
|
122
|
-
/**
|
|
123
|
-
* ensure that the script is executed after the current event loop.
|
|
124
|
-
* Otherwise, the brython script will not be able to access the graphics output.
|
|
125
|
-
*/
|
|
126
|
-
setTimeout(() => {
|
|
127
|
-
(window as any).__BRYTHON__.runPythonSource(
|
|
128
|
-
src,
|
|
129
|
-
{
|
|
130
|
-
pythonpath: [libDir]
|
|
131
|
-
}
|
|
132
|
-
);
|
|
133
|
-
}, 0);
|
|
134
|
-
};
|
|
135
|
-
const load = async () => {
|
|
136
|
-
return loadData(storage);
|
|
137
|
-
};
|
|
138
|
-
const _set = async (script: StoredScript) => {
|
|
139
|
-
setState((s) => ({...s, status: canSave ? Status.SYNCING : s.status}));
|
|
140
|
-
if (syncStorageScript(script, storage)) {
|
|
141
|
-
setState((s) => ({...s, status: canSave ? Status.SUCCESS : s.status}));
|
|
142
|
-
return Status.SUCCESS;
|
|
143
|
-
}
|
|
144
|
-
setState((s) => ({...s, status: canSave ? Status.ERROR : s.status}));
|
|
145
|
-
return Status.ERROR;
|
|
146
|
-
};
|
|
147
|
-
|
|
148
|
-
const set = throttle(
|
|
149
|
-
_set,
|
|
150
|
-
syncMaxOnceEvery,
|
|
151
|
-
{leading: false, trailing: true}
|
|
152
|
-
);
|
|
153
|
-
|
|
154
|
-
const _addVersion = (version: Version) => {
|
|
155
|
-
if (!props.versioned || !props.id) {
|
|
156
|
-
return;
|
|
157
|
-
}
|
|
158
|
-
const versions = [...state.versions];
|
|
159
|
-
versions.push(version);
|
|
160
|
-
setState((s) => ({...s, versions: versions}));
|
|
161
|
-
}
|
|
162
|
-
const addVersion = throttle(
|
|
163
|
-
_addVersion,
|
|
164
|
-
syncMaxOnceEvery,
|
|
165
|
-
{leading: false, trailing: true}
|
|
166
|
-
);
|
|
167
|
-
|
|
168
|
-
const saveNow = async () => {
|
|
169
|
-
addVersion.flush();
|
|
170
|
-
return set.flush();
|
|
171
|
-
}
|
|
172
|
-
|
|
173
|
-
const del = async () => {
|
|
174
|
-
storage.del();
|
|
175
|
-
return Status.SUCCESS;
|
|
176
|
-
}
|
|
177
|
-
const codeData = prepareCode(props.raw, { stateNotInitialized: true });
|
|
178
|
-
const setExecuting = (isExecuting: boolean) => {
|
|
179
|
-
setState((s) => ({...s, isExecuting: isExecuting}))
|
|
180
|
-
};
|
|
181
|
-
const addLogMessage = (log: LogMessage) => {
|
|
182
|
-
setState((s) => ({...s, logs: [...s.logs, log]}));
|
|
183
|
-
};
|
|
184
|
-
const clearLogMessages = () => {
|
|
185
|
-
setState((s) => ({...s, logs: []}));
|
|
186
|
-
};
|
|
187
|
-
const closeGraphicsModal = () => {
|
|
188
|
-
setState((s) => ({...s, isGraphicsmodalOpen: false}));
|
|
189
|
-
};
|
|
190
|
-
const stopScript = () => {
|
|
191
|
-
const code = document.getElementById(DOM_ELEMENT_IDS.communicator(state.codeId));
|
|
192
|
-
if (code) {
|
|
193
|
-
code.removeAttribute('data--start-time');
|
|
194
|
-
}
|
|
195
|
-
};
|
|
196
|
-
let state: Script = {
|
|
197
|
-
id: id,
|
|
198
|
-
codeId: codeId,
|
|
199
|
-
lang: props.lang,
|
|
200
|
-
showRaw: false,
|
|
201
|
-
pristineCode: codeData.code,
|
|
202
|
-
isExecuting: false,
|
|
203
|
-
logs: [],
|
|
204
|
-
isGraphicsmodalOpen: false,
|
|
205
|
-
hasEdits: false,
|
|
206
|
-
createdAt: createdAt,
|
|
207
|
-
isLoaded: false,
|
|
208
|
-
status: Status.IDLE,
|
|
209
|
-
versions: [],
|
|
210
|
-
versionsLoaded: false,
|
|
211
|
-
isPasted: false,
|
|
212
|
-
...codeData
|
|
213
|
-
};
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
const getState = () => state;
|
|
217
|
-
const listeners = new Set<() => void>();
|
|
218
|
-
const setState = (fn: (state: Script) => Script) => {
|
|
219
|
-
state = fn(state);
|
|
220
|
-
listeners.forEach((l) => l());
|
|
221
|
-
};
|
|
222
|
-
const subscribe = (listener: () => void) => {
|
|
223
|
-
listeners.add(listener);
|
|
224
|
-
return () => listeners.delete(listener);
|
|
225
|
-
};
|
|
226
|
-
const loadVersions = async () => {
|
|
227
|
-
// noop
|
|
228
|
-
state.isLoaded = false;
|
|
229
|
-
load();
|
|
230
|
-
setState((s) => ({...s, versionsLoaded: true}));
|
|
231
|
-
return Promise.resolve();
|
|
232
|
-
}
|
|
233
|
-
|
|
234
|
-
return {
|
|
235
|
-
getState,
|
|
236
|
-
setState,
|
|
237
|
-
subscribe,
|
|
238
|
-
saveNow,
|
|
239
|
-
addLogMessage,
|
|
240
|
-
clearLogMessages,
|
|
241
|
-
closeGraphicsModal,
|
|
242
|
-
setCode,
|
|
243
|
-
execScript,
|
|
244
|
-
setExecuting,
|
|
245
|
-
stopScript,
|
|
246
|
-
load,
|
|
247
|
-
loadVersions
|
|
248
|
-
} satisfies Store;
|
|
249
|
-
};
|
|
250
|
-
|
|
251
|
-
type Selector<T, R> = (state: T) => R;
|
|
252
|
-
export const useStore = <T, R>(store: Store<T>, selector: Selector<T, R>): R => {
|
|
253
|
-
return useSyncExternalStore(
|
|
254
|
-
store.subscribe,
|
|
255
|
-
useCallback(() => selector(store.getState()), [store, selector])
|
|
256
|
-
);
|
|
257
|
-
}
|
|
258
|
-
|
|
259
|
-
export const Context = React.createContext<{store: Store} | undefined>(undefined);
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
const ScriptContext = (props: InitState & { children: React.ReactNode; }) => {
|
|
263
|
-
const {libDir, syncMaxOnceEvery} = usePluginData('docusaurus-live-brython') as {libDir: string, syncMaxOnceEvery: number};
|
|
264
|
-
const [store, setStore] = React.useState<Store | null>(null);
|
|
265
|
-
React.useEffect(() => {
|
|
266
|
-
const store = createStore(props, libDir, syncMaxOnceEvery);
|
|
267
|
-
setStore(store);
|
|
268
|
-
store.load();
|
|
269
|
-
}, [props.id, libDir]);
|
|
270
|
-
|
|
271
|
-
if (!store) {
|
|
272
|
-
return <div>Load</div>;
|
|
273
|
-
}
|
|
274
|
-
|
|
275
|
-
return (
|
|
276
|
-
<Context.Provider value={{store: store}}>
|
|
277
|
-
{props.children}
|
|
278
|
-
</Context.Provider>
|
|
279
|
-
);
|
|
280
|
-
}
|
|
281
|
-
|
|
282
|
-
export function useScript(): {store: Store} {
|
|
283
|
-
const context = React.useContext(Context);
|
|
284
|
-
if (context === null) {
|
|
285
|
-
throw new ReactContextError(
|
|
286
|
-
'ScriptContextProvider',
|
|
287
|
-
'The Component must be a child of the CodeContextProvider component',
|
|
288
|
-
);
|
|
289
|
-
}
|
|
290
|
-
return context;
|
|
291
|
-
}
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
export default ScriptContext;
|
package/src/types.ts
DELETED
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
export type ThemeOptions = {
|
|
3
|
-
/**
|
|
4
|
-
* The path to the brython source file.
|
|
5
|
-
* @default 'https://raw.githack.com/brython-dev/brython/master/www/src/brython.js
|
|
6
|
-
*/
|
|
7
|
-
brython_src?: string;
|
|
8
|
-
/**
|
|
9
|
-
* The path to the brython standard library source file.
|
|
10
|
-
* @default 'https://raw.githack.com/brython-dev/brython/master/www/src/brython_stdlib.js'
|
|
11
|
-
*/
|
|
12
|
-
brython_stdlib_src?: string;
|
|
13
|
-
/**
|
|
14
|
-
* The folder path to brython specific libraries.
|
|
15
|
-
* When a python file imports a module, the module is searched in the libDir directory.
|
|
16
|
-
* By default, the libDir is created in the static folder and the needed python files are copied there.
|
|
17
|
-
* This can be changed by setting skipCopyAssetsToLibDir to true and setting libDir to a custom path.
|
|
18
|
-
* Make sure to copy the needed python files to the custom libDir.
|
|
19
|
-
* @default '/bry-libs/'
|
|
20
|
-
*/
|
|
21
|
-
libDir?: string;
|
|
22
|
-
/**
|
|
23
|
-
* Skip copying the brython specific libraries to the libDir.
|
|
24
|
-
* Make sure to copy the needed python files to the custom libDir yourself.
|
|
25
|
-
* @ref [needed python files](https://github.com/lebalz/docusaurus-live-brython/tree/main/src/assets)
|
|
26
|
-
* @default false
|
|
27
|
-
*/
|
|
28
|
-
skipCopyAssetsToLibDir?: boolean;
|
|
29
|
-
}
|