how to allow mailto schemes in webview flutter - flutter

I am working on Flutter webview apps using Flutter Webview plugin.
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
import 'package:url_launcher/url_launcher.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
body: SafeArea(
child : const WebView(
initialUrl: 'https://google.com',
javascriptMode: JavascriptMode.unrestricted,
),
)
)
);
}
}
However, if any links inside the opened web page is an app link, like: fb://profile, I will get net::ERR_UNKNOWN_URL_SCHEME.
In android, I found the solution is to override shouldOverrideUrlLoading as mentioned here, but what should I do in flutter?
I'm trying the solution mentioned here.
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
import 'package:url_launcher/url_launcher.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
body: SafeArea(
child : const WebView(
initialUrl: 'https://google.com',
javascriptMode: JavascriptMode.unrestricted,
navigationDelegate: (NavigationRequest request) {
if (request.url.contains("mailto:")) {
launch(request.url);
return NavigationDecision.navigate;
}
},
),
)
)
);
}
}
But it is throwing errors like
Error: Not a constant expression.
if (request.url.contains("mailto:")) {

You can copy paste run full code below
Step 1: You can remove const keyword from const WebView
Step 2: You can use NavigationDecision.prevent
working demo
full code
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
import 'package:url_launcher/url_launcher.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
body: SafeArea(
child: WebView(
initialUrl:
'https://google.com', //'''https://www.scottseverance.us/mailto.html',
javascriptMode: JavascriptMode.unrestricted,
navigationDelegate: (NavigationRequest request) {
print(request.url);
if (request.url.contains("mailto:")) {
launch(request.url);
return NavigationDecision.prevent;
} else {
return NavigationDecision.navigate;
}
},
),
)));
}
}

Related

WebView on Flutter

When trying to run the below code, we got the error
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() {
runApp(
const MaterialApp(
home: WebViewApp(),
),
);
}
class WebViewApp extends StatefulWidget {
const WebViewApp({super.key});
#override
State<WebViewApp> createState() => _WebViewAppState();
}
class _WebViewAppState extends State<WebViewApp> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Flutter WebView'),
),
body: const WebView(
initialUrl: 'https://flutter.dev',
),
);
}
}
In import 'package:webview_flutter/webview_flutter.dart';
we got the error:
Target of URI doesn't exist: 'package:webview_flutter/webview_flutter.dart'.
Try creating the file referenced by the URI, or try using a URI for a file that does exist.

Flutter app crash with appbunddle but works with apk

Everything's working fine with the apk but when deploy on the playstore I had to create an appbundle (.aab), I can download the app from the playstore but it crash when I try to open it
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
body: WebViewLoad()
)
);
}
}
class WebViewLoad extends StatefulWidget {
WebViewLoadUI createState() => WebViewLoadUI();
}
class WebViewLoadUI extends State<WebViewLoad>{
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
toolbarHeight: 0,
),
body: WebView(
initialUrl: 'https://www.google.fr',
javascriptMode: JavascriptMode.unrestricted,
)
);
}
}
I ran this command to create the appbuild
flutter build appbuild --release --no-sound-null-safety
Any idea of what it doesn't work?

Flutter webview showing blank screen

I am trying to use WebView() on my flutter app. After I wrote the code there are not any errors, however, when running the debug mode on my simulator the page is blank. The AppBar is there and the text is on it also, but the body is a blank screen.
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
class Audio extends StatefulWidget {
#override
_AudioState createState() => _AudioState();
}
class _AudioState extends State<Audio> {
#override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Audio"),
),
body: WebView(
key: UniqueKey(),
initialUrl: "http://google.com",
javascriptMode: JavascriptMode.unrestricted
),
);
}
}
This is pretty much an intended behavior. It seems that the initialUrl you've provided is an insecure HTTP connection.
The documentation "Insecure HTTP connections are disabled by default on iOS and Android" explains everything about this:
Starting with Android API
28
and iOS
9,
these platforms disable insecure HTTP connections by default.
With this change Flutter also disables insecure connections on mobile
platforms. Other platforms (desktop, web, etc) are not affected.
You can override this behavior by following the platform-specific
guidelines to define a domain-specific network policy. See the
migration guide below for details.
Much like the platforms, the application can still open insecure
socket connections. Flutter does not enforce any policy at socket
level; you would be responsible for securing the connection.
Here are the sample scenarios:
Scenario 1:
Using "http://google.com"
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() {
runApp(Audio());
}
class Audio extends StatefulWidget {
#override
_AudioState createState() => _AudioState();
}
class _AudioState extends State<Audio> {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text("Audio"),
),
body: WebView(
key: UniqueKey(),
initialUrl: "http://google.com",
javascriptMode: JavascriptMode.unrestricted),
),
);
}
}
Scenario 2:
Using "google.com"
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() {
runApp(Audio());
}
class Audio extends StatefulWidget {
#override
_AudioState createState() => _AudioState();
}
class _AudioState extends State<Audio> {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text("Audio"),
),
body: WebView(
key: UniqueKey(),
initialUrl: "google.com",
javascriptMode: JavascriptMode.unrestricted),
),
);
}
}
Scenario 3:
Using "https://www.google.com/"
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() {
runApp(Audio());
}
class Audio extends StatefulWidget {
#override
_AudioState createState() => _AudioState();
}
class _AudioState extends State<Audio> {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text("Audio"),
),
body: WebView(
key: UniqueKey(),
initialUrl: "https://www.google.com/",
javascriptMode: JavascriptMode.unrestricted),
),
);
}
}

