Illegal argument exception and thread issues on lockCanvas
I am attempting to take a picture, and in the onPictureTaken I atempt to make some layout changes and then pass the image data to a new activity. When making layout changes the app crashes with an illegal argument error that traces back to the CameraWorker thread running in JavaCameraView.
I know this is kind of long but I'm really stumped. I'd really appreciate any help.
The idea is like this: When the onPictureTaken is called i freeze the preview (to show the user the image he captured) and display an "ok" button and a "retry" button. However when I attempt to change the layout (i.e make the buttons visible) the app crashes wit the above error and the following stacktrace:
E/SurfaceHolder: Exception locking surface
java.lang.IllegalArgumentException
at android.view.Surface.nativeLockCanvas(Native Method)
at android.view.Surface.lockCanvas(Surface.java:267)
at android.view.SurfaceView$4.internalLockCanvas(SurfaceView.java:973)
at android.view.SurfaceView$4.lockCanvas(SurfaceView.java:941)
at org.opencv.android.CameraBridgeViewBase.deliverAndDrawFrame(CameraBridgeViewBase.java:405)
at org.opencv.android.JavaCameraView$CameraWorker.run(JavaCameraView.java:308)
at java.lang.Thread.run(Thread.java:818)
The methods are in CameraBridgeViewBase and are called via a thread that is running in JavaCameraView which is why I think this is a thread issue. Unfortunately I dont know where to go from here.
My methods that cause the crash are here:
@Override
public void onPictureTaken(byte[] data, Camera camera) {
Log.i(TAG, "Saving a bitmap to file");
Toast.makeText(context,"Not Starting New Activity. Look at me now error!",Toast.LENGTH_LONG).show();;
//attempt to export all this to JavaCameraView, i have a feeling that there is a conflict with his thread....maybe that will help
buttonManager(data);
}
private void buttonManager(byte[] data) {
//find buttons
final byte[] img_data = data;
final int width = this.getWidth();
final int height = this.getHeight();
okButton.setVisibility(View.VISIBLE);
retryButton.setVisibility(View.VISIBLE);
captureImageButton.setVisibility(View.GONE);
okButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Intent startImgProc = new Intent(context,ImageProcessing.class);
startImgProc.putExtra("image",img_data);
startImgProc.putExtra("width",width);
startImgProc.putExtra("height",height);
disconnectCamera();
context.startActivity(startImgProc);
((Activity) context).finish();
}
});
retryButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
captureImageButton.setVisibility(View.VISIBLE);
okButton.setVisibility(View.GONE);
retryButton.setVisibility(View.GONE);
}
});
}
The call to deliverAndDrawFrame is from JavaCameraView here:
private class CameraWorker implements Runnable {
@Override
public void run() {
do {
boolean hasFrame = false;
synchronized (JavaCameraView.this) {
try {
while (!mCameraFrameReady && !mStopThread) {
JavaCameraView.this.wait();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
if (mCameraFrameReady)
{
mChainIdx = 1 - mChainIdx;
mCameraFrameReady = false;
hasFrame = true;
}
}
if (!mStopThread && hasFrame) {
if (!mFrameChain[1 - mChainIdx].empty())
deliverAndDrawFrame(mCameraFrame[1 - mChainIdx]);
}
} while (!mStopThread);
Log.d(TAG, "Finish processing thread");
}
}
and the method itself
protected void deliverAndDrawFrame(CvCameraViewFrame frame) {
Mat modified;
if (mListener != null) {
modified = mListener.onCameraFrame(frame);
} else {
modified = frame.rgba();
}
boolean bmpValid = true;
if (modified != null) {
try {
Utils.matToBitmap(modified, mCacheBitmap);
} catch(Exception e) {
Log.e(TAG, "Mat type: " + modified);
Log.e(TAG, "Bitmap type: " + mCacheBitmap.getWidth ...
your SO link is useless here. if you're too lazy to give us the details HERE, probably noone will answer it.
There isn't a code format option here. I assumed that was the best alternative. Happy to provide details here. Coming right up.
"There isn't a code format option here." -- there is ! mark your code with mouse, and press
crtl-k
(or use the10101
button)