8wDlpd.png
8wDFp9.png
8wDEOx.png
8wDMfH.png
8wDKte.png

使用 dart 在 javascript 上下文中等待

Porcupine Andrew 3月前

42 0

目标是能够等待 dart 代码在 javascript 上下文中处理并接收其输出,但我无法做到。我无法等待 dart:js (code1)。我可以等待我们……

目标是能够等待 dart 代码在 javascript 上下文中处理并接收其输出,但我无法做到这一点。

我无法使用 dart:js (code1) 等待。我可以使用 flutter_js(code2) 等待。flutter_js 的问题在于它不适用于 flutter web。

是否可以使用 dart:js 或其他适用于 flutter web 的软件包来等待?

我发现这个堆栈溢出是类似的::

如何在 Flutter 中异步调用 JavaScript?

如何在 Flutter Web 中从异步 JS 函数获取回调或返回值到 Dart?

https://github.com/dart-lang/sdk/issues/50530

第二和第三个链接正是我在寻找的,但我不明白答案是什么。

非常感谢任何帮助/

代码1::

import 'package:flutter/material.dart';
import 'dart:js' as js;
import 'package:flutter/material.dart';
class JsCompilerUtil {
  Future<bool?> process_client_script({
    required String script,
    required Map<String, dynamic> current,
  }) async {
    js.JsObject jsObject = js.JsObject.jsify(current);
    js.context['c'] = jsObject;
    // js.context['c'] = current;
    var result = js.context.callMethod("eval", [script]);
    return result;
  }
}
class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key});
  @override
  State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
  JsCompilerUtil jsCompilerUtil = JsCompilerUtil();
  @override
  void initState() {
    // TODO: implement initState
    super.initState();
    *initialize*data();
  }
  Future<void> *initialize*data() async {
    String script = """
console.log("Hi from js, this is the inputed name: "+c.name);
var res = c.dummyWait();
console.log("res:")
""";
    Map<String, dynamic> current = {
      "name": "Juan",
      "dummyWait": dummyWait
    };
    final res = await jsCompilerUtil.process_client_script(script: script, current: current);
  }
  @override
  Widget build(BuildContext context) {
    return SizedBox();
  }
  Future<String> dummyWait() async {
    print("dummyWait()\n");
    await Future.delayed(const Duration(seconds: 1));
    return 'MESSAGE FROM DART';
  }
}

代码1的输出::

Restarted application in 28ms.
The debugEmulateFlutterTesterEnvironment getter is deprecated and will be removed in a future release. Please use `debugEmulateFlutterTesterEnvironment` from `dart:ui_web` instead.
Hi from js, this is the inputed name: Juan
dummyWait()
res:

代码2:

import 'package:flutter/material.dart';
import 'package:flutter_js/flutter_js.dart';
import 'dart:convert';

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

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  late JavascriptRuntime flutterJs;

  @override
  void initState() {
    super.initState();
    flutterJs = getJavascriptRuntime();
    _setupJavaScriptBridge();
  }

  void _setupJavaScriptBridge() {
    flutterJs.onMessage('dummyAwait', (args) async {
      String result = await dummyAwaitFunction();
      return result;
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('JavaScript in Dart'),
      ),
      body: Center(
        child: ElevatedButton(
          onPressed: _logic,
          child: Text('Run JavaScript'),
        ),
      ),
    );
  }

  Future<void> _logic() async {
    String result = await runJavaScript();
    print("JavaScript result: $result");
  }

  Future<String> runJavaScript() async {
    // Dart map
    final current = {"name": "juan"};

    // Convert Dart map to JSON string
    String jsonString = jsonEncode(current);

    // JavaScript script to parse JSON string, call Dart function, and print result
    String script = '''
      var current = JSON.parse('$jsonString');
      async function waitForDart() {
        var res = await sendMessage('dummyAwait');
        console.log("INSDE OF JS: " + res);
        return res;
      }
      waitForDart();
    ''';

    // Evaluate JavaScript script
    JsEvalResult jsResult = await flutterJs.evaluateAsync(script);

    return jsResult.stringResult;
  }

  Future<String> dummyAwaitFunction() async {
    await Future.delayed(const Duration(seconds: 1));
    return 'MESSAGE FROM DART';
  }
}

帖子版权声明 1、本帖标题:使用 dart 在 javascript 上下文中等待
    本站网址:http://xjnalaquan.com/
