stencil icon indicating copy to clipboard operation
stencil copied to clipboard

Flickering when using conditional rendering

Open m00k opened this issue 5 years ago • 10 comments

Stencil version:

 @stencil/[email protected]

I'm submitting a:

[x] bug report [ ] feature request [ ] support request => Please do not submit support requests here, use one of these channels: https://stencil-worldwide.herokuapp.com/ or https://forum.ionicframework.com/

Current behavior:

There is noticable flickering when using conditional rendering even with the simplest stencil component I could come up with.

Expected behavior:

No flickering.

Steps to reproduce:

I created a simple repo to reproduce the error https://github.com/m00k/stencil-render-performance. Use the buttons to switch between components.

Related code:

{this.showNo === 0 && <app-cmp1 class='cmp'></app-cmp1>}
{this.showNo === 1 && <app-cmp2 class='cmp'></app-cmp2>}
{this.showNo === 2 && <app-cmp3 class='cmp'></app-cmp3>}
{this.showNo === 3 && <app-cmp1 class='cmp'></app-cmp1>}

Cmp1 CmpEmpty Cmp2

Other information:

Tested with Chrome Version 76.0.3809.132 (Official Build) (64-bit) on Linux Ubuntu 18.10
Might be duplicate of https://github.com/ionic-team/stencil/issues/1703

m00k avatar Aug 27 '19 07:08 m00k

Using functional components there is no flickering (https://github.com/m00k/stencil-render-performance/tree/functional-components).

{this.showNo === 0 && <Cmp1/>}
{this.showNo === 1 && <Cmp2/>}
{this.showNo === 2 && <Cmp3/>}
{this.showNo === 3 && <Cmp1/>}

Unfortunately this is not always an option.

m00k avatar Sep 29 '19 09:09 m00k

You can actually see this exact same issue in action on the Ionic documentation page: Screen Recording 2019-10-22 at 11 47 AM It first updates the already mounted custom-elements that are common between the pages over two frames, and then in the last frame it hydrates the requisite custom-elements that are not present on the first page.

It seems that the vdom is able to update any components that are already mounted on the page really quickly (often within a single animation frame), but mounting any new custom elements within a vdom render always requires at least one additional animation frame to complete. This is pretty disappointing for more complex use cases because it makes dynamic UIs built using Stencil components always feel subtly janky. I'm uncertain if this is a limitation of how custom-elements mount, or if it's a limitation of how the Stencil vdom rendering implementation throttles DOM updates, or perhaps some combination of the two..

maxjustus avatar Oct 22 '19 18:10 maxjustus

I think this is a very serious bug that causes our app to look very janky and broken. If there is a way to mitigate this, this would be great. Thanks.

pixelbucket-dev avatar Nov 22 '19 00:11 pixelbucket-dev

Might be related to: https://github.com/ionic-team/stencil/issues/2148

I was able to get around the flicker by adding

extras: { initializeNextTick: false, }, to my stencil.config.ts

Here is the commit that adds this to the config.

Here is the version notes about it.

jordanranz avatar Apr 27 '20 21:04 jordanranz

@jordanranz You saved me another day of debugging Shadow DOM and Stencil. Thank you!

Gbuomprisco avatar Jun 12 '20 10:06 Gbuomprisco

For me this is still an issue and the workaround is not working. It also seems like Stencil's initializeNextTick defaults to false in the meantime.

For our company this issue makes Stencil unusable for medium-complex applications, since besides the flickering, also the components that are below move up for a split second and then move down again as soon as the conditional component finished rendering and takes up its space.

Any further input or idea how this could be fixed?

no-creative-name avatar Aug 31 '21 07:08 no-creative-name

@no-creative-name never got it to work either. checked back a couple times to see if later versions of stencil had solved this issue - but no luck. eventually moved on...

m00k avatar Aug 31 '21 08:08 m00k

I am facing this issue as well. The following code causes flicker in rendering <fd-page highlighted={this.selectedAssetId === this.page.id} .... >

I am using: "@stencil/core": "2.11.0"

amjadghazi avatar Dec 01 '21 13:12 amjadghazi

I still have UI flickering on every custom element render when in local development mode. https://github.com/wavebeem/example-stencil-task-queue

but when I use the app in a production build, it works completely fine https://determined-mccarthy-f892a2.netlify.app/

I spent a few hours today digging through the Stencil source code and making changes, but nothing could fix local development. I tried replacing nextTick and requestAnimationFrame with functions that just immediately invoked their callbacks (cb => { cb(); return 0; }) and that didn't work.

My only other thought at this point is that it might be HMR related? I haven't had the time to explore that possibility yet though.

wavebeem avatar Dec 24 '21 00:12 wavebeem

I'm bringing this back to life.

Can't find anything about this issue other than this thread.

Has there been any improvements or solutions to this? We still get a lot of flickering, enough for me to almost want to put the browser in perma throttle mode. Tried adding initializeNextTick, but as someone else said above, that already seem to be the default.

Omxz avatar Apr 30 '24 13:04 Omxz