JavaScriptCore for Flutter use dart:ffi.

Overview

flutter_jscore

License Awesome Flutter Pub

JavaScriptCore for Flutter. The plugin provides the ability to evaluate JavaScript programs from within dart.

Demo

Screen recording Apk
Code Download

Getting Started

Add plugin

// pub
dependencies:
  flutter_jscore: ^last_version

// import
dependencies:
  flutter_jscore:
    path: Your local path

// git
dependencies:
  flutter_jscore:
    git:
      url: git://github.com/xuelongqy/flutter_jscore.git

Add dynamic library

Due to the size limitation of pub on package upload, you need to add JavaScriptCore dynamic library to the project by yourself.
You can refer to the example. of course you can refer to webkit to compile it.
Set JscFfi.lib to use the JavaScriptCore dynamic library.

JscFfi.lib = Platform.isIOS || Platform.isMacOS
  ? DynamicLibrary.open('JavaScriptCore.framework/JavaScriptCore')
  : Platform.isWindows
  ? DynamicLibrary.open('JavaScriptCore.dll')
  : Platform.isLinux
  ? DynamicLibrary.open('libjavascriptcoregtk-4.0.so.18')
  : DynamicLibrary.open('libjsc.so');

Android

You can get the aar file containing libjsc.so in jsc-android, and add to your project.
Take the libs folder as an example, add it to the build.gradle of the module.

android {
    repositories {
        flatDir {
            dirs 'libs'
        }
    }
}
dependencies {
    implementation(name:'**', ext:'aar')
}

You also need to add libc++_shared.so, because this is a dependency of libjsc.so.
Take the jniLibs folder as an example, add it to the build.gradle of the module.

android {
    sourceSets {
        main {
            jniLibs.srcDirs = ['jniLibs']
        }
    }
}

If your project uses C++, then you can add the code in the module’s build.gradle.

android {
    defaultConfig {
        externalNativeBuild {
            make {
                arguments "-DANDROID_STL=c++_shared"
            }
        }
    }
}

iOS and macOS

You don’t need to do anything, because JavaScriptCore comes with iOS and macOS.

Windows

You can use the dynamic library in the example, or compile it yourself. And configure in CMakeLists.txt.

# Add JavaScriptCore libs
install(DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/JavaScriptCore/"
  DESTINATION "${INSTALL_BUNDLE_LIB_DIR}"
  COMPONENT Runtime)

Linux

You can use libjavascriptcoregtk as a dependency, or compile webkitgtk yourself.
The names of dynamic libraries in different Linux distributions may be different. So you need to set JscFfi.lib.

ubuntn or Debian

apt-get install libjavascriptcoregtk-4.0-18
JscFfi.lib = DynamicLibrary.open('libjavascriptcoregtk-4.0.so.18');

Archlinux

pacman -S webkit2gtk
JscFfi.lib = DynamicLibrary.open('libjavascriptcoregtk-4.0.so');

Usage

import 'package:flutter_jscore/flutter_jscore.dart';

void runJS() {
    JSContext jsContext = JSContext.createInGroup();
    // Replace '1 + 1' with your JavaScript code
    JSValue jsValue = jsContext.evaluate('1 + 1');
    print(jsValue.string);
    jsContext.release();
}

JavaScriptCore

Evaluate JavaScript programs from within an app, and support JavaScript scripting of your app.

Documentation

dart:ffi

Foreign Function Interface for interoperability with the C programming language. flutter_jscore uses dart:ffi so you don't have to worry about performance loss across programming languages.

dart:ffi

Supported platforms

  • iOS (7.0+)
  • macOS (10.5+)
  • Android (arm32, arm64, x86, x86_64)
  • Windows (x86_64)
  • Linux (x86_64)

Linux dependencies

If you use it on Linux, you must make sure to have the following dependencies.

  • libglib-2.0.so.0
  • libicui18n.so.66
  • libicuuc.so.66
  • libdl.so.2
  • libgio-2.0.so.0
  • libgobject-2.0.so.0
  • libpthread.so.0
  • libstdc++.so.6
  • libm.so.6
  • libgcc_s.so.1
  • libc.so.6
  • ld-linux-x86-64.so.2

