Flutter整合原生遇到的問題彙總

語言: CN / TW / HK

Flutter整合iOS原生遇到的問題彙總:

下面列舉一些最近在進行混編時遇到的一些問題:

Failed to register observatory port with mDNS with error -65555.

官方描述

On iOS 14 and higher, enable the Dart multicast DNS service in the Debug version of your app to add debugging functionalities such as hot-reload and DevTools via flutter attach.

解決方法

  • 將應用程式的Info.plist重新命名為Info-Debug.plist。複製一個名為Info-Release.plist的副本,並將其新增到Xcode專案中

截圖2022-05-14 18.54.49.png

  • 在Info-Debug.plist中,新增鍵 Bonjour services 並將值設定為 _dartobservatory._tcp

可選的設定Privacy - Local Network Usage Description,並將值設定為Allow Flutter tools on your computer to connect and debug your application.This prompt will not appear on release builds.

截圖2022-05-14 18.58.50.png

  • 在TARGETS中, build settings 修改 Info.plist File 路徑 path/to/Info.plist 為 path/to/Info-$(CONFIGURATION).plist.

截圖2022-05-14 19.02.49.png

In iOS 14+,debug mode Flutter apps can only be launched from Flutter tooling,IDEs with Flutter pl...

截圖2022-05-14 19.05.12.png

分析原因

在 iOS14 的真機上安裝了 debug模式 編譯出來的 flutter 應用,那麼在斷開編譯安裝連線後,將無法從桌面上開啟該應用程式

解決方案

  1. 使用flutter的release模式,終端輸入

js flutter run --release

  1. 修改main.dart的配置

截圖2022-05-14 19.15.04.png

截圖2022-05-14 19.10.22.png

Reason: tried: '/usr/lib/swift/App.framework/App' (no such file), '/usr/lib/swift/App.framework/App' (no such file),

分析原因

FlutterApp.framework沒有匯入

解決辦法

開啟 Pods-xx-frameworks.sh,然後新增以下程式碼

install_framework "${PODS_ROOT}/../flutter/.ios/Flutter/App.framework"

但是這樣只能一時解決問題,下次pod install後又沒有這個配置了,終極解決辦法是:

重灌Cocoapods和ruby-macho:

js 解除安裝ruby-macho和Cocoapods sudo gem uninstall ruby-macho sudo gem uninstall cocoapods 重新安裝ruby-macho和Cocoapods sudo gem install ruby-macho sudo gem install cocoapods

No podspec found for Flutter in ../flutter/.ios/Flutter/engine

分析原因

這個是在這個路徑下缺少這個檔案

解決辦法

可以看下其他Flutter專案下,是否有這個檔案直接拷貝過來,這個就是和Flutter引擎相關的檔案。假如有ios資料夾,看下這個檔案下有沒有那個檔案

Undefined symbol: OBJC_CLASS$_TestViewController

截圖2022-05-14 19.42.06.png

分析原因

這個是我建立一個繼承自FlutterViewController的類,沒有發現

解決辦法

在這個裡面新增這個類的.m檔案即可

截圖2022-05-14 19.43.12.png

底部Widget不跟隨鍵盤彈起而彈起

分析原因

預設resizeToAvoidBottomInset:true,Scaffold 內部會將 mediaQuery.viewInsets.bottom 參與到 BoxConstraints 的大小計算,也就是鍵盤彈起時調整了內部的 bottom 位置來迎合鍵盤。

解決辦法

設定 resizeToAvoidBottomInset: false

MissingPluginException(No implementation found for method resetPlugin on channel com.dooboolab.flutter_sound_player)

9.2.13版本以前,假如是iOS和Flutter混編專案,如果首次進入Flutter模組,這個外掛使用是沒有問題的,但是當離開這個模組第二次進入就會出現註冊外掛出錯、初始化失敗的情況。報錯如下:

