@blocklet/editor 2.4.88 → 2.4.90

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.
@@ -70,6 +70,7 @@ export class CustomComponentNode extends DecoratorBlockNode {
70
70
  'x-cards': () => ({ conversion: convertCustomComponentElement, priority: 1 }),
71
71
  'x-code-group': () => ({ conversion: convertCustomComponentElement, priority: 1 }),
72
72
  'x-steps': () => ({ conversion: convertCustomComponentElement, priority: 1 }),
73
+ 'x-field': () => ({ conversion: convertCustomComponentElement, priority: 1 }),
73
74
  };
74
75
  }
75
76
  static importJSON(serializedNode) {
@@ -358,7 +358,7 @@ function CodeHeader({ title, icon, actions }) {
358
358
  p: 1.5,
359
359
  borderBottom: 1,
360
360
  borderColor: 'divider',
361
- bgcolor: 'background.paper',
361
+ bgcolor: 'grey.50',
362
362
  borderRadius: '8px 8px 0 0',
363
363
  }, children: [_jsxs(Box, { sx: { display: 'flex', alignItems: 'center', gap: 1, flex: 1 }, children: [icon && (_jsx(Box, { component: Icon, icon: icon, sx: {
364
364
  fontSize: '24px',
@@ -432,6 +432,7 @@ const XCode = styled('div')(({ theme }) => ({
432
432
  pre: {
433
433
  margin: 0,
434
434
  borderRadius: 0,
435
+ background: 'transparent !important',
435
436
  code: {
436
437
  margin: 0,
437
438
  border: 0,
@@ -0,0 +1,9 @@
1
+ export interface FieldProps {
2
+ name: string;
3
+ type: string;
4
+ default?: string;
5
+ required?: 'false' | 'true';
6
+ deprecated?: 'false' | 'true';
7
+ body?: string;
8
+ }
9
+ export default function Field({ name, type, default: defaultVal, required, deprecated, body }: FieldProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,32 @@
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import { Stack, Box, styled, alpha } from '@mui/material';
3
+ import useMobile from '../../../main/hooks/use-mobile';
4
+ const Tag = styled(Box)(({ theme }) => ({
5
+ borderRadius: theme.shape.borderRadius * 0.75,
6
+ padding: theme.spacing(0.25, 1),
7
+ fontSize: '14px',
8
+ }));
9
+ const Bar = styled(Box)(({ theme }) => ({
10
+ display: 'flex',
11
+ alignItems: 'center',
12
+ lineHeight: '1.25em',
13
+ flexWrap: 'wrap',
14
+ gap: theme.spacing(1.25),
15
+ }));
16
+ export default function Field({ name, type, default: defaultVal, required, deprecated, body }) {
17
+ const isMobile = useMobile();
18
+ const isRequired = required === 'true';
19
+ const isDeprecated = deprecated === 'true';
20
+ const metaInfo = (_jsxs(_Fragment, { children: [_jsx(Tag, { sx: { backgroundColor: ({ palette }) => alpha(palette.grey[100], 0.6) }, children: type }), isRequired && (_jsx(Tag, { sx: { color: 'error.main', background: ({ palette }) => alpha(palette.error.main, 0.1), fontWeight: 500 }, children: "required" })), isDeprecated && (_jsx(Tag, { sx: {
21
+ color: 'warning.light',
22
+ background: ({ palette }) => alpha(palette.warning.light, 0.1),
23
+ fontWeight: 500,
24
+ }, children: "deprecated" })), defaultVal && (_jsxs(Tag, { sx: { backgroundColor: ({ palette }) => alpha(palette.grey[100], 0.6) }, children: [_jsx(Box, { component: "span", sx: { color: 'text.secondary', mr: 0.5 }, children: "default:" }), defaultVal] }))] }));
25
+ return (_jsxs(Stack, { className: "x-param-field", sx: {
26
+ borderBottom: '1px solid',
27
+ borderColor: 'divider',
28
+ pt: 1.25,
29
+ pb: 2.5,
30
+ my: 1.25,
31
+ }, children: [_jsxs(Bar, { children: [_jsx(Box, { sx: { color: 'primary.main', fontWeight: 500 }, children: name }), !isMobile && metaInfo] }), isMobile && _jsx(Bar, { sx: { mt: 1.25 }, children: metaInfo }), body && _jsx(Box, { sx: { color: 'text.secondary', mt: 2 }, children: body })] }));
32
+ }
@@ -1,9 +1,11 @@
1
1
  import Card from './Card';
2
2
  import Cards from './Cards';
3
3
  import Code from './Code';
4
+ import Field from './Field';
4
5
  declare const components: {
5
6
  code: typeof Code;
6
7
  card: typeof Card;
7
8
  cards: typeof Cards;
9
+ field: typeof Field;
8
10
  };
9
11
  export default components;
@@ -1,9 +1,11 @@
1
1
  import Card from './Card';
2
2
  import Cards from './Cards';
3
3
  import Code from './Code';
4
+ import Field from './Field';
4
5
  const components = {
5
6
  code: Code,
6
7
  card: Card,
7
8
  cards: Cards,
9
+ field: Field,
8
10
  };
9
11
  export default components;
@@ -0,0 +1,2 @@
1
+ import { Box } from '@mui/material';
2
+ export declare const EditorRoot: typeof Box;
@@ -0,0 +1,46 @@
1
+ import { Box, styled } from '@mui/material';
2
+ export const EditorRoot = styled(Box)(({ theme }) => {
3
+ const { palette } = theme;
4
+ return {
5
+ container: 'blocklet-editor / inline-size',
6
+ margin: '0 auto',
7
+ borderRadius: '4px',
8
+ position: 'relative',
9
+ lineHeight: '1.7',
10
+ fontWeight: '400',
11
+ textAlign: 'left',
12
+ // mui-*
13
+ '--mui-palette-grey-50': palette.grey[50],
14
+ '--mui-palette-grey-200': palette.grey[200],
15
+ '--mui-palette-background-paper': palette.background.paper,
16
+ '--mui-palette-divider': palette.divider,
17
+ '--mui-palette-primary-main': palette.primary.main,
18
+ '--mui-palette-primary-light': palette.primary.light,
19
+ '--mui-palette-text-primary': palette.text.primary,
20
+ '--mui-palette-text-secondary': palette.text.secondary,
21
+ // lexical-*
22
+ '--lexical-text-code': 'inherit',
23
+ // lexical-code-*
24
+ '--lexical-code-comment': '#1e8449',
25
+ '--lexical-code-punctuation': '#2c3e50',
26
+ '--lexical-code-property': '#e67e22',
27
+ '--lexical-code-selector': '#c0392b',
28
+ '--lexical-code-operator': '#8e44ad',
29
+ '--lexical-code-attr': '#2980b9',
30
+ '--lexical-code-variable': '#27ae60',
31
+ '--lexical-code-function': '#f39c12',
32
+ // dark mode
33
+ '&[data-mode="dark"]': {
34
+ '--lexical-text-code': palette.grey[800],
35
+ // lexical-code-*
36
+ '--lexical-code-comment': '#6a9955',
37
+ '--lexical-code-punctuation': '#d4d4d4',
38
+ '--lexical-code-property': '#9cdcfe',
39
+ '--lexical-code-selector': '#d7ba7d',
40
+ '--lexical-code-operator': '#d4d4d4',
41
+ '--lexical-code-attr': '#9cdcfe',
42
+ '--lexical-code-variable': '#9cdcfe',
43
+ '--lexical-code-function': '#dcdcaa',
44
+ },
45
+ };
46
+ });
@@ -0,0 +1,4 @@
1
+ import { type Breakpoint } from '@mui/material/styles';
2
+ export default function useMobile({ key }?: {
3
+ key: Breakpoint | number;
4
+ }): boolean;
@@ -0,0 +1,6 @@
1
+ import { useTheme } from '@mui/material/styles';
2
+ import useMediaQuery from '@mui/material/useMediaQuery';
3
+ export default function useMobile({ key } = { key: 'md' }) {
4
+ const theme = useTheme();
5
+ return useMediaQuery(theme.breakpoints.down(key));
6
+ }
package/lib/main/index.js CHANGED
@@ -7,7 +7,6 @@ import { jsx as _jsx } from "react/jsx-runtime";
7
7
  *
8
8
  */
9
9
  import { cx } from '@emotion/css';
10
- import styled from '@emotion/styled';
11
10
  import { LexicalComposer } from '@lexical/react/LexicalComposer';
12
11
  import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext';
13
12
  import { useCallback, useEffect, useRef } from 'react';
@@ -17,6 +16,7 @@ import { SettingsContext } from './context/SettingsContext';
17
16
  import { SharedAutocompleteContext } from './context/SharedAutocompleteContext';
18
17
  import { SharedHistoryContext } from './context/SharedHistoryContext';
19
18
  import Editor from './editor';
19
+ import { EditorRoot } from './editor-root';
20
20
  import PlaygroundNodes from './nodes/PlaygroundNodes';
21
21
  import { TableContext } from './plugins/TablePlugin';
22
22
  import { useCustomTheme } from './themes/customTheme';
@@ -34,9 +34,10 @@ export default function BlockletEditor({ editorState, nodes = PlaygroundNodes, e
34
34
  },
35
35
  theme,
36
36
  };
37
- return (_jsx(SettingsContext, { children: _jsx(SharedHistoryContext, { children: _jsx(SharedAutocompleteContext, { children: _jsx(TableContext, { children: _jsx(LexicalComposer, { initialConfig: initialConfig, children: _jsx(EditorShell, { ...props, editable: editable }) }, muiTheme.palette.mode) }) }) }) }));
37
+ return (_jsx(SettingsContext, { children: _jsx(SharedHistoryContext, { children: _jsx(SharedAutocompleteContext, { children: _jsx(TableContext, { children: _jsx(LexicalComposer, { initialConfig: initialConfig, children: _jsx(EditorShell, { ...props, editable: editable }) }) }) }) }) }));
38
38
  }
39
39
  function EditorShell({ placeholder, children, prepend, editable, onChange, autoFocus, showToolbar = true, editorRef, onReady, enableHeadingsIdPlugin, ...props }) {
40
+ const muiTheme = useTheme();
40
41
  const [editor] = useLexicalComposerContext();
41
42
  useEffect(() => {
42
43
  editor.setEditable(editable ?? true);
@@ -47,14 +48,5 @@ function EditorShell({ placeholder, children, prepend, editable, onChange, autoF
47
48
  editor.focus();
48
49
  }
49
50
  }, []);
50
- return (_jsx(EditorRoot, { ...props, className: cx(props.className, 'be-shell'), ref: shellRef, onClick: onShellClick, children: _jsx(Editor, { onChange: onChange, placeholder: placeholder, autoFocus: autoFocus, showToolbar: showToolbar, editorRef: editorRef, onReady: onReady, enableHeadingsIdPlugin: enableHeadingsIdPlugin, prepend: prepend, children: children }) }));
51
+ return (_jsx(EditorRoot, { ...props, className: cx(props.className, 'be-shell'), ref: shellRef, "data-mode": muiTheme.palette.mode, onClick: onShellClick, children: _jsx(Editor, { onChange: onChange, placeholder: placeholder, autoFocus: autoFocus, showToolbar: showToolbar, editorRef: editorRef, onReady: onReady, enableHeadingsIdPlugin: enableHeadingsIdPlugin, prepend: prepend, children: children }) }));
51
52
  }
52
- const EditorRoot = styled.div `
53
- container: blocklet-editor / inline-size;
54
- margin: 0 auto;
55
- border-radius: 4px;
56
- position: relative;
57
- line-height: 1.7;
58
- font-weight: 400;
59
- text-align: left;
60
- `;
@@ -1,11 +1,11 @@
1
1
  import { jsx as _jsx } from "react/jsx-runtime";
2
2
  import { cx } from '@emotion/css';
3
- import styled from '@emotion/styled';
4
3
  import { LexicalComposer } from '@lexical/react/LexicalComposer';
5
4
  import { useLexicalComposerContext } from '@lexical/react/LexicalComposerContext';
6
5
  import { useCallback, useEffect, useRef } from 'react';
7
6
  import { $convertFromMarkdownString } from '@lexical/markdown';
8
7
  import Editor from './editor';
8
+ import { EditorRoot } from '../editor-root';
9
9
  import nodes from './nodes';
10
10
  import { useCustomTheme } from '../themes/customTheme';
11
11
  import { MarkdownEditorThemeProvider } from './theme';
@@ -40,11 +40,3 @@ function EditorShell({ placeholder, children, editable, onChange, autoFocus, sho
40
40
  }, []);
41
41
  return (_jsx(EditorRoot, { ...props, className: cx(props.className, 'be-shell'), ref: shellRef, onClick: onShellClick, children: _jsx(Editor, { onChange: onChange, placeholder: placeholder, autoFocus: autoFocus, showToolbar: showToolbar, editorRef: editorRef, onReady: onReady, enableHeadingsIdPlugin: enableHeadingsIdPlugin, mediaUrlPrefix: mediaUrlPrefix, children: children }) }));
42
42
  }
43
- const EditorRoot = styled.div `
44
- margin: 0 auto;
45
- border-radius: 4px;
46
- position: relative;
47
- line-height: 1.7;
48
- font-weight: 400;
49
- text-align: left;
50
- `;
@@ -1,35 +1,4 @@
1
- export declare const codeHighlightDark: {
2
- atrule: string;
3
- attr: string;
4
- boolean: string;
5
- builtin: string;
6
- cdata: string;
7
- char: string;
8
- class: string;
9
- comment: string;
10
- constant: string;
11
- deleted: string;
12
- doctype: string;
13
- entity: string;
14
- function: string;
15
- important: string;
16
- inserted: string;
17
- keyword: string;
18
- namespace: string;
19
- number: string;
20
- operator: string;
21
- prolog: string;
22
- property: string;
23
- punctuation: string;
24
- regex: string;
25
- selector: string;
26
- string: string;
27
- symbol: string;
28
- tag: string;
29
- url: string;
30
- variable: string;
31
- };
32
- export declare const codeHighlightLight: {
1
+ declare const codeHighlight: {
33
2
  atrule: string;
34
3
  attr: string;
35
4
  boolean: string;
@@ -60,3 +29,4 @@ export declare const codeHighlightLight: {
60
29
  url: string;
61
30
  variable: string;
62
31
  };
32
+ export default codeHighlight;
@@ -1,55 +1,30 @@
1
1
  import { css } from '@emotion/css';
2
2
  // Dark theme tokens
3
3
  const tokenComment = css `
4
- color: #6a9955;
4
+ color: var(--lexical-code-comment);
5
5
  `;
6
6
  const tokenPunctuation = css `
7
- color: #d4d4d4;
7
+ color: var(--lexical-code-punctuation);
8
8
  `;
9
9
  const tokenProperty = css `
10
- color: #9cdcfe;
10
+ color: var(--lexical-code-property);
11
11
  `;
12
12
  const tokenSelector = css `
13
- color: #d7ba7d;
13
+ color: var(--lexical-code-selector);
14
14
  `;
15
15
  const tokenOperator = css `
16
- color: #d4d4d4;
16
+ color: var(--lexical-code-operator);
17
17
  `;
18
18
  const tokenAttr = css `
19
- color: #9cdcfe;
19
+ color: var(--lexical-code-attr);
20
20
  `;
21
21
  const tokenVariable = css `
22
- color: #9cdcfe;
22
+ color: var(--lexical-code-variable);
23
23
  `;
24
24
  const tokenFunction = css `
25
- color: #dcdcaa;
25
+ color: var(--lexical-code-function);
26
26
  `;
27
- // Light theme tokens - 更有活力和年轻化的配色,优化对比度
28
- const tokenCommentLight = css `
29
- color: #1e8449;
30
- `;
31
- const tokenPunctuationLight = css `
32
- color: #2c3e50;
33
- `;
34
- const tokenPropertyLight = css `
35
- color: #e67e22;
36
- `;
37
- const tokenSelectorLight = css `
38
- color: #c0392b;
39
- `;
40
- const tokenOperatorLight = css `
41
- color: #8e44ad;
42
- `;
43
- const tokenAttrLight = css `
44
- color: #2980b9;
45
- `;
46
- const tokenVariableLight = css `
47
- color: #27ae60;
48
- `;
49
- const tokenFunctionLight = css `
50
- color: #f39c12;
51
- `;
52
- export const codeHighlightDark = {
27
+ const codeHighlight = {
53
28
  atrule: tokenAttr,
54
29
  attr: tokenAttr,
55
30
  boolean: tokenProperty,
@@ -80,34 +55,4 @@ export const codeHighlightDark = {
80
55
  url: tokenOperator,
81
56
  variable: tokenVariable,
82
57
  };
83
- export const codeHighlightLight = {
84
- atrule: tokenAttrLight,
85
- attr: tokenAttrLight,
86
- boolean: tokenPropertyLight,
87
- builtin: tokenSelectorLight,
88
- cdata: tokenCommentLight,
89
- char: tokenSelectorLight,
90
- class: tokenFunctionLight,
91
- comment: tokenCommentLight,
92
- constant: tokenPropertyLight,
93
- deleted: tokenPropertyLight,
94
- doctype: tokenCommentLight,
95
- entity: tokenOperatorLight,
96
- function: tokenFunctionLight,
97
- important: tokenVariableLight,
98
- inserted: tokenSelectorLight,
99
- keyword: tokenAttrLight,
100
- namespace: tokenVariableLight,
101
- number: tokenPropertyLight,
102
- operator: tokenOperatorLight,
103
- prolog: tokenCommentLight,
104
- property: tokenPropertyLight,
105
- punctuation: tokenPunctuationLight,
106
- regex: tokenVariableLight,
107
- selector: tokenSelectorLight,
108
- string: tokenSelectorLight,
109
- symbol: tokenPropertyLight,
110
- tag: tokenPropertyLight,
111
- url: tokenOperatorLight,
112
- variable: tokenVariableLight,
113
- };
58
+ export default codeHighlight;
@@ -1,9 +1,8 @@
1
1
  import { css } from '@emotion/css';
2
2
  import { useTheme } from '@mui/material';
3
3
  import defaultTheme from './defaultTheme';
4
- import { codeHighlightLight, codeHighlightDark } from './code-highlight';
4
+ import codeHighlight from './code-highlight';
5
5
  const createCustomTheme = (theme) => {
6
- const { palette } = theme;
7
6
  const noMarginTopStyle = css(`
8
7
  // 首个元素的 margin-top 设置为 0
9
8
  .be-editable &:first-child {
@@ -30,7 +29,7 @@ const createCustomTheme = (theme) => {
30
29
  `, theme.typography.body1, noMarginTopStyle);
31
30
  const quote = css(`
32
31
  margin: 1.6em 0;
33
- border-left-color: ${palette.grey[200]};
32
+ border-left-color: var(--mui-palette-grey-200);
34
33
  border-left-width: 2px;
35
34
  border-left-style: solid;
36
35
  padding-left: 1.5rem;
@@ -76,7 +75,7 @@ const createCustomTheme = (theme) => {
76
75
  const link = css(`
77
76
  color: inherit;
78
77
  text-decoration: none;
79
- border-bottom: 1px solid ${palette.primary.main};
78
+ border-bottom: 1px solid var(--mui-palette-primary-main);
80
79
  &:hover {
81
80
  border-bottom-width: 2px;
82
81
  }
@@ -108,12 +107,12 @@ const createCustomTheme = (theme) => {
108
107
  fontSize: '.875em',
109
108
  fontWeight: 500,
110
109
  borderRadius: '.25rem',
111
- border: `1px solid ${palette.grey[200]}`,
110
+ border: '1px solid var(--mui-palette-grey-200)',
112
111
  padding: '1px .375rem',
113
112
  fontFamily: 'Menlo, Consolas, Monaco, monospace',
114
113
  fontVariantLigatures: 'none',
115
- backgroundColor: palette.grey[50],
116
- ...(palette.mode === 'dark' && { color: palette.grey[800] }),
114
+ backgroundColor: 'var(--mui-palette-grey-50)',
115
+ color: 'var(--lexical-text-code)',
117
116
  });
118
117
  const olCommon = {
119
118
  margin: 0,
@@ -156,15 +155,15 @@ const createCustomTheme = (theme) => {
156
155
  padding-left: 24px;
157
156
  padding-right: 24px;
158
157
  &:before {
159
- border: 1px solid ${palette.primary.main};
160
- background-color: ${palette.primary.main};
158
+ border: 1px solid var(--mui-palette-primary-main);
159
+ background-color: var(--mui-palette-primary-main);
161
160
  top: 4px;
162
161
  }
163
162
  &:after {
164
163
  top: 7px;
165
164
  }
166
165
  &:focus:before {
167
- box-shadow: 0 0 0 1px ${palette.primary.light};
166
+ box-shadow: 0 0 0 1px var(--mui-palette-primary-light);
168
167
  }
169
168
  `;
170
169
  const listItemUnchecked = css `
@@ -177,7 +176,7 @@ const createCustomTheme = (theme) => {
177
176
  left: 1px;
178
177
  }
179
178
  &:focus:before {
180
- box-shadow: 0 0 0 1px ${palette.primary.light};
179
+ box-shadow: 0 0 0 1px var(--mui-palette-primary-light);
181
180
  }
182
181
  `;
183
182
  const nestedListItem = css `
@@ -193,14 +192,14 @@ const createCustomTheme = (theme) => {
193
192
  padding: 8px 0;
194
193
  `;
195
194
  const embedBlockFocus = css `
196
- outline: 2px solid ${palette.primary.light};
195
+ outline: 2px solid var(--mui-palette-primary-light);
197
196
  `;
198
197
  const alert = css `
199
198
  // user-select: none;
200
199
  padding: 8px 0;
201
200
  `;
202
201
  const alertFocus = css `
203
- outline: 2px solid ${palette.primary.light};
202
+ outline: 2px solid var(--mui-palette-primary-light);
204
203
  `;
205
204
  const image = css `
206
205
  .image-caption-container {
@@ -220,7 +219,7 @@ const createCustomTheme = (theme) => {
220
219
  .ImageNode__contentEditable {
221
220
  padding: 0;
222
221
  p {
223
- color: ${palette.text.secondary};
222
+ color: var(--mui-palette-text-secondary);
224
223
  font-size: 12px;
225
224
  }
226
225
  }
@@ -228,8 +227,8 @@ const createCustomTheme = (theme) => {
228
227
  }
229
228
  `;
230
229
  const code = css `
231
- background-color: ${palette.background.paper};
232
- color: ${palette.text.primary};
230
+ background-color: var(--mui-palette-background-paper);
231
+ color: var(--mui-palette-text-primary);
233
232
  font-family: Menlo, Consolas, Monaco, monospace;
234
233
  display: block;
235
234
  // padding: 16px;
@@ -244,7 +243,7 @@ const createCustomTheme = (theme) => {
244
243
  overflow-x: auto;
245
244
  position: relative;
246
245
  border-radius: ${theme.shape.borderRadius}px;
247
- border: 1px solid ${palette.divider};
246
+ border: 1px solid var(--mui-palette-divider);
248
247
 
249
248
  &:before {
250
249
  content: attr(data-gutter);
@@ -294,7 +293,7 @@ const createCustomTheme = (theme) => {
294
293
  olDepth: [ol1, ol2, ol3, ol4, ol5],
295
294
  ul,
296
295
  },
297
- codeHighlight: palette.mode === 'dark' ? codeHighlightDark : codeHighlightLight,
296
+ codeHighlight,
298
297
  embedBlock: {
299
298
  base: embedBlock,
300
299
  focus: embedBlockFocus,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@blocklet/editor",
3
- "version": "2.4.88",
3
+ "version": "2.4.90",
4
4
  "main": "lib/index.js",
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -71,7 +71,7 @@
71
71
  "ufo": "^1.5.4",
72
72
  "url-join": "^4.0.1",
73
73
  "zustand": "^4.5.5",
74
- "@blocklet/pdf": "2.4.88"
74
+ "@blocklet/pdf": "2.4.90"
75
75
  },
76
76
  "devDependencies": {
77
77
  "@babel/core": "^7.25.2",