【发布时间】:2020-11-19 08:48:03
【问题描述】:
我想让用户在点击“上传图片”按钮后从图库中选择一张图片,但我的代码似乎无法正常工作。用户选择所需图片后,应用程序立即崩溃。
这是我在 MainActivity 中的 OnCreate 代码:
public static final int RESULT_LOAD_IMAGE = 100;
private final int PICK_IMAGE = 1;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
faceServiceClient = new FaceServiceRestClient("INSERT ENDPOINT HERE",
"INSERT API KEY HERE");
takePicture = findViewById(R.id.takePic);
imageView = findViewById(R.id.imageView);
hidden = findViewById(R.id.hidden);
imageView.setVisibility(View.INVISIBLE);
uploadPicture = findViewById(R.id.uploadPic);
process = findViewById(R.id.processClick);
takePicture.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (ContextCompat.checkSelfPermission(getApplicationContext(), Manifest.permission.CAMERA) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(MainActivity.this, new String[]{Manifest.permission.CAMERA, Manifest.permission.WRITE_EXTERNAL_STORAGE}, 0);
} else {
//IMPORTANT: You may notice that the pictures from the camera are low quality.
//TO FIX THIS: You need to request permission to write external storage that way you can access the full-quality image
//from the device, rather than a low quality thumbnail.
if (checkSelfPermission(Manifest.permission.WRITE_EXTERNAL_STORAGE)
== PackageManager.PERMISSION_GRANTED) {
values = new ContentValues();
values.put(MediaStore.Images.Media.TITLE, "New Picture");
values.put(MediaStore.Images.Media.DESCRIPTION, "From your Camera");
imageUri = getContentResolver().insert(
MediaStore.Images.Media.EXTERNAL_CONTENT_URI, values);
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
intent.putExtra(MediaStore.EXTRA_OUTPUT, imageUri);
startActivityForResult(intent, 100);
} else {
if (counter == 2 || (counter > 2 && counter % 2 == 0)) {
Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
startActivityForResult(intent, 1);
} else //Requesting storage permissions so we can get a high quality image.
ActivityCompat.requestPermissions(MainActivity.this, new String[]{Manifest.permission.WRITE_EXTERNAL_STORAGE}, 0);
counter++;
}
}
}
});
uploadPicture.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
intent.setType("image/*");
startActivityForResult(Intent.createChooser(
intent, "Select Picture"), PICK_IMAGE);
}
});
process.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (ready) {
detectandFrame(mBitmap);
} else {
makeToast("Please take a picture.");
}
}
});
}
这是我在 MainActivity 中的 onActivityResult:
Uri imageUri;
ContentValues values;
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == 100) { //High Quality picture using URI and storage
if (resultCode == RESULT_OK) {
imageView.setVisibility(View.VISIBLE);
try {
mBitmap = MediaStore.Images.Media.getBitmap(
getContentResolver(), imageUri);
Bitmap rotatedBitmap = mBitmap;
ExifInterface ei = new ExifInterface(getRealPathFromURI(imageUri));
int orientation = ei.getAttributeInt(ExifInterface.TAG_ORIENTATION,
ExifInterface.ORIENTATION_UNDEFINED);
switch (orientation) {
case ExifInterface.ORIENTATION_ROTATE_90:
rotatedBitmap = rotateImage(mBitmap, 90);
break;
case ExifInterface.ORIENTATION_ROTATE_180:
rotatedBitmap = rotateImage(mBitmap, 180);
break;
case ExifInterface.ORIENTATION_ROTATE_270:
rotatedBitmap = rotateImage(mBitmap, 270);
break;
case ExifInterface.ORIENTATION_NORMAL:
default:
rotatedBitmap = mBitmap;
}
imageView.setImageBitmap(rotatedBitmap);
} catch (IOException e) {
//Error getting high quality image --> Use low quality thumbnail.
makeToast("Error: " + e.toString());
//mBitmap = (Bitmap) data.getExtras().get("data");
e.printStackTrace();
imageView.setImageBitmap(mBitmap);
}
ready = true;
hidden.setVisibility(View.INVISIBLE);
}
}else if(requestCode == 1 && resultCode == RESULT_OK){
//Low Quality image
imageView.setVisibility(View.VISIBLE);
mBitmap = (Bitmap) data.getExtras().get("data");
imageView.setImageBitmap(mBitmap);
ready = true;
hidden.setVisibility(View.INVISIBLE);
}
if (requestCode == RESULT_LOAD_IMAGE && resultCode == RESULT_OK && null != data) {
Uri selectedImage = data.getData();
String[] filePathColumn = { MediaStore.Images.Media.DATA };
Cursor cursor = getContentResolver().query(selectedImage,
filePathColumn, null, null, null);
cursor.moveToFirst();
int columnIndex = cursor.getColumnIndex(filePathColumn[0]);
String picturePath = cursor.getString(columnIndex);
cursor.close();
}
if (requestCode == PICK_IMAGE && resultCode == RESULT_OK &&
data != null && data.getData() != null) {
Uri uri = data.getData();
try {
imageView.setVisibility(View.VISIBLE);
Bitmap bitmap = MediaStore.Images.Media.getBitmap(
getContentResolver(), uri);
ImageView imageView = findViewById(R.id.imageView);
imageView.setImageBitmap(bitmap);
ready = true;
hidden.setVisibility(View.INVISIBLE);
} catch (IOException e) {
e.printStackTrace();
}
}
}
public String getRealPathFromURI(Uri uri) {
Cursor cursor = getContentResolver().query(uri, null, null, null, null);
cursor.moveToFirst();
int idx = cursor.getColumnIndex(MediaStore.Images.ImageColumns.DATA);
return cursor.getString(idx);
}
public static Bitmap rotateImage(Bitmap source, float angle) {
Matrix matrix = new Matrix();
matrix.postRotate(angle);
return Bitmap.createBitmap(source, 0, 0, source.getWidth(), source.getHeight(),
matrix, true);
}
}
这是我的 AndroidManifest.xml 代码。我意识到,当我在清单中包含“WRITE_EXTERNAL_STORAGE”时,我的从相机拍照功能在点击处理按钮后不起作用。它会在很长一段时间内显示“检测”并在之后崩溃。所以不会显示结果。但是,在我删除清单中的“WRITE_EXTERNAL_STORAGE”后,它可以正常显示结果。但是在用户选择一张图片后,从图库中的选择仍然崩溃。
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.anany.emotionrecognition">
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.CAMERA"></uses-permission>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"></uses-permission>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"></uses-permission>
<application
android:allowBackup="true"
android:icon="@drawable/smiling"
android:label="@string/app_name"
android:roundIcon="@drawable/smiling"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<uses-library android:name="org.apache.http.legacy" android:required="false" />
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name=".ResultActivity"></activity>
</application>
这是我的错误日志。
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.anany.emotionrecognition, PID: 30227
java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=1, result=-1, data=Intent { dat=content://com.miui.gallery.open/raw//storage/emulated/0/WhatsApp/Media/WhatsApp Images/IMG-20201016-WA0028.jpg typ=image/jpeg flg=0x1 }} to activity {com.example.anany.emotionrecognition/com.example.anany.emotionrecognition.MainActivity}: java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.Object android.os.Bundle.get(java.lang.String)' on a null object reference
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.Object android.os.Bundle.get(java.lang.String)' on a null object reference
at com.example.anany.emotionrecognition.MainActivity.onActivityResult(MainActivity.java:216)
【问题讨论】:
-
The app crashed right after user select desired picture.那将在 onActivityResult 中。您发布了太多代码。只有这个功能和使用的意图就足够了。发布 logcat 而不是所有不相关的代码。 -
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.Object android.os.Bundle.get(java.lang.String)' on a null object reference at com.example.anany.emotionrecognition.MainActivity.onActivityResult(MainActivity.java:216)216行是什么? -
代码还是太多了。
-
getRealPathFromURI(imageUri)该函数将返回null。不要使用这么可怕的功能。 -
@blackapps (MainActivity.java:216) 是 mBitmap = (Bitmap) data.getExtras().get("data");它在 }else if(requestCode == 1 && resultCode == RESULT_OK){
标签: android image android-intent bitmapimage android-external-storage