Andriod4.2 Camera 架构与实现
1.Camera架构包括客户端和服务端,他们之间的通信采用Binder机制实现。Camera的实现主要包括本地代码和Java代码两个层次:Camera本地框架:frameworks/native/include/uiframeworks/native/libs/uiframeworks/av/camera/Camera的本地实现包含在上述目录中,这部分内容被编译生成库libui.so和libcamera_client.so。Camera服务部分:frameworks/av/services/camera/libcameraservice这部分编译生成libcameraservice.so。Camera HAL:frameworks/av/cameraframeworks/av/services/camera/libcameraservice/CameraHardwareInte易做图ce.hCameraHardwareInte易做图ce.h是HAL接口的定义,需要各个系统根据自己的情况实现。2.AndroidCamera采用C/S架构,client与server两个独立的线程之间使用Binder通信。这里将介绍Camera从设备开机,到进入相机应用是如何完成初始化工作的。首先既然Camera是利用binder通信,它肯定要将它的service注册到ServiceManager里面,以备后续Client引用,那么这一步是在哪里进行的呢?在frameworks/av/media/mediaserver/main_mediaserver.cpp下有个main函数,可以用来注册媒体服务。在这里,CameraService完成了服务的注册。intmain(int argc, char** argv){sp<ProcessState>proc(ProcessState::self());sp<IServiceManager> sm= defaultServiceManager();ALOGI("ServiceManager:%p", sm.get());AudioFlinger::instantiate();MediaPlayerService::instantiate();CameraService::instantiate();AudioPolicyService::instantiate();ProcessState::self()->startThreadPool();IPCThreadState::self()->joinThreadPool();}可是我们到CameraService文件里面却找不到instantiate()这个函数,它在哪?继续追到它的一个父类BinderServicetemplate<typenameSERVICE>classBinderService{public:static status_t publish(bool allowIsolated =false) {sp<IServiceManager>sm(defaultServiceManager());returnsm->addService(String16(SERVICE::getServiceName()), new SERVICE(),allowIsolated);}static void publishAndJoinThreadPool(boolallowIsolated = false) {sp<IServiceManager>sm(defaultServiceManager());sm->addService(String16(SERVICE::getServiceName()),new SERVICE(), allowIsolated);ProcessState::self()->startThreadPool();IPCThreadState::self()->joinThreadPool();}staticvoid instantiate(){ publish(); }static status_t shutdown() {return NO_ERROR;}};可以发现在publish()函数中,CameraService完成服务的注册。这里面有个SERVICE,源码中有说明template<typenameSERVICE>这表示SERVICE是个模板,这里是注册CameraService,所以可以用CameraService代替sm->addService(String16(SERVICE::getServiceName()),new SERVICE(), allowIsolated);这样,Camera就在ServiceManager完成服务注册,提供给client随时使用。Main_MediaServer主函数由init.rc在启动是调用,所以在设备开机的时候Camera就会注册一个服务,用作binder通信。servicemedia /system/bin/mediaserverclass mainuser mediagroup audio camera inetnet_bt net_bt_admin net_bw_acct drmrpcioprio rt 4Binder服务已注册,那接下来就看看client如何连上server端,并打开camera模块。咱们先从testingcameraapp的源码入手。在setUpCamera()函数中专门有一个open(mCameraId)函数进入framework层,调用frameworks/base/core/java/android/hardware/Camera.java类的open方法。publicstatic Camera open(int cameraId) {return newCamera(cameraId);}这里调用了Camera的构造函数,在看看构造函数Camera(int cameraId) {mShutterCallback = null;mRawImageCallback = null;mJpegCallback = null;mPreviewCallback = null;mPostviewCallback = null;mZoomListener = null;Looper looper;if ((looper =Looper.myLooper()) != null) {mEventHandler = newEventHandler(this, looper);} else if ((looper =Looper.getMainLooper()) != null) {mEventHandler = newEventHandler(this, looper);} else {mEventHandler = null;}native_setup(newWeakReference<Camera>(this), cameraId);}好,终于来到JNI了,继续看camera的JNI文件frameworks/base/core/jni/android_hardware_Camera.cpp// connect to cameraservicestatic voidandroid_hardware_Camera_native_setup(JNIEnv *env, jobject thiz,jobject weak_this,jint cameraId){sp<Camera>camera = Camera::connect(cameraId);if (camera == NULL) {jniThrowRuntimeException(env,"Fail to connect to camera service");return;}// make sure camerahardware is aliveif(camera->getStatus() != NO_ERROR) {jniThrowRuntimeException(env,"Camera initialization failed");return;}jclass clazz =env->GetObjectClass(thiz);if (clazz == NULL) {jniThrowRuntimeException(env,"Can't find android/hardware/Camera");return;}// We use a weakreference so the Camera object can be garbage collected.// The reference isonly used as a proxy for callbacks.sp<JNICameraContext>context = new JNICameraContext(env, weak_this, clazz, camera);context->incStrong(thiz);camera->setListener(context);// save context inopaque fieldenv->SetIntField(thiz,fields.context, (int)context.get());}JNI函数里面,我们找到CameraC/S架构的客户端了,它调用connect函数向服务器发送连接请求。JNICameraContext这个类是一个监听类,用于处理底层Camera回调函数传来的数据和消息看看客户端的connect函数有什么===>>>frameworks/av/camera/Camera.cppsp<Camera>Camera::connect(int cameraId){ALOGV("connect");sp<Camera> c = new Camera();const sp<ICameraService>& cs =getCameraService();if (cs !=补充:移动开发 , Android ,
上一个:Android 学习技巧积累
下一个:android中定时开关机的实现