gpt4 book ai didi

android - 在 Camera 中配置更改后,返回到带有空 ImageView 的应用程序

转载 作者:行者123 更新时间:2023-11-29 01:34:15 25 4
gpt4 key购买 nike

我没有在网上找到任何解决此特定问题的内容。我有一个使用 Android 相机应用程序拍摄照片或视频的 Activity 。然后它从相机返回图像或视频,并在 View 中显示。当我处于相同配置时,我的视频和图像、捕获和显示都可以正常工作。 但是如果我从我的应用程序启动相机,比如说,纵向,然后当我在相机应用程序中时,我决定将它更改为横向,然后一旦我从相机应用程序返回,我的图像显示空白 ImageView 如果我保持相同的配置,它工作正常。就像当我以纵向模式开始,然后也以纵向模式使用相机应用程序时,我的 ImageView 会在返回时显示图像。由于我无法为相机应用程序编写代码,因此不确定如何处理。

但是,如果我在使用相机视频期间改变方向,我的视频没有问题。当它返回到我的应用程序时,无论我在应用程序或相机应用程序中处于哪个方向,它都能正常显示。

但是为什么图像有问题呢?我试图在 onSaveInstanceStateonRestoreInstanceState 中保存状态,但这不会影响任何东西。当我记录它们时(也适用于视频),我在这些方法中获得所有变量的空值。我想是因为它可能与我的 Intent 数据有更多关系?但这只是一个猜测。我查看了 Intent,没有发现任何遗漏。图像 Intent 与视频 Intent 略有不同,所以也许我遗漏了一些东西。

我确实有 2 个不同的 xml 文件用于纵向和横向布局,但它们是相同的并且位于正确的文件夹中。当我更改配置时,Android 会自动选择它们。

如果有人有提示,非常感谢。

更新:

我试图在 list 中添加一行代码:android:configChanges="keyboardHidden|orientation|screenSize"

并且我覆盖了 onConfigurationChanged(),但现在我的图像返回为黑屏。这两个布局文件都在我的 layout 文件夹中。

@Override
public void onConfigurationChanged(Configuration newConfig) {
super.onConfigurationChanged(newConfig);

// Checks the orientation of the screen
if (newConfig.orientation == Configuration.ORIENTATION_LANDSCAPE) {
setContentView(R.layout.activity_make_photo_video_land);
} else if (newConfig.orientation == Configuration.ORIENTATION_PORTRAIT){
setContentView(R.layout.activity_make_photo_video);
}
}

更新 2:

我撤消了我在更新 1 中尝试的所有内容。因为那给了我黑屏和其他无法修复的错误。

这次,我在onCreate中添加了一个配置选择器来手动改变 View :

// Checks the orientation of the screen
if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE) {
setContentView(R.layout.activity_make_photo_video_land);
mImageView = (ImageView) findViewById(R.id.taken_photo_land);
} else if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) {
setContentView(R.layout.activity_make_photo_video);
mImageView = (ImageView) findViewById(R.id.taken_photo);
}

经过更多日志记录后,我意识到当我更改相机应用中的配置时,以下方法按此顺序执行(从第一个 Activity 开始列出):

  1. onCreate()

  2. onSavedInstanceState() - 我离开我的应用去相机

  3. onCreate() - 我从带有照片的应用返回,mImageBitmap 上的日志为空。

  4. onRestoreInstanceState()

  5. inActivityResult() - 然后处理从相机拍摄的照片。

我唯一坚持使用 onSavedInstanceState() 的是 mCurrentPhotoPath,它是在 中运行 setPic() 方法所必需的>inActivityResult()

onSavedInstanceState() 中:outState.putString("FILE_PATH", mCurrentPhotoPath);

onCreate() 中:

if (savedInstanceState != null) {
mCurrentPhotoPath = savedInstanceState.getString("FILE_PATH");
}

这个过程很好,位图值上的日志不为空。那为什么图片发不出去呢??

MakePhotoVideo.java

package org.azurespot.makecute;

import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.content.res.Configuration;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.support.v7.app.ActionBarActivity;
import android.util.Log;
import android.view.Gravity;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.VideoView;

import org.azurespot.R;
import org.azurespot.cutecollection.CuteCollection;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Random;

