react-native webview doesn't appear - react-native

For some reason, my react-native webview doesn't show up at all. Nothing shows up after my text field. Here's my code
import React, { Component } from 'react';
import {
View,
Text,
WebView,
} from 'react-native';
export default class Home extends Component {
render() {
return (
<View style={{flexDirection:'column'}}>
<Text>Show webview</Text>
<WebView source={{html:"<html><body style='color:red'>Hello<br/>This is a test</body></html>"}} style={{width:200,height:200,backgroundColor:'blue',marginTop:20}} />
</View>
);
}
}
What am I doing wrong?

Add flex: 1 to your <View /> component.
<View style={{flex: 1, flexDirection:'column'}}>
<Text>Show webview</Text>
<WebView source={{html:"<html><body style='color:red'>Hello<br/>This is a test</body></html>"}} style={{width:200,height:200,backgroundColor:'blue',marginTop:20}} />
</View>
Here's a demo

According to the ReactNative docs as of (Nov 2019) they say this:
Warning Please use thereact-native-community/react-native-webviewfork of this component instead. To reduce the surface area of React Native, <WebView/> is going to be removed from the React Native core. For more information, please read The Slimmening proposal.
I wasn't able to get the ReactNative <WebView/> to work at all in my Expo app. So switching to the react-native-community/react-native-webview <WebView/> component worked for me. I hope that helps!

Try out this:
import { WebView } from 'react-native-webview';
export default AppWebview = () => (
<View style={styles.container}>
<WebView
source={{uri: 'https://www.youtube.com/embed/MhkGQAoc7bc'}}
style={styles.video}
/>
<WebView
source={{uri: 'https://www.youtube.com/embed/PGUMRVowdv8'}}
style={styles.video}
/>
</View>
);
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: 'center',
justifyContent: 'space-between',
},
video: {
marginTop: 20,
maxHeight: 200,
width: 320,
flex: 1
}
});

Related

How to allow popup in reactnative web view

In my app,
I need to allow popups in the web view itself.
now its try to redirect to the native browser when the popup comes.
I'm using (https://www.npmjs.com/package/react-native-webview) for web view.
current my code like this.
import React from 'react';
import { StyleSheet, Text, View } from 'react-native';
import { WebView } from 'react-native-webview';
const URL="https://google.com";
export default function App() {
return (
<View style={styles.container}>
<View style={{width:'100%',height:'100%'}}>
<WebView
source={{ uri: URL }}
/>
</View>
<StatusBar style="auto" />
</View>
);
}
const styles = StyleSheet.create({
container: {
marginTop: 28,
flex: 1,
backgroundColor: '#000',
alignItems: 'center',
justifyContent: 'center',
},
});
Is there any way to enable popups?
appreciate your help. thank you.
javaScriptCanOpenWindowsAutomatically,
A Boolean value indicates whether JavaScript can open windows without user interaction. The default value is false.
You can set it as true. Then popups will allow.
<WebView
javaScriptCanOpenWindowsAutomatically=true,
source={{ uri: URL }}
/>

react-native-webview why is the goBack() method not working?