```js ERROR during registerWithRegistrar: flutterSoundPlayerManager != nil

MissingPluginException(No implementation found for method resetPlugin on channel com.dooboolab.flutter_sound_player)

```

分析原因

這是第二次進入,註冊失敗,其他外掛都能正常註冊,後來提了問題給開發人員

解決辦法

這是外掛確實存在的bug,目前作者已經在最新版本9.2.13上做了修復。

後續再遇到新的問題,會繼續更新的~

Could not build the precompiled application for the device. Error (Xcode): Undefined symbol: ___gxx_personality_v0

我單獨在Xcode裡面執行,發現是下面這個原因引起的,這個是在flutter裡引入的錄音外掛flutter_sound

截圖2022-06-15 14.26.53.png

分析原因

最開始讓我百思不解,後來我才想到是不是這個外掛裡面用到了C++

解決辦法

Xcode中 Build Phases->link Binary with Libraries中新增libc++.tbd,這樣就解決了這個問題

截圖2022-06-15 14.25.27.png

Unhandled Exception: PlatformException(channel-error, Unable to establish connection on channel., null, null)

解決辦法

進行了專案混編,需要註冊外掛。

  • iOS在AppDelegate中didFinishLaunchingWithOptions方法裡面呼叫 GeneratedPluginRegistrant.register(with: self)
  • Android新增 GeneratedPluginRegistrant.registerWith(flutterEngine)

Flutter配置抓包

需要手動配置IP

