1- import React , { useCallback , useImperativeHandle , useRef } from 'react' ;
1+ import React , {
2+ useCallback ,
3+ useImperativeHandle ,
4+ useMemo ,
5+ useRef ,
6+ } from 'react' ;
7+ // This import path isn't handled by @types/react-native
8+ // @ts -ignore
9+ import resolveAssetSource from 'react-native/Libraries/Image/resolveAssetSource' ;
210import {
311 requireNativeComponent ,
412 UIManager ,
@@ -116,7 +124,10 @@ type Props = {
116124 stateMachineName ?: string ;
117125 autoplay ?: boolean ;
118126 children ?: React . ReactNode ;
119- } & XOR < { resourceName : string } , { url : string } > ;
127+ } & XOR <
128+ XOR < { resourceName : string } , { url : string } > ,
129+ { source : number | { uri : string } }
130+ > ;
120131
121132export const RiveViewManager = requireNativeComponent < RiveProps > ( VIEW_NAME ) ;
122133
@@ -133,19 +144,59 @@ const RiveContainer = React.forwardRef<RiveRef, Props>(
133144 onError,
134145 style,
135146 autoplay = true ,
136- resourceName,
137- url,
147+ resourceName : resourceNameProp ,
148+ url : urlProp ,
138149 alignment = Alignment . Center ,
139150 fit = Fit . Contain ,
140151 layoutScaleFactor,
141152 artboardName,
142153 referencedAssets : referencedAssets ,
143154 animationName,
155+ source,
144156 stateMachineName,
145157 testID,
146158 } ,
147159 ref
148160 ) => {
161+ const assetID = typeof source === 'number' ? source : null ;
162+ const sourceURI = typeof source === 'object' ? source . uri : null ;
163+ const { resourceName, url } = useMemo ( ( ) => {
164+ if ( resourceNameProp ) {
165+ return { resourceName : resourceNameProp } ;
166+ }
167+
168+ if ( urlProp ) {
169+ return { url : urlProp } ;
170+ }
171+
172+ const assetURI = assetID ? resolveAssetSource ( assetID ) ?. uri : sourceURI ;
173+
174+ if ( ! assetURI ) {
175+ return { } ;
176+ }
177+
178+ // handle http address and dev server
179+ if ( assetURI . match ( / h t t p s ? : \/ \/ / ) ) {
180+ return { url : assetURI } ;
181+ }
182+
183+ // handle iOS bundled asset
184+ if ( assetURI . match ( / f i l e : \/ \/ / ) ) {
185+ // strip resource name from file path
186+ return { resourceName : assetURI . match ( / f i l e : \/ \/ ( .* \/ ) + ( .* ) \. r i v / ) [ 2 ] } ;
187+ }
188+
189+ // handle Android bundled asset or resource name uri
190+ return {
191+ resourceName : assetURI ,
192+ } ;
193+ } , [ assetID , sourceURI , resourceNameProp , urlProp ] ) ;
194+ if ( ! resourceName && ! url ) {
195+ throw new Error (
196+ 'Invalid Rive resource. Please provide a valid resource.'
197+ ) ;
198+ }
199+
149200 const riveRef = useRef ( null ) ;
150201
151202 const isUserHandlingErrors = onError !== undefined ;
0 commit comments