I have a simple React Native project in Expo, it launches a website using react-native-webview.
Here is the source code:
import React from "react";
import { StyleSheet, View, SafeAreaView } from "react-native";
import { AntDesign } from "#expo/vector-icons";
import { WebView } from "react-native-webview";
export default function App() {
const goback = () => {
WebView.goBack();
};
return (
<SafeAreaView>
<WebView source={{ uri: "https://google.co.uk" }} />
<View style={styles.navbar}>
<View style={styles.forward}>
<AntDesign name="right" size={25} color="grey" />
</View>
<View style={styles.back}>
<AntDesign name="left" size={25} color="grey" onPress={goback} />
</View>
</View>
</SafeAreaView>
);
}
const styles = StyleSheet.create({
navbar: {
height: 40,
width: "100%",
flexDirection: "row-reverse",
paddingTop: 6,
backgroundColor: "#fefefe",
borderTopColor: "grey",
borderTopWidth: 1,
},
back: {
width: 50,
height: 50,
marginRight: 10,
},
forward: {
width: 50,
height: 50,
},
});
The WebView component loads the website fine (google.co.uk) but I can not get the navigation to work. I simply want to create a back button, that allows the user to navigate back to other pages they have viewed in the WebView, and forward if they have gone back and want to go forward.
For now I am trying to get the back button working. I load the app, then navigate to a different page on the WebView. When the back button is pressed, the following error is generated:
TypeError: _reactNativeWebview.WebView.goBack is not a function (In
'_reactNativeWebview.WebView.goBack()','_reactNativeWebview.WebView.goBack'
is undefined)
According to the doc's the goBack() method exists:
goBack()
I found this but it is implementing a class based component so I couldn't easily map the suggestions into my functional component, and further, I think that solution is overkill as they are intercepting the navigation, I believe what I am trying to achieve should be simpler, but I can't get the basic navigation to work on the WebView (i.e. go back and forward to previously viewed pages).
Everything mentioned by you is correct Gary. The only thing that you need to change is the way how goBack function is called. goBack is not a component's direct function rather you need to pass on a reference to the WebView component to get this function. In your case you can change your component as below to get this working:-
import React, { useRef } from "react";
import { StyleSheet, View, SafeAreaView } from "react-native";
import { AntDesign } from "#expo/vector-icons";
import { WebView } from "react-native-webview";
export default function App() {
const webViewRef = useRef(null)
const goback = () => {
webViewRef.current.goBack();
};
return (
<SafeAreaView>
<WebView ref={webViewRef} source={{ uri: "https://google.co.uk" }} />
<View style={styles.navbar}>
<View style={styles.forward}>
<AntDesign name="right" size={25} color="grey" />
</View>
<View style={styles.back}>
<AntDesign name="left" size={25} color="grey" onPress={goback} />
</View>
</View>
</SafeAreaView>
);
}
const styles = StyleSheet.create({
navbar: {
height: 40,
width: "100%",
flexDirection: "row-reverse",
paddingTop: 6,
backgroundColor: "#fefefe",
borderTopColor: "grey",
borderTopWidth: 1,
},
back: {
width: 50,
height: 50,
marginRight: 10,
},
forward: {
width: 50,
height: 50,
},
});
This refernce will help you in calling any reference functions mentioned in the documentation of webview module. Enjoy!
also you can see different usage of webview in this package. https://github.com/ilkerkesici/react-native-beauty-webview

Hide component under a ScrollView when keyboard is open on Android in React Native?

My layout is a ScrollView above a footer. When the keyboard isnt open I need the footer to always be visible on the screen:
https://snack.expo.io/#jamesweblondon/privileged-cashew1
export default function App() {
return (
<SafeAreaView style={styles.container}>
<ScrollView style={styles.content}>
<TextInput style={styles.input} value={"Text Input"} />
</ScrollView>
<View style={styles.footer}>
<Text>Footer</Text>
</View>
</SafeAreaView>
);
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
content: {
backgroundColor: "tomato",
padding: 50,
},
input: {
backgroundColor: "grey",
padding: 50,
},
footer: {
backgroundColor: "green",
padding: 50,
},
});
This works great on iOS. When the keyboard opens you no longer see the footer:
However on Android the footer moves above the keyboard:
Can I stop this behaviour? Ive tried using Keyboard events however keyboardWillShow and keyboardWillHide arn't supported on Android. If I use keyboardDidShow and keyboardDidHide then the delay means the footer is visible as the keyboard animates up and then disappears, which feels jerky and unpleasant.
export default function App() {
const [keyboardIsOpen, setKeyboardIsOpen] = React.useState(false);
Keyboard.addListener("keyboardDidShow", () => {
setKeyboardIsOpen(true);
});
Keyboard.addListener("keyboardDidHide", () => {
setKeyboardIsOpen(false);
});
return (
<SafeAreaView style={styles.container}>
<ScrollView style={styles.content}>
<TextInput style={styles.input} value={"Text Input"} />
</ScrollView>
{!keyboardIsOpen && (
<View style={styles.footer}>
<Text>Footer</Text>
</View>
)}
</SafeAreaView>
);
}
I also couldn't get it working with the KeyboardAvoidingView. I'm using Expo.
android:windowSoftInputMode already available in EXPO
here is demo: https://snack.expo.io/#nomi9995/01d462
you should give full height to container instead of flex:1
Code:
import React from "react";
import {
StyleSheet,
Text,
View,
ScrollView,
SafeAreaView,
TextInput,
Dimensions
} from "react-native";
const height = Dimensions.get("window").height;
export default function App() {
return (
<SafeAreaView style={styles.container}>
<ScrollView style={styles.content}>
<View style={{flex:1}}>
<TextInput style={styles.input} value={"Text Input"} />
</View>
</ScrollView>
<View style={styles.footer}>
<Text>Footer</Text>
</View>
</SafeAreaView>
);
}
const styles = StyleSheet.create({
container: {
height: height
},
content: {
backgroundColor: "tomato",
padding: 50,
},
input: {
backgroundColor: "grey",
padding: 50,
},
footer: {
backgroundColor: "green",
padding: 50
},
});
I found this ready npm package. You can install and use it.
Installation from https://www.npmjs.com/package/react-native-hide-with-keyboard
You just need to cover the component you want to hide, with <HideWithKeyboard>, for example,
<HideWithKeyboard>
<Footer>
<FooterTab>
...More Content Here...
</FooterTab>
</Footer>
</HideWithKeyboard>
To handle this at the code level you can set the footer display property to absolute and bottom:0.
If you want to keep the footer at the bottom specially for the android you can set windowSoftInputMode in the manifest file. Inside the <application> and under <activity> block add the following property.
android:windowSoftInputMode="adjustResize"
then rebuild the app for android, if that still does not work you can also set that to
android:windowSoftInputMode="adjustPan"
It works for me of React-Native version: 0.61.2
android:windowSoftInputMode="adjustPan"

