我为Android开发了一个OCR文本到语音应用程序。我被中间击中了。当我运行应用程序时,它检测到文档并发出相机快门声并发出“意外应用已停止” 请有人帮我解决这个问题。 图像捕获,保存到存储和保存文本文件都在下面的两个类中编码
HelloOpenCvActivity.java
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Timer;
import java.util.TimerTask;
import org.opencv.android.BaseLoaderCallback;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewFrame;
import org.opencv.android.CameraBridgeViewBase.CvCameraViewListener2;
import org.opencv.android.LoaderCallbackInterface;
import org.opencv.android.OpenCVLoader;
import org.opencv.core.Mat;
import org.opencv.core.MatOfPoint;
import org.opencv.core.Scalar;
import org.opencv.imgproc.Imgproc;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.hardware.Camera.Size;
import android.media.Ringtone;
import android.media.RingtoneManager;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.speech.tts.TextToSpeech;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.SurfaceView;
import android.view.WindowManager;
import android.widget.Toast;
public class HelloOpenCvActivity extends Activity implements
CvCameraViewListener2, TextToSpeech.OnInitListener {
public static TextToSpeech mTts;
private static final int MY_DATA_CHECK_CODE = 1234;
private HelloViewer mOpenCvCameraView;
private boolean killed = false;
private Uri notification;
private Ringtone ringTone;
private Timer timer = new Timer();
private MenuItem mItemLanguage = null;
private boolean mIsJavaCamera = true;
public static String lang = "eng";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
setContentView(R.layout.opencv_layout);
// setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_SENSOR_PORTRAIT);
mOpenCvCameraView = (HelloViewer) findViewById(R.id.HelloOpenCvView);
mOpenCvCameraView.setVisibility(SurfaceView.VISIBLE);
mOpenCvCameraView.setCvCameraViewListener(this);
notification = RingtoneManager
.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
ringTone = RingtoneManager.getRingtone(getApplicationContext(),
notification);
// Fire off an intent to check if a TTS engine is installed
Intent checkIntent = new Intent();
checkIntent.setAction(TextToSpeech.Engine.ACTION_CHECK_TTS_DATA);
startActivityForResult(checkIntent, MY_DATA_CHECK_CODE);
}
@Override
public void onPause() {
super.onPause();
//shutdownCamera();
}
@Override
public void onDestroy() {
super.onDestroy();
shutdownCamera();
if (mTts != null) {
mTts.stop();
mTts.shutdown();
}
}
@Override
public void onCameraViewStarted(int width, int height) {
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
Log.e(Util.TAG, "Sleeping failed before starting camera view. ", e);
}
Size resolution = mOpenCvCameraView.getResolution();
mOpenCvCameraView.setResolution(resolution);
mOpenCvCameraView.setAutoFocus();
}
@Override
public void onCameraViewStopped() {
}
@Override
public Mat onCameraFrame(CvCameraViewFrame inputFrame) {
Mat mRgba = null;
try {
mRgba = inputFrame.rgba();
List<MatOfPoint> contours = new ArrayList<MatOfPoint>();
contours.add(DetectSquares.find(mRgba));
if (contours.get(0) != null) {
Imgproc.drawContours(mRgba, contours, -1, new Scalar(0, 255, 0), 4);
if (!killed) {
killed = true;
ringTone.play();
timer = new Timer();
timer.schedule(new TimerTask() {
@Override
public void run() {
ringTone.stop();
captureImage();
}
}, 4 * 1000);
}
} else {
killed = false;
ringTone.stop();
timer.cancel();
}
} catch (Exception exc) {
Log.e(Util.TAG, "Error occured" + exc.getMessage());
}
return mRgba;
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
mItemLanguage = menu.add("Toggle between languages");
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
String toastMesage = new String();
Log.i(Util.TAG, "called onOptionsItemSelected; selected item: " + item);
if (item == mItemLanguage) {
mOpenCvCameraView.setVisibility(SurfaceView.GONE);
mIsJavaCamera = !mIsJavaCamera;
if (mIsJavaCamera) {
String english = "Language English is selected";
toastMesage = english;
lang = "eng";
mTts.speak(english, TextToSpeech.QUEUE_ADD, null);
} else {
String sinhala = "Language Sinhala is selected";
toastMesage = sinhala;
lang = "sin";
mTts.speak(sinhala, TextToSpeech.QUEUE_ADD, null);
}
mOpenCvCameraView.setVisibility(SurfaceView.VISIBLE);
mOpenCvCameraView.setCvCameraViewListener(this);
mOpenCvCameraView.enableView();
Toast toast = Toast.makeText(this, toastMesage, Toast.LENGTH_LONG);
toast.show();
}
return true;
}
@SuppressLint("SimpleDateFormat")
private void captureImage() {
try {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd_HH-mm-ss");
String currentDateandTime = sdf.format(new Date());
String fileName = Environment.getExternalStorageDirectory().getPath() + "/project/" + currentDateandTime;
mOpenCvCameraView.takePicture(fileName);
} catch (Exception exc) {
Log.e(Util.TAG, "Error in capture image", exc);
}
}
private BaseLoaderCallback mLoaderCallback = new BaseLoaderCallback(this) {
@Override
public void onManagerConnected(int status) {
switch (status) {
case LoaderCallbackInterface.SUCCESS:
Log.i(Util.TAG, "OpenCV loaded successfully");
mOpenCvCameraView.enableView();
break;
default:
super.onManagerConnected(status);
break;
}
}
};
@Override
public void onResume() {
super.onResume();
OpenCVLoader.initAsync(OpenCVLoader.OPENCV_VERSION_3_0_0, this,
mLoaderCallback);
}
public void onActivityResult(int requestCode, int resultCode, Intent data) {
if (requestCode == MY_DATA_CHECK_CODE) {
if (resultCode == TextToSpeech.Engine.CHECK_VOICE_DATA_PASS) {
// success, create the TTS instance
mTts = new TextToSpeech(this, this);
} else {
// missing TTS data, install it
Intent installIntent = new Intent();
installIntent.setAction(TextToSpeech.Engine.ACTION_INSTALL_TTS_DATA);
startActivity(installIntent);
}
}
}
@Override
public void onInit(int arg0) {
// Drop all pending entries in the playback queue.
mTts.speak("Place your mobile on top of the document, and move it up slowly.", TextToSpeech.QUEUE_FLUSH, null);
}
private void shutdownCamera() {
if (mOpenCvCameraView != null) {
if (mOpenCvCameraView.getCamera() != null) {
mOpenCvCameraView.getCamera().stopPreview();
mOpenCvCameraView.getCamera().release();
mOpenCvCameraView.setCamera(null);
}
mOpenCvCameraView.disableView();
}}}
HelloViewer.java
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileWriter;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import org.opencv.android.JavaCameraView;
import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Bitmap;
import android.hardware.Camera;
import android.hardware.Camera.PictureCallback;
import android.hardware.Camera.ShutterCallback;
import android.hardware.Camera.Size;
import android.os.AsyncTask;
import android.os.Environment;
import android.speech.tts.TextToSpeech;
import android.util.AttributeSet;
import android.util.Log;
public class HelloViewer extends JavaCameraView implements PictureCallback, ShutterCallback {
private String mPictureFileName;
public HelloViewer(Context context, AttributeSet attrs) {
super(context, attrs);
}
public void setResolution(Size resolution) {
disconnectCamera();
mMaxHeight = 480; // resolution.width;
mMaxWidth = 640; // resolution.height;
//connectCamera(getWidth(), getHeight());
// Sets the preview size of camera.
connectCamera(getWidth(),getHeight());
}
public Size getResolution() {
List<Camera.Size> sizes = mCamera.getParameters().getSupportedPictureSizes();
for (Camera.Size size : sizes) {
Log.i(Util.TAG, "Picture sizes height : " + size.height + ", width : " + size.width);
}
return mCamera.getParameters().getPreviewSize();
}
public void setAutoFocus() {
Log.i(Util.TAG, "Seting autofocus mode to Continuous picture.");
Camera.Parameters parameters = mCamera.getParameters();
parameters.setFocusMode("continuous-picture");
// Enable in nexus 3
//parameters.setPictureSize(2592, 1944);
mCamera.setParameters(parameters);
}
public void takePicture(final String fileName) {
Log.i(Util.TAG, "Taking picture");
this.mPictureFileName = fileName;
// PictureCallback is implemented by the current class
mCamera.takePicture(this, null, null, this);
}
@Override
public void onPictureTaken(byte[] data, Camera camera) {
Log.i(Util.TAG, "Saving a bitmap to file");
HelloOpenCvActivity.mTts.speak("Please wait, Character recognition process is in progress.", TextToSpeech.QUEUE_ADD, null);
// Write the image in a file (in jpg format)
try {
File file = new File(mPictureFileName + ".jpg");
FileOutputStream fos = new FileOutputStream(file);
fos.write(data);
fos.close();
} catch (IOException e) {
Log.e(Util.TAG, "Exception in photoCallback", e);
} finally {
processOCR(mPictureFileName);
// The camera preview was automatically stopped. Start it again.
// TODO: Stop this recall and let the program terminate.
mCamera.startPreview();
mCamera.setPreviewCallback(this);
}
}
public void processOCR(String mPictureFileName2) {
try {
Log.i(Util.TAG, "Started processing OCR");
BitmapWorkerTask task = new BitmapWorkerTask();
AsyncTask<String, Void, Bitmap> aTask = task.execute(mPictureFileName + ".jpg");
OCRProcessor ocr = new OCRProcessor();
String text = ocr.getOCRText(aTask.get());
// Write text to file
HelloOpenCvActivity.mTts.speak(text, TextToSpeech.QUEUE_ADD, null);
Log.i(Util.TAG, "TEXT \n" + text);
writeToFile(text, mPictureFileName + ".txt");
}
catch (Exception exc) {
Log.e(Util.TAG, "Error occured in processing OCR", exc);
HelloOpenCvActivity.mTts.speak("Error occurred in processing document, Please refetch the document", TextToSpeech.QUEUE_FLUSH, null);
}
}
private void writeToFile(String text, String fileName) {
try {
File file = new File(fileName);
FileWriter writer = new FileWriter(file);
writer.write(text);
writer.close();
}
catch (Exception e) {
Log.e(Util.TAG, "File write failed: " + e.toString());
}
}
@Override
public void onShutter() {
}
public Camera getCamera() {
return mCamera;
}
public void setCamera(Camera camera) {
this.mCamera = camera;
}}
这是运行时应用程序的Logcat文件的一部分
11-02 12:58:16.862: I/dalvikvm-heap(19979): Grow heap (frag case)
to 14.125MB for 4519746-byte allocation
11-02 12:58:16.882: I/DREAMVISION::(19979): Saving a bitmap to file
11-02 12:58:16.892: E/DREAMVISION::(19979): Exception in photoCallback
11-02 12:58:16.892: E/DREAMVISION::(19979):
java.io.FileNotFoundException: /storage/emulated/0/project
/2015-11-02_12-58-16.jpg: open failed: ENOENT (No such file or
directory)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
libcore.io.IoBridge.open(IoBridge.java:449)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
java.io.FileOutputStream.<init>(FileOutputStream.java:77)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
com.hello.HelloViewer.onPictureTaken(HelloViewer.java:81)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
android.hardware.Camera$EventHandler.handleMessage(Camera.java:932)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
android.os.Handler.dispatchMessage(Handler.java:102)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
android.os.Looper.loop(Looper.java:136)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
android.app.ActivityThread.main(ActivityThread.java:5291)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
java.lang.reflect.Method.invokeNative(Native Method)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
java.lang.reflect.Method.invoke(Method.java:515)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run
(ZygoteInit.java:849)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
com.android.internal.os.ZygoteInit.main(ZygoteInit.java:665)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
dalvik.system.NativeStart.main(Native Method)
11-02 12:58:16.892: E/DREAMVISION::(19979): Caused by:
libcore.io.ErrnoException: open failed: ENOENT (No such file or
directory)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
libcore.io.Posix.open(Native Method)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
libcore.io.BlockGuardOs.open(BlockGuardOs.java:110)
11-02 12:58:16.892: E/DREAMVISION::(19979): at
libcore.io.IoBridge.open(IoBridge.java:440)
11-02 12:58:16.892: E/DREAMVISION::(19979): ... 11 more
11-02 12:58:16.892: I/DREAMVISION::(19979): Started processing OCR
11-02 12:58:16.902: E/BitmapFactory(19979): Unable to decode stream:
java.io.FileNotFoundException: /storage/emulated/0/project
/2015-11-02_12-58-16.jpg: open failed: ENOENT (No such file or
directory)
11-02 12:58:16.902: E/DREAMVISION::(19979): Error occured in
processing OCR
11-02 12:58:16.902: E/DREAMVISION::(19979):
java.util.concurrent.ExecutionException: java.lang.NullPointerException
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.util.concurrent.FutureTask.report(FutureTask.java:93)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.util.concurrent.FutureTask.get(FutureTask.java:163)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.os.AsyncTask.get(AsyncTask.java:483)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.hello.HelloViewer.processOCR(HelloViewer.java:107)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.hello.HelloViewer.onPictureTaken(HelloViewer.java:88)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.hardware.Camera$EventHandler.handleMessage(Camera.java:932)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.os.Handler.dispatchMessage(Handler.java:102)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.os.Looper.loop(Looper.java:136)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.app.ActivityThread.main(ActivityThread.java:5291)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.lang.reflect.Method.invokeNative(Native Method)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.lang.reflect.Method.invoke(Method.java:515)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.android.internal.os.ZygoteInit$MethodAndAr
gsCaller.run(ZygoteInit.java:849)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.android.internal.os.ZygoteInit.main(ZygoteInit.java:665)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
dalvik.system.NativeStart.main(Native Method)
11-02 12:58:16.902: E/DREAMVISION::(19979): Caused by:
java.lang.NullPointerException
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.hello.BitmapWorkerTask.rotateBitMap(BitmapWorkerTask.java:26)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.hello.BitmapWorkerTask.doInBackground(BitmapWorkerTask.java:17)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
com.hello.BitmapWorkerTask.doInBackground(BitmapWorkerTask.java:1)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.os.AsyncTask$2.call(AsyncTask.java:288)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.util.concurrent.FutureTask.run(FutureTask.java:237)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:231)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolEx
ecutor.java:1112)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExe
cutor. java:587)
11-02 12:58:16.902: E/DREAMVISION::(19979): at
java.lang.Thread.run(Thread.java:841)
答案 0 :(得分:0)
在HelloViewer.java
:
...
File file = new File(mPictureFileName + ".jpg");
File folder = file.getParentFile().getCanonicalFile();
folder.mkdirs();
FileOutputStream fos = new FileOutputStream(file);
...