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

Performance Issue: Avoidable Re-renders in the Component Tree (React Motion) #4431

Closed
joncursi opened this issue Jun 5, 2016 · 6 comments
Closed

Comments

@joncursi
Copy link

joncursi commented Jun 5, 2016

I'm working on an app that leverages MUI for various UI components, such as the top-bar, icons, and buttons. The default components seem to render and update at a performant speed, unnoticeable to the naked eye. But now I have the desire to animate all the things with React motion to improve app UX, and I'm running into highly noticeable performance issues.

I.e., in trying to tween the position of a Paper component that contains a list:

      <Motion
        style={{
          x: spring(open ? 0 : -100, presets.noWobble),
        }}
      >
        {interpolatingStyle => (
          <div>
            <Paper
              className="bottom-sheet"
              style={{
                bottom: `${interpolatingStyle.x}%`,
              }}
            >
            ...
            // a list with list items, etc.
            ...
            </Paper>
          </div>
        )}
      </Motion>

The paper janks across the screen very slowly. After scratching my head over this for a while, I opted to install the Why DId You Update? React package to investigate (https://github.com/garbles/why-did-you-update), and noticed that MUI components are re-rendering deep within the Paper component, tens of thousands of times:

screen shot 2016-06-05 at 10 04 34 am

In searching this repo, I came across a few issues previously existed for avoidable re-renders, but they were closed. Does anyone experiencing these issues have any tips for how to handle this? Thanks!

@joncursi joncursi changed the title Performance Issue: Avoidable Re-renders in the Component Tree Performance Issue: Avoidable Re-renders in the Component Tree (React Motion) Jun 5, 2016
@joncursi
Copy link
Author

joncursi commented Jun 5, 2016

Ah, after changing my search query to "performance" instead of "re-render", I found the gold mine of open threads for similar performance issues (pretty much all revolving around shouldComponentUpdate). Not sure how many community members are trying to extend MUI default animations with more advanced animations via libs like React Motion, but from my experiences above, MUI and JavaScript animation currently do not mix well.

Per #2832 (comment), I'm going to try out recompose to see if wrapping components can prevent the avoidable re-renders and enable usage of React Motion.

@zikangyao
Copy link

@joncursi Have you solved the issue yet? I came across almost the same issue. I have a list of checkboxes that is rendered inside a panel and then I use react-motion to animate the panel. But the animation is not smooth. And I also tried recompose. It didn't work for me.

@joncursi
Copy link
Author

@zikanguao unfortunately not yet. I don't know there's much that can be done from the outside in, it seems to be a library issue from my estimation

@zikangyao
Copy link

@joncursi I gave up and switched over to css transition to animate the panel, which is way smoother than using React-motion. Even though it's not their fault. XD

@oliviertassinari
Copy link
Member

oliviertassinari commented Sep 17, 2016

From your example, it seems that you just want to animate the bottom property.
Why not animating a wrapper instead of the <Paper /> component and pruning the rendering with another pure wrapper?

Yes, our styling approach makes re-rendering costly (we don't cache the style), but that doesn't mean you have to waste CPU cycles with work you should avoid in the first place.
I hope it helps.

@oliviertassinari
Copy link
Member

oliviertassinari commented Feb 12, 2017

I'm closing this issue as I have already proposed a solution.

Besides:

  • the next branch makes rerendering more efficient.
  • I would avoid using react-motion. For instance, I have been refactoring react-swipeable-views to remove that dependency. The implementation is simpler and more performant using simple CSS transition. Consider using data-biding with animated if you need complex animations.

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

No branches or pull requests

3 participants