WebView is empty in React Native

Problem. The WebView is empty in React Native. However, the link works.
The code :
import React from 'react';
import { StyleSheet, View, WebView } from 'react-native';
import { Constants } from 'expo';
export default class App extends React.Component {
render() {
return (
<View>
<View style={styles.statusBar} />
<WebView
source={{uri: 'https://lapommeculturelle.com'}}
renderError={() => alert('Merci de vérifier votre connexion Internet - Internet non disponible')}
/>
</View>
);
}
}
const styles = StyleSheet.create({
statusBar: {
backgroundColor: "#1D3B57",
height: Constants.statusBarHeight,
}
});
For this project, I used Expo XDE. Thanks.
I believe you need to be specifying the height and width of the webview, as well as specifying the flex for the wrapping view.
Try this:
<View style={{flex:1}}>
<View style={styles.statusBar} />
<WebView
style={{height: 300, width: 300}}
source={{uri: 'https://lapommeculturelle.com'}}
renderError={() => alert('Merci de vérifier votre connexion Internet', 'Internet non disponible')}
/>
</View>
At the bare minimum, you need a style for the View that wraps the rest of them.
I'd recommend <View style={{flex: 1}}> just to get you started.
In an ideal world, you'd make that a style associated with your container and be pulling it from your StyleSheet:
import React from 'react';
import { StyleSheet, Text, View, WebView, ActivityIndicator } from 'react-native';
import { Constants } from 'expo';
export default class App extends React.Component {
render() {
return (
<View style={styles.container}>
<View style={styles.statusBar} />
<WebView
source={{uri: 'https://lapommeculturelle.com'}}
renderError={() => alert('Merci de vérifier votre connexion Internet', 'Internet non disponible')}
/>
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
},
statusBar: {
backgroundColor: "#1D3B57",
height: Constants.statusBarHeight,
}
});
My fix for iOS, for some reason, is this style:
<WebView
// fixes warning when page has an iframe (about:srcdoc)
originWhitelist={['http://*', 'https://*', 'about:srcdoc']}
renderLoading={this._renderLoadingWebView}
scrollEnabled
source={{ uri }}
style={{ borderWidth: 1, borderColor: 'transparent' }}
/>
react-native-webview 7.5.2

RN: Center spinner using flexbox?

I am trying to get as spinner centered vertically and horizontally (iOS and Android - currently testing on iOS). Here is my JSX
<View>
<Spinner/>
</View>
of course, Spinner is a custom component which is simply this that contains a ActivityIndicator
const Spinner = ({size}) => {
return (
<View style={styles.spinnerStyle}>
<ActivityIndicator/>
</View>
);
};
const styles = {
spinnerStyle: {
flex: 1,
justifyContent : 'center',
alignItems: 'center'
}
}
export {Spinner}
The spinner works but its always at the top of the screen, the spinner contains a VIEW and also the flex items that I think should work. But it doesn't
I also tried add some styles of the the first VIEW that holds the custom component ie..
<View style={....}>
<Spinner/>
</View>
But no joy.
I think you are almost there! The only thing that is missing is to set flex: 1 to the <View> around the <Spinner /> component.
I did create an example on Expo's Sketch. Feel free to have a look at it. Try removing the flex: 1 and add a background color to see how it behaves. Hope it helps!
import React, { Component } from 'react';
import { View, StyleSheet, ActivityIndicator } from 'react-native';
const spinnerStyles = StyleSheet.create({
spinnerStyle: {
flex: 1,
justifyContent: 'center',
alignItems: 'center',
},
});
class Spinner extends Component {
render() {
return (
<View style={spinnerStyles.spinnerStyle}>
<ActivityIndicator size="small" />
</View>
);
}
}
export default class App extends Component {
render() {
return (
<View style={styles.container}>
<Spinner />
</View>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
// backgroundColor: '#4286f4',
},
});