diff --git a/lib/api/package.json b/lib/api/package.json index 4973b2637428..ea1b22ad8a42 100644 --- a/lib/api/package.json +++ b/lib/api/package.json @@ -42,7 +42,6 @@ "prop-types": "^15.6.2", "react": "^16.8.3", "semver": "^6.0.0", - "shallow-equal": "^1.1.0", "store2": "^2.7.1", "telejson": "^3.2.0", "ts-dedent": "^1.1.1", diff --git a/lib/api/src/index.tsx b/lib/api/src/index.tsx index 0ff0f611655d..62848ab2fb31 100644 --- a/lib/api/src/index.tsx +++ b/lib/api/src/index.tsx @@ -1,7 +1,14 @@ -import React, { ReactElement, Component, useContext, useEffect, useMemo, ReactNode } from 'react'; -import memoize from 'memoizerific'; -// @ts-ignore shallow-equal is not in DefinitelyTyped -import shallowEqualObjects from 'shallow-equal/objects'; +import React, { + Component, + Fragment, + FunctionComponent, + ReactElement, + ReactNode, + useContext, + useEffect, + useMemo, + useRef, +} from 'react'; import { STORIES_CONFIGURED, @@ -115,16 +122,16 @@ interface Children { type StatePartial = Partial; -export type Props = Children & RouterData & ProviderData & DocsModeData; +export type ManagerProviderProps = Children & RouterData & ProviderData & DocsModeData; -class ManagerProvider extends Component { +class ManagerProvider extends Component { api: API; modules: any[]; static displayName = 'Manager'; - constructor(props: Props) { + constructor(props: ManagerProviderProps) { super(props); const { provider, @@ -211,7 +218,7 @@ class ManagerProvider extends Component { this.api = api; } - static getDerivedStateFromProps = (props: Props, state: State) => { + static getDerivedStateFromProps = (props: ManagerProviderProps, state: State) => { if (state.path !== props.path) { return { ...state, @@ -234,7 +241,7 @@ class ManagerProvider extends Component { }); } - shouldComponentUpdate(nextProps: Props, nextState: State) { + shouldComponentUpdate(nextProps: ManagerProviderProps, nextState: State) { const prevState = this.state; const prevProps = this.props; @@ -254,57 +261,45 @@ class ManagerProvider extends Component { api: this.api, }; - // @ts-ignore - const content: ReactNode = typeof children === 'function' ? children(value) : children; - - return {content}; + return ( + + {children} + + ); } } -interface ConsumerProps { - filter?: (combo: C) => S; - pure?: boolean; - children: (d: S | C) => ReactElement | null; +interface ManagerConsumerProps

