I have a react custom component called HomeContent that accepts some props.
To make that animated as per the react-spring documentation I made
const animatedHomeContent = animated(HomeContent);
Then for rendering I did like this:
<animatedHomeContent
id={1}
avatar="O"
image="..."
image_title="Onion"
title=" Medium Sized Onions"
subtitle="November 08, 2020"
desc="Onions from farms of Nasik"
price="74"
quantity="1kg"
/>
But I see the props are not getting passed. Please tell me how to do it.
It depends on how you want to interact with your component, do you want to use the api or simply supply updated props?
Updating by regenerating the spring
With the first example, using one of the animated native elements (
animated.XXX) you will rerender the animated wrapper every time you want to update the state, because you will pass it a new, updatedspringPropsobject every time you update it, which will cause it to rerender. Or... this is only partially true, the individualSpringValue's in the returned object will be the same with both methods so if you pass them as individual props, rerendering would theoretically not be necessary but if you pass them as a whole object (whenspringPropsis astyleobject for example) it will be a changed object from last render and cause a rerender of theanimatedwrapper.When you use a custom element that does not take a ref inside the wrapper instead of one of the native elements, the component will rerender once for every animation frame. This is suboptimal from a performance perspective, but with this strategy, you can use whichever api (prop names) you want for your component, much like you have done.
Here is a sandbox with this solution that works: sandbox
You can observe that the animation works but also that the component rerenders a lot.
Updating via the api
If you want to make it more efficient, and use the api for updating your custom component, you need to adhere to a few rules. When you use the api,
react-springupdates the element via a ref on the corresponding DOM element, and therefore,react-springmust understand how to update the element without requiring React to rerender it. This implies:forwardRefdoesn't allow you to add multiple refs, changes cannot take place on multiple DOM elements inside your custom component if you want to wrap it inanimated(there are other strategies to solve this, such as NOT wrapping your component inanimatedand instead use nativeanimated.XXXelements inside your component and passSpringValues as props).react-springwill not understand how to update this element.Since your element has a lot of custom properties,
react-springwon't be able to update your component via the api. It will attempt to do so by simply setting the updated properties on the element to which the ref is attached, but since you need React to map the custom properties to the actual properties on the DOM element, this will fail (no DOM element that I know of have the set of properties that you provide).As an example of how to accomplish this, here is a sandbox showing the outlines of this strategy: sandbox
Here you can see that the component renders only once and can still be updated. You can also see that the properties used on the custom component wrapped in
animatedcorresponds to props on adivelement, enablingreact-springto do exactly what we want (the children of theAnimatedHomeContentis a special prop in React namedprops.childrenwhichreact-springknows how to deal with).In the sandbox is also a bad example where other property names are used.
To get a correct behaviour from this version, React has to process the component to map the input props to the native DOM element props. When updating this version via the api,
react-springdoes not rerender the component (since it can take a ref) and instead sets the updated properties on the element to which the ref is attached (inspect the element in the console to see for yourself that these props are set after updating). Since the properties are not real properties, nothing updates or animates on the component.