ameraTraits这个结构体用来管理Camera的特性,定义如下:
Z:\SA800U_Android9.0_R01_r220\frameworks\av\include\camera\CameraBase.h
template <>
struct CameraTraits<Camera>
{
typedef CameraListener TCamListener;
typedef ::android::hardware::ICamera TCamUser;
typedef ::android::hardware::ICameraClient TCamCallbacks;
typedef ::android::binder::Status(::android::hardware::ICameraService::*TCamConnectService)
(const sp<::android::hardware::ICameraClient>&,
int, const String16&, int, int,
/*out*/
sp<::android::hardware::ICamera>*);
static TCamConnectService fnConnectService;
};
这里我们可以看到使用全特化来限制输入类型为Camera类型,从这个萃取器我们可以拿到Camra的一些特征,比如回调等等。注意这里使用了类成员函数指针定义了一个TCamConnectService函数,并且定义fnConnectService函数指针用来引用相应的函数,这个看起来比较难理解,可参考之前的语法知识2.2来学习。
其中fnConnectService初始化在下面文件中
Z:\SA800U_Android9.0_R01_r220\frameworks\av\camera\Camera.cpp
CameraTraits<Camera>::TCamConnectService CameraTraits<Camera>::fnConnectService =
&::android::hardware::ICameraService::connect;
这个函数的调用是在:
Z:\SA800U_Android9.0_R01_r220\frameworks\av\camera\CameraBase.cpp
template <typename TCam, typename TCamTraits>
sp<TCam> CameraBase<TCam, TCamTraits>::connect(int cameraId,
const String16& clientPackageName,
int clientUid, int clientPid)
{
ALOGV("%s: connect", __FUNCTION__);
sp<TCam> c = new TCam(cameraId);
sp<TCamCallbacks> cl = c;
const sp<::android::hardware::ICameraService> cs = getCameraService();
binder::Status ret;
if (cs != nullptr) {
TCamConnectService fnConnectService = TCamTraits::fnConnectService;
ret = (cs.get()->*fnConnectService)(cl, cameraId, clientPackageName, clientUid,
clientPid, /*out*/ &c->mCamera);
}
if (ret.isOk() && c->mCamera != nullptr) {
IInterface::asBinder(c->mCamera)->linkToDeath(c);
c->mStatus = NO_ERROR;
} else {
ALOGW("An error occurred while connecting to camera %d: %s", cameraId,
(cs == nullptr) ? "Service not available" : ret.toString8().string());
c.clear();
}
return c;
}
这里可以看到cs为getCameraService()获取,并且返回值为const sp<::android::hardware::ICameraService>,最终调用的地方ret = (cs.get()->*fnConnectService)(cl, cameraId, clientPackageName, clientUid, clientPid, /*out*/ &c->mCamera);综上所述调用的即是ICameraService中的connect函数。
这里的ICameraService为安卓的Binder跨进程调用,最终会调用到CameraService的connect函数。