Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

SDK51 : Property 'Icon' doesn't exist #303

Open
lc3t35 opened this issue May 26, 2024 · 7 comments
Open

SDK51 : Property 'Icon' doesn't exist #303

lc3t35 opened this issue May 26, 2024 · 7 comments

Comments

@lc3t35
Copy link

lc3t35 commented May 26, 2024

image

The source code of build/createIconSet.js :

export default function (glyphMap, fontName, expoAssetId, fontStyle) {
    const font = { [fontName]: expoAssetId };
    const RNVIconComponent = createIconSet(glyphMap, fontName, null, fontStyle);
    return class Icon extends React.Component {
        static defaultProps = RNVIconComponent.defaultProps;
        static Button = createIconButtonComponent(Icon);                    ====> Icon does not exist in the js file !
@geovane7881
Copy link

same problem here, version 14 broke my icons, I workaround using version 13:

"@expo/vector-icons": "^13.0.0"

@lc3t35
Copy link
Author

lc3t35 commented May 31, 2024

In version 13, the code seems to be based on a React.Component not a function -> workaround is also working for me. Thank you @geovane7881

@brentvatne
Copy link
Member

hi there! do you have a minimal reproducible example that you can share?

@lc3t35
Copy link
Author

lc3t35 commented Jun 16, 2024

@brentvatne I gave the exact location of the issue (build/createIconSet.js), the previous code @13.0.0 works and the new code @14.0.0 does not work.

The code in @14 returns a class Icon extends React.Component and uses Icon inside the function which is not correct, the code in 13 (as a component) stores the class in a var _a :

   var _a;
   const font = { [fontName]: expoAssetId };
   const RNVIconComponent = createIconSet(glyphMap, fontName, null, fontStyle);
   return _a = class Icon extends React.Component {
           constructor() { ...},
          ...
       }, 
       _a.defaultProps = RNVIconComponent.defaultProps,
       _a.Button = createIconButtonComponent(_a),
      ....
      _a;
  }

This looks like a generated code ... from ts or babel ? It's interesting to know why the @14 code was not generated this way ...
Easy to fix, store the class, update the props Button and others, return the modified class ...

Do you really need a reproducible example ?

@lc3t35
Copy link
Author

lc3t35 commented Jun 30, 2024

This is how I fixed this error :

export default function (glyphMap, fontName, expoAssetId, fontStyle) {
    const font = { [fontName]: expoAssetId };
    const RNVIconComponent = createIconSet(glyphMap, fontName, null, fontStyle);
    class Icon extends React.Component {
        static defaultProps = RNVIconComponent.defaultProps;
        static glyphMap = glyphMap;
        static getRawGlyphMap = () => glyphMap;
        static getFontFamily = () => fontName;
        static loadFont = () => Font.loadAsync(font);
        static font = font;
        _mounted = false;
        _icon;
        state = {
          fontIsLoaded: Font.isLoaded(fontName),
        };
        async componentDidMount() {
          this._mounted = true;
          if (!this.state.fontIsLoaded) {
            await Font.loadAsync(font);
            /* eslint-disable react/no-did-mount-set-state */
            this._mounted && this.setState({ fontIsLoaded: true });
          }
        }
        componentWillUnmount() {
          this._mounted = false;
        }
        setNativeProps(props) {
          if (this._icon) {
            this._icon.setNativeProps(props);
          }
        }
        render() {
          if (__DEV__ && this.props.name && !(this.props.name in glyphMap)) {
            console.warn(`"${this.props.name}" is not a valid icon name for family "${fontName}"`);
          }
          if (!this.state.fontIsLoaded) {
            return <Text />;
          }
          return (<RNVIconComponent ref={(view) => {
            this._icon = view;
          }} {...this.props}/>);
        }
      };
    
      Icon.Button = createIconButtonComponent(Icon); // Move this line after the class definition
    
      return Icon;
}

@lc3t35
Copy link
Author

lc3t35 commented Jun 30, 2024

And the patch file @expo+vector-icons+14.0.2.patch for anybody who has the issue and wants to use 14.0.2 :

diff --git a/node_modules/@expo/vector-icons/build/createIconSet.js b/node_modules/@expo/vector-icons/build/createIconSet.js
index e8e1ec0..41d085a 100644
--- a/node_modules/@expo/vector-icons/build/createIconSet.js
+++ b/node_modules/@expo/vector-icons/build/createIconSet.js
@@ -7,9 +7,9 @@ export { DEFAULT_ICON_COLOR, DEFAULT_ICON_SIZE, } from './vendor/react-native-ve
 export default function (glyphMap, fontName, expoAssetId, fontStyle) {
     const font = { [fontName]: expoAssetId };
     const RNVIconComponent = createIconSet(glyphMap, fontName, null, fontStyle);
-    return class Icon extends React.Component {
+    
+    class Icon extends React.Component {
         static defaultProps = RNVIconComponent.defaultProps;
-        static Button = createIconButtonComponent(Icon);
         static glyphMap = glyphMap;
         static getRawGlyphMap = () => glyphMap;
         static getFontFamily = () => fontName;
@@ -18,35 +18,39 @@ export default function (glyphMap, fontName, expoAssetId, fontStyle) {
         _mounted = false;
         _icon;
         state = {
-            fontIsLoaded: Font.isLoaded(fontName),
+          fontIsLoaded: Font.isLoaded(fontName),
         };
         async componentDidMount() {
-            this._mounted = true;
-            if (!this.state.fontIsLoaded) {
-                await Font.loadAsync(font);
-                /* eslint-disable react/no-did-mount-set-state */
-                this._mounted && this.setState({ fontIsLoaded: true });
-            }
+          this._mounted = true;
+          if (!this.state.fontIsLoaded) {
+            await Font.loadAsync(font);
+            /* eslint-disable react/no-did-mount-set-state */
+            this._mounted && this.setState({ fontIsLoaded: true });
+          }
         }
         componentWillUnmount() {
-            this._mounted = false;
+          this._mounted = false;
         }
         setNativeProps(props) {
-            if (this._icon) {
-                this._icon.setNativeProps(props);
-            }
+          if (this._icon) {
+            this._icon.setNativeProps(props);
+          }
         }
         render() {
-            if (__DEV__ && this.props.name && !(this.props.name in glyphMap)) {
-                console.warn(`"${this.props.name}" is not a valid icon name for family "${fontName}"`);
-            }
-            if (!this.state.fontIsLoaded) {
-                return <Text />;
-            }
-            return (<RNVIconComponent ref={(view) => {
-                    this._icon = view;
-                }} {...this.props}/>);
+          if (__DEV__ && this.props.name && !(this.props.name in glyphMap)) {
+            console.warn(`"${this.props.name}" is not a valid icon name for family "${fontName}"`);
+          }
+          if (!this.state.fontIsLoaded) {
+            return <Text />;
+          }
+          return (<RNVIconComponent ref={(view) => {
+            this._icon = view;
+          }} {...this.props}/>);
         }
-    };
+      };
+    
+      Icon.Button = createIconButtonComponent(Icon); // Move this line after the class definition
+    
+      return Icon;
 }
 //# sourceMappingURL=createIconSet.js.map
\ No newline at end of file

I tryed to provide a reproduction repo but it does happen with the simple repo I've built ...

@erickreutz
Copy link

Also having this problem upgrading @expo/vector-icons from 13 to 14

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

4 participants