最近項目中需要在界面中點(diǎn)擊按鈕拍照,但不展示預(yù)覽界面(吐槽:什么鬼需求),本來以為比較簡單,但在實現(xiàn)時遇到幾個問題,在此記錄下
本人的實現(xiàn)思路是將預(yù)覽界面的大小設(shè)置為一個寬高都為1px的界面就可以了
一開始的代碼
Camera camera;
private void takePhoto(){
if (camera == null)
camera = Camera.open();
if (camera != null) {
SurfaceView surfaceView = new SurfaceView(this);
//設(shè)置預(yù)覽
try {
camera.setPreviewDisplay(surfaceView.getHolder());
} catch (IOException e) {
e.printStackTrace();
}
camera.startPreview();
camera.takePicture(null, null, new Camera.PictureCallback() {
@Override
public void onPictureTaken(byte[] data, Camera camera) {
try {
File file = getFile();
if (file == null) {
return;
}
FileOutputStream fos = new FileOutputStream(file);
fos.write(data);
fos.close();
Log.e("PhotoHandler", "圖片保存完成");
} catch (Exception error) {
error.printStackTrace();
}
camera.stopPreview();
}
});
}
}
private String FILE_PATH = Environment
.getExternalStorageDirectory().getAbsolutePath()
+ "/testImage/";
private File getFile() {
File f = new File(FILE_PATH);
if (!f.exists()) {
f.mkdirs();
}
String timeStamp = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date());
File file;
file = new File(FILE_PATH,
"IMG_" + timeStamp + ".jpg");
try {
if (!file.exists()) {
file.createNewFile();
}
} catch (IOException e) {
e.printStackTrace();
}
return file;
}
報錯:Caused by: java.lang.RuntimeException: takePicture failed
百度了下找到解決方法
問題是在相機(jī)實例上開始預(yù)覽后,需要一些時間才能拍照
camera.startPreview();
camera.setOneShotPreviewCallback(new Camera.PreviewCallback() {
@Override
public void onPreviewFrame(byte[] data, Camera camera) {
camera.takePicture(null, null, new Camera.PictureCallback() {
@Override
public void onPictureTaken(byte[] data, Camera camera) {
// do something you want with your picture and stop preview
camera.stopPreview();
}
});
將takePicture方法放在setOneShotPreviewCallback回調(diào)中解決問題
又遇見問題 調(diào)用后沒反應(yīng),回調(diào)中也沒走
后來發(fā)現(xiàn)是SurfaceView 問題,直接new的話就會有這個問題,在xml文件中聲明就沒有問題(暫時不知道原因,哪位大佬知道麻煩告知,謝謝)
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#ffffff">
<SurfaceView
android:id="@+id/sview"
android:layout_width="1px"
android:layout_height="1px"/>
<ImageView
android:layout_margin="5dp"
android:id="@+id/button"
android:layout_centerInParent="true"
android:layout_width="30dp"
android:layout_height="30dp"
android:background="@mipmap/ic_launcher_round"/>
</RelativeLayout>
Camera camera;
private SurfaceView surfaceview;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
surfaceview = findViewById(R.id.sview);
ImageView button = findViewById(R.id.button);
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
takePhoto();
}
});
}
private void takePhoto(){
if (camera == null)
camera = Camera.open();
if (camera != null) {
// SurfaceView surfaceView = new SurfaceView(this);
//設(shè)置預(yù)覽
try {
camera.setPreviewDisplay(surfaceview.getHolder());
} catch (IOException e) {
e.printStackTrace();
}
.......
}
}
最終實現(xiàn)需求