フラッターと c の間で渡されるインタラクティブなパラメーター

まずは公式記事で基本的な使い方を紹介:公式ドキュメント

基本的な使い方

参考記事:フラッターでcコードを使う - (1)ソースコードでプロジェクト_SimpleCoder's Blog - CSDN博客_flutterでcコードを呼び出す 

1. コマンドを使用して vscode で新しいプラグイン プロジェクトを作成します: flutter create -t​​ plugin native_add
2. 新しく作成された native_add プロジェクトで、新しい native_add.cpp ファイルを作成し、以下に示すように ios/Classes/ に配置します。

3. Native_add.cpp は 2 つのメソッドを追加します

#include <stdint.h>

extern "C" {
// __attribute__((visibility("default"))) __attribute__((used))
int32_t native_add(int32_t x, int32_t y) { return x + y; }

double double_add(double x, double y) { return x + y; }
}

4. android ディレクトリで、新しい CMakeLists.txt を作成します。

cmake_minimum_required(VERSION 3.4.1)  # for example

add_library( native_add

    # Sets the library as a shared library.
    SHARED

    # Provides a relative path to your source file(s).
    ../ios/Classes/native_add.cpp )

5. android/build.gradle ファイル

android{
    // ...
    externalNativeBuild {
        cmake {
            path "CMakeLists.txt"
        }
    }
}


6. lib/native_add.dart の下にコンテンツを追加します

import 'dart:async';

import 'package:flutter/services.dart';

import 'dart:ffi'; // For FFI
import 'dart:io'; // For Platform.isX

final DynamicLibrary nativeAddLib = Platform.isAndroid
    ? DynamicLibrary.open("libnative_add.so")
    : DynamicLibrary.process();

final int Function(int x, int y) nativeAdd =
  nativeAddLib
    .lookup<NativeFunction<Int32 Function(Int32, Int32)>>("native_add")
    .asFunction();

class NativeAdd {
  static const MethodChannel _channel =
      const MethodChannel('native_add');

  static Future<String> get platformVersion async {
    final String version = await _channel.invokeMethod('getPlatformVersion');
    return version;
  }
}


7. example/lib/main.dart で使用

8. vscode のターミナル ウィンドウで、cd example を使用して native_add プロジェクトの example ディレクトリに入り、flutter run を実行して、nativeAdd メソッドが正常に呼び出されるかどうかをテストします。


9. テスト結果: nativeAdd(1, 2) は 3 に等しい

以上が簡単な純粋なffi公式の説明と使い方です。しかし、使用の過程で、データ型は int と double だけでなく、私が遭遇して解決した他のいくつかの問題もあります。

システムの ffi メソッドと一緒に、pub.dev の ffi メソッドを使用することをお勧めします。

拡張機能と発生した問題と修正:

1. 1 つだけでなく、多数の c ファイルがあり、c ファイルは既に存在します。それを使用するための対話型ロジックを作成するだけです。

まず第一に、前のファイルに従って、c ファイルは引き続き ios/Classes/ の下に配置されます。

CMakeLists.txt にすべてのファイルを追加することを忘れないでください。C ファイルの場合は、パブリックインポート メソッドでヘッダー ファイルをインポートする必要があることに注意してください。

extern “C”{

#include “OOXX.h”

}

注意格式换行要正确。

そうしないと、コンパイル時に例外が発生します: Undefined reference to ****

2. パラメータ型にセカンダリ ポインタ char ** がある

公式のデモでは int と double の基本的な型についてのみ説明されていますが、c には char * と char ** のパラメーター型もあります. ブリッジングに使用する必要がある dart 型は何ですか? (コード、特に char ** で検証済み、一部の記事では Pointer<Uint8> を使用すると書いてありますが、dart を使用すると対応するものに変換できません。 )

char *    使用Pointer<Utf8>来接。

char **   使用Pointer<Pointer<Utf8>>来接

使用例 (ここで使用する toNativeUtf8() は、使用する pub ライブラリの ffi:1.1.2 の拡張です):

