dumi 2.3.0-beta.2 → 2.3.0-beta.4

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.
Files changed (42) hide show
  1. package/dist/client/misc/reactDemoCompiler.d.ts +3 -0
  2. package/dist/client/misc/reactDemoCompiler.js +24 -0
  3. package/dist/client/pages/Demo/index.js +15 -0
  4. package/dist/client/theme-api/types.d.ts +9 -0
  5. package/dist/client/theme-api/useLiveDemo.d.ts +7 -3
  6. package/dist/client/theme-api/useLiveDemo.js +133 -50
  7. package/dist/client/theme-api/useNavData.js +11 -8
  8. package/dist/client/theme-api/usePrefersColor.js +1 -1
  9. package/dist/client/theme-api/useRouteMeta.d.ts +1 -1
  10. package/dist/client/theme-api/useRouteMeta.js +4 -8
  11. package/dist/client/theme-api/useSidebarData.d.ts +9 -1
  12. package/dist/client/theme-api/useSidebarData.js +9 -6
  13. package/dist/client/theme-api/useSiteSearch/useSearchData.js +2 -1
  14. package/dist/client/theme-api/utils.d.ts +0 -10
  15. package/dist/client/theme-api/utils.js +0 -25
  16. package/dist/constants.d.ts +1 -0
  17. package/dist/constants.js +3 -0
  18. package/dist/features/compile/index.js +39 -10
  19. package/dist/features/exports.js +0 -2
  20. package/dist/features/parser.js +23 -1
  21. package/dist/features/theme/index.js +13 -11
  22. package/dist/loaders/markdown/index.js +25 -7
  23. package/dist/loaders/markdown/transformer/index.d.ts +2 -1
  24. package/dist/loaders/markdown/transformer/index.js +1 -0
  25. package/dist/loaders/markdown/transformer/rehypeDemo.js +5 -2
  26. package/dist/loaders/markdown/transformer/remarkEmbed.js +2 -1
  27. package/dist/techStacks/react.d.ts +1 -0
  28. package/dist/techStacks/react.js +3 -0
  29. package/dist/templates/meta/exports.ts.tpl +33 -1
  30. package/dist/types.d.ts +14 -0
  31. package/dist/utils.d.ts +1 -3
  32. package/dist/utils.js +8 -2
  33. package/package.json +1 -1
  34. package/theme-default/builtins/Previewer/index.js +11 -31
  35. package/theme-default/builtins/Previewer/index.less +59 -15
  36. package/theme-default/slots/ColorSwitch/index.js +4 -1
  37. package/theme-default/slots/PreviewerActions/index.d.ts +1 -0
  38. package/theme-default/slots/PreviewerActions/index.js +18 -20
  39. package/theme-default/slots/SearchBar/index.less +3 -0
  40. package/theme-default/slots/SearchResult/index.js +18 -5
  41. package/theme-default/slots/SourceCodeEditor/index.d.ts +1 -0
  42. package/theme-default/slots/SourceCodeEditor/index.js +8 -31
