【发布时间】:2021-09-14 15:13:50
【问题描述】:
朋友们,我正在尝试在 android 和 Flutter 之间创建一个通道。
我在尝试在 Flutter 中调用 Android 布局时遇到此错误:
致命异常:主要 E/AndroidRuntime(30163):进程:com.example.monitoramento,PID:30163 E/AndroidRuntime(30163): java.lang.RuntimeException: 无法启动活动 ComponentInfo{com.example.monitoramento/com.example.monitoramento.DemoCamActivity}: java.lang.RuntimeException: 活动/片段的根视图不能是其他比线性/相对/框架布局
这是我的 MainActivity 类:
package com.example.monitoramento;
import android.content.Intent;
import androidx.annotation.NonNull;
import io.flutter.embedding.android.FlutterActivity;
import io.flutter.embedding.engine.FlutterEngine;
import io.flutter.plugin.common.MethodCall;
import io.flutter.plugin.common.MethodChannel;
import io.flutter.plugins.GeneratedPluginRegistrant;
public class MainActivity extends FlutterActivity {
public static final String CHANNEL = "flutter.rortega.com.basicchannelcommunication";
public void configureFlutterEngine(@NonNull FlutterEngine flutterEngine) {
super.configureFlutterEngine(flutterEngine);
new MethodChannel(getFlutterEngine().getDartExecutor().getBinaryMessenger(),
CHANNEL).setMethodCallHandler(new MethodChannel.MethodCallHandler() {
@Override
public void onMethodCall(@NonNull MethodCall call, @NonNull MethodChannel.Result result) {
if(call.method.equals("showNativeView")){
Intent i = new Intent(MainActivity.this, DemoCamActivity.class);
startActivity(i);
result.success(true);
}else{
result.notImplemented();
}
}
});
}
}
这里是 DemoActivity:
package com.example.monitoramento;/*
* Copyright 2016 Keval Patel.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import android.Manifest;
import android.annotation.SuppressLint;
import android.content.pm.PackageManager;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.os.Handler;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.core.app.ActivityCompat;
import com.example.androidhiddencamera.CameraConfig;
import com.example.androidhiddencamera.CameraError;
import com.example.androidhiddencamera.HiddenCameraActivity;
import com.example.androidhiddencamera.HiddenCameraUtils;
import com.example.androidhiddencamera.config.CameraFacing;
import com.example.androidhiddencamera.config.CameraFocus;
import com.example.androidhiddencamera.config.CameraImageFormat;
import com.example.androidhiddencamera.config.CameraResolution;
import com.example.androidhiddencamera.config.CameraRotation;
import java.io.ByteArrayOutputStream;
import java.io.File;
public class DemoCamActivity extends HiddenCameraActivity {
private static final int REQ_CODE_CAMERA_PERMISSION = 1253;
private CameraConfig mCameraConfig;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mCameraConfig = new CameraConfig()
.getBuilder(this)
.setCameraFacing(CameraFacing.FRONT_FACING_CAMERA)
.setCameraResolution(CameraResolution.HIGH_RESOLUTION)
.setImageFormat(CameraImageFormat.FORMAT_JPEG)
.setImageRotation(CameraRotation.ROTATION_270)
.setCameraFocus(CameraFocus.AUTO)
.build();
//Check for the camera permission for the runtime
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.CAMERA)
== PackageManager.PERMISSION_GRANTED) {
//Start camera preview
startCamera(mCameraConfig);
} else {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.CAMERA},
REQ_CODE_CAMERA_PERMISSION);
}
int noOfSecond = 1;
final Button btn1 = findViewById(R.id.capture_btn);
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
//TODO Set your button auto perform click.
btn1.performClick();
}
}, noOfSecond * 3000);
//Take a picture
findViewById(R.id.capture_btn).setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
//Take picture using the camera without preview.
takePicture();
}
});
}
@SuppressLint("MissingPermission")
@Override
public void onRequestPermissionsResult(int requestCode,
@NonNull String[] permissions,
@NonNull int[] grantResults) {
if (requestCode == REQ_CODE_CAMERA_PERMISSION) {
if (grantResults[0] == PackageManager.PERMISSION_GRANTED) {
startCamera(mCameraConfig);
} else {
Toast.makeText(this, R.string.error_camera_permission_denied, Toast.LENGTH_LONG).show();
}
} else {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
}
@Override
public byte[] onImageCapture(@NonNull File imageFile) {
// Convert file to bitmap.
// Do something.
BitmapFactory.Options options = new BitmapFactory.Options();
options.inPreferredConfig = Bitmap.Config.RGB_565;
Bitmap bitmap = BitmapFactory.decodeFile(imageFile.getAbsolutePath(), options);
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.PNG, 100, byteArrayOutputStream);
byte[] byteArray = byteArrayOutputStream .toByteArray();
//Display the image to the image view
((ImageView) findViewById(R.id.cam_prev)).setImageBitmap(bitmap);
return byteArray;
}
@Override
public void onCameraError(@CameraError.CameraErrorCodes int errorCode) {
switch (errorCode) {
case CameraError.ERROR_CAMERA_OPEN_FAILED:
//Camera open failed. Probably because another application
//is using the camera
Toast.makeText(this, R.string.error_cannot_open, Toast.LENGTH_LONG).show();
break;
case CameraError.ERROR_IMAGE_WRITE_FAILED:
//Image write failed. Please check if you have provided WRITE_EXTERNAL_STORAGE permission
Toast.makeText(this, R.string.error_cannot_write, Toast.LENGTH_LONG).show();
break;
case CameraError.ERROR_CAMERA_PERMISSION_NOT_AVAILABLE:
//camera permission is not available
//Ask for the camera permission before initializing it.
Toast.makeText(this, R.string.error_cannot_get_permission, Toast.LENGTH_LONG).show();
break;
case CameraError.ERROR_DOES_NOT_HAVE_OVERDRAW_PERMISSION:
//Display information dialog to the user with steps to grant "Draw over other app"
//permission for the app.
HiddenCameraUtils.openDrawOverPermissionSetting(this);
break;
case CameraError.ERROR_DOES_NOT_HAVE_FRONT_CAMERA:
Toast.makeText(this, R.string.error_not_having_camera, Toast.LENGTH_LONG).show();
break;
}
}
}
我可以使用什么设置或功能来解决此问题? 我的 AndroidManifest.xml:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.monitoramento">
<application
android:label="monitoramento"
android:icon="@mipmap/ic_launcher">
<activity
android:name=".MainActivity"
android:launchMode="singleTop"
android:theme="@style/Theme.AppCompat.Light"
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated="true"
android:windowSoftInputMode="adjustResize">
<!-- Specifies an Android theme to apply to this Activity as soon as
the Android process has started. This theme is visible to the user
while the Flutter UI initializes. After that, this theme continues
to determine the Window background behind the Flutter UI. -->
<meta-data
android:name="io.flutter.embedding.android.NormalTheme"
android:resource="@style/NormalTheme"
/>
<!-- Displays an Android View that continues showing the launch screen
Drawable until Flutter paints its first frame, then this splash
screen fades out. A splash screen is useful to avoid any visual
gap between the end of Android's launch screen and the painting of
Flutter's first frame. -->
<meta-data
android:name="io.flutter.embedding.android.SplashScreenDrawable"
android:resource="@drawable/launch_background"
/>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<activity android:name=".DemoCamActivity"/>
<!-- Don't delete the meta-data below.
This is used by the Flutter tool to generate GeneratedPluginRegistrant.java -->
<meta-data
android:name="flutterEmbedding"
android:value="2" />
</application>
</manifest>
感谢任何 cmets!
【问题讨论】:
标签: android flutter dart channel