android native開發-native實現對camera的操作
阿新 • • 發佈:2018-12-17
通過native實現camera的操作
原始碼路徑:frameworks/av/camera/ndk/ 參考的test原始碼路徑:cts/tests/tests/graphics/jni/CameraTestHelpers.cpp
1/* 2 * Copyright 2018 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 * 16 */ 17 18#ifndef ANDROID_CAMERATESTHELPERS_H 19#define ANDROID_CAMERATESTHELPERS_H 20 21// Must come before NdkCameraCaptureSession.h 22#include <camera/NdkCaptureRequest.h> 23 24#include <camera/NdkCameraCaptureSession.h> 25#include <camera/NdkCameraDevice.h> 26#include <camera/NdkCameraError.h> 27#include <camera/NdkCameraManager.h> 28#include <cstdlib> 29#include <cstring> 30#include <jni.h> 31#include <media/NdkImage.h> 32#include <media/NdkImageReader.h> 33 34// A helper class which can be used to initialize/control the camera. 35class CameraHelper { 36public: 37 ~CameraHelper(); 38 39 int initCamera(ANativeWindow *imgReaderAnw); 40 bool isCapabilitySupported( 41 acamera_metadata_enum_android_request_available_capabilities_t cap); 42 bool isCameraReady() { return mIsCameraReady; } 43 void closeCamera(); 44 int takePicture(); 45 46 static void onDeviceDisconnected(void * /*obj*/, ACameraDevice * /*device*/) { 47 } 48 static void onDeviceError(void * /*obj*/, ACameraDevice * /*device*/, 49 int /*errorCode*/) {} 50 static void onSessionClosed(void * /*obj*/, 51 ACameraCaptureSession * /*session*/) {} 52 static void onSessionReady(void * /*obj*/, 53 ACameraCaptureSession * /*session*/) {} 54 static void onSessionActive(void * /*obj*/, 55 ACameraCaptureSession * /*session*/) {} 56 57private: 58 ACameraDevice_StateCallbacks mDeviceCb{this, onDeviceDisconnected, 59 onDeviceError}; 60 ACameraCaptureSession_stateCallbacks mSessionCb{ 61 this, onSessionClosed, onSessionReady, onSessionActive}; 62 63 ANativeWindow *mImgReaderAnw{nullptr}; // not owned by us. 64 65 // Camera manager 66 ACameraManager *mCameraManager{nullptr}; 67 ACameraIdList *mCameraIdList{nullptr}; 68 // Camera device 69 ACameraMetadata *mCameraMetadata{nullptr}; 70 ACameraDevice *mDevice{nullptr}; 71 // Capture session 72 ACaptureSessionOutputContainer *mOutputs{nullptr}; 73 ACaptureSessionOutput *mImgReaderOutput{nullptr}; 74 ACameraCaptureSession *mSession{nullptr}; 75 // Capture request 76 ACaptureRequest *mCaptureRequest{nullptr}; 77 ACameraOutputTarget *mReqImgReaderOutput{nullptr}; 78 79 bool mIsCameraReady{false}; 80 const char *mCameraId{nullptr}; 81}; 82 83#endif // ANDROID_CAMERATHELPERS_H 84
/* 2 * Copyright 2018 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 * 16 */ 17 18#define LOG_TAG "CameraTestHelpers" 19 20#include "CameraTestHelpers.h" 21 22#include <android/log.h> 23 24#define ALOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__) 25#define ALOGW(...) __android_log_print(ANDROID_LOG_WARN, LOG_TAG, __VA_ARGS__) 26#define ALOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__) 27 28CameraHelper::~CameraHelper() { closeCamera(); } 29 30int CameraHelper::initCamera(ANativeWindow *imgReaderAnw) { 31 if (imgReaderAnw == nullptr) { 32 ALOGE("Cannot initialize camera before image reader get initialized."); 33 return -1; 34 } 35 36 mImgReaderAnw = imgReaderAnw; 37 mCameraManager = ACameraManager_create(); 38 if (mCameraManager == nullptr) { 39 ALOGE("Failed to create ACameraManager."); 40 return -1; 41 } 42 43 int ret = ACameraManager_getCameraIdList(mCameraManager, &mCameraIdList); 44 if (ret != AMEDIA_OK) { 45 ALOGE("Failed to get cameraIdList: ret=%d", ret); 46 return ret; 47 } 48 if (mCameraIdList->numCameras < 1) { 49 ALOGW("Device has no NDK compatible camera."); 50 return 0; 51 } 52 ALOGI("Found %d camera(s).", mCameraIdList->numCameras); 53 54 // We always use the first camera. 55 mCameraId = mCameraIdList->cameraIds[0]; 56 if (mCameraId == nullptr) { 57 ALOGE("Failed to get cameraId."); 58 return -1; 59 } 60 61 ret = ACameraManager_openCamera(mCameraManager, mCameraId, &mDeviceCb, 62 &mDevice); 63 if (ret != AMEDIA_OK || mDevice == nullptr) { 64 ALOGE("Failed to open camera, ret=%d, mDevice=%p.", ret, mDevice); 65 return -1; 66 } 67 68 ret = ACameraManager_getCameraCharacteristics(mCameraManager, mCameraId, 69 &mCameraMetadata); 70 if (ret != ACAMERA_OK || mCameraMetadata == nullptr) { 71 ALOGE("Get camera %s characteristics failure. ret %d, metadata %p", 72 mCameraId, ret, mCameraMetadata); 73 return -1; 74 } 75 76 if (!isCapabilitySupported( 77 ACAMERA_REQUEST_AVAILABLE_CAPABILITIES_BACKWARD_COMPATIBLE)) { 78 ALOGW("Camera does not support BACKWARD_COMPATIBLE."); 79 return 0; 80 } 81 82 // Create capture session 83 ret = ACaptureSessionOutputContainer_create(&mOutputs); 84 if (ret != AMEDIA_OK) { 85 ALOGE("ACaptureSessionOutputContainer_create failed, ret=%d", ret); 86 return ret; 87 } 88 ret = ACaptureSessionOutput_create(mImgReaderAnw, &mImgReaderOutput); 89 if (ret != AMEDIA_OK) { 90 ALOGE("ACaptureSessionOutput_create failed, ret=%d", ret); 91 return ret; 92 } 93 ret = ACaptureSessionOutputContainer_add(mOutputs, mImgReaderOutput); 94 if (ret != AMEDIA_OK) { 95 ALOGE("ACaptureSessionOutputContainer_add failed, ret=%d", ret); 96 return ret; 97 } 98 ret = ACameraDevice_createCaptureSession(mDevice, mOutputs, &mSessionCb, 99 &mSession); 100 if (ret != AMEDIA_OK) { 101 ALOGE("ACameraDevice_createCaptureSession failed, ret=%d", ret); 102 return ret; 103 } 104 105 // Create capture request 106 ret = ACameraDevice_createCaptureRequest(mDevice, TEMPLATE_RECORD, 107 &mCaptureRequest); 108 if (ret != AMEDIA_OK) { 109 ALOGE("ACameraDevice_createCaptureRequest failed, ret=%d", ret); 110 return ret; 111 } 112 ret = ACameraOutputTarget_create(mImgReaderAnw, &mReqImgReaderOutput); 113 if (ret != AMEDIA_OK) { 114 ALOGE("ACameraOutputTarget_create failed, ret=%d", ret); 115 return ret; 116 } 117 ret = ACaptureRequest_addTarget(mCaptureRequest, mReqImgReaderOutput); 118 if (ret != AMEDIA_OK) { 119 ALOGE("ACaptureRequest_addTarget failed, ret=%d", ret); 120 return ret; 121 } 122 123 mIsCameraReady = true; 124 return 0; 125} 126 127bool CameraHelper::isCapabilitySupported( 128 acamera_metadata_enum_android_request_available_capabilities_t cap) { 129 ACameraMetadata_const_entry entry; 130 ACameraMetadata_getConstEntry(mCameraMetadata, 131 ACAMERA_REQUEST_AVAILABLE_CAPABILITIES, &entry); 132 for (uint32_t i = 0; i < entry.count; i++) { 133 if (entry.data.u8[i] == cap) { 134 return true; 135 } 136 } 137 return false; 138} 139 140void CameraHelper::closeCamera() { 141 // Destroy capture request 142 if (mReqImgReaderOutput) { 143 ACameraOutputTarget_free(mReqImgReaderOutput); 144 mReqImgReaderOutput = nullptr; 145 } 146 if (mCaptureRequest) { 147 ACaptureRequest_free(mCaptureRequest); 148 mCaptureRequest = nullptr; 149 } 150 // Destroy capture session 151 if (mSession != nullptr) { 152 ACameraCaptureSession_close(mSession); 153 mSession = nullptr; 154 } 155 if (mImgReaderOutput) { 156 ACaptureSessionOutput_free(mImgReaderOutput); 157 mImgReaderOutput = nullptr; 158 } 159 if (mOutputs) { 160 ACaptureSessionOutputContainer_free(mOutputs); 161 mOutputs = nullptr; 162 } 163 // Destroy camera device 164 if (mDevice) { 165 ACameraDevice_close(mDevice); 166 mDevice = nullptr; 167 } 168 if (mCameraMetadata) { 169 ACameraMetadata_free(mCameraMetadata); 170 mCameraMetadata = nullptr; 171 } 172 // Destroy camera manager 173 if (mCameraIdList) { 174 ACameraManager_deleteCameraIdList(mCameraIdList); 175 mCameraIdList = nullptr; 176 } 177 if (mCameraManager) { 178 ACameraManager_delete(mCameraManager); 179 mCameraManager = nullptr; 180 } 181 mIsCameraReady = false; 182} 183 184int CameraHelper::takePicture() { 185 return ACameraCaptureSession_capture(mSession, nullptr, 1, &mCaptureRequest, 186 nullptr); 187} 188