@@ -53,7 +53,10 @@ var ColorSwitch = function ColorSwitch() {
53
53
  onChange: function onChange(ev) {
54
54
  return setPrefersColor(ev.target.value);
55
55
  },
56
- value: prefersColor
56
+ value: prefersColor,
57
+ onClick: function onClick(e) {
58
+ return e.stopPropagation();
59
+ }
57
60
  }, ['light', 'dark', 'auto'].map(function (c) {
58
61
  return /*#__PURE__*/React.createElement("option", {
59
62
  value: c,
@@ -16,6 +16,7 @@ export interface IPreviewerActionsProps extends IPreviewerProps {
16
16
  err?: null;
17
17
  source: Record<string, string>;
18
18
  }) => void;
19
+ onSourceChange?: (source: Record<string, string>) => void;
19
20
  }
20
21
  declare const PreviewerActions: FC<IPreviewerActionsProps>;
21
22
  export default PreviewerActions;
@@ -15,7 +15,7 @@ import { ReactComponent as IconSketch } from '@ant-design/icons-svg/inline-svg/o
15
15
  import { ReactComponent as IconStackBlitz } from '@ant-design/icons-svg/inline-svg/outlined/thunderbolt.svg';
16
16
  import classNames from 'classnames';
17
17
  import copy from 'copy-to-clipboard';
18
- import { getSketchJSON, openCodeSandbox, openStackBlitz, useIntl } from 'dumi';
18
+ import { getSketchJSON, openCodeSandbox, openStackBlitz, useDemo, useIntl } from 'dumi';
19
19
  import SourceCode from 'dumi/theme/builtins/SourceCode';
20
20
  import PreviewerActionsExtra from 'dumi/theme/slots/PreviewerActionsExtra';
21
21
  import SourceCodeEditor from 'dumi/theme/slots/SourceCodeEditor';
@@ -53,6 +53,8 @@ var PreviewerActions = function PreviewerActions(props) {
53
53
  type = _ref2[1].type;
54
54
  return type === 'FILE';
55
55
  });
56
+ var _ref3 = useDemo(props.asset.id),
57
+ renderOpts = _ref3.renderOpts;
56
58
  var _useState = useState(0),
57
59
  _useState2 = _slicedToArray(_useState, 2),
58
60
  activeKey = _useState2[0],
@@ -167,31 +169,24 @@ var PreviewerActions = function PreviewerActions(props) {
167
169
  onChange: function onChange(key) {
168
170
  return setActiveKey(Number(key));
169
171
  },
170
- items: files.map(function (_ref3, i) {
171
- var _ref4 = _slicedToArray(_ref3, 1),
172
- filename = _ref4[0];
172
+ items: files.map(function (_ref4, i) {
173
+ var _ref5 = _slicedToArray(_ref4, 1),
174
+ filename = _ref5[0];
173
175
  return {
174
176
  key: String(i),
175
177
  // remove leading ./ prefix
176
178
  label: filename.replace(/^\.\//, ''),
177
179
  // only support to edit entry file currently
178
- children: i === 0 ? /*#__PURE__*/React.createElement(SourceCodeEditor, {
180
+ children: i === 0 && renderOpts !== null && renderOpts !== void 0 && renderOpts.compile ? /*#__PURE__*/React.createElement(SourceCodeEditor, {
179
181
  lang: lang,
180
182
  initialValue: files[i][1].value.trim(),
181
- onTranspile: function onTranspile(_ref5) {
182
- var err = _ref5.err,
183
- code = _ref5.code;
184
- if (err) {
185
- var _props$onSourceTransp;
186
- (_props$onSourceTransp = props.onSourceTranspile) === null || _props$onSourceTransp === void 0 ? void 0 : _props$onSourceTransp.call(props, {
187
- err: err
188
- });
189
- } else {
190
- var _props$onSourceTransp2;
191
- (_props$onSourceTransp2 = props.onSourceTranspile) === null || _props$onSourceTransp2 === void 0 ? void 0 : _props$onSourceTransp2.call(props, {
192
- source: _defineProperty({}, files[i][0], code)
193
- });
194
- }
183
+ onChange: function onChange(code) {
184
+ var _props$onSourceChange, _props$onSourceTransp;
185
+ (_props$onSourceChange = props.onSourceChange) === null || _props$onSourceChange === void 0 ? void 0 : _props$onSourceChange.call(props, _defineProperty({}, files[i][0], code));
186
+ // FIXME: remove before publish
187
+ (_props$onSourceTransp = props.onSourceTranspile) === null || _props$onSourceTransp === void 0 ? void 0 : _props$onSourceTransp.call(props, {
188
+ source: _defineProperty({}, files[i][0], code)
189
+ });
195
190
  },
196
191
  extra: /*#__PURE__*/React.createElement("button", {
197
192
  type: "button",
@@ -202,7 +197,10 @@ var PreviewerActions = function PreviewerActions(props) {
202
197
  }, /*#__PURE__*/React.createElement(IconEdit, null))
203
198
  }) : /*#__PURE__*/React.createElement(SourceCode, {
204
199
  lang: lang,
205
- extra: /*#__PURE__*/React.createElement("button", {
200
+ extra:
201
+ // only show readonly tip for non-entry files
202
+ // because readonly entry file means live compile is not available for this demo tech stack
203
+ i !== 0 && /*#__PURE__*/React.createElement("button", {
206
204
  type: "button",
207
205
  className: "dumi-default-previewer-editor-tip-btn",
208
206
  "data-dumi-tooltip": intl.formatMessage({
@@ -56,7 +56,10 @@
56
56
  background-color: @c-site-bg-dark;
57
57
  box-shadow: 0 0 0 3px fade(@c-primary-dark, 10%);
58
58
  }
59
+ }
59
60
 
61
+ &:focus,
62
+ &:not(:placeholder-shown) {
60
63
  ~ .@{prefix}-search-shortcut {
61
64
  opacity: 0;
62
65
  }
@@ -5,7 +5,8 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
5
5
  function _iterableToArrayLimit(arr, i) { var _i = null == arr ? null : "undefined" != typeof Symbol && arr[Symbol.iterator] || arr["@@iterator"]; if (null != _i) { var _s, _e, _x, _r, _arr = [], _n = !0, _d = !1; try { if (_x = (_i = _i.call(arr)).next, 0 === i) { if (Object(_i) !== _i) return; _n = !1; } else for (; !(_n = (_s = _x.call(_i)).done) && (_arr.push(_s.value), _arr.length !== i); _n = !0); } catch (err) { _d = !0, _e = err; } finally { try { if (!_n && null != _i.return && (_r = _i.return(), Object(_r) !== _r)) return; } finally { if (_d) throw _e; } } return _arr; } }
6
6
  function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
7
7
  import { ReactComponent as IconInbox } from '@ant-design/icons-svg/inline-svg/outlined/inbox.svg';
8
- import { FormattedMessage, history, Link } from 'dumi';
8
+ import animateScrollTo from 'animated-scroll-to';
9
+ import { FormattedMessage, history, Link, useLocation } from 'dumi';
9
10
  import React, { Fragment, useCallback, useEffect, useState } from 'react';
10
11
  import "./index.less";
11
12
  var IconTitle = function IconTitle() {
@@ -98,6 +99,20 @@ var SearchResult = function SearchResult(props) {
98
99
  _useState4 = _slicedToArray(_useState3, 2),
99
100
  activeIndex = _useState4[0],
100
101
  setActiveIndex = _useState4[1];
102
+ var _useLocation = useLocation(),
103
+ pathname = _useLocation.pathname;
104
+ var onItemSelect = function onItemSelect(item) {
105
+ var _props$onItemSelect;
106
+ (_props$onItemSelect = props.onItemSelect) === null || _props$onItemSelect === void 0 ? void 0 : _props$onItemSelect.call(props, item);
107
+ var url = new URL(item === null || item === void 0 ? void 0 : item.link, location.origin);
108
+ if ((url === null || url === void 0 ? void 0 : url.pathname) === pathname && !url.hash) {
109
+ setTimeout(function () {
110
+ animateScrollTo(0, {
111
+ maxDuration: 300
112
+ });
113
+ }, 1);
114
+ }
115
+ };
101
116
  useEffect(function () {
102
117
  var handler = function handler(ev) {
103
118
  // TODO: scroll into view for invisible items
@@ -106,12 +121,11 @@ var SearchResult = function SearchResult(props) {
106
121
  } else if (ev.key === 'ArrowUp') {
107
122
  setActiveIndex((activeIndex + histsCount - 1) % histsCount);
108
123
  } else if (ev.key === 'Enter' && activeIndex >= 0) {
109
- var _props$onItemSelect;
110
124
  var _item = data.find(function (item) {
111
125
  return item.type === 'hint' && item.activeIndex === activeIndex;
112
126
  }).value;
113
127
  history.push(_item.link);
114
- (_props$onItemSelect = props.onItemSelect) === null || _props$onItemSelect === void 0 ? void 0 : _props$onItemSelect.call(props, _item);
128
+ onItemSelect === null || onItemSelect === void 0 ? void 0 : onItemSelect(_item);
115
129
  document.activeElement.blur();
116
130
  }
117
131
  if (['Escape', 'Enter'].includes(ev.key)) {
@@ -140,8 +154,7 @@ var SearchResult = function SearchResult(props) {
140
154
  to: item.value.link,
141
155
  "data-active": activeIndex === item.activeIndex || undefined,
142
156
  onClick: function onClick() {
143
- var _props$onItemSelect2;
144
- return (_props$onItemSelect2 = props.onItemSelect) === null || _props$onItemSelect2 === void 0 ? void 0 : _props$onItemSelect2.call(props, item.value);
157
+ return onItemSelect === null || onItemSelect === void 0 ? void 0 : onItemSelect(item.value);
145
158
  }
146
159
  }, /*#__PURE__*/React.createElement(ICONS_MAPPING[item.value.type]), /*#__PURE__*/React.createElement("h4", null, /*#__PURE__*/React.createElement(Highlight, {
147
160
  texts: item.value.highlightTitleTexts
@@ -10,6 +10,7 @@ interface ISourceCodeEditorProps extends Omit<ComponentProps<typeof SourceCode>,
10
10
  err?: null;
11
11
  code: string;
12
12
  }) => void;
13
+ onChange?: (code: string) => void;
13
14
  }
14
15
  /**
15
16
  * simple source code editor based on textarea
@@ -6,8 +6,7 @@ function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len
6
6
  function _iterableToArrayLimit(arr, i) { var _i = null == arr ? null : "undefined" != typeof Symbol && arr[Symbol.iterator] || arr["@@iterator"]; if (null != _i) { var _s, _e, _x, _r, _arr = [], _n = !0, _d = !1; try { if (_x = (_i = _i.call(arr)).next, 0 === i) { if (Object(_i) !== _i) return; _n = !1; } else for (; !(_n = (_s = _x.call(_i)).done) && (_arr.push(_s.value), _arr.length !== i); _n = !0); } catch (err) { _d = !0, _e = err; } finally { try { if (!_n && null != _i.return && (_r = _i.return(), Object(_r) !== _r)) return; } finally { if (_d) throw _e; } } return _arr; } }
7
7
  function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
8
8
  import SourceCode from 'dumi/theme/builtins/SourceCode';
9
- import throttle from 'lodash.throttle';
10
- import React, { useCallback, useEffect, useRef, useState } from 'react';
9
+ import React, { useEffect, useRef, useState } from 'react';
11
10
  import "./index.less";
12
11
  /**
13
12
  * simple source code editor based on textarea
@@ -22,25 +21,6 @@ var SourceCodeEditor = function SourceCodeEditor(props) {
22
21
  _useState4 = _slicedToArray(_useState3, 2),
23
22
  code = _useState4[0],
24
23
  setCode = _useState4[1];
25
- var sucraseDefer = useRef();
26
- var transpile = useCallback(throttle(function (value) {
27
- // transform code when change
28
- sucraseDefer.current.then(function (transform) {
29
- try {
30
- var _props$onTranspile;
31
- (_props$onTranspile = props.onTranspile) === null || _props$onTranspile === void 0 ? void 0 : _props$onTranspile.call(props, {
32
- code: transform(value, {
33
- transforms: ['typescript', 'jsx', 'imports']
34
- }).code
35
- });
36
- } catch (err) {
37
- var _props$onTranspile2;
38
- (_props$onTranspile2 = props.onTranspile) === null || _props$onTranspile2 === void 0 ? void 0 : _props$onTranspile2.call(props, {
39
- err: err
40
- });
41
- }
42
- });
43
- }, 500), [props.onTranspile]);
44
24
 
45
25
  // generate style from pre element, for adapting to the custom theme
46
26
  useEffect(function () {
@@ -67,18 +47,15 @@ var SourceCodeEditor = function SourceCodeEditor(props) {
67
47
  className: "dumi-default-source-code-editor-textarea",
68
48
  style: style,
69
49
  value: code,
70
- onFocus: function onFocus() {
71
- // load sucrase when focus on editor
72
- if (!sucraseDefer.current) {
73
- sucraseDefer.current = import('sucrase').then(function (_ref) {
74
- var transform = _ref.transform;
75
- return transform;
76
- });
77
- }
78
- },
79
50
  onChange: function onChange(ev) {
51
+ var _props$onChange, _props$onTranspile;
80
52
  setCode(ev.target.value);
81
- transpile(ev.target.value);
53
+ (_props$onChange = props.onChange) === null || _props$onChange === void 0 ? void 0 : _props$onChange.call(props, ev.target.value);
54
+ // FIXME: remove before publish
55
+ (_props$onTranspile = props.onTranspile) === null || _props$onTranspile === void 0 ? void 0 : _props$onTranspile.call(props, {
56
+ err: null,
57
+ code: ev.target.value
58
+ });
82
59
  },
83
60
  onKeyDown: function onKeyDown(ev) {
84
61
  // support tab to space