public class MakePhotoVideo extends ActionBarActivity {

private static final int ACTION_TAKE_PHOTO = 1;
private static final int ACTION_TAKE_VIDEO = 2;
private static final String BITMAP_STORAGE_KEY = "viewbitmap";
private static final String IMAGEVIEW_VISIBILITY_STORAGE_KEY = "imageviewvisibility";
private ImageView mImageView;
private Bitmap mImageBitmap;

private static final String VIDEO_STORAGE_KEY = "viewvideo";
private static final String VIDEOVIEW_VISIBILITY_STORAGE_KEY = "videoviewvisibility";
private VideoView mVideoView;
private Uri mVideoUri;
private File fileVideo;

private String mCurrentPhotoPath;
String videoPath;
private int position = 0;

private static final String JPEG_FILE_PREFIX = "IMG_";
private static final String JPEG_FILE_SUFFIX = ".jpg";

private PhotoStorageDirFactory mPhotoStorageDirFactory = null;



/* Photo album for this application */
private String getAlbumName() {
return getString(R.string.album_name);
}

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_make_photo_video);

mImageView = (ImageView) findViewById(R.id.taken_photo);
mVideoView = (VideoView) findViewById(R.id.video_view);
mVideoView.setVisibility(View.INVISIBLE);
mImageView.setSaveEnabled(true);

Button photoBtn = (Button) findViewById(R.id.click);
setBtnListenerOrDisable(photoBtn, mTakePicOnClickListener, MediaStore.ACTION_IMAGE_CAPTURE);

Button videoBtn = (Button) findViewById(R.id.record_video);
setBtnListenerOrDisable(videoBtn,mTakeVidOnClickListener, MediaStore.ACTION_VIDEO_CAPTURE);

mPhotoStorageDirFactory = new BasePhotoDirFactory();

// Shows the up carat near app icon in ActionBar
getSupportActionBar().setDisplayUseLogoEnabled(false);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);

}


public void viewCollection(View v){

// finishes/restarts the activity so the unsaved video does not corrupt
Intent intent = getIntent();
finish();
startActivity(intent);

// goes to Cute Collection activity
Intent i = new Intent(this, CuteCollection.class);
startActivity(i);
}

private File getAlbumDir() {
File storageDir = null;

if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())) {

storageDir = mPhotoStorageDirFactory.getAlbumStorageDir(getAlbumName());

if (storageDir != null) {
if (! storageDir.mkdirs()) {
if (! storageDir.exists()){
Log.d("Camera", "failed to create directory");
return null;
}
}
}

} else {
Log.v(getString(R.string.app_name), "External storage is not mounted READ/WRITE.");
}

return storageDir;
}

private File createImageFile() throws IOException {
// Create an image file name
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = JPEG_FILE_PREFIX + timeStamp + "_";
File albumF = getAlbumDir();
File imageF = File.createTempFile(imageFileName, JPEG_FILE_SUFFIX, albumF);
return imageF;
}

private File setUpPhotoFile() throws IOException {

File f = createImageFile();
mCurrentPhotoPath = f.getAbsolutePath();

return f;
}

private void setPic() {

/* There isn't enough memory to open up more than a couple camera photos */
/* So pre-scale the target bitmap into which the file is decoded */

/* Get the size of the ImageView */
int targetW = mImageView.getWidth();
int targetH = mImageView.getHeight();

/* Get the size of the image */
BitmapFactory.Options bmOptions = new BitmapFactory.Options();
bmOptions.inJustDecodeBounds = true;
BitmapFactory.decodeFile(mCurrentPhotoPath, bmOptions);
int photoW = bmOptions.outWidth;
int photoH = bmOptions.outHeight;

/* Figure out which way needs to be reduced less */
int scaleFactor = 1;
if ((targetW > 0) || (targetH > 0)) {
scaleFactor = Math.min(photoW/targetW, photoH/targetH);
}

/* Set bitmap options to scale the image decode target */
bmOptions.inJustDecodeBounds = false;
bmOptions.inSampleSize = scaleFactor;
bmOptions.inPurgeable = true;

/* Decode the JPEG file into a Bitmap */
mImageBitmap = BitmapFactory.decodeFile(mCurrentPhotoPath, bmOptions);


if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) {
mImageBitmap = rotateBitmap(mImageBitmap, 90);
}

