Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Screen blinks once when rendering a WebView on Android

I use react-native-webview to render a WebView in my React Native app. All works fine on iOS, but on Android, when the WebView is rendered, my screen blinks (black, then white, then display the web page).

According to this answer, I tried to add android:hardwareAccelerated="false" in the <application> tag of my AndroidManifest.xml, but that doesn't solve my problem. (Also, it hides all shadow effects created with elevation style property)

<DelayedComponent key={key} style={{ height: 200, ...style }}>
  <WebView
    style={{ alignSelf: "stretch" }}
    source={{ uri: /* a youtube url */ }}
    renderLoading={() => <Loading />}
    startInLoadingState={true}
    scrollEnabled={false}
  />
</DelayedComponent>

<DelayedComponent> is just a test component that renders the <WebView> after one second (using a basic setTimeout).

export class DelayedComponent extends React.PureComponent<
  { delay?: number; renderLoading?: any } & ViewProps,
  { show: boolean }
> {
  constructor(props) {
    super(props);
    this.state = { show: false };
  }

  public render() {
    console.log("RENDER DELAYED", this.state);
    const loadingComp = this.props.renderLoading || (
      <Text>Just wait a second...</Text>
    );
    const { delay, renderLoading, ...forwardProps } = this.props;
    return (
      <View {...forwardProps}>
        {this.state.show ? this.props.children : loadingComp}
      </View>
    );
  }

  public async componentDidMount() {
    const delay = this.props.delay || 1000;
    await (() => new Promise(resolve => setTimeout(resolve, delay)))();
    this.setState({ show: true });
  }
}

The screen blinks one second after the <DelayedComponent> renders, when the <WebView> is displayed.

Here is a link to a video showing whan happens : https://drive.google.com/open?id=1dX7ofANFI9oR2DFCtCRgI3_0DcsOD12B

I expect that the screen doesn't blink when the WebView is rendered, like it happens on iOS devices.

Thank you for your help !

like image 713
Thaledric Avatar asked Jan 10 '19 15:01

Thaledric


3 Answers

Just set opacity to WebView style to 0.99.

<WebView style={{ opacity: 0.99 }} />

It's probably related with: Rendering webview on android device overlaps previous siblings from same parent

Edit: Wrapping WebView component in View with overflow: 'hidden': <View style={{flex: 1, overflow: 'hidden'}}><WebView ... /></View> also works but it can result in occasionally application crashes for some reason.

like image 117
Lukáš Pikora Avatar answered Nov 11 '22 16:11

Lukáš Pikora


i got in Flutter avoiding the resize when keyboard appear, so i add in scafold widget:

  resizeToAvoidBottomInset: false,

If you are using a different framework, try to avoid the resize of the keyboard.

Good luck and happy coding!

like image 39
Pedro Molina Avatar answered Nov 11 '22 17:11

Pedro Molina


This trick worked for me, at least the user don't see the blink between those 0.5 seconds

<WebView
    onLoadStart={event => {
      setTimeout(() => {
        this.setState({ webViewHasLoadedContent: true })
      }, 500)
    }}
    style={{
      opacity: this.state.webViewHasLoadedContent ? 1 : 0,
    }}
  />
like image 37
Agustin Jiménez Avatar answered Nov 11 '22 16:11

Agustin Jiménez