main.dart 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278
  1. import 'dart:async';
  2. import 'package:flutter/material.dart';
  3. import 'package:flutter_webview_plugin/flutter_webview_plugin.dart';
  4. const kAndroidUserAgent =
  5. 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/62.0.3202.94 Mobile Safari/537.36';
  6. String selectedUrl = 'https://flutter.io';
  7. void main() => runApp(MyApp());
  8. class MyApp extends StatelessWidget {
  9. final flutterWebViewPlugin = FlutterWebviewPlugin();
  10. @override
  11. Widget build(BuildContext context) {
  12. return MaterialApp(
  13. title: 'Flutter WebView Demo',
  14. theme: ThemeData(
  15. primarySwatch: Colors.blue,
  16. ),
  17. routes: {
  18. '/': (_) => const MyHomePage(title: 'Flutter WebView Demo'),
  19. '/widget': (_) {
  20. return WebviewScaffold(
  21. url: selectedUrl,
  22. appBar: AppBar(
  23. title: const Text('Widget WebView'),
  24. ),
  25. withZoom: true,
  26. withLocalStorage: true,
  27. hidden: true,
  28. initialChild: Container(
  29. color: Colors.redAccent,
  30. child: const Center(
  31. child: Text('Waiting.....'),
  32. ),
  33. ),
  34. bottomNavigationBar: BottomAppBar(
  35. child: Row(
  36. children: <Widget>[
  37. IconButton(
  38. icon: const Icon(Icons.arrow_back_ios),
  39. onPressed: () {
  40. flutterWebViewPlugin.goBack();
  41. },
  42. ),
  43. IconButton(
  44. icon: const Icon(Icons.arrow_forward_ios),
  45. onPressed: () {
  46. flutterWebViewPlugin.goForward();
  47. },
  48. ),
  49. IconButton(
  50. icon: const Icon(Icons.autorenew),
  51. onPressed: () {
  52. flutterWebViewPlugin.reload();
  53. },
  54. ),
  55. ],
  56. ),
  57. ),
  58. );
  59. },
  60. },
  61. );
  62. }
  63. }
  64. class MyHomePage extends StatefulWidget {
  65. const MyHomePage({Key key, this.title}) : super(key: key);
  66. final String title;
  67. @override
  68. _MyHomePageState createState() => _MyHomePageState();
  69. }
  70. class _MyHomePageState extends State<MyHomePage> {
  71. // Instance of WebView plugin
  72. final flutterWebViewPlugin = FlutterWebviewPlugin();
  73. // On destroy stream
  74. StreamSubscription _onDestroy;
  75. // On urlChanged stream
  76. StreamSubscription<String> _onUrlChanged;
  77. // On urlChanged stream
  78. StreamSubscription<WebViewStateChanged> _onStateChanged;
  79. StreamSubscription<WebViewHttpError> _onHttpError;
  80. StreamSubscription<double> _onProgressChanged;
  81. StreamSubscription<double> _onScrollYChanged;
  82. StreamSubscription<double> _onScrollXChanged;
  83. final _urlCtrl = TextEditingController(text: selectedUrl);
  84. final _codeCtrl = TextEditingController(text: 'window.navigator.userAgent');
  85. final _scaffoldKey = GlobalKey<ScaffoldState>();
  86. final _history = [];
  87. @override
  88. void initState() {
  89. super.initState();
  90. flutterWebViewPlugin.close();
  91. _urlCtrl.addListener(() {
  92. selectedUrl = _urlCtrl.text;
  93. });
  94. // Add a listener to on destroy WebView, so you can make came actions.
  95. _onDestroy = flutterWebViewPlugin.onDestroy.listen((_) {
  96. if (mounted) {
  97. // Actions like show a info toast.
  98. _scaffoldKey.currentState.showSnackBar(const SnackBar(content: const Text('Webview Destroyed')));
  99. }
  100. });
  101. // Add a listener to on url changed
  102. _onUrlChanged = flutterWebViewPlugin.onUrlChanged.listen((String url) {
  103. if (mounted) {
  104. setState(() {
  105. _history.add('onUrlChanged: $url');
  106. });
  107. }
  108. });
  109. _onProgressChanged = flutterWebViewPlugin.onProgressChanged.listen((double progress) {
  110. if (mounted) {
  111. setState(() {
  112. _history.add("onProgressChanged: $progress");
  113. });
  114. }
  115. });
  116. _onScrollYChanged = flutterWebViewPlugin.onScrollYChanged.listen((double y) {
  117. if (mounted) {
  118. setState(() {
  119. _history.add('Scroll in Y Direction: $y');
  120. });
  121. }
  122. });
  123. _onScrollXChanged = flutterWebViewPlugin.onScrollXChanged.listen((double x) {
  124. if (mounted) {
  125. setState(() {
  126. _history.add('Scroll in X Direction: $x');
  127. });
  128. }
  129. });
  130. _onStateChanged = flutterWebViewPlugin.onStateChanged.listen((WebViewStateChanged state) {
  131. if (mounted) {
  132. setState(() {
  133. _history.add('onStateChanged: ${state.type} ${state.url}');
  134. });
  135. }
  136. });
  137. _onHttpError = flutterWebViewPlugin.onHttpError.listen((WebViewHttpError error) {
  138. if (mounted) {
  139. setState(() {
  140. _history.add('onHttpError: ${error.code} ${error.url}');
  141. });
  142. }
  143. });
  144. }
  145. @override
  146. void dispose() {
  147. // Every listener should be canceled, the same should be done with this stream.
  148. _onDestroy.cancel();
  149. _onUrlChanged.cancel();
  150. _onStateChanged.cancel();
  151. _onHttpError.cancel();
  152. _onProgressChanged.cancel();
  153. _onScrollXChanged.cancel();
  154. _onScrollYChanged.cancel();
  155. flutterWebViewPlugin.dispose();
  156. super.dispose();
  157. }
  158. @override
  159. Widget build(BuildContext context) {
  160. return Scaffold(
  161. key: _scaffoldKey,
  162. appBar: AppBar(
  163. title: const Text('Plugin example app'),
  164. ),
  165. body: SingleChildScrollView(
  166. child: Column(
  167. mainAxisAlignment: MainAxisAlignment.center,
  168. children: [
  169. Container(
  170. padding: const EdgeInsets.all(24.0),
  171. child: TextField(controller: _urlCtrl),
  172. ),
  173. RaisedButton(
  174. onPressed: () {
  175. flutterWebViewPlugin.launch(
  176. selectedUrl,
  177. rect: Rect.fromLTWH(0.0, 0.0, MediaQuery.of(context).size.width, 300.0),
  178. userAgent: kAndroidUserAgent,
  179. invalidUrlRegex: r'^(https).+(twitter)', // prevent redirecting to twitter when user click on its icon in flutter website
  180. );
  181. },
  182. child: const Text('Open Webview (rect)'),
  183. ),
  184. RaisedButton(
  185. onPressed: () {
  186. flutterWebViewPlugin.launch(selectedUrl, hidden: true);
  187. },
  188. child: const Text('Open "hidden" Webview'),
  189. ),
  190. RaisedButton(
  191. onPressed: () {
  192. flutterWebViewPlugin.launch(selectedUrl);
  193. },
  194. child: const Text('Open Fullscreen Webview'),
  195. ),
  196. RaisedButton(
  197. onPressed: () {
  198. Navigator.of(context).pushNamed('/widget');
  199. },
  200. child: const Text('Open widget webview'),
  201. ),
  202. Container(
  203. padding: const EdgeInsets.all(24.0),
  204. child: TextField(controller: _codeCtrl),
  205. ),
  206. RaisedButton(
  207. onPressed: () {
  208. final future = flutterWebViewPlugin.evalJavascript(_codeCtrl.text);
  209. future.then((String result) {
  210. setState(() {
  211. _history.add('eval: $result');
  212. });
  213. });
  214. },
  215. child: const Text('Eval some javascript'),
  216. ),
  217. RaisedButton(
  218. onPressed: () {
  219. setState(() {
  220. _history.clear();
  221. });
  222. flutterWebViewPlugin.close();
  223. },
  224. child: const Text('Close'),
  225. ),
  226. RaisedButton(
  227. onPressed: () {
  228. flutterWebViewPlugin.getCookies().then((m) {
  229. setState(() {
  230. _history.add('cookies: $m');
  231. });
  232. });
  233. },
  234. child: const Text('Cookies'),
  235. ),
  236. Text(_history.join('\n'))
  237. ],
  238. ),
  239. ),
  240. );
  241. }
  242. }