Flutter-填平菜鳥和高手之間的溝壑

Flutter-填平菜鳥和高手之間的溝壑java

準備寫做中...android

 

一、Flutter-skia-影像,Flutter skia-圖形渲染層、應用渲染層
二、方法通道使用示例,用於演示如何使用方法通道實現與原生代碼的交互
需求:提示用戶跳轉到應用市場去評分
在實際業務中,提示用戶跳轉到應用市場(iOS 爲 App Store、Android 則爲各種手機應用市場)去評分是一個高頻需求,考慮到 Flutter 並未提供這樣的接口,而跳轉方式在 Android 和 iOS 上各不相同,所以咱們須要分別在 Android 和 iOS 上實現這樣的功能,並暴露給 Dart 相關的接口。
咱們先來看看做爲客戶端的 Flutter,怎樣實現一次方法調用請求,實際上與調用一個 Dart 對象的方法徹底同樣。
(1)首先,咱們須要肯定一個惟一的字符串標識符,來構造一個命名通道;
(2)而後,在這個通道之上,Flutter 經過指定方法名「openAppMarket」來發起一次方法調用請求。
(3)最後,由於方法調用過程是異步的,須要用非阻塞(或者註冊回調)方式來等待原生代碼給予響應。數組

三、把發起方法調用請求的語句用 try-catch 包裝起來,處理異常
須要注意的是,與網絡調用相似,方法調用請求有可能會失敗(好比,Flutter 發起了原生代碼不支持的 API 調用,或是調用過程出錯等),所以咱們須要把發起方法調用請求的語句用 try-catch 包裝起來。網絡

//聲明MethodChannel
const platform = MethodChannel('samples.chenhang/utils');app

//處理按鈕點擊
handleButtonClick() async {
int result;
//異常捕獲
try {
//異步等待方法通道的調用結果
result = await platform.invokeMethod('openAppMarket');
} catch (e) {
result = -1;
}
print("Result:$result");
}異步

四、分別在 Android 和 iOS 兩個平臺上完成對應的接口實現,在原生代碼中完成方法調用的響應
調用方的實現搞定了,接下來就須要在原生代碼宿主中完成方法調用的響應實現了。因爲咱們須要適配 Android 和 iOS 兩個平臺,因此咱們分別須要在兩個平臺上完成對應的接口實現。async

首先,咱們來看看 Android 端的實現方式。
(1)在上一小結最後我提到,在 Android 平臺,方法調用的處理和響應是在 Flutter 應用的入口,也就是在 MainActivity 中的 FlutterView 裏實現的,所以咱們須要打開 Flutter 的 Android 宿主 App,找到 MainActivity.java 文件,並在其中添加相關的邏輯。
A、用 AS 打開 Flutter 項目 flutter_app_top_tab_03
B、而後,在 Flutter 項目 flutter_app_top_tab_03 中,右擊該項目的 android 子項目選擇用 Android 打開。若是直接在 Flutter 項目中編寫安卓代碼,會有許多紅線報錯,也沒有安卓命令提示、沒法用 Ctrl + Alt + L 進行代碼格式化ide

(2)調用方與響應方都是經過命名通道進行信息交互的,因此咱們須要在 onCreate 方法中,建立一個與調用方 Flutter 所使用的通道名稱同樣的 MethodChannel,並在其中設置方法處理回調,響應 openAppMarket 方法,打開應用市場的 Intent。
(3)一樣地,考慮到打開應用市場的過程可能會出錯,咱們也須要增長 try-catch 來捕獲可能的異常:this

r:\FlutterProject\FlutterProject35\26_native_method\android\app\src\main\java\com\example\native_method\MainActivity.java
文件內容:
package com.hangchen.native_method;操作系統

import android.os.Bundle;
import io.flutter.app.FlutterActivity;
import io.flutter.plugin.common.MethodCall;
import io.flutter.plugin.common.MethodChannel;
import io.flutter.plugins.GeneratedPluginRegistrant;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
public class MainActivity extends FlutterActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
GeneratedPluginRegistrant.registerWith(this);

new MethodChannel(getFlutterView(), "samples.chenhang/navigation").setMethodCallHandler(
new MethodChannel.MethodCallHandler() {
@Override
public void onMethodCall(MethodCall call, MethodChannel.Result result) {
// Note: this method is invoked on the main thread.
if(call.method.equals("openAppStore")) {
try {
Uri uri = Uri.parse("market://details?id=com.tencent.mm");
Intent intent = new Intent(Intent.ACTION_VIEW, uri);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);
} catch (Exception e) {
result.error("UNAVAILABLE", "沒有安裝應用市場", null);
}
}
else {
result.notImplemented();
}
}
});
}
}

五、在 Flutter 應用中經過調用 openAppMarket 方法,實現打開應用市場的功能, 須要注意的是,在 Flutter 使用方法通道進行方法調用和原生代碼返回處理結果的過程當中,存在傳輸信息的序列化和反序列化。 接下來,咱們就能夠在 Flutter 應用裏,經過調用 openAppMarket 方法,實現打開不一樣操做系統提供的應用市場功能了。 須要注意的是,在原生代碼處理完畢後將處理結果返回給 Flutter 時,咱們在 Dart、Android 和 iOS 分別用了三種數據類型: Android 端返回的是 java.lang.Integer、 iOS 端返回的是 NSNumber、 Dart 端接收到返回結果時又變成了 int 類型。 這是爲何呢?這是由於在使用方法通道進行方法調用時,因爲涉及到跨系統數據交互,Flutter 會使用 StandardMessageCodec 對通道中傳輸的信息進行相似 JSON 的二進制序列化,以標準化數據傳輸行爲。這樣在咱們發送或者接收數據時,這些數據就會根據各自系統預約的規則自動進行序列化和反序列化。 看到這裏,你是否是對這樣相似網絡調用的方法通道技術有了更深入的印象呢。對於上面提到的例子,類型爲 java.lang.Integer 或 NSNumber 的返回值,先是被序列化成了一段二進制格式的數據在通道中傳輸,而後當該數據傳遞到 Flutter 後,又被反序列化成了 Dart 語言中的 int 類型的數據。 關於 Android、iOS 和 Dart 平臺間的常見數據類型轉換,我總結成了下面一張表格,幫助你理解與記憶。你只要記住,像 null、布爾、整型、字符串、數組和字典這些基本類型,是能夠在各個平臺之間以平臺定義的規則去混用的,就能夠了。

相關文章
相關標籤/搜索