2、本网站的资源部分来源于网络,如有侵权,请联系站长进行删除处理。
3、会员发帖仅代表会员个人观点,并不代表本站赞同其观点和对其真实性负责。
4、本站一律禁止以任何方式发布或转载任何违法的相关信息,访客发现请向站长举报
5、站长邮箱:yeweds@126.com 除非注明,本帖由Porcupine Andrew在本站《javascript》版块原创发布, 转载请注明出处!
最新回复 (0)
  • 我正在尝试创建一个 zip 文件,并通过分段上传路由将该 zip 文件上传到 AWS S3。但是,我遇到了一个问题,即文件成功生成,但内容

    我正在尝试创建一个 zip 文件并通过分段上传路由将该 zip 文件上传到 AWS S3。但是,我遇到一个问题,即文件成功生成,但文件内的内容被损坏。

    这是我尝试取消存档文件时遇到的错误:

    Archive:  test2MB.zip
      End-of-central-directory signature not found.  Either this file is not
      a zipfile, or it constitutes one disk of a multi-part archive.  In the
      latter case the central directory and zipfile comment will be found on
      the last disk(s) of this archive.
    unzip:  cannot find zipfile directory in one of test2MB.zip or
            test2MB.zip.zip, and cannot find test2MB.zip.ZIP, period.
    

    以下是我为此编写的代码片段

    private Single<List<CompletedPart>> zipAndUploadZipParts(String uploadId) {
            List<Single<CompletedPart>> uploadPartObservables = new ArrayList<>();
            final int[] partNumber = {Constants.START_PART_NUMBER};
    
            ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
            ZipOutputStream zipOutputStream = new ZipOutputStream(byteArrayOutputStream);
            return zipMetadata(zipOutputStream)
                    .andThen(uploadZipPart(byteArrayOutputStream, uploadPartObservables, partNumber, uploadId)
                            .onErrorResumeNext(error -> {
                                this.contextRx.log().error(String.format("placeholder", partNumber[0], this.logIdentifier, error.getMessage()), error);
                                return Completable.error(new RuntimeException("Placeholder"));
                            }))
                    .andThen(finalizeZipUpload(uploadPartObservables, zipOutputStream, byteArrayOutputStream));
        }
    
        private Completable zipMetadata(ZipOutputStream zipOutputStream) {
            return Completable.create(emitter -> {
                try {
                    ZipEntry metadataEntry = new ZipEntry(Constants.METADATA_FILE_NAME);
                    zipOutputStream.putNextEntry(metadataEntry);
                    zipOutputStream.write(this.catalogObjectsMetadata.getBytes());
                    zipOutputStream.closeEntry();
                    emitter.onComplete();
                } catch (IOException exception) {
                    this.contextRx.log().error(String.format(Constants.LOG_ERROR_ZIPPING_METADATA, this.logIdentifier, exception.getMessage()), exception);
                    emitter.onError(new RuntimeException(String.format(Constants.ERROR_ZIPPING_METADATA)));
                }
            });
        }
    
        private Completable uploadZipPart(ByteArrayOutputStream byteArrayOutputStream, List<Single<CompletedPart>> uploadPartObservables, int[] partNumber, String uploadId) {
            return Completable.create(emitter -> {
                try {
                    byte[] zipData = byteArrayOutputStream.toByteArray();
                    uploadPartObservables.add(uploadPart(zipData, partNumber[0]++, uploadId));
                    byteArrayOutputStream.reset();
                    this.contextRx.log().info(String.format("Uploaded part %d for uploadId %s", partNumber[0] - 1, uploadId));
                    emitter.onComplete();
                } catch (Exception exception) {
                    emitter.onError(exception);
                }
            });
        }
    
    private Single<List<CompletedPart>> finalizeZipUpload(List<Single<CompletedPart>> uploadPartObservables, ZipOutputStream zipOutputStream, ByteArrayOutputStream byteArrayOutputStream) {
            return Single.defer(() -> {
                try {
                    zipOutputStream.finish();
                } catch (IOException e) {
                    return Single.error(new RuntimeException("Error finishing zip output stream", e));
                } finally {
                    try {
                        zipOutputStream.close();
                    } catch (IOException e) {
                        return Single.error(new RuntimeException("Error closing zip output stream", e));
                    }
                    try {
                        byteArrayOutputStream.close();
                    } catch (IOException e) {
                        return Single.error(new RuntimeException("Error closing byte array output stream", e));
                    }
                }
                return Single.merge(uploadPartObservables)
                        .toList()
                        .doOnSuccess(parts -> this.contextRx.log().info(String.format(Constants.ALL_PARTS_UPLOADED, this.logIdentifier, parts)))
                        .onErrorReturnItem(new ArrayList<>());
            });
        }
    

    有人可以指导一下我的代码出了什么问题,导致我的 zip 文件损坏吗?

    压缩文件中的内容不应该被损坏。

返回
作者最近主题: