- [Flutter] "Do it! 플러터 앱 프로그래밍" - 네이티브 API와 통신하기 | MissingPluginException에러 미해결 ㅠ2022년 02월 21일 00시 11분 15초에 업로드 된 글입니다.작성자: DandyNow728x90반응형
"조준수. (2021). Do it! 플러터 앱 프로그래밍. 이지스퍼블리싱", 12장을 실습하였다. "네이티브 소스로 인코딩/디코딩 구현"에서 에러가 해결되지 않아 더 이상의 실습은 곤란했다. 전체적인 내용을 보고 어떤 흐름으로 네이티브 API와 통신하는지 살펴보는 것으로 만족했다. 추후 이 파트에 대한 다른 자료를 더 찾아보고 실습해봐야 겠다.
안드로이드 네이티브와 통신하기
기기 자체의 정보, 배터리 정보, 운영체제에 맞게 개발된 오픈소스 등을 사용해야할 때 네이티브 언어로 작성된 API를 이용해야 한다. 다트 언어를 사용하는 플러터에서 네이티브 언어로 된 API를 사용하려면 서로 데이터를 주고받을 수 있는 연결자가 필요한데 그 역할을 MethodChannel이 해준다.
플러터 앱에서 네이티브 함수 호출하기
플러터 앱에서 안드로이드 함수를 호출했지만 응답하지 않아 기기의 정보를 받아올 수 없다. 따라서 [그림 1]과 같이 _deviceInfo 변수의 초깃값인 'Unknown info'가 출력됐다.
// main.dart import 'package:flutter/material.dart'; import 'package:flutter/cupertino.dart'; import 'dart:io'; import 'package:flutter/services.dart'; void main() { runApp(MyApp()); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { // 운영체제가 iOS면 실행 // 플러터는 Platform 객체를 이용해 실행 중인 운영체제를 알 수 있다. dat:io를 import해야 한다. if (Platform.isIOS) { return CupertinoApp( // home: CupertinoNativeApp(), ); } else { // 이외의 운영체제면 실행 return MaterialApp( title: 'Flutter Demo', theme: ThemeData( primarySwatch: Colors.blue, ), home: NativeApp(), ); } } } class NativeApp extends StatefulWidget { @override State<StatefulWidget> createState() => _NativeApp(); } class _NativeApp extends State<NativeApp> { // 안드로이드와 통신 채널로 사용할 MethodChannel을 상수 선언 static const platform = const MethodChannel( 'com.flutter.dev/info'); // 어떤 통신을 할 것인지 구분하는 키값, 이 값을 통해 플러터 앱과 안드로이드 간에 메시지 주고 받음 String _deviceInfo = "Unknown info"; // 안드로이드에서 전달받은 기기 정보 @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( title: Text('Native 통신 예제'), ), body: Container( child: Center( child: Text( _deviceInfo, style: TextStyle(fontSize: 30), ), ), ), floatingActionButton: FloatingActionButton( onPressed: () { _getDeviceInfo(); // 기기 정보를 가져오는 함수 호출 }, child: Icon(Icons.get_app), ), ); } // 기기 정보를 가져오는 함수 Future<void> _getDeviceInfo() async { String deviceInfo; try { // platform.invokeMethod()는 메서트 채널로 연결된 안드로이드에서 네이티브 API를 호출, getDeviceInfo는 안드로이드 네이티브 소스에서 호출할 함수 이름. final String result = await platform.invokeMethod('getDeviceInfo'); deviceInfo = 'Device info : $result'; } on PlatformException catch (e) { deviceInfo = 'Failed to get Device info:${e.message}.'; } setState(() { _deviceInfo = deviceInfo; }); } }
안드로이드 네이티브와 데이터 주고받기
네이티브 소스로 인코딩/디코딩 구현
인코딩(encoding)은 데이터의 형식을 보안, 처리 속도, 공간 절약 등을 위해 다른 형식으로 변환하는 것이고, 디코딩(decoding)은 원래 데이터로 되돌리는 것이다. 여기에서는 64개의 안전한 출력 문자만 사용해 다른 시스템 간에 똑같이 데이터를 주고받을 수 있는 Base64를 이용한다.
에러에 의한 실습 중단
AVD에서 핫리로드시 콘솔에 아래의 메시지가 뜨고 "... 11 more" 무한 install하여 강제 종료하였다.
E/AndroidRuntime(10733): Caused by: java.lang.ClassNotFoundException: Didn't find class "com.example.flutter_native_example.MainActivity" on path: DexPathList[[zip file "/data/app/com.example.flutter_native_example-Kv6KOfDa1d72AuSHUnZ8Fw==/base.apk"],nativeLibraryDirectories=[/data/app/com.example.flutter_native_example-Kv6KOfDa1d72AuSHUnZ8Fw==/lib/x86, /data/app/com.example.flutter_native_example-Kv6KOfDa1d72AuSHUnZ8Fw==/base.apk!/lib/x86, /system/lib, /system/product/lib]]
디바이스를 윈도우로 선택하면 [그림 2]와 같은 화면을 볼 수 있는데 플로팅 버튼을 누르면 다음의 에러가 발생하였다. 구글링 해보니 터미널에서 "flutter clean" 해주면 된다고 되어 있는데, 이 경우에는 차도가 없었다.
728x90반응형'언어·프레임워크 > Flutter' 카테고리의 다른 글
다음글이 없습니다.이전글이 없습니다.댓글