定义MyCameraContext类,该类必须继承CameraListener,采集到数据时,将会触发该类内部定义的回调函数:postData。注意android2.3,和2.2在构造函数上是有区别的
//MyCameraContext.h #ifndef MY_CAMERA_H #define MY_CAMERA_H #include "jni.h" //#include "JNIHelp.h" #include "android_runtime/AndroidRuntime.h" #include <utils/Vector.h> #include <surfaceflinger/Surface.h> #include <camera/Camera.h> #include <binder/IMemory.h> #include <stdint.h> using namespace android; class MyCameraContext: public CameraListener { public: MyCameraContext(const sp<Camera>& camera); ~MyCameraContext() { ; } //特殊事件通知回调,包括错误之类....目前在Demo中未使用 virtual void notify(int32_t msgType, int32_t ext1, int32_t ext2); //采集数据回调.... virtual void postData(int32_t msgType, const sp<IMemory>& dataPtr); //获取时间回调........目前在Demo中未使用 virtual void postDataTimestamp(nsecs_t timestamp, int32_t msgType, const sp<IMemory>& dataPtr); void setCallbackMode(); void getcallbackfunc(void(*p)(void* lpdata,int len) ){mcallbackfunc=p; }; sp<Camera> getCamera() { return mCamera; } private: void(*mcallbackfunc)(void* lpdata,int len) ; void copyAndPost(const sp<IMemory>& dataPtr, int msgType); sp<Camera> mCamera; // strong reference to native object // Mutex mLock; }; sp<Camera> CreateCamera(); sp<MyCameraContext> CreateCameraContext(sp<Camera>& spCamera); int setPreviewDisplaysurface(sp<Camera>& spCamera, sp<Surface>& surface); #endif //MyCameraContext.cpp #include "MyCamera.h" MyCameraContext::MyCameraContext(const sp<Camera>& camera) { mCamera = camera; } void MyCameraContext::notify(int32_t msgType, int32_t ext1, int32_t ext2) { } void MyCameraContext::copyAndPost( const sp<IMemory>& dataPtr, int msgType) { jbyteArray obj = NULL; if (dataPtr != NULL) { ssize_t offset; size_t size; sp<IMemoryHeap> heap = dataPtr->getMemory(&offset, &size); mcallbackfunc((void*)(heap->getBase()+offset),size); uint8_t *heapBase = (uint8_t*)heap->base(); } } void MyCameraContext::postData(int32_t msgType, const sp<IMemory>& dataPtr) { copyAndPost(dataPtr, msgType); } void MyCameraContext::postDataTimestamp(nsecs_t timestamp, int32_t msgType, const sp<IMemory>& dataPtr) { postData(msgType, dataPtr); } void MyCameraContext::setCallbackMode() { mCamera->setPreviewCallbackFlags(FRAME_CALLBACK_FLAG_CAMERA); } #ifdef ANDROID2_3 //android2.3 sp<Camera> CreateCamera() { int NumberOfCameras=Camera::getNumberOfCameras(); CameraInfo cameraInfo; for (int i = 0; i < NumberOfCameras; i++) { status_t rc = Camera::getCameraInfo(i, &cameraInfo); if (rc != NO_ERROR) { break; } if(cameraInfo.facing==CAMERA_FACING_BACK) { sp<Camera> camera = Camera::connect(i); return camera; } } return NULL; } #else //android 2.2 sp<Camera> CreateCamera() { sp<Camera> camera = Camera::connect(); if(camera->get()) return camera; return NULL; } #endif sp<MyCameraContext> CreateCameraContext(sp<Camera>& spCamera) { sp<MyCameraContext> context = new MyCameraContext(spCamera); spCamera->setListener(context); return context; } int setPreviewDisplaysurface(sp<Camera>& spCamera, sp<Surface>& surface) { if (spCamera->setPreviewDisplay(surface) != NO_ERROR) return -1; return 1; } //测试demo: #include "MyCamera.h" void databackfunc(void *base,int size); void databackfunc(void *base,int size) { //注意数据格式的处理 //spCamera->getParameters(); 获取各种采集参数包括格式 //数据处理 } JNIEXPORT jint Java_lpc_bairui_android_lpc_camera(JNIEnv* env, jclass clazz) { sp<Surface> sps; sp<Camera> spCamera=CreateCamera(); if(spCamera.get()){ spCameraContext=CreateCameraContext(spCamera); if(spCameraContext.get()){ /*并没有为sps赋值,所以它不指向任何Surface,所以将不会创建预览格式,仅仅获取数据 setPreviewDisplaysurface函数在*/ if( setPreviewDisplaysurface(spCamera,sps)==1){ //String8 str("preview-size=240x320"); //spCamera->setParameters(str); //spCamera->getParameters().string(); spCameraContext->setCallbackMode(); //设置处理采集到数据的回调函数 spCameraContext->getcallbackfunc(databackfunc); //开始采集 spCamera->startPreview(); return 1; } } } return 0; }