savePhoto(mImageBitmap);

/* Associate the Bitmap to the ImageView, make sure the VideoView
* is cleared to replace with ImageView */
mImageView.setImageBitmap(mImageBitmap);

Log.d("TAG", "Value of mImageBitmap inside setPic(): " + mImageBitmap);
mVideoUri = null;
mImageView.setVisibility(View.VISIBLE);
mVideoView.setVisibility(View.INVISIBLE);

}

// save your photo to SD card
private void savePhoto(final Bitmap bitmapPhoto){
// set OnClickListener to save the photo
mImageView.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
boolean success = false;

File photoDir = new File(Environment.getExternalStoragePublicDirectory
(Environment.DIRECTORY_PICTURES) + "/Cute Photos");
photoDir.mkdirs();
Random generator = new Random();
int n = 10000;
n = generator.nextInt(n);
String photoName = "Photo"+ n +".jpg";
File filePhoto = new File (photoDir, photoName);
// if (filePhoto.exists ()) filePhoto.delete ();
try {
FileOutputStream out = new FileOutputStream(filePhoto);
bitmapPhoto.compress(Bitmap.CompressFormat.JPEG, 100, out);
out.flush();
out.close();
success = true;
} catch (Exception e) {
e.printStackTrace();
}

if (success) {
Toast toast = Toast.makeText(getApplicationContext(), "Cute photo saved!",
Toast.LENGTH_LONG);
LinearLayout toastLayout = (LinearLayout) toast.getView();
toastLayout.setBackgroundColor(getResources().getColor(R.color.toast_color));
TextView toastTV = (TextView) toastLayout.getChildAt(0);
toastTV.setTextSize(30);
toast.setGravity(Gravity.CENTER_VERTICAL, 0, 80);
toast.show();
} else {
Toast.makeText(getApplicationContext(),
"Error during image saving", Toast.LENGTH_SHORT).show();
}

}
});
}


// save your video to SD card
protected void saveVideo(final Uri uriVideo){

// click the video to save it
mVideoView.setOnTouchListener(new View.OnTouchListener() {

public boolean onTouch(View v, MotionEvent event) {

boolean success = false;

if(event.getAction() == MotionEvent.ACTION_UP) {

try {
// make the directory
File vidDir = new File(android.os.Environment.getExternalStoragePublicDirectory
(Environment.DIRECTORY_MOVIES) + File.separator + "Cute Videos");
vidDir.mkdirs();

// create unique identifier
Random generator = new Random();
int n = 100;
n = generator.nextInt(n);
// create file name
String videoName = "Video" + n + ".mp4";

fileVideo = new File(vidDir.getAbsolutePath(), videoName);

videoPath = fileVideo.getAbsolutePath();

Log.d("TAG", "Value of videoPath:" + videoPath);

fileVideo.setWritable(true, false);

OutputStream out = new FileOutputStream(fileVideo);
InputStream in = getContentResolver().openInputStream(uriVideo);

byte buffer[] = new byte[1024];
int length = 0;
while ((length = in.read(buffer)) > 0) {
out.write(buffer, 0, length);
}

out.close();
in.close();

success = true;

} catch (Exception e) {
e.printStackTrace();
}

if (success) {
Toast toast = Toast.makeText(getApplicationContext(), "Cute video saved!",
Toast.LENGTH_SHORT);
LinearLayout toastLayout = (LinearLayout) toast.getView();
toastLayout.setBackgroundColor(getResources().getColor(R.color.toast_color));
TextView toastTV = (TextView) toastLayout.getChildAt(0);
toastTV.setTextSize(30);
toast.setGravity(Gravity.CENTER_VERTICAL, 0, 80);
toast.show();
} else {
Toast.makeText(getApplicationContext(),
"Error during video saving", Toast.LENGTH_SHORT).show();
}
}

return true;
}
});
}


public Bitmap rotateBitmap(Bitmap source, int angle)
{
Matrix matrix = new Matrix();
matrix.set(matrix);
matrix.setRotate(angle);
return Bitmap.createBitmap(source, 0, 0, source.getWidth(),
source.getHeight(), matrix, false);
}

private void galleryAddPic() {
Intent mediaScanIntent = new Intent("android.intent.action.MEDIA_SCANNER_SCAN_FILE");
File f = new File(mCurrentPhotoPath);
Uri contentUri = Uri.fromFile(f);
mediaScanIntent.setData(contentUri);
this.sendBroadcast(mediaScanIntent);
}

private void dispatchTakePictureIntent(int actionCode) {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);

switch(actionCode) {
case ACTION_TAKE_PHOTO:
File f;

try {
f = setUpPhotoFile();
mCurrentPhotoPath = f.getAbsolutePath();
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(f));
} catch (IOException e) {
e.printStackTrace();
f = null;
mCurrentPhotoPath = null;
}
break;

default:
break;
} // switch

startActivityForResult(takePictureIntent, actionCode);
}

// Captures video from Android camera component
protected void dispatchTakeVideoIntent() {
Intent takeVideoIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
if (takeVideoIntent.resolveActivity(getPackageManager()) != null) {
// set the video image quality to high
takeVideoIntent.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 1);
startActivityForResult(takeVideoIntent, ACTION_TAKE_VIDEO);
}
}

private void handleCameraPhoto() {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);

Log.d("TAG", "Value of mCurrentPhotoPath: " + mCurrentPhotoPath);


if (mCurrentPhotoPath != null) {
setPic();
galleryAddPic();
mCurrentPhotoPath = null;
}

}
// Post recorded video into VideoView
private Uri handleCameraVideo(Intent intent) {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);

mVideoUri = intent.getData();
mVideoView.setVideoURI(mVideoUri);
// mImageBitmap = null;
mVideoView.setVisibility(View.VISIBLE);
mImageView.setVisibility(View.INVISIBLE);
mVideoView.start();
// saves video to file
saveVideo(mVideoUri);

return mVideoUri;

}

// click listener for the Android Camera button (not my app's button)
Button.OnClickListener mTakePicOnClickListener =
new Button.OnClickListener() {
@Override
public void onClick(View v) {
// mImageBitmap = null;
dispatchTakePictureIntent(ACTION_TAKE_PHOTO);
// releases the orientation lock
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
}
};
Button.OnClickListener mTakeVidOnClickListener =
new Button.OnClickListener() {
@Override
public void onClick(View v) {
dispatchTakeVideoIntent();
// releases the orientation lock
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
}
};


// Intent data is how the photo and video transfer into their views
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
switch (requestCode) {
case ACTION_TAKE_PHOTO: {
if (resultCode == RESULT_OK) {
handleCameraPhoto();
} else {
Log.d("TAG", "Result of photo not work.");
}
break;
} // ACTION_TAKE_PHOTO

case ACTION_TAKE_VIDEO: {
if (resultCode == RESULT_OK) {
handleCameraVideo(data);
}
break;
} // ACTION_TAKE_VIDEO
} // switch
}


// Some lifecycle callbacks so that the image can survive orientation change
@Override
protected void onSaveInstanceState(Bundle outState) {
outState.putParcelable(BITMAP_STORAGE_KEY, mImageBitmap);
outState.putParcelable(VIDEO_STORAGE_KEY, mVideoUri);
outState.putBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY, (mImageBitmap != null) );
outState.putBoolean(VIDEOVIEW_VISIBILITY_STORAGE_KEY, (mVideoUri != null) );
outState.putString("FILE_PATH", mCurrentPhotoPath);


if (mVideoUri != null) {
// use onSaveInstanceState in order to store the video or photo
outState.putInt("PositionVideo", mVideoView.getCurrentPosition());
// playback position for orientation change
mVideoView.pause();
}

// super should be last in this method
super.onSaveInstanceState(outState);

}

@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {


mCurrentPhotoPath = savedInstanceState.getString("FILE_PATH");

mImageView.setImageBitmap(mImageBitmap);
mImageView.setVisibility(
savedInstanceState.getBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY) ?
ImageView.VISIBLE : ImageView.INVISIBLE
);


mVideoUri = savedInstanceState.getParcelable(VIDEO_STORAGE_KEY);


mVideoView.setVideoURI(mVideoUri);
mVideoView.setVisibility(
savedInstanceState.getBoolean(VIDEOVIEW_VISIBILITY_STORAGE_KEY) ?
ImageView.VISIBLE : ImageView.INVISIBLE
);


if (mVideoUri != null) {
// for video, restores position it was playing
position = savedInstanceState.getInt("PositionVideo");
mVideoView.seekTo(position);
}


super.onRestoreInstanceState(savedInstanceState);


}

/**
* Indicates whether the specified action can be used as an intent. This
* method queries the package manager for installed packages that can
* respond to an intent with the specified action. If no suitable package is
* found, this method returns false.
* http://android-developers.blogspot.com/2009/01/can-i-use-this-intent.html
*
* @param context The application's environment.
* @param action The Intent action to check for availability.
*
* @return True if an Intent with the specified action can be sent and
* responded to, false otherwise.
*/
public static boolean isIntentAvailable(Context context, String action) {
final PackageManager packageManager = context.getPackageManager();
final Intent intent = new Intent(action);
List<ResolveInfo> list =
packageManager.queryIntentActivities(intent,
PackageManager.MATCH_DEFAULT_ONLY);
return list.size() > 0;
}

private void setBtnListenerOrDisable(Button btn, Button.OnClickListener onClickListener,
String intentName) {
if (isIntentAvailable(this, intentName)) {
btn.setOnClickListener(onClickListener);

} else {
btn.setClickable(false);
}
}


@Override
public boolean onOptionsItemSelected(MenuItem item) {

// Makes the UP caret go back to the previous fragment MakeCuteFragment
switch (item.getItemId()) {
case android.R.id.home:
android.app.FragmentManager fm= getFragmentManager();
fm.popBackStack();
finish();

return true;
default:
return super.onOptionsItemSelected(item);
}
}

}

最佳答案

经过反复试验,我终于找到了问题所在。我的第二次更新非常接近,唯一的错误是

mImageView.setVisibility(
savedInstanceState.getBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY) ?
ImageView.VISIBLE : ImageView.INVISIBLE
);

方法。我在 onCreate 中有这个,只有在它通过 null 检查时才执行,但我忘记的是当相机应用程序中的配置更改时,图像位图确实返回 null ,因此可见性将始终设置为不可见。 IMAGEVIEW_VISIBILITY_STORAGE_KEY 设置为如果位图为空则为真,如果为空则为假。所以一旦我摆脱了这个,我的其他保存状态代码就非常有效。下面是最终的工作代码。

MakePhotoVideo.java

package org.azurespot.makecute;

import android.content.Context;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.content.res.Configuration;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Matrix;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.support.v7.app.ActionBarActivity;
import android.util.Log;
import android.view.Gravity;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import android.widget.VideoView;

import org.azurespot.R;
import org.azurespot.cutecollection.CuteCollection;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Random;

public class MakePhotoVideo extends ActionBarActivity {

private static final int ACTION_TAKE_PHOTO = 1;
private static final int ACTION_TAKE_VIDEO = 2;
private static final String BITMAP_STORAGE_KEY = "viewbitmap";
private static final String IMAGEVIEW_VISIBILITY_STORAGE_KEY = "imageviewvisibility";
private ImageView mImageView;
private Bitmap mImageBitmap;

private static final String VIDEO_STORAGE_KEY = "viewvideo";
private static final String VIDEOVIEW_VISIBILITY_STORAGE_KEY = "videoviewvisibility";
private VideoView mVideoView;
private Uri mVideoUri;
private File fileVideo;

private String mCurrentPhotoPath;
String videoPath;
private int position = 0;
int targetH;
int targetW;

private static final String JPEG_FILE_PREFIX = "IMG_";
private static final String JPEG_FILE_SUFFIX = ".jpg";

private PhotoStorageDirFactory mPhotoStorageDirFactory = null;


/* Photo album for this application */
private String getAlbumName() {
return getString(R.string.album_name);
}

@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_make_photo_video);

mImageView = (ImageView) findViewById(R.id.taken_photo);
mVideoView = (VideoView) findViewById(R.id.video_view);
mImageView.setVisibility(View.VISIBLE);
mVideoView.setVisibility(View.INVISIBLE);
mImageView.setSaveEnabled(true);

Button photoBtn = (Button) findViewById(R.id.click);
setBtnListenerOrDisable(photoBtn, mTakePicOnClickListener, MediaStore.ACTION_IMAGE_CAPTURE);

Button videoBtn = (Button) findViewById(R.id.record_video);
setBtnListenerOrDisable(videoBtn, mTakeVidOnClickListener, MediaStore.ACTION_VIDEO_CAPTURE);

mPhotoStorageDirFactory = new BasePhotoDirFactory();

// Shows the up carat near app icon in ActionBar
getSupportActionBar().setDisplayUseLogoEnabled(false);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);

}


public void viewCollection(View v){

// finishes/restarts the activity so the unsaved video does not corrupt
Intent intent = getIntent();
finish();
startActivity(intent);

// goes to Cute Collection activity
Intent i = new Intent(this, CuteCollection.class);
startActivity(i);
}

private File getAlbumDir() {
File storageDir = null;

if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())) {

storageDir = mPhotoStorageDirFactory.getAlbumStorageDir(getAlbumName());

if (storageDir != null) {
if (! storageDir.mkdirs()) {
if (! storageDir.exists()){
Log.d("Camera", "failed to create directory");
return null;
}
}
}

} else {
Log.v(getString(R.string.app_name), "External storage is not mounted READ/WRITE.");
}

return storageDir;
}

private File createImageFile() throws IOException {
// Create an image file name
String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
String imageFileName = JPEG_FILE_PREFIX + timeStamp + "_";
File albumF = getAlbumDir();
File imageF = File.createTempFile(imageFileName, JPEG_FILE_SUFFIX, albumF);
return imageF;
}

private File setUpPhotoFile() throws IOException {

File f = createImageFile();
mCurrentPhotoPath = f.getAbsolutePath();

return f;
}


private void setPic() {

mImageView.setVisibility(View.VISIBLE);
mVideoView.setVisibility(View.INVISIBLE);

/* There isn't enough memory to open up more than a couple camera photos */
/* So pre-scale the target bitmap into which the file is decoded */

/* Get the size of the image */
BitmapFactory.Options bmOptions = new BitmapFactory.Options();
bmOptions.inJustDecodeBounds = true;

if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_LANDSCAPE){
targetH = 570;
targetW = 960;
} else if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT){
targetH = 960;
targetW = 570;
}

BitmapFactory.decodeFile(mCurrentPhotoPath, bmOptions);
int photoW = bmOptions.outWidth;
int photoH = bmOptions.outHeight;

/* Figure out which way needs to be reduced less */
int scaleFactor = Math.min(photoW/targetW, photoH/targetH);

/* Set bitmap options to scale the image decode target */
bmOptions.inJustDecodeBounds = false;
bmOptions.inPreferredConfig = Bitmap.Config.RGB_565;
bmOptions.inSampleSize = scaleFactor;
bmOptions.inBitmap = mImageBitmap;
bmOptions.inPurgeable = true;


/* Decode the JPEG file into a Bitmap */
mImageBitmap = BitmapFactory.decodeFile(mCurrentPhotoPath, bmOptions);


if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) {
mImageBitmap = rotateBitmap(mImageBitmap, 90);
}

savePhoto(mImageBitmap);

/* Associate the Bitmap to the ImageView, make sure the VideoView
* is cleared to replace with ImageView */
mImageView.setImageBitmap(mImageBitmap);
mVideoUri = null;
}

// save your photo to SD card
private void savePhoto(final Bitmap bitmapPhoto){
// set OnClickListener to save the photo
mImageView.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
boolean success = false;

File photoDir = new File(Environment.getExternalStoragePublicDirectory
(Environment.DIRECTORY_PICTURES) + "/Cute Photos");
photoDir.mkdirs();
Random generator = new Random();
int n = 10000;
n = generator.nextInt(n);
String photoName = "Photo"+ n +".jpg";
File filePhoto = new File (photoDir, photoName);

try {
FileOutputStream out = new FileOutputStream(filePhoto);
bitmapPhoto.compress(Bitmap.CompressFormat.JPEG, 100, out);
out.flush();
out.close();
success = true;
} catch (Exception e) {
e.printStackTrace();
}

if (success) {
Toast toast = Toast.makeText(getApplicationContext(), "Cute photo saved!",
Toast.LENGTH_LONG);
LinearLayout toastLayout = (LinearLayout) toast.getView();
toastLayout.setBackgroundColor(getResources().getColor(R.color.toast_color));
TextView toastTV = (TextView) toastLayout.getChildAt(0);
toastTV.setTextSize(30);
toast.setGravity(Gravity.CENTER_VERTICAL, 0, 80);
toast.show();
} else {
Toast.makeText(getApplicationContext(),
"Error during image saving", Toast.LENGTH_SHORT).show();
}

}
});
}


