当前位置: 首页 > article >正文

flutter-web中使用js工具类

文章目录

      • 为什么要调用js
      • 1. flutter-web
        • 1. 引入js web/index.html
        • 2. 创建工具js web/CryptoEnc.js
        • 3. 创建对应的lib/js/js_interop.dart
        • 4. 由于引入的js是针对web平台的,所以引入需要做引入处理
        • 5. 使用
      • 2. Android
        • 1. 引入依赖
        • 2. index.html
        • 3. dart
        • 引用

为什么要调用js

JavaScript拥有庞大且成熟的工具生态系统

1. flutter-web

1. 引入js web/index.html
 <!-- Add the required JS libraries -->
  <script src="https://cdnjs.cloudflare.com/ajax/libs/crypto-js/4.2.0/crypto-js.min.js" integrity="sha512-a+SUDuwNzXDvz4XrIcXHuCf089/iJAoN4lmrXJg18XnduKK6YlDHNRalv4yd1N40OKI80tFidF+rqTFKGPoWFQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>
  <script src="https://cdnjs.cloudflare.com/ajax/libs/crypto-js/4.2.0/md5.min.js" integrity="sha512-ENWhXy+lET8kWcArT6ijA6HpVEALRmvzYBayGL6oFWl96exmq8Fjgxe2K6TAblHLP75Sa/a1YjHpIZRt+9hGOQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

  <!-- Register the js file where the logic is written -->
  <script src="CryptoEnc.js" type="application/javascript"></script>
2. 创建工具js web/CryptoEnc.js
function CryptoEnc() {}

CryptoEnc.prototype.encrypt = function(toEncObj){
    var toEnc = toEncObj.value;

    var encrypted = CryptoJS.MD5(toEnc);

    return encrypted;
}


CryptoEnc.prototype.testFunc = function(toEncObj2){
  var toEnc = toEncObj2.value;
    return "========bbbbtestFunc"+toEnc;
}

3. 创建对应的lib/js/js_interop.dart
// #1
()
library js_interop;

// The above two lines are required
import 'package:js/js.dart';

// #2
()
class CryptoEnc {
  external CryptoEnc();

  external String encrypt(ToEncrypt toEncrypt);
  external String testFunc(ToEncrypt2 toEncrypt2);
}

// #3
()

class ToEncrypt {
  external String get value;

  external factory ToEncrypt({String value});
}
()

class ToEncrypt2 {
  external String get value;

  external factory ToEncrypt2({String value});
}


4. 由于引入的js是针对web平台的,所以引入需要做引入处理
///encrypt.dart
class ToEncrypt {
  final String value;

  ToEncrypt({
    required this.value,
  });
}

class ToEncrypt2 {
  final String value;

  ToEncrypt2({
    required this.value,
  });
}

class CryptoEnc {
  CryptoEnc();

  String encrypt(ToEncrypt toEncrypt) {
    // We are not implementing any encryption for mobile for now.
    // This is just for demonstration.
    throw UnimplementedError();
  }
  String testFunc(ToEncrypt2 toEncrypt) {
    // We are not implementing any encryption for mobile for now.
    // This is just for demonstration.
    throw UnimplementedError();
  }
}

///export_encrypt.dart
export 'encrypt.dart' if (dart.library.js) 'js_interop.dart';
5. 使用
   var encVal = CryptoEnc().encrypt(
      ToEncrypt(
        value: "aaaaaa",
      ),
    );
    var encVal2 = CryptoEnc().testFunc(ToEncrypt2(
      value: "cccc",
    ));
    print(encVal);
    print("testFunc=$encVal2");

2. Android

1. 引入依赖
webview_flutter: ^4.4.2
2. index.html
<!DOCTYPE html>
<html>
<head>
    <title>Test js dart</title>

</head>
<body>
<script>
   function inputClick (url) {
    console.log('inputClick=>'+url);
   }
   function playUrl(url) {
    console.log('playUrl=>'+url);
   }
   function startPlay() {
     console.log('startPlay');
   }
   function postMsg() {
     console.log('postMsg');
     //向dart发送消息
     Print.postMessage('postMsg');
   }

</script>
</body>
</html>
3. dart
import 'package:flutter/material.dart';
import 'package:tvboxstudy/log_extensions.dart';
import 'package:webview_flutter/webview_flutter.dart';

class LocalHtmlWebView extends StatefulWidget {
  const LocalHtmlWebView({super.key});

  
  LocalHtmlWebViewState createState() => LocalHtmlWebViewState();
}

