Java android opencv摄像头应用程序挂起
我正在使用opencv创建一个android摄像头应用程序。首先,当我点击开始按钮时,它开始拍照,每秒钟拍一张照片并存储在存储器中。它对我非常有效 然后我试着让它变得有些棘手,强迫它在一秒钟内拍5张照片,效果很好 但事实上,当我在一秒钟内拍摄到20张照片时,我遇到了这个问题。它不起作用。只要我点击开始按钮,应用程序就会挂起。我不知道为什么。但我认为问题在于线程 有人能帮我怎么做吗 我的项目中有两个java文件,下面是代码Java android opencv摄像头应用程序挂起,java,android,multithreading,opencv,freeze,Java,Android,Multithreading,Opencv,Freeze,我正在使用opencv创建一个android摄像头应用程序。首先,当我点击开始按钮时,它开始拍照,每秒钟拍一张照片并存储在存储器中。它对我非常有效 然后我试着让它变得有些棘手,强迫它在一秒钟内拍5张照片,效果很好 但事实上,当我在一秒钟内拍摄到20张照片时,我遇到了这个问题。它不起作用。只要我点击开始按钮,应用程序就会挂起。我不知道为什么。但我认为问题在于线程 有人能帮我怎么做吗 我的项目中有两个java文件,下面是代码 package org.opencv.samples.tutorial3;
package org.opencv.samples.tutorial3;
import java.io.FileOutputStream;
import java.util.List;
import org.opencv.android.JavaCameraView;
import android.content.Context;
import android.hardware.Camera;
import android.hardware.Camera.PictureCallback;
import android.hardware.Camera.Size;
import android.util.AttributeSet;
import android.util.Log;
public class Tutorial3View extends JavaCameraView implements PictureCallback {
private static final String TAG = "Sample::Tutorial3View";
private String mPictureFileName;
public Tutorial3View(Context context, AttributeSet attrs) {
super(context, attrs);
}
public List<String> getEffectList() {
return mCamera.getParameters().getSupportedColorEffects();
}
public boolean isEffectSupported() {
return (mCamera.getParameters().getColorEffect() != null);
}
public String getEffect() {
return mCamera.getParameters().getColorEffect();
}
public void setEffect(String effect) {
Camera.Parameters params = mCamera.getParameters();
params.setColorEffect(effect);
mCamera.setParameters(params);
}
public List<Size> getResolutionList() {
return mCamera.getParameters().getSupportedPreviewSizes();
}
public void setResolution(Size resolution) {
disconnectCamera();
mMaxHeight = resolution.height;
mMaxWidth = resolution.width;
connectCamera(getWidth(), getHeight());
}
public Size getResolution() {
return mCamera.getParameters().getPreviewSize();
}
public void takePicture(final String fileName) {
Log.i(TAG, "Taking picture");
this.mPictureFileName = fileName;
// Postview and jpeg are sent in the same buffers if the queue is not empty when performing a capture.
// Clear up buffers to avoid mCamera.takePicture to be stuck because of a memory issue
mCamera.setPreviewCallback(null);
// PictureCallback is implemented by the current class
mCamera.takePicture(null, null, this);
}
@Override
public void onPictureTaken(byte[] data, Camera camera) {
Log.i(TAG, "Saving a bitmap to file");
// The camera preview was automatically stopped. Start it again.
mCamera.startPreview();
mCamera.setPreviewCallback(this);
// Write the image in a file (in jpeg format)
try {
FileOutputStream fos = new FileOutputStream(mPictureFileName);
fos.write(data);
fos.close();
} catch (java.io.IOException e) {
Log.e("PictureDemo", "Exception in photoCallback", e);
}
}
}
package org.opencv.samples.tutorial3;
导入java.io.FileOutputStream;
导入java.util.List;
导入org.opencv.android.JavaCameraView;
导入android.content.Context;
导入android.hardware.Camera;
导入android.hardware.Camera.PictureCallback;
导入android.hardware.Camera.Size;
导入android.util.AttributeSet;
导入android.util.Log;
公共类教程3View扩展JavaCameraView实现PictureCallback{
私有静态最终字符串TAG=“Sample::Tutorial3View”;
私有字符串mPictureFileName;
公共教程3视图(上下文、属性集属性){
超级(上下文,attrs);
}
公共列表getEffectList(){
返回mCamera.getParameters().getSupportedColorEffects();
}
公共布尔值受支持(){
返回值(mCamera.getParameters().getColorEffect()!=null);
}
公共字符串getEffect(){
返回mCamera.getParameters().getColorEffect();
}
公共无效设置效果(字符串效果){
Camera.Parameters params=mCamera.getParameters();
参数setColorEffect(效果);
mCamera.setParameters(参数);
}
公共列表getResolutionList(){
返回mCamera.getParameters().getSupportedPreviewSizes();
}
公共空间分辨率(大小分辨率){
断开摄像头();
mMaxHeight=分辨率.height;
mMaxWidth=分辨率.width;
连接摄像头(getWidth(),getHeight());
}
公共大小getResolution(){
返回mCamera.getParameters().getPreviewSize();
}
public void takePicture(最终字符串文件名){
Log.i(标签“拍照”);
this.mPictureFileName=文件名;
//如果执行捕获时队列不为空,则Postview和jpeg将在相同的缓冲区中发送。
//清除缓冲区以避免mCamera.takePicture因内存问题而被卡住
mCamera.setPreviewCallback(null);
//PictureCallback由当前类实现
takePicture(null,null,this);
}
@凌驾
公共void onPictureTaken(字节[]数据,摄像头){
Log.i(标记“将位图保存到文件”);
//相机预览已自动停止。请重新启动。
mCamera.startPreview();
mCamera.setPreviewCallback(此);
//将图像写入文件(jpeg格式)
试一试{
FileOutputStream fos=新的FileOutputStream(mPictureFileName);
写入(数据);
fos.close();
}捕获(java.io.ioe异常){
Log.e(“PictureDemo”,“photoCallback中的异常”,e);
}
}
}
第二个是:
package org.opencv.samples.tutorial3;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.ListIterator;
import org.opencv.android.BaseLoaderCallback;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;
import org.opencv.android.LoaderCallbackInterface;
import org.opencv.android.OpenCVLoader;
import org.opencv.core.Mat;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.hardware.Camera.Size;
import android.os.Bundle;
import android.os.Environment;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.SubMenu;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnTouchListener;
import android.view.WindowManager;
import android.widget.Button;
import android.widget.Toast;
public class Tutorial3Activity extends Activity implements CvCameraViewListener2 {
private static final String TAG = "OCVSample::Activity";
private Tutorial3View mOpenCvCameraView;
private List<Size> mResolutionList;
private MenuItem[] mEffectMenuItems;
private SubMenu mColorEffectsMenu;
private MenuItem[] mResolutionMenuItems;
private SubMenu mResolutionMenu;
Thread thread;
Button start,stop;
boolean loop=false;
private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {
@Override
public void onManagerConnected(int status) {
switch (status) {
case LoaderCallbackInterface.SUCCESS:
{
Log.i(TAG, "OpenCV loaded successfully");
mOpenCvCameraView.enableView();
} break;
default:
{
super.onManagerConnected(status);
} break;
}
}
};
public Tutorial3Activity() {
Log.i(TAG, "Instantiated new " + this.getClass());
}
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
Log.i(TAG, "called onCreate");
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
setContentView(R.layout.tutorial3_surface_view);
start=(Button)findViewById(R.id.button2) ;
start.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
loop=true;
thread = new Thread(new task());
thread.start();
}
});
stop=(Button) findViewById(R.id.button);
stop.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
loop=false;
}
});
mOpenCvCameraView = (Tutorial3View) findViewById(R.id.tutorial3_activity_java_surface_view);
mOpenCvCameraView.setVisibility(SurfaceView.VISIBLE);
mOpenCvCameraView.setCvCameraViewListener(this);
}
@Override
public void onPause()
{
super.onPause();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
@Override
public void onResume()
{
super.onResume();
if (!OpenCVLoader.initDebug()) {
Log.d(TAG, "Internal OpenCV library not found. Using OpenCV Manager for initialization");
OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_3_0_0, this, mLoaderCallback);
} else {
Log.d(TAG, "OpenCV library found inside package. Using it!");
mLoaderCallback.onManagerConnected(LoaderCallbackInterface.SUCCESS);
}
}
public void onDestroy() {
super.onDestroy();
if (mOpenCvCameraView != null)
mOpenCvCameraView.disableView();
}
public void onCameraViewStarted(int width, int height) {
}
public void onCameraViewStopped() {
}
public Mat onCameraFrame(CvCameraViewFrame inputFrame) {
return inputFrame.rgba();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
List<String> effects = mOpenCvCameraView.getEffectList();
if (effects == null) {
Log.e(TAG, "Color effects are not supported by device!");
return true;
}
mColorEffectsMenu = menu.addSubMenu("Color Effect");
mEffectMenuItems = new MenuItem[effects.size()];
int idx = 0;
ListIterator<String> effectItr = effects.listIterator();
while(effectItr.hasNext()) {
String element = effectItr.next();
mEffectMenuItems[idx] = mColorEffectsMenu.add(1, idx, Menu.NONE, element);
idx++;
}
mResolutionMenu = menu.addSubMenu("Resolution");
mResolutionList = mOpenCvCameraView.getResolutionList();
mResolutionMenuItems = new MenuItem[mResolutionList.size()];
ListIterator<Size> resolutionItr = mResolutionList.listIterator();
idx = 0;
while(resolutionItr.hasNext()) {
Size element = resolutionItr.next();
mResolutionMenuItems[idx] = mResolutionMenu.add(2, idx, Menu.NONE,
Integer.valueOf(element.width).toString() + "x" + Integer.valueOf(element.height).toString());
idx++;
}
return true;
}
public boolean onOptionsItemSelected(MenuItem item) {
Log.i(TAG, "called onOptionsItemSelected; selected item: " + item);
if (item.getGroupId() == 1)
{
mOpenCvCameraView.setEffect((String) item.getTitle());
Toast.makeText(this, mOpenCvCameraView.getEffect(), Toast.LENGTH_SHORT).show();
}
else if (item.getGroupId() == 2)
{
int id = item.getItemId();
Size resolution = mResolutionList.get(id);
mOpenCvCameraView.setResolution(resolution);
resolution = mOpenCvCameraView.getResolution();
String caption = Integer.valueOf(resolution.width).toString() + "x" + Integer.valueOf(resolution.height).toString();
Toast.makeText(this, caption, Toast.LENGTH_SHORT).show();
}
return true;
}
class task implements Runnable {
public void run() {
while (loop) {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH-mm-ss");
String currentDateandTime = sdf.format(new Date());
final String fileName = Environment.getExternalStorageDirectory().getPath() +
"/sample_picture_" + currentDateandTime + ".jpg";
mOpenCvCameraView.takePicture(fileName);
runOnUiThread(new Runnable() {
@Override
public void run() {
Toast.makeText(Tutorial3Activity.this, fileName + " saved", Toast.LENGTH_SHORT).show();
}
});
try {
thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
package org.opencv.samples.tutorial3;
导入java.text.simpleDataFormat;
导入java.util.Date;
导入java.util.List;
导入java.util.ListIterator;
导入org.opencv.android.BaseLoaderCallback;
导入org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;
导入org.opencv.android.LoaderCallbackInterface;
导入org.opencv.android.OpenCVLoader;
导入org.opencv.core.Mat;
导入org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;
导入android.annotation.SuppressLint;
导入android.app.Activity;
导入android.hardware.Camera.Size;
导入android.os.Bundle;
导入android.os.Environment;
导入android.util.Log;
导入android.view.Menu;
导入android.view.MenuItem;
导入android.view.MotionEvent;
导入android.view.SubMenu;
导入android.view.SurfaceView;
导入android.view.view;
导入android.view.view.OnTouchListener;
导入android.view.WindowManager;
导入android.widget.Button;
导入android.widget.Toast;
公共类教程3活动扩展活动实现CvCameraViewListener2{
私有静态最终字符串TAG=“OCVSample::Activity”;
私人教程3查看mOpenCvCameraView;
私有列表mResolutionList;
私有菜单项[]效果菜单项;
专用子菜单mColorEffectsMenu;
私有菜单项[]mResolutionMenuItems;
专用子菜单mResolutionMenu;
螺纹;
按钮启动、停止;
布尔循环=假;
专用BaseLoaderCallback mlLoaderCallback=新BaseLoaderCallback(此){
@凌驾
已连接管理器上的公共无效(int状态){
开关(状态){
案例加载程序CallbackInterface.SUCCESS:
{
Log.i(标记“OpenCV已成功加载”);
mOpenCvCameraView.enableView();
}中断;
违约:
{
超级管理器已连接(状态);
}中断;
}
}
};
公共教程3活动(){
Log.i(标记“实例化新”+this.getClass());
}
/**在首次创建活动时调用*/
@凌驾
创建时的公共void(Bundle savedInstanceState){
Log.i(标记“calledoncreate”);
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG\u保持屏幕打开);
setContentView(R.layout.tutorial3_surface_视图);
开始=(按钮)findViewById(R.id.button2);
start.setOnClickListener(新视图.OnClickListener(){
@凌驾
公共void onClick(视图){
循环=真;
线程=新线程(新任务(