APIs

I don't think there is much to describe, flutter_jscore just makes a simple package. You can refer to the documentation of JavaScriptCore and the documentation on pub.

JavaScriptCore

flutter_jscore

Donation

If you like my project, please in the upper right corner of the project "Star". Your support is my biggest encouragement! ^_^ You can also scan the qr code below or Donate to this project using Paypal, donation to Author.

If in donation message note name, will be record to the list if you are making open source authors, donation can leave when making project address or personal home page, a link will be added to the list have the effect of promoting each other

Donation list

QQ Group - 554981921

Into the group of instructions

The group is not only solve the problem of EasyreFresh, any Flutter related issues can be discussed. Just as its name, craigslist, as long as there is time, group of Lord will help you solve problems together.

Comments
  • 异步调用回调方法崩溃

    异步调用回调方法崩溃

    我这里创建一个test方法,接收一个回调函数。如果我同步触发这个函数可以正常工作。 如果异步触发就直接崩溃了。

    class TestBug2 extends StatelessWidget {
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          body: Center(
              child: RaisedButton(
            child: Text('TEST2'),
            onPressed: () {
              final jsContext = JSContext.createInGroup();
              jsContext.globalObject.setProperty(
                  'test',
                  JSObject.makeFunctionWithCallback(
                      jsContext, 'test',
                      Pointer.fromFunction(testFunction)
                  ).toValue(),
                  JSPropertyAttributes.kJSPropertyAttributeDontDelete);
    
              jsContext.evaluate('test((n) => n + n)');
            },
          )),
        );
      }
    
      static Pointer testFunction(
          Pointer ctx,
          Pointer function,
          Pointer thisObject,
          int argumentCount,
          Pointer<Pointer> arguments,
          Pointer<Pointer> exception) {
        final context = JSContext(ctx);
    
        final jsv = JSValue(context, arguments[0]);
    //    jsv.protect();
        // ⬇️同步执行 没有问题直接输出结果
        final data = jsv.toObject().callAsFunction(JSObject(context, thisObject), JSValuePointer(JSValue.makeNumber(context, 2.0).pointer));
        print(data.toNumber());
    
        // ⬇️模拟异步执行,直接崩溃
        Future.delayed(const Duration(milliseconds: 300), () {
          final data = jsv.toObject().callAsFunction(JSObject(context, thisObject), JSValuePointer(JSValue.makeNumber(context, 2.0).pointer));
          print(data.toNumber());
        });
      }
    }
    

    崩溃代码

    F/libc    ( 9378): Fatal signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 0x0 in tid 9417 (Thread-2), pid 9378 ()
    *** *** *** *** *** *** *** *** *** *** *** *** *** *** *** ***
    Build fingerprint: 'google/coral/coral:10/QQ2A.200305.003/6156912:user/release-keys'
    Revision: 'MP1.0'
    ABI: 'arm64'
    Timestamp: 2020-03-17 14:29:15+0800
    pid: 9378, tid: 9417, name: Thread-2  >>> com.example.jsrun <<<
    uid: 10289
    signal 11 (SIGSEGV), code 1 (SEGV_MAPERR), fault addr 0x0
    Cause: null pointer dereference
        x0  0000006ff2a46c98  x1  0000000000000000  x2  0000006fdc7e5b40  x3  0000006ff2a45f40
        x4  0000006fcd6c2ee0  x5  0000006fdc7e5b40  x6  0000006fd63515e4  x7  0000006fd4cb48f1
        x8  0000006ff2a44000  x9  0000000000000001  x10 0000000000000001  x11 0000007040000000
        x12 0000000000000a00  x13 000000000c4ef110  x14 0000000000000068  x15 0000006ff2a46cc0
        x16 0000000000000000  x17 0000007051dc0970  x18 0000000000000002  x19 0000006fdc7e5b40
        x20 0000000000000000  x21 0000006fcd6c2ee0  x22 0000006ff2a45f40  x23 0000007051d2e2b8
        x24 0000006fe2d80041  x25 0000006ff296e000  x26 0000007051dc0400  x27 0000006fe1187010
        x28 0000000000000004  x29 0000006ff2a46cd8
        sp  0000006ff2a46c80  lr  0000006fd635161c  pc  0000006fd6906e8c
    backtrace:
          #00 pc 0000000000680e8c  /data/app/com.example.jsrun-IMKGo_ZTkeXv0aKVB8-Nmw==/lib/arm64/libjsc.so
          #01 pc 00000000000cb618  /data/app/com.example.jsrun-IMKGo_ZTkeXv0aKVB8-Nmw==/lib/arm64/libjsc.so (JSValueToObject+52)
          #02 pc 000000000000485c  <anonymous:6fe2d00000>
    Lost connection to device.
    
    opened by xioxin 10
  • support for windows and linux platform

    support for windows and linux platform

    近期会添加windows和linux平台支持吗? 我找到一个支持windows、linux、macos的JSC项目 Lichtso/JSC-Standalone,它的头文件flutter_jscore/lib/binding 下声明一致,但是这个项目时间太古老,链接库是六年前的了,缺少一些方法。 如果coming soon还要等比较久的话,我准备用这个老版本先凑合用。

    opened by mabDc 5
  • Failed to lookup symbol (undefined symbol: JSObjectMakeDeferredPromise)

    Failed to lookup symbol (undefined symbol: JSObjectMakeDeferredPromise)

    I want to create a function return promise to javascript, but the code only run to print('2') and got error at JSObject.makeDeferredPromise

     Pointer _getUser(
          Pointer ctx,
          Pointer function,
          Pointer thisObject,
          int argumentCount,
          Pointer<Pointer> arguments,
          Pointer<Pointer> exception) {
        print('getUrl called');
        final resolve = JSObject.makeFunction(
            _jsContext, 'resolve', JSStringPointer.array(['value']), '', '');
    
        final reject = JSObject.makeFunction(
            _jsContext, 'reject', JSStringPointer.array(['value']), '', '');
    
        print('2');
    
        final promise = JSObject.makeDeferredPromise(_jsContext,
            JSObjectPointer(resolve.pointer), JSObjectPointer(reject.pointer));
    
        print('3');
    
        return promise.pointer;
      }
    

    both version from pub.dev or git got the error

    flutter_jscore:
        git:
          url: https://github.com/xuelongqy/flutter_jscore.git
    

    flutter doctor

    [✓] Flutter (Channel stable, 1.22.4, on Mac OS X 10.14.6 darwin-x64,
        locale en-US)
    [✓] Android toolchain - develop for Android devices (Android SDK version 30.0.2)
    [!] Android Studio (version 4.1)
        ✗ Flutter plugin not installed; this adds Flutter specific functionality.
        ✗ Dart plugin not installed; this adds Dart specific functionality.
    [✓] VS Code (version 1.51.1)
    [✓] Connected device (1 available)
    
    opened by winterdl 1
  • jscore中类的使用问题

    jscore中类的使用问题

    我在dart里创建的类,js里初始化后返回到dart再取值发现取到的都是最后一个

    js执行的: [new Text('测试1'), new Text('测试2'), new Text('测试3')]; 到dart中取到的内容是 (测试3, 测试3, 测试3) 全部变成最后一个了

    大佬帮忙看看是不是用的方法不对.

    完整代码如下:

    
    class TestBug extends StatelessWidget {
    
      static Pointer jsClassInitialize(
          Pointer ctx,
          Pointer constructor,
          int argumentCount,
          Pointer<Pointer> arguments,
          Pointer<Pointer> exception) {
        String text;
        final context = JSContext(ctx);
        final that = JSValue(context, constructor).toObject();
        if (argumentCount >= 1) {
          final arg1 = JSValue(context, arguments[0]);
          if (arg1.isString) {
            text = arg1.string;
          }
        }
        that.setProperty(
            'text',
            JSValue.makeString(context, text),
            JSPropertyAttributes.kJSPropertyAttributeDontDelete);
        return constructor;
      }
    
      @override
      Widget build(BuildContext context) {
        return Scaffold(
          body: Center(
              child: RaisedButton(
                child: Text('TEST'),
                onPressed: () {
                  final jsContext = JSContext.createInGroup();
                  final classDef = JSClassDefinition(
                    version: 0,
                    attributes: JSClassAttributes.kJSClassAttributeNone,
                    className: 'Text',
                    callAsConstructor: Pointer.fromFunction(jsClassInitialize),
                    staticFunctions: [],
                  );
                  var flutterJSClass = JSClass.create(classDef);
                  var flutterJSObject = JSObject.make(jsContext, flutterJSClass);
                  jsContext.globalObject.setProperty('Text', flutterJSObject.toValue(),
                      JSPropertyAttributes.kJSPropertyAttributeDontDelete);
                  final data = jsContext.evaluate("""
                  [new Text('测试1'), new Text('测试2'), new Text('测试3')]
                """);
                  final list = jsValueToList(data).map((e) => e.toObject().getProperty('text').string);
                  print(list);
                 // I/flutter ( 8752): (测试3, 测试3, 测试3)
                },
              )),
        );
      }
    }
    
    opened by xioxin 1
  • Error: Property 'count' cannot be accessed on 'JSValuePointer?' because it is potentially null.

    Error: Property 'count' cannot be accessed on 'JSValuePointer?' because it is potentially null.

    I have following error after migrate to null safety .

    lib/js/js_engine.dart:71:32: Error: Property 'count' cannot be accessed on 'JSValuePointer?' because it is potentially null.
     - 'JSValuePointer' is from 'package:myApp/js/js_core_mock.dart' ('lib/js/js_core_mock.dart').
    Try accessing using ?. instead.
          if (jsContext!.exception.count > 0) {
                                   ^^^^^
    lib/js/js_engine.dart:71:38: Error: Operator '>' cannot be called on 'int?' because it is potentially null.
          if (jsContext!.exception.count > 0) {
                                         ^
    lib/js/js_engine.dart:72:50: Error: Property 'count' cannot be accessed on 'JSValuePointer?' because it is potentially null.
     - 'JSValuePointer' is from 'package:myApp/js/js_core_mock.dart' ('lib/js/js_core_mock.dart').
    Try accessing using ?. instead.
            for (int i = 0; i < jsContext!.exception.count; i++)
    
    opened by Gursewak-Uppal 0
  • require这类要加载第三方的函数要这么做

    require这类要加载第三方的函数要这么做

    本地js种使用到了require 自己本地通过setProperty的方式 的确让require在执行的时候 回调了回来 但是自己接管了require以后 就等于自身默认不在支持require语法

     var jsAlertFunction =
            JSObject.makeFunctionWithCallback(_jsContext, 'require', Pointer.fromFunction(require));
        _jsContext.globalObject.setProperty('require', jsAlertFunction.toValue(),
            JSPropertyAttributes.kJSPropertyAttributeNone);
    

    比如这种语法 image

    就会提示报错

    我现在的问题 就是 如何能让jscore自身就支持require语法 并且可以自己去找指定文件读取

    opened by fangkyi03 16
Releases(v1.0.0)
Owner
KnoYo
KnoYo
A Dart FFI package to send 💬 toasts on Windows. Written in C++, based on WinToast.

desktoasts A Dart package to send native ?? toasts on Windows. Installation For Flutter dependencies: ... desktoasts: ^0.0.2 For Dart CLI here Sup

Hitesh Kumar Saini 37 Mar 7, 2022
FFI binding generator

Binding generator for FFI bindings. Note: ffigen only supports parsing C headers. Example For some header file example.h: int sum(int a, int b); Add c

Dart 288 Dec 22, 2022
Use Dart to call Shell, complete the work of compiling Golang CGO code into a so, dll, a, WASM, and etc.

Use Dart to call Shell, complete the work of compiling Golang CGO code into a so, dll, a, WASM, and etc. And place it in the corresponding source file directory of each Flutter platform.

Dorain Gray 30 Dec 30, 2022
Windows95 UI components for Flutter apps. Bring back the nostalgic look and feel of old operating systems with this set of UI components ready to use.

Flutter95 Windows95 UI components for Flutter apps. UNDER CONSTRUCTION Screenshots Components Scaffold95 Scaffold as a Windows95 styled window. Provid

Miguel Beltran 141 Dec 26, 2022
Flutter date range pickers use a dialog window to select a range of date on mobile.

[Deprecated] Date Range Picker Currently Flutter has supported date range picker, so I think my mission is done. Thanks for using my lib. Link: https:

null 225 Dec 28, 2022
A project that makes use of a Typescript back end and a Flutter web front end to consume the Jira API in order to visualize and interact with issues.

A project that makes use of a Typescript back end and a Flutter web front end to consume the Jira API in order to visualize and interact with issues.

Lucas Coelho 1 Mar 20, 2022
A simple-to-use flutter update package for Windows, MacOS, and Linux.

Updat - The simple-to-use, flutter-based desktop update package Updat is a simple-to-use reliable flutter-native updater that handles your application

Eduardo M. 14 Dec 21, 2022
Pure Dart Argon2 algorithm (the winner of the Password Hash Competition 2015) for all Dart platforms (JS/Web, Flutter, VM/Native).

argon2 Pure Dart Argon2 algorithm (the winner of the Password Hash Competition 2015) for all Dart platforms (JS/Web, Flutter, VM/Native). Based on the

Graciliano Monteiro Passos 8 Dec 22, 2021
Dart web - Experimental web framework for Dart. Supports SPA and SSR

dart_web Experimental web framework for Dart. Supports SPA and SSR. Relies on pa

Kilian Schulte 307 Dec 23, 2022
A Dart/Flutter package to register/query/remove URI Schemes without hassle.

protocol_registry Register/query/remove URI Schemes without hassle. Available for Windows and Linux. Installation flutter pub add protocol_registry Us

ZYROUGE 10 Oct 25, 2022
Biyi (比译) is a convenient translation and dictionary app written in dart / Flutter.

biyi_app Biyi is a convenient translation and dictionary app written in dart / Flutter. View document "Biyi" (比译) is the Chinese word for "Comparison

biyidev 894 Jan 1, 2023
Implementation of libadwaita for flutter/dart

Implementation of the theme from libadwaita. Inspired by the yaru theme for flutter. Usage import 'package:flutter/material.dart'; import 'package:adw

GTK Flutter 164 Dec 26, 2022
Serverpod is a next-generation app and web server, explicitly built for the Flutter and Dart ecosystem.

Serverpod Serverpod is a next-generation app and web server, explicitly built for the Flutter and Dart ecosystem. It allows you to write your server-s

Serverpod 1k Jan 8, 2023
Dawn - a Dart web package for developing UIs in a pattern similar to Flutter.

dawn Description Dawn is a Dart web package for developing UIs in a pattern similar to Flutter. Links GitHub Repository Pub Page Documentation An Exam

Hamed Aarab 45 Jan 6, 2023
Native Dart client library for DBus

A native Dart client implementation of D-Bus. Accessing a remote object using dart-dbus The easiest way to get started is to use dart-dbus to generate

Canonical 81 Oct 28, 2022
Build Win32 apps with Dart!

A package that wraps some of the most common Win32 API calls using FFI to make them accessible to Dart code without requiring a C compiler or the Wind

Tim Sneath 609 Jan 2, 2023
A pure Dart implementation of Firebase with initial support aimed at FlutterFire for Linux & Windows.

FlutterFire Desktop A work in progress pure Dart implementation of Firebase with initial support aimed at FlutterFire for Linux & Windows. A FlutterFi

Invertase 293 Jan 4, 2023
Experimental web framework for Dart. Supports SPAs and SSR.

jaspr Experimental web framework for Dart. Supports SPAs and SSR. Main Features: Familiar component model similar to Flutter widgets Easy Server Side

Kilian Schulte 310 Jan 4, 2023
Flutter Installer is an installer for Flutter built with Flutter 💙😎✌

Flutter Installer Flutter Installer is an installer for Flutter built with Flutter ?? ?? ✌ Flutter and the related logo are trademarks of Google LLC.

Yazeed AlKhalaf 406 Dec 27, 2022