(_dio!.httpClientAdapter as DefaultHttpClientAdapter).onHttpClientCreate = (HttpClient client) { client.findProxy = (uri) { return "PROXY localhost:8888"; }; //這個是Android手機抓包需要配置的,不然驗證證書一直失敗 client.badCertificateCallback = (cert, host, port) => true; };

設定指示器的樣式

flutter SwiperCustomPagination(builder: (BuildContext context, SwiperPluginConfig config) { return Align( alignment: const Alignment(0, 0.85), child: Row( mainAxisAlignment: MainAxisAlignment.center, crossAxisAlignment: CrossAxisAlignment.center, children: controller.imageList .asMap() .keys .map((index) { return index == config.activeIndex ? Container( width: 16.0, height: 6.0, margin: const EdgeInsets.fromLTRB( 3.0, 0, 3.0, 0), decoration: BoxDecoration( color: Colors.white, borderRadius: BorderRadius.circular(3)), ) : Container( width: 6.0, height: 6.0, margin: const EdgeInsets.fromLTRB( 3.0, 0, 3.0, 0), decoration: BoxDecoration( color: const Color(0x7FFFFFFF), borderRadius: BorderRadius.circular(3)), ); }).toList(), ), ); })

實現效果

截圖2022-06-26 15.21.07.png

No application found for TargetPlatform.ios. Is your project missing an ios/Runner/Info.plist? Consider running "flutter create ." to create one.

分析原因

專案程式碼中沒有生成iOS工程檔案

解決辦法

在終端根據提示輸入 flutter create . 即可自動生成iOS和Android工程程式碼。

ListView巢狀ListView,存在內容區域不顯示

分析原因

主要是因為內容缺少了邊界約束

解決辦法

  • 使用Container包裹著子ListView,並且設定高度;
  • 修改ListView的shrinkWrap屬性為True,因為True表示滾動方向的滾動檢視內容是否應該由正在檢視的內容所決定

整合百度地圖外掛時報錯找不到標頭檔案

截圖2022-07-06 16.34.04.png

解決辦法

js Xcode-TARGETS -> build settings -> Allow Non-modular Includes In Famework Modules設定為YES

設定文字的最大寬度

dart ConstrainedBox( constraints: const BoxConstraints( maxWidth: 100, ), child: const Text( '設定文字的最大寬度', overflow: TextOverflow.ellipsis, softWrap: true, style: TextStyle( fontSize: 20, ), ) , )

隱藏Flutter導航顯示原生導航

讓AppDelegate遵循UINavigationControllerDelegate

navigationController.delegate = self

實現代理方法

```swift func navigationController(_ navigationController: UINavigationController, willShow viewController: UIViewController, animated: Bool) {

//如果是Flutter頁面,導航欄就隱藏     navigationController.navigationBar.isHidden = viewController.isKind(of: FlutterViewController.self)   } ```

"extended_nested_scroll_view-master" is not a valid Dart package name.

分析原因

這個是我在github上面拉的一個專案,想跑起來看下頁面效果。直接報出了工程專案名不符合命名規範。

解決辦法

專案名裡面出現了 - ,需要改為下劃線 _

Flutter命名規範: - 檔名全部小寫,單詞用下劃線_分割; - 類名,大駝峰命名; - 變數名、方法名,小駝峰命名; - 私有變數需要加下劃線; - Preferences -> Languages & Frameworks -> Flutter -> Editor,然後選中 選中Format code on save 和 Organize imports on save 。然後點選 OK 這樣書寫程式碼就會自動格式化了;

No application found for TargetPlatform.ios. Is your project missing an ios/Runner/Info.plist? Consider running "flutter create ." to create one.

在Android上面報這個錯誤 AndroidManifest.xml could not be found.

分析原因

這個是專案缺少ios和android目錄

解決辦法

當前專案下,執行 flutter create . 即可。

截圖2022-06-21 11.45.05.png

Failed assertion: line 269 pos 15: 'padding == null || padding.isNonNegative': is not true.

分析原因

設定的 padding 引數有問題

設定文字的最大寬度

dart ConstrainedBox( constraints:BoxConstraints( maxWidth: 100, ), child:Text( "設定文字的最大寬度", overflow: TextOverflow.ellipsis, softWrap:true, style: TextStyle( fontSize: 20, ), ), ),

NetWork location failed because baidu location service check the key is unlegal, please check the key in AndroidManifest.xml !

分析原因

這個是整合百度地圖後Android端定位出的問題,這個首先要檢查,定位許可權是否開啟,GPS定位開關是否開啟,如果都開啟了,就要檢視下百度開放平臺的Android SHA1是否正確。

Xcode - TARGETS - build settings - Allow Non-modular Includes In Famework Modules 設定為 YES。

### bottom overflowed by 10 PIXELS

#### 分析原因

這就是當我們在一個固定大小的Widget中佈局時,內容顯示不全時報的問題

### 解決辦法

使用 SingleChildScrollView包裹要顯示的內容,這樣可以使得內容可以滾動,就解決了這個問題。但是SingleChildScrollView 不支援基於Sliver的延遲例項化模型。所以假如內容超過顯示區域太多時,不建議使用這個。

非同步網路請求完成後重新整理UI

```dart Future fun1() async { return '1'; }

Future fun2() async { return '2'; }

Future fun3() async { return '3'; }

void test() { Future.wait([fun1(), fun2(), fun3()]).then((List responses) { print(responses); }).catchError((error) { print(error); }); } ```

Flutter 版本的操作

  • 檢視當前Flutter版本:flutter --version
  • 檢查展示安裝資訊:flutter doctor
  • 檢視所有分支和當前分支:flutter channel
  • 切換到指定分支:flutter channel stable
  • 升級到最新版本:flutter upgrade
  • 升級到指定版本:flutter upgrade v3.0.1
  • 降級到指定版本:git reset --hard [commit_id]
  • 這個commit_id是在這裡找到的,首先開啟 https://github.com/flutter/flutter

截圖2022-08-05 11.14.07.png

截圖2022-08-05 11.14.07.png

以上是最近我做新專案遇到的問題,但是這個裡面沒有講關於專案的架構設計、功能封裝、外掛選型這些。這裡只是記錄在開發中遇到的問題,後續會把專案遇到的問題持續更新!!!