// save your video to SD card
protected void saveVideo(final Uri uriVideo){

// click the video to save it
mVideoView.setOnTouchListener(new View.OnTouchListener() {

public boolean onTouch(View v, MotionEvent event) {

boolean success = false;

if(event.getAction() == MotionEvent.ACTION_UP) {

try {
// make the directory
File vidDir = new File(android.os.Environment.getExternalStoragePublicDirectory
(Environment.DIRECTORY_MOVIES) + File.separator + "Cute Videos");
vidDir.mkdirs();

// create unique identifier
Random generator = new Random();
int n = 100;
n = generator.nextInt(n);
// create file name
String videoName = "Video" + n + ".mp4";

fileVideo = new File(vidDir.getAbsolutePath(), videoName);

videoPath = fileVideo.getAbsolutePath();

Log.d("TAG", "Value of videoPath:" + videoPath);

fileVideo.setWritable(true, false);

OutputStream out = new FileOutputStream(fileVideo);
InputStream in = getContentResolver().openInputStream(uriVideo);

byte buffer[] = new byte[1024];
int length = 0;
while ((length = in.read(buffer)) > 0) {
out.write(buffer, 0, length);
}

out.close();
in.close();

success = true;

} catch (Exception e) {
e.printStackTrace();
}

if (success) {
Toast toast = Toast.makeText(getApplicationContext(), "Cute video saved!",
Toast.LENGTH_SHORT);
LinearLayout toastLayout = (LinearLayout) toast.getView();
toastLayout.setBackgroundColor(getResources().getColor(R.color.toast_color));
TextView toastTV = (TextView) toastLayout.getChildAt(0);
toastTV.setTextSize(30);
toast.setGravity(Gravity.CENTER_VERTICAL, 0, 80);
toast.show();
} else {
Toast.makeText(getApplicationContext(),
"Error during video saving", Toast.LENGTH_SHORT).show();
}
}

return true;
}
});
}


public Bitmap rotateBitmap(Bitmap source, int angle)
{
Matrix matrix = new Matrix();
matrix.set(matrix);
matrix.setRotate(angle);
return Bitmap.createBitmap(source, 0, 0, source.getWidth(),
source.getHeight(), matrix, false);
}

private void galleryAddPic() {
Intent mediaScanIntent = new Intent("android.intent.action.MEDIA_SCANNER_SCAN_FILE");
File f = new File(mCurrentPhotoPath);
Uri contentUri = Uri.fromFile(f);
mediaScanIntent.setData(contentUri);
this.sendBroadcast(mediaScanIntent);
}

private void dispatchTakePictureIntent(int actionCode) {
Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);

switch(actionCode) {
case ACTION_TAKE_PHOTO:
File f;

try {
f = setUpPhotoFile();
Log.d("TAG", "Value of f in picture intent: " + f);
mCurrentPhotoPath = f.getAbsolutePath();
takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(f));
} catch (IOException e) {
e.printStackTrace();
f = null;
mCurrentPhotoPath = null;
}
break;

default:
break;
} // switch

startActivityForResult(takePictureIntent, actionCode);
}

// Captures video from Android camera component
protected void dispatchTakeVideoIntent() {
Intent takeVideoIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
if (takeVideoIntent.resolveActivity(getPackageManager()) != null) {
// set the video image quality to high
takeVideoIntent.putExtra(MediaStore.EXTRA_VIDEO_QUALITY, 1);
startActivityForResult(takeVideoIntent, ACTION_TAKE_VIDEO);
}
}

private void handleCameraPhoto() {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);

if (mCurrentPhotoPath != null) {
setPic();
galleryAddPic();
mCurrentPhotoPath = null;
}

}
// Post recorded video into VideoView
private Uri handleCameraVideo(Intent intent) {
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);

