I have a simple Flutter WebView application to display my website. The problem is, in my website I have 2 functionalities that open a new browser window.
For example, one of them is a facebook login function, when the user clicks on login with facebook, it loads the facebook login api page, when the login is done, it tells the user to go back to the other page, but as I am in a WebView, i can't go back to the other page.
Is there some way for me to open 2 WebViews on Flutter to load different pages? If not, is there any other possible solution for this problem?
The webview_flutter
plugin doesn't offer an event to manage and intercept when a new window will open, for example when you click on a link button with target="_blank"
or when window.open()
is called by JavaScript side.
So, you can use my plugin flutter_inappwebview, which is a Flutter plugin that allows you to add inline WebViews or open an in-app browser window and has a lot of events, methods, and options to control WebViews.
It implements the onCreateWindow
event, that is an event fired when the WebView requests the host application to create a new window, for example when trying to open a link with target="_blank"
or when window.open()
is called by JavaScript side.
Here is an example where I load a simple initial HTML (just for the sake of the example) that has a button <button id="login-button">LOGIN</button>
, that when it is clicked, it opens a new WebView inside an AlertDialog
. With this new WebView you can listen to URL changes through the onLoadStop
event or using the shouldOverrideUrlLoading
event or you can check and get a specific cookie after the user as logged in. You can put whatever logic in this new WebView.
Here is the code example:
import 'dart:async';
import 'package:flutter/material.dart';
import 'package:flutter_inappwebview/flutter_inappwebview.dart';
Future main() async {
WidgetsFlutterBinding.ensureInitialized();
runApp(MyApp());
}
class MyApp extends StatefulWidget {
@override
_MyAppState createState() => new _MyAppState();
}
class _MyAppState extends State<MyApp> {
@override
void initState() {
super.initState();
}
@override
void dispose() {
super.dispose();
}
@override
Widget build(BuildContext context) {
return MaterialApp(initialRoute: '/', routes: {
'/': (context) => InAppWebViewExampleScreen(),
});
}
}
class InAppWebViewExampleScreen extends StatefulWidget {
@override
_InAppWebViewExampleScreenState createState() =>
new _InAppWebViewExampleScreenState();
}
class _InAppWebViewExampleScreenState extends State<InAppWebViewExampleScreen> {
InAppWebViewController _webViewController;
CookieManager _cookieManager = CookieManager.instance();
@override
void initState() {
super.initState();
}
@override
void dispose() {
super.dispose();
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: Text("InAppWebView")),
body: Container(
child: Column(children: <Widget>[
Expanded(
child: InAppWebView(
initialData: InAppWebViewInitialData(data: """
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>InAppWebViewInitialDataTest</title>
</head>
<body>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Morbi dolor diam, interdum vitae pellentesque sit amet, scelerisque at magna. Orci varius natoque penatibus et magnis dis parturient montes, nascetur ridiculus mus.</p>
<p>Nullam vitae fringilla mauris, eu efficitur erat. Nulla aliquam ligula nec leo ornare varius. Curabitur ornare ultrices convallis.</p>
<button id="login-button">LOGIN</button>
<script>
document.querySelector('#login-button').addEventListener('click', function (event) {
window.open('https://github.com/', '_blank');
});
</script>
</body>
</html>
"""),
initialHeaders: {},
initialOptions: InAppWebViewGroupOptions(
crossPlatform: InAppWebViewOptions(
debuggingEnabled: true,
),
android:
AndroidInAppWebViewOptions(supportMultipleWindows: true)),
onWebViewCreated: (InAppWebViewController controller) {
_webViewController = controller;
},
onLoadStart: (InAppWebViewController controller, String url) {
},
onLoadStop: (InAppWebViewController controller, String url) {
},
onCreateWindow: (controller, onCreateWindowRequest) {
showDialog(
context: context,
builder: (context) {
return AlertDialog(
content: Container(
width: 700,
child: Column(children: <Widget>[
Expanded(
child: InAppWebView(
initialUrl: onCreateWindowRequest.url,
initialOptions: InAppWebViewGroupOptions(
crossPlatform: InAppWebViewOptions(
debuggingEnabled: true,
useShouldOverrideUrlLoading: true)),
onLoadStart: (InAppWebViewController controller,
String url) {},
onLoadStop: (controller, url) async {
print(url);
if (url == "myURL") {
Navigator.pop(context);
return;
}
var loggedInCookie = await _cookieManager.getCookie(url: url, name: "logged_in");
if (loggedInCookie.value == "yes") {
Navigator.pop(context);
return;
}
},
shouldOverrideUrlLoading: (controller,
shouldOverrideUrlLoadingRequest) async {
print(shouldOverrideUrlLoadingRequest.url);
if (shouldOverrideUrlLoadingRequest.url == "myURL") {
Navigator.pop(context);
}
return ShouldOverrideUrlLoadingAction.ALLOW;
},
))
])));
},
);
},
))
])));
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With