UNPKG

wix-storybook-utils

Version:

Utilities for automated component documentation within Storybook

196 lines 11.1 kB
import { __assign, __extends } from "tslib"; import React from 'react'; import PropTypes from 'prop-types'; import { LiveProvider, LiveError, LivePreview } from 'react-live'; import classnames from 'classnames'; import { Collapse } from 'react-collapse'; import DuplicateSmall from '../icons/DuplicateSmall'; import RevertSmall from '../icons/RevertSmall'; import CodeSmall from '../icons/CodeSmall'; import MagicWandSmall from '../icons/MagicWandSmall'; import LinkSmall from '../icons/LinkSmall'; import { transformCode, formatCode } from './doctor-code'; import { CopyButton } from '../CopyButton'; import ToggleSwitch from '../ui/toggle-switch'; import TextButton from '../TextButton'; import Editor from './Editor'; import styles from './index.scss'; import { getComponentsHints } from '../utils'; var LiveCodeExample = /** @class */ (function (_super) { __extends(LiveCodeExample, _super); function LiveCodeExample(props) { var _this = _super.call(this, props) || this; _this.prettifyCode = function () { try { _this.setState(function (_a) { var code = _a.code; return ({ code: formatCode(code) }); }, function () { return _this.state.setEditorValue(_this.state.code); }); } catch (e) { console.error('Unable to prettify code', e); } }; _this.onResetCode = function () { var code = formatCode(_this.props.initialCode); _this.state.setEditorValue(code); _this.setState({ code: code }); }; _this.onEditorChange = function (code) { var _a = _this.props, title = _a.title, onChange = _a.onChange, storyName = _a.storyName, storage = _a.storage; _this.setState({ code: code }, function () { return onChange(_this.state.code); }); storage && storage.setItem("".concat(storyName, "-").concat(title), code); }; _this.onToggleRtl = function (isRtl) { return _this.setState({ isRtl: isRtl }); }; _this.onToggleBackground = function (isDarkBackground) { return _this.setState({ isDarkBackground: isDarkBackground }); }; _this.onToggleCode = function () { return _this.setState(function (state) { return ({ isEditorOpened: !state.isEditorOpened, }); }); }; _this.transformCode = function (code) { if (code === void 0) { code = ''; } var parseError = _this.state.parseError; var newParseError; var returnValue = code; try { returnValue = transformCode(code); newParseError = null; } catch (error) { // @ts-expect-error newParseError = error.message; } if (newParseError !== parseError) { _this.setState({ parseError: newParseError }); } return returnValue; }; _this.previewWarning = function () { return _this.props.previewWarning({ onConfirm: function () { return _this.setState({ renderPreview: true }); }, }); }; _this.renderError = function () { if (_this.state.renderPreview) { return _this.state.parseError ? (React.createElement("div", { className: styles.error }, _this.state.parseError)) : (React.createElement(LiveError, { className: styles.error })); } return null; }; _this.renderLivePreview = function () { var _a = _this.props, examplesPreviewWrapper = _a.examplesPreviewWrapper, previewProps = _a.previewProps, previewRow = _a.previewRow; var livePreviewComp = (React.createElement(LivePreview, __assign({}, previewProps, { className: previewRow ? styles.previewRow : null }))); return examplesPreviewWrapper ? examplesPreviewWrapper({ component: livePreviewComp }) : livePreviewComp; }; var storyName = props.storyName, title = props.title, initialCode = props.initialCode, darkBackground = props.darkBackground, compact = props.compact, initiallyOpen = props.initiallyOpen, previewWarning = props.previewWarning, storage = props.storage, forceInitialCode = props.forceInitialCode; var codeFromStorage = storage && storage.getItem("".concat(storyName, "-").concat(title)); var initialOriginalCode = formatCode(initialCode).trim(); var formattedCode = codeFromStorage && !forceInitialCode ? codeFromStorage : initialOriginalCode; _this.state = { initialOriginalCode: initialOriginalCode, initialFormattedCode: formattedCode, code: formattedCode, isRtl: false, isDarkBackground: darkBackground, isEditorOpened: !compact || initiallyOpen, parseError: null, renderPreview: !Boolean(previewWarning), setEditorValue: null, }; return _this; } LiveCodeExample.prototype.componentDidUpdate = function (prevProps) { var renderPreview = this.state.renderPreview; if (this.props.previewWarning !== prevProps.previewWarning && typeof prevProps.previewWarning === 'function' && renderPreview) { this.setState({ renderPreview: false }); } }; LiveCodeExample.prototype.componentDidMount = function () { var _a = this.props, hints = _a.hints, scope = _a.scope; this.setState({ hints: hints || getComponentsHints(scope) }); }; LiveCodeExample.prototype.render = function () { var _a, _b; var _this = this; var _c = this.props, scope = _c.scope, compact = _c.compact, previewProps = _c.previewProps, autoRender = _c.autoRender, noBackground = _c.noBackground, hideCodeEditor = _c.hideCodeEditor, figmaLink = _c.figmaLink; var _d = this.state, code = _d.code, isRtl = _d.isRtl, isDarkBackground = _d.isDarkBackground, isEditorOpened = _d.isEditorOpened, renderPreview = _d.renderPreview, hints = _d.hints; var dirty = this.state.initialOriginalCode !== this.state.code; return (React.createElement("div", { className: classnames(styles.wrapper, (_a = {}, _a[styles.compact] = compact, _a)) }, !hideCodeEditor && !compact && (React.createElement("div", { className: styles.header }, React.createElement(CopyButton, { source: this.state.code, prefixIcon: React.createElement(DuplicateSmall, null) }), React.createElement("div", { className: styles.spacer }), dirty && (React.createElement("div", { className: styles.headerControl }, React.createElement(TextButton, { onClick: function () { return _this.prettifyCode(); }, prefixIcon: React.createElement(MagicWandSmall, null) }, "Prettify"))), React.createElement("div", { className: styles.headerControl }, "Imitate RTL:\u00A0", React.createElement(ToggleSwitch, { size: "small", checked: isRtl, onChange: this.onToggleRtl })), React.createElement("div", { className: styles.headerControl }, "Dark Background:\u00A0", React.createElement(ToggleSwitch, { size: "small", checked: isDarkBackground, onChange: this.onToggleBackground })), dirty && (React.createElement(TextButton, { onClick: this.onResetCode, prefixIcon: React.createElement(RevertSmall, null) }, "Reset")))), React.createElement(LiveProvider, { code: code.trim(), scope: __assign({ isRtl: isRtl }, scope), noInline: !autoRender, transformCode: this.transformCode }, React.createElement("div", { className: styles.liveExampleWrapper }, React.createElement("div", { className: classnames(styles.preview, previewProps.className, (_b = { rtl: isRtl }, _b[styles.darkPreview] = isDarkBackground, _b[styles.compactPreview] = compact && !noBackground, _b)), dir: isRtl ? 'rtl' : '' }, renderPreview ? this.renderLivePreview() : this.previewWarning(), this.renderError()), !hideCodeEditor && (React.createElement(Collapse, { isOpened: isEditorOpened, className: styles.editor }, React.createElement(Editor, { initialFormattedCode: this.state.initialFormattedCode, onChange: this.onEditorChange, hints: hints, editorCodeUpdater: function (updater) { return _this.setState({ setEditorValue: updater }); } }))))), !hideCodeEditor && compact && (React.createElement("div", { className: styles.controlButtons }, React.createElement(CopyButton, { source: this.state.code, prefixIcon: React.createElement(DuplicateSmall, null) }), figmaLink && React.createElement(TextButton, { className: styles.figmaLink, prefixIcon: React.createElement(LinkSmall, null), onClick: function () { return window.open(figmaLink, '_blank'); } }, "Figma"), dirty && (React.createElement(TextButton, { onClick: function () { return _this.prettifyCode(); }, prefixIcon: React.createElement(MagicWandSmall, null) }, "Prettify")), React.createElement("div", { style: { marginLeft: 'auto' } }), dirty && (React.createElement(TextButton, { onClick: this.onResetCode, prefixIcon: React.createElement(RevertSmall, null) }, "Reset")), React.createElement(TextButton, { onClick: this.onToggleCode, prefixIcon: React.createElement(CodeSmall, null) }, this.state.isEditorOpened ? 'Hide' : 'Show', " code"))))); }; LiveCodeExample.propTypes = { initialCode: PropTypes.string, title: PropTypes.string, figmaLink: PropTypes.string, storyName: PropTypes.string, storage: PropTypes.object, scope: PropTypes.object, compact: PropTypes.bool, initiallyOpen: PropTypes.bool, previewRow: PropTypes.bool, previewProps: PropTypes.object, autoRender: PropTypes.bool, darkBackground: PropTypes.bool, noBackground: PropTypes.bool, forceInitialCode: PropTypes.bool, }; LiveCodeExample.defaultProps = { compact: false, initiallyOpen: false, previewRow: false, previewProps: {}, autoRender: true, darkBackground: false, noBackground: false, forceInitialCode: false, onChange: function () { }, scope: {}, }; return LiveCodeExample; }(React.PureComponent)); export default LiveCodeExample; //# sourceMappingURL=LiveCodeExample.js.map