Flutter webview failed to fit webpage with screen

i'm using webview_flutter: ^0.3.14+1.
Webview can't load web page https://m.bilibili.com/video/av57346110.html correctly. The web page is oversized
But if I open it with chrome, the web page fits screen correctly.
And I don't understand the difference between web browser and flutter webview.
Here's minimal codes to reproduce:
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() => runApp(new MyApp());
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => new _MyAppState();
}
class _MyAppState extends State<MyApp> {
#override
Widget build(BuildContext context) {
return new MaterialApp(
home: new Scaffold(
appBar: new AppBar(),
body: Container(
child: WebView(
initialUrl: "https://m.bilibili.com/video/av57346110.html",
javascriptMode: JavascriptMode.unrestricted,
navigationDelegate: (NavigationRequest request) {
print("Loading... ${request.url}");
if(request.url.startsWith("http")) {
return NavigationDecision.navigate;
} else {
return NavigationDecision.prevent;
}
},
),
),
),
);
}
}
I implement this with same plugin 'webview_flutter' and it is working just fine.
Here is my code
WebView(
initialUrl: 'https://m.bilibili.com/video/av57346110.html',
javascriptMode: JavascriptMode.unrestricted,
allowsInlineMediaPlayback: true,
)

WebView can not load two different urls in flutter?

I print the url message at the first line in build method. And here, the url is right, but the webView has no effect.
I use the webview_flutter lib, and the version is 0.3.13;
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() => runApp(WebPage());
class WebPage extends StatefulWidget {
#override
State<StatefulWidget> createState() {
return _WebPageState();
}
}
class _WebPageState extends State<WebPage> {
String url = "https://flutter.dev/";
void _changeUrl() {
setState(() {
this.url = "https://github.com/flutter/flutter";
});
}
#override
Widget build(BuildContext context) {
print("url:" + url);
return MaterialApp(
theme: ThemeData(primarySwatch: Colors.blue),
home: Scaffold(
appBar: AppBar(
title: Text("WebPage"),
),
body: WebView(
initialUrl: url,
javascriptMode: JavascriptMode.unrestricted,
),
floatingActionButton: FloatingActionButton(
onPressed: _changeUrl,
child: Icon(Icons.replay),
),
));
}
}
I excepted the webView load the second url, but it not.
you need to use web-view controller class methods like this
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:webview_flutter/webview_flutter.dart';
void main() => runApp(WebPage());
class WebPage extends StatefulWidget {
#override
State<StatefulWidget> createState() {
return _WebPageState();
}
}
class _WebPageState extends State<WebPage> {
WebViewController controller;
var url = "https://flutter.dev/";
changeUrl() {
setState(() {
url = "https://github.com/flutter/flutter";
controller.loadUrl(url);
});
}
#override
Widget build(BuildContext context) {
print("url:" + url);
return MaterialApp(
theme: ThemeData(primarySwatch: Colors.blue),
home: Scaffold(
appBar: AppBar(
title: Text("WebPage"),
),
body: WebView(
// key: _key,
javascriptMode: JavascriptMode.unrestricted,
initialUrl: url,
onWebViewCreated: (WebViewController webViewController) {
controller = webViewController;
}),
floatingActionButton: FloatingActionButton(
onPressed: () {
changeUrl();
},
child: Icon(Icons.replay),
),
));
}
}
more methods to controller could be found here flutter web-view class methods