{ + filter?: (combo: Combo) => P; + children: FunctionComponent

| ReactNode; } -interface SubState { - [key: string]: any; -} +const defaultFilter = (c: Combo) => c; -class ManagerConsumer extends Component> { - prevChildren?: ReactElement | null; +function ManagerConsumer

({ + // @ts-ignore + filter = defaultFilter, + children, +}: ManagerConsumerProps

): ReactElement { + const c = useContext(ManagerContext); + const renderer = useRef(children); + const filterer = useRef(filter); - prevData?: SubState; + if (typeof renderer.current !== 'function') { + return {renderer.current}; + } - dataMemory?: (combo: Combo) => SubState; + const data = filterer.current(c); - constructor(props: ConsumerProps) { - super(props); - this.dataMemory = props.filter ? memoize(10)(props.filter) : null; - } + const l = useMemo(() => { + return [...Object.entries(data).reduce((acc, keyval) => acc.concat(keyval), [])]; + }, [c.state]); - render() { - const { children, pure } = this.props; + return useMemo(() => { + const Child = renderer.current as FunctionComponent

; - return ( - - {d => { - const data = this.dataMemory ? this.dataMemory(d) : d; - if ( - pure && - this.prevChildren && - this.prevData && - shallowEqualObjects(data, this.prevData) - ) { - return this.prevChildren; - } - this.prevChildren = children(data); - this.prevData = data; - return this.prevChildren; - }} - - ); - } + return ; + }, l); } export function useStorybookState(): State { @@ -359,7 +354,7 @@ export function useParameter(parameterKey: string, defaultValue?: S) { } type StateMerger = (input: S) => S; -// chache for taking care of HMR +// cache for taking care of HMR const addonStateCache: { [key: string]: any; } = {}; diff --git a/lib/ui/src/components/preview/preview.tsx b/lib/ui/src/components/preview/preview.tsx index 0051f246b311..0251c4a2ef37 100644 --- a/lib/ui/src/components/preview/preview.tsx +++ b/lib/ui/src/components/preview/preview.tsx @@ -63,14 +63,7 @@ const createCanvas = (id: string, baseUrl = 'iframe.html', withLoader = true): A render: p => { return ( - {({ - customCanvas, - storyId, - viewMode, - queryParams, - getElements, - isLoading, - }: ReturnType) => ( + {({ customCanvas, storyId, viewMode, queryParams, getElements, isLoading }) => ( {({ value: scale }) => { const wrappers = [...defaultWrappers, ...getWrapper(getElements)]; diff --git a/lib/ui/src/components/preview/toolbar.tsx b/lib/ui/src/components/preview/toolbar.tsx index 5e113d8d1777..d197b20cf282 100644 --- a/lib/ui/src/components/preview/toolbar.tsx +++ b/lib/ui/src/components/preview/toolbar.tsx @@ -39,7 +39,7 @@ export const fullScreenTool: Addon = { match: p => p.viewMode === 'story', render: () => ( - {({ toggle, value }: ReturnType) => ( + {({ toggle, value }) => ( p.viewMode === 'story', render: () => ( - {({ baseUrl, storyId, origin, pathname, queryParams }: ReturnType) => ( + {({ baseUrl, storyId, origin, pathname, queryParams }) => ( @@ -93,7 +93,7 @@ export const ejectTool: Addon = { match: p => p.viewMode === 'story', render: () => ( - {({ baseUrl, storyId, queryParams }: ReturnType) => ( + {({ baseUrl, storyId, queryParams }) => ( ({ title: 'title', render: () => ( - {({ viewMode, storyId, path, location }: ReturnType) => ( + {({ viewMode, storyId, path, location }) => ( {tabs diff --git a/lib/ui/src/containers/notifications.tsx b/lib/ui/src/containers/notifications.tsx index 227c04deb561..b71790ab6bad 100644 --- a/lib/ui/src/containers/notifications.tsx +++ b/lib/ui/src/containers/notifications.tsx @@ -13,9 +13,7 @@ export const mapper = ({ state }: Combo) => { }; const NotificationConnect: FunctionComponent = props => ( - - {(fromState: ReturnType) => } - + {fromState => } ); export default NotificationConnect; diff --git a/lib/ui/src/containers/panel.tsx b/lib/ui/src/containers/panel.tsx index 2ca96d5b3320..52acba18fe27 100644 --- a/lib/ui/src/containers/panel.tsx +++ b/lib/ui/src/containers/panel.tsx @@ -18,9 +18,7 @@ const mapper = ({ state, api }: Combo) => ({ }); const Panel: FunctionComponent = props => ( - - {(customProps: ReturnType) => } - + {customProps => } ); export default Panel; diff --git a/lib/ui/src/containers/preview.tsx b/lib/ui/src/containers/preview.tsx index 1aaa532a5991..ca10e2a759ea 100644 --- a/lib/ui/src/containers/preview.tsx +++ b/lib/ui/src/containers/preview.tsx @@ -50,7 +50,7 @@ function getBaseUrl(): string { const PreviewConnected = React.memo<{ id: string; withLoader: boolean }>(props => ( - {(fromState: ReturnType) => { + {fromState => { const p = { ...props, baseUrl: getBaseUrl(), diff --git a/lib/ui/src/containers/sidebar.tsx b/lib/ui/src/containers/sidebar.tsx index ad3c29764bbc..485342ea3af9 100755 --- a/lib/ui/src/containers/sidebar.tsx +++ b/lib/ui/src/containers/sidebar.tsx @@ -248,9 +248,7 @@ export const mapper = ({ state, api }: Combo) => { }; const Sidebar: FunctionComponent = props => ( - - {(fromState: ReturnType) => } - + {fromState => } ); export default Sidebar;