class LocalHtmlWebViewState extends State<LocalHtmlWebView> {
  late String localHtmlContents;
  late WebViewController controller;
  ValueNotifier<bool> isShowLoading = ValueNotifier(true);

  
  void initState() {
    super.initState();
    initController();
    loadLocalHtml();
    _registerJavascriptChannel();
  }

  void runJS(int type) {
    if (type == 1) {
      controller.runJavaScript(
        'inputClick();',
      );
    } else if (type == 2) {
      controller.runJavaScript(
        'startPlay();',
      );
    }else if (type == 3) {
      controller.runJavaScript(
        'postMsg();',
      );
    } else if (type == 4) {
      controller.runJavaScript(
        "playUrl('https://media.w3.org/2010/05/sintel/trailer.mp4');",
      );
    }
  }

  void _registerJavascriptChannel() {
    controller.addJavaScriptChannel(
      'Print',
      onMessageReceived: (JavaScriptMessage message) {
      	//收到消息做相应的处理
        print("onMessageReceived=>${message.message}");
      },
    );
  }

  void initController() {
    controller = WebViewController()
      ..setJavaScriptMode(JavaScriptMode.unrestricted)
      ..setBackgroundColor(Colors.transparent)
      ..setJavaScriptMode(JavaScriptMode.unrestricted)
      ..setNavigationDelegate(
        NavigationDelegate(
          onProgress: (int progress) {
            "progress=$progress".log();
            if (progress == 100) {
              isShowLoading.value = false;
            }
          },
          onPageStarted: (String url) {},
          onPageFinished: (String url) {
            controller
                .runJavaScriptReturningResult('document.body.scrollHeight')
                .then((value) {
                  "scrollHeight=>$value".log();
            });
          },
          onWebResourceError: (WebResourceError error) {},
          onNavigationRequest: (NavigationRequest request) {
            if (request.url.startsWith('https://www.youtube.com/')) {
              return NavigationDecision.prevent;
            }
            return NavigationDecision.navigate;
          },
        ),
      );
  }

  void loadLocalHtml() async {
    controller.loadFlutterAsset('assets/www/player/index2.html');
  }

  
  Widget build(BuildContext context) {
    return Scaffold(
      body: Column(
        children: [
          Row(
            children: [
              TextButton(onPressed: (){
                runJS(1);
              }, child: Text("inputClick")),
              TextButton(onPressed: (){
                runJS(2);
              }, child: Text("startPlay")),
              TextButton(onPressed: (){
                runJS(3);
              }, child: Text("postMsg")),
              TextButton(onPressed: (){
                runJS(4);
              }, child: Text("playUrl")),
            ],
          ),
          Expanded(
            child: Stack(
              children: [
                WebViewWidget(
                  controller: controller,
                ),
                ValueListenableBuilder(
                  valueListenable: isShowLoading,
                  builder: (BuildContext context, bool value, Widget? child) {
                    return isShowLoading.value
                        ? const Center(
                            child: CircularProgressIndicator(
                            color: Colors.white,
                          ))
                        : const SizedBox.shrink();
                  },
                )
              ],
            ),
          ),
        ],
      ),
    );
  }
}

引用

Utilizing JS Library for Flutter Web


http://www.kler.cn/a/156154.html

相关文章:

  • 使用支付宝沙箱完成商品下单
  • 超市里的货物架调整(算法解析)|豆包MarsCode AI刷题
  • Unity3D
  • Linux手动安装nginx
  • CSS 自定义滚动条样式
  • Node.Js+Knex+MySQL增删改查的简单示例(Typescript)
  • Linux系统配置深度学习环境之cudnn安装
  • 40 mysql join 的实现
  • jmeter下载地址
  • [Java] 模拟Jdk 以及 CGLib 代理原理
  • 网络接口规范
  • springBoot整合task
  • uniapp中uni.navigateBack返回后刷新页面数据
  • 线程池大小设置多少,比较合适?
  • 如何从 Jira 成功迁移到极狐GitLab,看这个就够了!
  • [leetcode 哈希表] 模版
  • AtCoder Beginner Contest 331 题解 A-E
  • postgreSQL 查询所有模式的语句
  • 算法设计与实现--动态规划篇
  • Matlab和python详解数独谜题问题
  • 2、设计在链式存储结构上交换二叉树中所有结点左右子树的算法。
  • MySQL进阶部分
  • C语言--每日选择题--Day34
  • (C)一些题6
  • 如何快速看懂市场行情?
  • 视频生成的发展史及其原理解析:从Gen2、Emu Video到PixelDance、SVD、Pika 1.0