i'm having problem dealing with camera application on real device. when i run my application on genymotion emulator version 4.4.2(API 19) it works fine.. but when i run it on my real device Huawei P9 Lite version 6 (API 23) it crashes. Here is the errors that shows on the Logcat :
05-01 23:31:10.963 9308-9308/edu.sfsu.cs.orange.ocr W/CameraBase: An error
occurred while connecting to camera: 0
05-01 23:31:10.963 9308-9308/edu.sfsu.cs.orange.ocr E/Camera-JNI:
android_hardware_Camera_native_setup Error: -1
05-01 23:31:10.963 9308-9308/edu.sfsu.cs.orange.ocr E/Camera: Camera new
cameraInitNormal:-1
in my class where i handle the camera object i see that "android.hardware.camera is deprecated"
i think it maybe from this and i should use "android.hardware.camera2" instead. But as i use alot the camera object and it's methods it's going to be alot of change in my code. Can this be avoided ? or is this problem from an other thing ?
The permission for the camera is already included in my manifest and i'm using this configuration in my build file :
compileSdkVersion 24
buildToolsVersion '25.0.0'
minSdkVersion 9
targetSdkVersion 24
UPDATE
Here is why i think the problem is from deprecated methods :
try {
// Open and initialize the camera
cameraManager.openDriver(surfaceHolder);
// Creating the handler starts the preview, which can also throw a RuntimeException.
handler = new CaptureActivityHandler(this, cameraManager, isContinuousModeActive);
} catch (IOException ioe) {
showErrorMessage("Error", "Couldn't initialize camera. Please try restarting device.");
} catch (RuntimeException e) {
// Barcode Scanner has seen crashes in the wild of this variety:
// java.?lang.?RuntimeException: Fail to connect to camera service
showErrorMessage("Error", "Could not initialize camera. Please try restarting device.");
}
When the application starts on my phone it throws this RuntimeException.
openDrive method :
public synchronized void openDriver(SurfaceHolder holder) throws IOException {
Camera theCamera = camera;
if (theCamera == null) {
theCamera = Camera.open();
if (theCamera == null) {
throw new IOException();
}
camera = theCamera;
}
camera.setPreviewDisplay(holder);
if (!initialized) {
initialized = true;
configManager.initFromCameraParameters(theCamera);
if (requestedFramingRectWidth > 0 && requestedFramingRectHeight > 0) {
adjustFramingRect(requestedFramingRectWidth, requestedFramingRectHeight);
requestedFramingRectWidth = 0;
requestedFramingRectHeight = 0;
}
}
configManager.setDesiredCameraParameters(theCamera);
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
reverseImage = prefs.getBoolean(PreferencesActivity.KEY_REVERSE_IMAGE, false);
}
any thoughts how i can solve this problem ? thanks in advance
A quick debug tip would be to compile the app for targetSdkVersion 19. Looks like between the API versions the Camera interface must have depriciated some stuff. Also if you have capability to see kernel logs via a serial terminal or via adb it would be helpful to see what the "Error: -1" means to the hardware i.e. is it really reaching the camera driver in kernel?
adb root
adb shell
#cat /proc/kmsg
Related
Is there a way to see Android logs that were logged before connecting to the Android Studio?
I have an app that tracks GPS location. The issue is that it terminates after some time and I get the Android system message that says "Application Terminated"
I want to see what went wrong and where. When I connect Android studio later, it shows logs that happened from time it is connected.
I want the logs from past.
There are couple of things you can try to resolve:
1) I generally write logs when I have such cases to test.
public static void writeToFile(String msg) {
Log.d("MyApp", msg);
try {
String state = Environment.getExternalStorageState();
if (Environment.MEDIA_MOUNTED.equals(state)) {
FileOutputStream dio = null;
File file = new File(Environment.getExternalStorageDirectory(), "MyApp_File_Logs.txt");
if (file != null) {
try {
dio = new FileOutputStream(file, true);
dio.write((msg+"\n").getBytes());
dio.close();
dio = null;
} catch (Exception e) {
e.printStackTrace();
}
}
}
} catch (Exception e) {
Log.e("MyApp", "Exception in writeToFile(): " + e.getMessage());
}
}
So instead of Log.d , Use this Utility method. You can add time in the message to be more precise.
Done forget to give write external storage permission to you app
2) Once you see crash , go to command prompt
and use the below commands:
adb shell
logcat -b crash
You might see something in this, if you connect within a minute or so
3) Increase the "Logger Buffer Size " in your developer options , but in this case you will see delay in getting logs when you connect your device to adb and open logcat.
you can add a log module into your app,let log module output your app's log into local file,like logger
I am using parts of the android vision barcode-reader sample to read QR-codes. Occasionally (like 2 in 500 Users) I'm getting a Firebase Crash report, which happens at Camera.open.
java.lang.RuntimeException:
at android.hardware.Camera.<init>(Camera.java:678)
at android.hardware.Camera.open(Camera.java:520)
at mobilevision.CameraSource.createCamera(CameraSource.java:0)
at <OR>.access$2200(CameraSource.java:0)
at mobilevision.CameraSource.release(CameraSource.java:0)
at <OR>.start(CameraSource.java:0)
at <OR>.getIdForRequestedCamera(CameraSource.java:0)
at <OR>.selectSizePair(CameraSource.java:0)
at <OR>.generateValidPreviewSizeList(CameraSource.java:0)
at <OR>.selectPreviewFpsRange(CameraSource.java:0)
at <OR>.setRotation(CameraSource.java:0)
at <OR>.createPreviewBuffer(CameraSource.java:0)
at <OR>.access$102(CameraSource.java:0)
at <OR>.access$202(CameraSource.java:0)
at <OR>.access$302(CameraSource.java:0)
at <OR>.access$502(CameraSource.java:0)
at <OR>.access$802(CameraSource.java:0)
at <OR>.access$1800(CameraSource.java:0)
at mobilevision.CameraSourcePreview.startIfReady(CameraSourcePreview.java:0)
at mobilevision.CameraSourcePreview.start(CameraSourcePreview.java:0)
at <OR>.start(CameraSourcePreview.java:0)
at <OR>.stop(CameraSourcePreview.java:0)
at <OR>.access$102(CameraSourcePreview.java:0)
at <OR>.access$200(CameraSourcePreview.java:0)
at mobilevision.CameraSourcePreview$SurfaceCallback.surfaceCreated(CameraSourcePreview.java:0)
at android.view.SurfaceView.updateWindow(SurfaceView.java:679)
at android.view.SurfaceView$3.onPreDraw(SurfaceView.java:206)
at android.view.ViewTreeObserver.dispatchOnPreDraw(ViewTreeObserver.java:944)
at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:2432)
at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1328)
at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:6730)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:894)
at android.view.Choreographer.doCallbacks(Choreographer.java:696)
at android.view.Choreographer.doFrame(Choreographer.java:631)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:880)
at android.os.Handler.handleCallback(Handler.java:815)
at android.os.Handler.dispatchMessage(Handler.java:104)
at android.os.Looper.loop(Looper.java:207)
at android.app.ActivityThread.main(ActivityThread.java:5765)
at java.lang.reflect.Method.invoke(Method.java:0)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:679)
Code part where exception is thrown:
int requestedCameraId = getIdForRequestedCamera(mFacing);
if (requestedCameraId == -1) {
throw new Exception("Could not find requested camera.");
}
Camera camera = Camera.open(requestedCameraId);
I'm asking for the camera permission similarly as it is implemented in the barcode-reader sample. Unfortunately I am not able to reproduce this exact exception.
But I was able to reproduce a similar exception when running the app in an emulator without camera (both cameras set to none). But since this exception happens in real devices, I'm wondering what might be the cause.
Phones in the crash report are e.g. Galaxy J1(2016) (j1x3g) with A5.1, Plume P6 Pro LTE (PGN528) with A6.0, 3600i (CP3600I) with A6.0.
Can anybody give me a hint on how to reproduce this exception or even better, does anybody know the reason why it is not possible to start a camera even though the permission is granted?
Thanks a lot!
It's my pleasure to answer your question.
There are corresponding checkPermission () methods, but these methods only determine whether the permissions have been registered in the manifest file. The user's actions are not accessible.
PackageManager packageManager = this.getPackageManager();
int permission = packageManager.checkPermission("android.permission.CAMERA", "your packageName");
if (PackageManager.PERMISSION_GRANTED == permission) {
// you can do something
} else {
// request permission
}
So how do we detect permissions in the system below 6.0?
The present method is the use of try{} catch){} way:
public boolean isCameraCanUse() {
boolean isCanUse = true;
Camera mCamera = null;
try {
mCamera = Camera.open();
Camera.Parameters mParameters = mCamera.getParameters(); //针对魅族手机
mCamera.setParameters(mParameters);
} catch (Exception e) {
isCanUse = false;
}
if (mCamera != null) {
try {
mCamera.release();
} catch (Exception e) {
e.printStackTrace();
return isCanUse;
}
}
return isCanUse;
}
I hope this helps.
I have a problem regarding the camera in the most recent Marshmallow build, more specifically the flashlight.
On any pre-Marshmallow version all I need to do to turn the flash on/off was the following:
private void turnFlashOn(final Camera camera, int flashLightDurationMs) {
if (!isFlashOn()) {
final List<String> supportedFlashModes = camera.getParameters().getSupportedFlashModes();
if (supportedFlashModes != null && supportedFlashModes.contains(Camera.Parameters.FLASH_MODE_TORCH)) {
mParams.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
camera.setParameters(mParams);
}
}
}
and
private void turnFlashOff(Camera camera) {
if (camera != null) {
final List<String> supportedFlashModes = camera.getParameters().getSupportedFlashModes();
if (supportedFlashModes != null && supportedFlashModes.contains(Camera.Parameters.FLASH_MODE_OFF)) {
mParams.setFlashMode(Camera.Parameters.FLASH_MODE_OFF);
camera.setParameters(mParams);
}
}
}
Unfortunately, Marshmallow devices began to crash in the wild. Somehow camera.getParameters() and camera.setParameters() began to fail with messages such as:
RuntimeException: getParameters failed (empty parameters)
RuntimeException: setParameters failed
I tried starting and stopping the preview before getting the parameters, which no longer throws errors. However the preview is not resumed when I call camera.startPreview().
I fear releasing the camera and reopening it is out of the question as this takes some seconds and would produce a bad experience.
Any suggestions on how to turn the flashlight on/off in Marshmallow reliably?
Google has introduced torchmode in OS 6 (Android M).
if your purpose is only to turn on/off the flash, below code can help you with that:
private static void handleActionTurnOnFlashLight(Context context){
try{
CameraManager manager = (CameraManager) context.getSystemService(Context.CAMERA_SERVICE);
String[] list = manager.getCameraIdList();
manager.setTorchMode(list[0], true);
}
catch (CameraAccessException cae){
Log.e(TAG, cae.getMessage());
cae.printStackTrace();
}
}
private static void handleActionTurnOffFlashLight(Context context){
try{
CameraManager manager = (CameraManager) context.getSystemService(Context.CAMERA_SERVICE);
manager.setTorchMode(manager.getCameraIdList()[0], false);
}
catch (CameraAccessException cae){
Log.e(TAG, cae.getMessage());
cae.printStackTrace();
}
}
All you have to do is: Get cameraid's list out of which camera ID zero(0) is your primary camera for which you want to turn flash on/off. Simply pass the cameraID to setTochMode API with boolean value for turning it on or off.
Do note that this piece of code will work only with OS 6, so you need to check for device OS and based upon that you need to select which API's to call for pre-marshmallow devices.
Kindly mark this as solution if it solves your problem.
As Saurabh7474 has responded, to check the version of Android and use setTorchMode API it's very correct.
Although you can also use params.setFlashMode (...) in marshmallow using
mCamera.setPreviewTexture (new SurfaceTexture (100))
after Camera.open (...) and before calling mCamera.startPreview();
try {
Log.i(TAG, "getCamera");
int requestedCameraId = getIdForRequestedCamera(mFacing);
if (requestedCameraId == -1) {
throw new RuntimeException("Could not find requested camera.");
}
mCamera = Camera.open(requestedCameraId);
mCamera.setPreviewTexture(new SurfaceTexture(DUMMY_TEXTURE_NAME));
params = mCamera.getParameters();
} catch (RuntimeException e) {
Log.e("Failed to Open. Error:", e.getMessage());
} catch (IOException e) {
Log.e("Failed to Open. can't setPreviewTexture:", e.getMessage());
}
then when you want, you can use
mParams.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH);
camera.setParameters(mParams);
My answer is based on CameraSource examples of Vision API that uses params.setFlashMode (...) and works in Api 23 and above.
If you decide to inspect CameraSource, the key method that has solved the same problem is "start ()", in the line 312 ...
https://github.com/googlesamples/android-vision/blob/master/visionSamples/barcode-reader/app/src/main/java/com/google/android/gms/samples/vision/barcodereader/ui/camera/CameraSource.java
The reason you can find here
https://stackoverflow.com/a/33333046/4114846
Update your app to check for permissions at runtime. You have to have android.permission.CAMERA granted. Including it in the manifest of your app is not going to grant it to you on Marshmallow. You'll need to detect whether or not it has been granted and request it.
Building off of Saurabh7474's answer, you can toggle Marshmallow's torchMode by registering a torchCallback:
final CameraManager mCameraManager = (CameraManager) getSystemService(Context.CAMERA_SERVICE);
CameraManager.TorchCallback torchCallback = new CameraManager.TorchCallback() {
#Override
public void onTorchModeUnavailable(String cameraId) {
super.onTorchModeUnavailable(cameraId);
}
#Override
public void onTorchModeChanged(String cameraId, boolean enabled) {
super.onTorchModeChanged(cameraId, enabled);
boolean currentTorchState = enabled;
try {
mCameraManager.setTorchMode(cameraId, !currentTorchState);
} catch (CameraAccessException e){}
}
};
mCameraManager.registerTorchCallback(torchCallback, null);//fires onTorchModeChanged upon register
mCameraManager.unregisterTorchCallback(torchCallback);
I try to Draw in the same surface that the camera will draw it self later, by using lock and unlock.
the strange thing is that the try to lock succeed, but after the call unlockCanvasAndPost() the mCamera.setPreviewDisplay() throw error "setPreviewDisplay failed".
Without calling lockCanvas() and unlockCanvasAndPost() the mCamera.setPreviewDisplay() work and i get my display.(running in android 4.1.1 compile with api 17)
Remarque:(running in android 4.0.4 compile with api 17) sometimes run and only
if i lock and unlock using java, and not work using lock and unlock
from jni c/c++(ANativeWindow_lock() and ANativeWindow_unlockAndPost()).
but let's discuss only the java solution and why calling lockCanvas() and unlockCanvasAndPost() prevent the camera from working:
mCamera=Camera.open();
try {
Canvas can;
can = imageView.getHolder().getSurface().lockCanvas(null);
Log.d("", "Canvas successfully acquired ");
imageView.getHolder().getSurface().unlockCanvasAndPost(can);
mCamera.setPreviewDisplay(this.imageView.getHolder());
} catch (IOException e) {
Log.d("",e.getMessage());
} catch (OutOfResourcesException e) {
e.printStackTrace();
}
mCamera.setPreviewCallback(previewCallback);
mCamera.startPreview();
Hi I'm trying to get camera functionality to work on my app. The problem is, on one phone in particular - Samsung Galaxy Mini.
After I take a picture using the camera and previews, the phone freezes when I call camera.release(). I have to remove battery to reset it.
This is how I release the camera:
try
{
mCamera.stopPreview();
mCamera.setPreviewDisplay(null);
mCamera.release();
mCamera = null;
}
catch (Exception e)
{
// ignore: tried to stop a non-existent preview
}
I am also getting this weird native exception in logcat after the call:
03-10 09:45:56.080: E/mm-camera(95): camera_issue_ctrl_cmd: error (Bad address): type 43, length 0, status 40856
Any help would be greatly appreciated!
use the below open source camera code it will help you
Open Camera
and use it on surface destroyed
if(flag){
camera.release();
camera = null;
previewing = false;
}else{
camera.stopPreview();
}