mVideoUri = intent.getData();
mVideoView.setVideoURI(mVideoUri);
mImageBitmap = null;
mVideoView.setVisibility(View.VISIBLE);
mImageView.setVisibility(View.INVISIBLE);
mVideoView.start();
// saves video to file
saveVideo(mVideoUri);

return mVideoUri;

}

// click listener for the Android Camera button (not my app's button)
Button.OnClickListener mTakePicOnClickListener =
new Button.OnClickListener() {
@Override
public void onClick(View v) {
// mImageBitmap = null;
dispatchTakePictureIntent(ACTION_TAKE_PHOTO);
// releases the orientation lock
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
}
};
Button.OnClickListener mTakeVidOnClickListener =
new Button.OnClickListener() {
@Override
public void onClick(View v) {
dispatchTakeVideoIntent();
// releases the orientation lock
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
}
};

// Intent data is how the photo and video transfer into their views
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
switch (requestCode) {
case ACTION_TAKE_PHOTO: {
if (resultCode == RESULT_OK) {
handleCameraPhoto();
}
break;
}
case ACTION_TAKE_VIDEO: {
if (resultCode == RESULT_OK) {
handleCameraVideo(data);
}
break;
}
}
}


// Some lifecycle callbacks so that the image can survive orientation change
@Override
protected void onSaveInstanceState(Bundle outState) {
outState.putParcelable(BITMAP_STORAGE_KEY, mImageBitmap);
outState.putParcelable(VIDEO_STORAGE_KEY, mVideoUri);

outState.putBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY, (mImageBitmap != null) );
outState.putBoolean(VIDEOVIEW_VISIBILITY_STORAGE_KEY, (mVideoUri != null) );

outState.putString("FILE_PATH", mCurrentPhotoPath);

if (mVideoUri != null) {
// use onSaveInstanceState in order to store the video or photo
outState.putInt("PositionVideo", mVideoView.getCurrentPosition());
// playback position for orientation change
mVideoView.pause();
}

// super should be last in this method
super.onSaveInstanceState(outState);

}

// this is called after onCreate (when returning from camera app),
// so br careful what you put here
@Override
protected void onRestoreInstanceState(Bundle savedInstanceState) {
mCurrentPhotoPath = savedInstanceState.getString("FILE_PATH");

mVideoUri = savedInstanceState.getParcelable(VIDEO_STORAGE_KEY);
mVideoView.setVideoURI(mVideoUri);
mVideoView.setVisibility(
savedInstanceState.getBoolean(VIDEOVIEW_VISIBILITY_STORAGE_KEY) ?
ImageView.VISIBLE : ImageView.INVISIBLE
);

if (mVideoUri != null) {
// for video, restores position it was playing
position = savedInstanceState.getInt("PositionVideo");
mVideoView.seekTo(position);
}

super.onRestoreInstanceState(savedInstanceState);
}

/**
* Indicates whether the specified action can be used as an intent. This
* method queries the package manager for installed packages that can
* respond to an intent with the specified action. If no suitable package is
* found, this method returns false.
* http://android-developers.blogspot.com/2009/01/can-i-use-this-intent.html
*
* @param context The application's environment.
* @param action The Intent action to check for availability.
*
* @return True if an Intent with the specified action can be sent and
* responded to, false otherwise.
*/
public static boolean isIntentAvailable(Context context, String action) {
final PackageManager packageManager = context.getPackageManager();
final Intent intent = new Intent(action);
List<ResolveInfo> list =
packageManager.queryIntentActivities(intent,
PackageManager.MATCH_DEFAULT_ONLY);
return list.size() > 0;
}

private void setBtnListenerOrDisable(Button btn, Button.OnClickListener onClickListener,
String intentName) {
if (isIntentAvailable(this, intentName)) {
btn.setOnClickListener(onClickListener);

} else {
btn.setClickable(false);
}
}


@Override
public boolean onOptionsItemSelected(MenuItem item) {

// Makes the UP caret go back to the previous fragment MakeCuteFragment
switch (item.getItemId()) {
case android.R.id.home:
android.app.FragmentManager fm= getFragmentManager();
fm.popBackStack();
finish();

return true;
default:
return super.onOptionsItemSelected(item);
}
}

}

关于android - 在 Camera 中配置更改后,返回到带有空 ImageView 的应用程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/29453858/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com