3. allocate.dart ファイルについては、一部のブロガーはアップロードしていません. ここで、c コインを必要としないリンクを整理します: flutter と c は、allocation.dart ファイルを呼び出す - その他のドキュメント リソース - CSDN ダウンロードhttps://download . csdn.net/download/BUG_delete/76844837、これは ffi:0.1.2 バージョンにあります。または、ここにコードを掲載します。

// Copyright (c) 2019, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

import 'dart:ffi';
import 'dart:io';

// Note that kernel32.dll is the correct name in both 32-bit and 64-bit.
final DynamicLibrary stdlib = Platform.isWindows
    ? DynamicLibrary.open("kernel32.dll")
    : DynamicLibrary.process();

typedef PosixMallocNative = Pointer Function(IntPtr);
typedef PosixMalloc = Pointer Function(int);
final PosixMalloc posixMalloc =
stdlib.lookupFunction<PosixMallocNative, PosixMalloc>("malloc");

typedef PosixFreeNative = Void Function(Pointer);
typedef PosixFree = void Function(Pointer);
final PosixFree posixFree =
stdlib.lookupFunction<PosixFreeNative, PosixFree>("free");

typedef WinGetProcessHeapFn = Pointer Function();
final WinGetProcessHeapFn winGetProcessHeap = stdlib
    .lookupFunction<WinGetProcessHeapFn, WinGetProcessHeapFn>("GetProcessHeap");
final Pointer processHeap = winGetProcessHeap();

typedef WinHeapAllocNative = Pointer Function(Pointer, Uint32, IntPtr);
typedef WinHeapAlloc = Pointer Function(Pointer, int, int);
final WinHeapAlloc winHeapAlloc =
stdlib.lookupFunction<WinHeapAllocNative, WinHeapAlloc>("HeapAlloc");

typedef WinHeapFreeNative = Int32 Function(
    Pointer heap, Uint32 flags, Pointer memory);
typedef WinHeapFree = int Function(Pointer heap, int flags, Pointer memory);
final WinHeapFree winHeapFree =
stdlib.lookupFunction<WinHeapFreeNative, WinHeapFree>("HeapFree");

/// Allocates memory on the native heap.
///
/// For POSIX-based systems, this uses malloc. On Windows, it uses HeapAlloc
/// against the default public heap. Allocation of either element size or count
/// of 0 is undefined.
///
/// Throws an ArgumentError on failure to allocate.
Pointer<T> allocate<T extends NativeType>({int count = 1}) {
  final int totalSize = count * sizeOf<T>();
  Pointer<T> result;
  if (Platform.isWindows) {
    result = winHeapAlloc(processHeap, /*flags=*/ 0, totalSize).cast();
  } else {
    result = posixMalloc(totalSize).cast();
  }
  if (result.address == 0) {
    throw ArgumentError("Could not allocate $totalSize bytes.");
  }
  return result;
}

/// Releases memory on the native heap.
///
/// For POSIX-based systems, this uses free. On Windows, it uses HeapFree
/// against the default public heap. It may only be used against pointers
/// allocated in a manner equivalent to [allocate].
///
/// Throws an ArgumentError on failure to free.
///
// TODO(dartbug.com/36855): Once we have a ffi.Bool type we can use it instead
// of testing the return integer to be non-zero.
void free(Pointer pointer) {
  if (Platform.isWindows) {
    if (winHeapFree(processHeap, /*flags=*/ 0, pointer) == 0) {
      throw ArgumentError("Could not free $pointer.");
    }
  } else {
    posixFree(pointer);
  }
}

使用:

Pointer<Uint8> soureData = allocate<Uint8>(count:source.length);

私のように割り当てメソッドを使用したときに sizeOf<T>(); エラー メッセージが最初の行に表示された場合は、この型を呼び出して、外部使用で乗算し、int 値に入れることもできます。 : 次のように変更できます。

使用する場所: 

おすすめ

転載: blog.csdn.net/BUG_delete/article/details/122586171