libcamera動態庫實現流程總結

libcamera.so 流程總結

framework/base/include/ui下的CameraHardwareInterface.h 定義了 libCameraService.so需要的所有接口:
getPreviewHeap(),startPreview(preview_callback cb, void* user),stopPreview(),previewEnabled(),
autoFocus(autofocus_callback, void* user),
takePicture(shutter_callback,raw_callback,jpeg_callback,void* user)
cancelPicture(bool cancel_shutter,bool cancel_raw,bool cancel_jpeg)
setParameters(),getParameters()
release(), dump(), openCameraHardware()

其中還定義了5個函數指針,分別指向CameraService.cpp中定義的5個callback函數:
void (*preview_callback)(const sp<IMemory>& mem, void* user);
void (*shutter_callback)(void* user);
void (*raw_callback)(const sp<IMemory>& mem, void* user);
void (*jpeg_callback)(const sp<IMemory>& mem, void* user);
void (*autofocus_callback)(bool focused, void* user);

libCamera.so是對CameraHardwareInterface.h的具體實現。其中S3C6410CameraHWInterface.cpp實現了接口中的全部函數。
S3C6410Camera.cpp負責與設備通信。被S3C6410CameraHWInterface.cpp調用。

libcameraService.so先調用openCameraHardware(),得到Camera實例。
然後調用S3C6410CameraHWInterface.cpp中的getParameters(),setParameters()初始化這個Camera實例.
S3C6410CameraHWInterface.cpp在setParameters()之後會調用initHeapLocked(),該函數用來分配存放幀數據的堆,
並在已分配的堆空間上分配Buffer數組,每個數組變量存儲一幀數據。
libcameraService.so在Startpreview()中調用getPreviewHeap()得到libcamera.so中存放幀數據的堆的首地址。
然後將這個地址註冊到SurfaceFlinger的Buffer中以便提高preview的顯示效率。

CameraService.cpp在調用S3C6410CameraHWInterface.cpp的Startpreview()時會將自己的previewCallback()函數傳進去,
這樣當libcamera.so在調用getPreview()收集到一幀新數據時,就可以通過函數指針調用libcameraService.so中的回調函數previewCallback(),
將新收集到的幀數據的首地址傳出去。CameraService.cpp接着調用postFrame(), surfcace->postBuffer()等將該地址傳到surfaceFlinger中以顯示當前的幀數據。

S3C6410CameraHWInterface.cpp在startpreview()中新建一個線程previewThread(),在該線程中調用S3C6410Camera.cpp中的getpreview()
將設備收集到的幀數據copy到存放幀數據的堆中。
然後在線程中接着調用CameraService.cpp中的回調函數previewCallback(),將當前幀的偏移地址傳給surfaceFlinger。

以上是camera的 preview過程的實現流程。

在調用takePicture()之前,cameraService.cpp會先調用autofocus(),同時將自己定義的autofocus函數傳進去。cameraService.cpp中的autofocus()
會調用S3C6410CameraHWInterface.cpp中的autoFocus()函數創建一個線程,在該線程中通過函數指針調用CameraService.cpp中的autoFocuscallback()
通知CameraService autofocus成功。
之後,上層的APK會調用getParameter(),setParameter()重新初始化Camera實例。
當調用takePicture()時,CameraService.cpp 會將自己定義的shuttercallback(),rawcallback(),jpegcallback()函數
傳給S3C6410CameraHWInterface.cpp中的takepicture()函數。
它會創建一個線程beginPictureThread(),在其中調用函數pictureThread()。
pictureThread()函數通過函數指針調用CameraService.cpp中的shuttercallback(),yuvPictureCallback(),
其中yuvPictureCallback()的作用是將要拍攝的圖像在preview模式下顯示出來。
爲了調用CameraService.cpp中的 jpegPictureCallback(),pictureThread()需要先調用S3C6410Camera中的getjpeg()函數取得jpeg數據流,
再重新開闢一塊堆空間,將jpeg數據流copy進去。
之後就可以通過函數指針調用CameraService.cpp中的 jpegPictureCallback(),將得到的jpeg數據流傳給CameraService.cpp.

得到jpeg數據流的過程:
S3C6410Camera中的getjpeg()先調用m_frameSize()計算getsnapshot()得到的原始數據所需的空間,按此大小開闢一塊內存區存放getsnapshot()得到的原始數據。
在通過yuv2Jpeg()函數將得到的原始數據壓縮成jpeg數據流。

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章