You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用js_interop替代js库实现Flutter Web滚动监听回调

用dart:js_interop替代package:js实现JS与Dart的回调交互

步骤1:替换依赖与导入

移除pubspec.yaml中的package:js依赖,改用Dart SDK内置的JS互操作库:

import 'dart:js_interop';
import 'dart:js_interop_unsafe' as js_unsafe;
import 'dart:html' as html; // 用于访问全局window对象
import 'package:flutter/material.dart';

步骤2:替换回调注册逻辑

原来的allowInterop可以用dart:js_interop_unsafe中的同名方法替代,同时调整全局变量的赋值方式:

方式1:直接通过window设置全局变量

class _YourWidgetState extends State<YourWidget> {
  double _zoomLevel = 1.0;

  @override
  void initState() {
    super.initState();
    // 将Dart函数转换为JS可调用函数,赋值给全局的dartCtrlWheelEventHandler
    html.window.dartCtrlWheelEventHandler = js_unsafe.allowInterop(_ctrlWheelEventHandler);
  }

  void _ctrlWheelEventHandler(num deltaY) {
    setState(() {
      _zoomLevel += deltaY > 0 ? -0.1 : 0.1;
      _zoomLevel = _zoomLevel.clamp(0.5, 2.0);
    });
    print(_zoomLevel);
  }

  // ... 其余Widget代码
}

方式2:使用外部注解定义全局setter

如果你更倾向于保留类似原@JS注解的写法,可以定义外部setter并转换函数类型:

// 定义全局变量的外部setter
@JS()
external set dartCtrlWheelEventHandler(JSFunction f);

class _YourWidgetState extends State<YourWidget> {
  double _zoomLevel = 1.0;

  @override
  void initState() {
    super.initState();
    // 将Dart函数转换为JSFunction并赋值
    dartCtrlWheelEventHandler = js_unsafe.allowInterop(_ctrlWheelEventHandler).cast<JSFunction>();
  }

  void _ctrlWheelEventHandler(num deltaY) {
    setState(() {
      _zoomLevel += deltaY > 0 ? -0.1 : 0.1;
      _zoomLevel = _zoomLevel.clamp(0.5, 2.0);
    });
    print(_zoomLevel);
  }

  // ... 其余Widget代码
}

注意事项

  • dart:js_interop_unsafe中的allowInterop仅适用于信任的JS环境(比如你自己编写的index.html代码),避免用于不可信的第三方JS代码
  • 保持index.html中的监听器逻辑不变,确保它能正确调用全局的dartCtrlWheelEventHandler函数:
<script>
document.addEventListener('wheel', (e) => {
  if (e.ctrlKey) {
    e.preventDefault();
    typeof dartCtrlWheelEventHandler === 'function' && dartCtrlWheelEventHandler(e.deltaY);
  }
});
</script>

内容的提问来源于stack exchange,提问作者RJJ

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.17 02:31:06