From f926986eb65a31941cb4564311f835554fd8ad88 Mon Sep 17 00:00:00 2001 From: Vjacheslav Trushkin Date: Wed, 27 Jan 2021 11:45:03 +0200 Subject: [PATCH] Clean up code for React with API for new React component compatibility --- packages/react-demo-with-api/src/App.js | 25 ++++++++++++++++++++--- packages/react-with-api/package-lock.json | 4 ++-- packages/react-with-api/package.json | 2 +- packages/react-with-api/rollup.config.js | 25 ++++++++++++++++++++--- packages/react-with-api/src/icon.ts | 21 +++++++++++-------- packages/react/src/icon.ts | 12 +++++++---- 6 files changed, 67 insertions(+), 22 deletions(-) diff --git a/packages/react-demo-with-api/src/App.js b/packages/react-demo-with-api/src/App.js index b5ea94e..d0480ea 100644 --- a/packages/react-demo-with-api/src/App.js +++ b/packages/react-demo-with-api/src/App.js @@ -1,5 +1,5 @@ import React from 'react'; -import { Icon, InlineIcon, enableCache } from '@iconify/react-with-api'; +import { Icon, InlineIcon, disableCache } from '@iconify/react-with-api'; import accountIcon from '@iconify-icons/mdi-light/account'; import homeIcon from '@iconify-icons/mdi-light/home'; @@ -9,8 +9,7 @@ import { InlineDemo } from './components/Inline'; import './App.css'; // Disable cache for test -enableCache('local', false); -enableCache('session', false); +disableCache('all'); class CheckboxIcon extends React.Component { constructor(props) { @@ -125,6 +124,26 @@ function App() { }} />

+

+ Testing reference by adding border to icon (unfortunately + should not work yet):{' '} + { + if (element) { + element.style.border = '1px solid red'; + } + }} + /> + { + if (element) { + element.style.border = '1px solid red'; + } + }} + /> +

diff --git a/packages/react-with-api/package-lock.json b/packages/react-with-api/package-lock.json index 10a38fe..1afe2fa 100644 --- a/packages/react-with-api/package-lock.json +++ b/packages/react-with-api/package-lock.json @@ -1,12 +1,12 @@ { "name": "@iconify/react-with-api", - "version": "1.0.0-rc.5", + "version": "1.0.0-rc.6", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "@iconify/react-with-api", - "version": "1.0.0-rc.5", + "version": "1.0.0-rc.6", "license": "MIT", "devDependencies": { "@babel/core": "^7.12.7", diff --git a/packages/react-with-api/package.json b/packages/react-with-api/package.json index e9cd266..94adf75 100644 --- a/packages/react-with-api/package.json +++ b/packages/react-with-api/package.json @@ -2,7 +2,7 @@ "name": "@iconify/react-with-api", "description": "Iconify icon component for React.", "author": "Vjacheslav Trushkin (https://iconify.design)", - "version": "1.0.0-rc.5", + "version": "1.0.0-rc.6", "license": "MIT", "bugs": "https://github.com/iconify/iconify/issues", "homepage": "https://iconify.design/", diff --git a/packages/react-with-api/rollup.config.js b/packages/react-with-api/rollup.config.js index 460d080..74e0d39 100644 --- a/packages/react-with-api/rollup.config.js +++ b/packages/react-with-api/rollup.config.js @@ -33,7 +33,13 @@ const config = [ }, ], external: ['react', 'axios'], - plugins: [resolve(), commonjs(), buble()], + plugins: [ + resolve(), + commonjs({ + ignore: ['cross-fetch'], + }), + buble(), + ], }, // Dev build { @@ -45,7 +51,13 @@ const config = [ }, ], external: ['react', 'axios'], - plugins: [resolve(), commonjs(), buble()], + plugins: [ + resolve(), + commonjs({ + ignore: ['cross-fetch'], + }), + buble(), + ], }, // Production { @@ -57,7 +69,14 @@ const config = [ }, ], external: ['react', 'axios'], - plugins: [resolve(), commonjs(), buble(), terser()], + plugins: [ + resolve(), + commonjs({ + ignore: ['cross-fetch'], + }), + buble(), + terser(), + ], }, ]; diff --git a/packages/react-with-api/src/icon.ts b/packages/react-with-api/src/icon.ts index 7113711..162d6e3 100644 --- a/packages/react-with-api/src/icon.ts +++ b/packages/react-with-api/src/icon.ts @@ -1,4 +1,4 @@ -import { createElement, Component } from 'react'; +import React from 'react'; import { IconifyJSON } from '@iconify/types'; // Parent component @@ -184,7 +184,7 @@ interface StatefulState { /** * Dynamic component */ -class DynamicComponent extends Component { +class DynamicComponent extends React.Component { protected _abort: IconifyIconLoaderAbort | null; /** @@ -215,17 +215,19 @@ class DynamicComponent extends Component { const state = this.state; if (!state.loaded) { // Empty - return null; + return React.createElement('span'); } // Replace icon in props with object + const props = this.props; let newProps: IconProps = {} as IconProps; - Object.assign(newProps, this.props, { + Object.assign(newProps, props, { icon: state.data, }); delete newProps['func']; + delete newProps.ref; - return this.props.func(newProps); + return React.createElement(this.props.func, newProps); } /** @@ -267,7 +269,7 @@ const component = (props: IconProps, func: typeof ReactIcon): JSX.Element => { if (typeof props.icon === 'string') { const iconName = stringToIcon(props.icon, true); if (!iconName) { - return null; + return React.createElement('span'); } iconData = getIconData(iconName); @@ -276,7 +278,7 @@ const component = (props: IconProps, func: typeof ReactIcon): JSX.Element => { let staticProps: IconProps = {} as IconProps; Object.assign(staticProps, props); staticProps.icon = iconData; - return func(staticProps); + return React.createElement(func, staticProps); } // Return dynamic component @@ -285,9 +287,10 @@ const component = (props: IconProps, func: typeof ReactIcon): JSX.Element => { icon: iconName, func, }); - return createElement(DynamicComponent, dynamicProps); + return React.createElement(DynamicComponent, dynamicProps); } else { - return func(props); + // Passed icon data as object: render @iconify/react component + return React.createElement(func, props); } }; diff --git a/packages/react/src/icon.ts b/packages/react/src/icon.ts index 8cdf263..a1a9837 100644 --- a/packages/react/src/icon.ts +++ b/packages/react/src/icon.ts @@ -60,10 +60,14 @@ export interface IconifyIconProps extends IconifyIconCustomisations { type IconifyElementProps = HTMLProps; type IconifySVGProps = SVGProps; +interface ReactRefProp { + ref?: typeof React.createRef; +} + /** * Mix of icon properties and HTMLElement properties */ -export type IconProps = IconifyElementProps & IconifyIconProps; +export type IconProps = IconifyElementProps & IconifyIconProps & ReactRefProp; /** * Default SVG attributes @@ -105,7 +109,7 @@ const component = ( ? storage[props.icon] : fullIcon(props.icon); if (!icon) { - return null; + return React.createElement('span'); } const customisations = merge( @@ -195,7 +199,7 @@ const component = ( * * @param props - Component properties */ -export const Icon = React.forwardRef((props: IconProps, ref) => +export const Icon = React.forwardRef((props: IconProps, ref?) => component(props, defaults, ref) ); @@ -204,7 +208,7 @@ export const Icon = React.forwardRef((props: IconProps, ref) => * * @param props - Component properties */ -export const InlineIcon = React.forwardRef((props: IconProps, ref) => +export const InlineIcon = React.forwardRef((props: IconProps, ref?) => component(props, inlineDefaults, ref) );