OMXFocus.cpp revision ac0cf36b98237ec911f49e7b1b93ef6464666e48
1c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev/*
2c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * Copyright (C) Texas Instruments - http://www.ti.com/
3c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev *
4c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * Licensed under the Apache License, Version 2.0 (the "License");
5c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * you may not use this file except in compliance with the License.
6c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * You may obtain a copy of the License at
7c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev *
8c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev *      http://www.apache.org/licenses/LICENSE-2.0
9c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev *
10c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * Unless required by applicable law or agreed to in writing, software
11c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * distributed under the License is distributed on an "AS IS" BASIS,
12c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * See the License for the specific language governing permissions and
14c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev * limitations under the License.
15c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev */
16c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
17c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
18c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev/**
19c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev* @file OMXFocus.cpp
20c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev*
21c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev* This file contains functionality for handling focus configurations.
22c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev*
23c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev*/
24c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
25c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev#undef LOG_TAG
26c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
27c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev#define LOG_TAG "CameraHAL"
28c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
29c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev#include "CameraHal.h"
30c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev#include "OMXCameraAdapter.h"
3100479a8f1d791824870513b8b0b9edd67d2560ffSundar Raman#include "ErrorUtils.h"
32c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
33c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev#define TOUCH_FOCUS_RANGE 0xFF
3405ea07dfe04d915b4288d3e71afbf70f8082fea4Tyler Luu#define AF_IMAGE_CALLBACK_TIMEOUT 5000000 //5 seconds timeout
3505ea07dfe04d915b4288d3e71afbf70f8082fea4Tyler Luu#define AF_VIDEO_CALLBACK_TIMEOUT 2800000 //2.8 seconds timeout
36c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
37c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevnamespace android {
38c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
39c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::setParametersFocus(const CameraParameters &params,
40c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                              BaseCameraAdapter::AdapterState state)
41c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
42c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
43c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    const char *str = NULL;
445458bdc45048501d1919b14d22456de91f7e8950Tyler Luu    Vector< sp<CameraArea> > tempAreas;
45708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    size_t MAX_FOCUS_AREAS;
46708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
47c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
48c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
495458bdc45048501d1919b14d22456de91f7e8950Tyler Luu    Mutex::Autolock lock(mFocusAreasLock);
505458bdc45048501d1919b14d22456de91f7e8950Tyler Luu
51c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    str = params.get(CameraParameters::KEY_FOCUS_AREAS);
52708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
53708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    MAX_FOCUS_AREAS = atoi(params.get(CameraParameters::KEY_MAX_NUM_FOCUS_AREAS));
54708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
559e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu    if ( NULL != str ) {
565458bdc45048501d1919b14d22456de91f7e8950Tyler Luu        ret = CameraArea::parseAreas(str, ( strlen(str) + 1 ), tempAreas);
579e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu    }
589e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu
595458bdc45048501d1919b14d22456de91f7e8950Tyler Luu    if ( (NO_ERROR == ret) && CameraArea::areAreasDifferent(mFocusAreas, tempAreas) ) {
605458bdc45048501d1919b14d22456de91f7e8950Tyler Luu        mFocusAreas.clear();
615458bdc45048501d1919b14d22456de91f7e8950Tyler Luu        mFocusAreas = tempAreas;
629e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu        if ( MAX_FOCUS_AREAS < mFocusAreas.size() ) {
639e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu            CAMHAL_LOGEB("Focus areas supported %d, focus areas set %d",
649e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu                         MAX_FOCUS_AREAS,
659e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu                         mFocusAreas.size());
669e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu            ret = -EINVAL;
67c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
68f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov        else {
69f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov            if ( !mFocusAreas.isEmpty() ) {
70f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov                setTouchFocus();
71f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov            }
72f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov        }
739e5cb561cc54d061fe9f3d05eae78f6efb70f2c2Tyler Luu    }
74c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
75c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
76c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
77c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
78c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
79c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
80c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::doAutoFocus()
81c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
82c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
83c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
84c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE focusControl;
8585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    OMX_PARAM_FOCUSSTATUSTYPE focusStatus;
862136042f80a20aeeef3ece24bab027c401426334Milen Mitkov    OMX_CONFIG_BOOLEANTYPE bOMX;
87ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev    nsecs_t timeout = 0;
88c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
89c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
90c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
91b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng    if ( OMX_StateInvalid == mComponentState )
92b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      {
93b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        CAMHAL_LOGEA("OMX component in Invalid state");
94b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        returnFocusStatus(false);
95b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        return -EINVAL;
96b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      }
97b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng
98c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateExecuting != mComponentState )
99c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
100c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEA("OMX component not in executing state");
101c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        returnFocusStatus(false);
102b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        return NO_ERROR;
103c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
104c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
105c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
106030e1a5962195aa5914e76e3d071669869555a9fTyler Luu    if( ((AF_ACTIVE & getState()) != AF_ACTIVE) && ((AF_ACTIVE & getNextState()) != AF_ACTIVE) ) {
107030e1a5962195aa5914e76e3d071669869555a9fTyler Luu       CAMHAL_LOGDA("Auto focus got canceled before doAutoFocus could be called");
108030e1a5962195aa5914e76e3d071669869555a9fTyler Luu       return NO_ERROR;
109030e1a5962195aa5914e76e3d071669869555a9fTyler Luu    }
110030e1a5962195aa5914e76e3d071669869555a9fTyler Luu
111aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    // If the app calls autoFocus, the camera will stop sending face callbacks.
112aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    pauseFaceDetection(true);
113aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu
114f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    // This is needed for applying FOCUS_REGION correctly
115f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    if ( (!mFocusAreas.isEmpty()) && (!mFocusAreas.itemAt(0)->isZeroArea()))
116f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    {
117f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    //Disable face priority
118f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    setAlgoPriority(FACE_PRIORITY, FOCUS_ALGO, false);
119f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov
120f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    //Enable region algorithm priority
121f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    setAlgoPriority(REGION_PRIORITY, FOCUS_ALGO, true);
122f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov    }
123f2ac1cc4c58440d94972f0015f50bcbb13838611Atanas Stefov
12485c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    OMX_INIT_STRUCT_PTR (&focusControl, OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE);
12585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    focusControl.eFocusControl = ( OMX_IMAGE_FOCUSCONTROLTYPE ) mParameters3A.Focus;
12685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
1270e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu    if (mParameters3A.FocusLock) {
1280e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        // this basically means user never called cancelAutoFocus after a scan...
1290e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        // if this is the case we need to unlock AF to ensure we will do a scan
1300e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        if (set3ALock(mUserSetExpLock, mUserSetWbLock, OMX_FALSE) != NO_ERROR) {
1310e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            CAMHAL_LOGEA("Error Unlocking 3A locks");
1320e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        } else {
1330e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            CAMHAL_LOGDA("AE/AWB unlocked successfully");
1340e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        }
135f5f41aa7943adde4e7bfb3fc181de154c4b0b9b0Sundar Raman
1360e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu    } else if ( mParameters3A.Focus == OMX_IMAGE_FocusControlAuto ) {
1370e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        // In case we have CAF running we should first check the AF status.
1380e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        // If it has managed to lock, then do as usual and return status
139057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        // immediately.
14085c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        ret = checkFocus(&focusStatus);
14185c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        if ( NO_ERROR != ret ) {
14285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman            CAMHAL_LOGEB("Focus status check failed 0x%x!", ret);
14385c859b69b3c003b8db810371e24fe41599fc7deSundar Raman            return ret;
14485c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        } else {
14585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman            CAMHAL_LOGDB("Focus status check 0x%x!", focusStatus.eFocusStatus);
14685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        }
14785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
148c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
1493c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov    if ( (focusControl.eFocusControl == OMX_IMAGE_FocusControlAuto
150b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov            && (focusStatus.eFocusStatus == OMX_FocusStatusRequest
151b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov             || focusStatus.eFocusStatus == OMX_FocusStatusUnableToReach) ) ||
1523c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov            (mParameters3A.Focus !=  (OMX_IMAGE_FOCUSCONTROLTYPE)OMX_IMAGE_FocusControlAuto) )
1533c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov        {
1542136042f80a20aeeef3ece24bab027c401426334Milen Mitkov        OMX_INIT_STRUCT_PTR (&bOMX, OMX_CONFIG_BOOLEANTYPE);
1552136042f80a20aeeef3ece24bab027c401426334Milen Mitkov        bOMX.bEnabled = OMX_TRUE;
1562136042f80a20aeeef3ece24bab027c401426334Milen Mitkov
1572136042f80a20aeeef3ece24bab027c401426334Milen Mitkov        //Enable focus scanning
1582136042f80a20aeeef3ece24bab027c401426334Milen Mitkov        eError = OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
1592136042f80a20aeeef3ece24bab027c401426334Milen Mitkov                               (OMX_INDEXTYPE)OMX_TI_IndexConfigAutofocusEnable,
1602136042f80a20aeeef3ece24bab027c401426334Milen Mitkov                               &bOMX);
161c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
162b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov        // force AF, Ducati will take care of whether CAF
163b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov        // or AF will be performed, depending on light conditions
1647a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng        if ( focusControl.eFocusControl == OMX_IMAGE_FocusControlAuto
165b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov		&& focusStatus.eFocusStatus == OMX_FocusStatusUnableToReach )
166b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov			{
167b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov			focusControl.eFocusControl = OMX_IMAGE_FocusControlAutoLock;
168b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov			}
169b92d77425f939a35c0404a5317c3dcd6c2008ecbMilen Mitkov
1703c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov        if ( focusControl.eFocusControl != OMX_IMAGE_FocusControlAuto )
1713c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov            {
1723c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov            eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
1733c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov                                    OMX_IndexConfigFocusControl,
1743c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov                                    &focusControl);
1753c272a993dfc4ca153b09e5ec1e651f75eab90c4Milen Mitkov            }
1766b5eaf29c3d17a24731bf9271bd0d199d433813eAkwasi Boateng
1770e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        if ( OMX_ErrorNone != eError ) {
1780e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            CAMHAL_LOGEB("Error while starting focus 0x%x", eError);
1790e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            return INVALID_OPERATION;
1800e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        } else {
1810e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            CAMHAL_LOGDA("Autofocus started successfully");
1820e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu        }
1836b5eaf29c3d17a24731bf9271bd0d199d433813eAkwasi Boateng
1847a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng        // configure focus timeout based on capture mode
185ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev        timeout = (mCapMode == VIDEO_MODE) ?
186ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev                        ( ( nsecs_t ) AF_VIDEO_CALLBACK_TIMEOUT * 1000 ) :
187ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev                        ( ( nsecs_t ) AF_IMAGE_CALLBACK_TIMEOUT * 1000 );
188ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev
189ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            {
190ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            Mutex::Autolock lock(mDoAFMutex);
191ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            ret = mDoAFCond.waitRelative(mDoAFMutex, timeout);
192ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            }
19305ea07dfe04d915b4288d3e71afbf70f8082fea4Tyler Luu
1947a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng        //If somethiing bad happened while we wait
1957a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng        if (mComponentState == OMX_StateInvalid) {
1967a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng          CAMHAL_LOGEA("Invalid State after Auto Focus Exitting!!!");
197057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu          return -EINVAL;
1987a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng        }
1996b5eaf29c3d17a24731bf9271bd0d199d433813eAkwasi Boateng
200057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        if(ret != NO_ERROR) {
2017a1746145a89cca0dafe26478a7675c15d5623a3Akwasi Boateng            CAMHAL_LOGEA("Autofocus callback timeout expired");
202057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            ret = returnFocusStatus(true);
20385c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        } else {
204c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            ret = returnFocusStatus(false);
205c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
2060e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu    } else { // Focus mode in continuous
20785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        if ( NO_ERROR == ret ) {
208ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            ret = returnFocusStatus(true);
209f50bf42f39a1d1ca8505d198b41c557e8ca83668Heechan Park            mPending3Asettings |= SetFocus;
210c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
21185c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
21285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
213c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
214c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
215c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
216c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
217c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
218c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::stopAutoFocus()
219c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
220c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
221c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
222c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE focusControl;
223c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
224c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
225c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
226b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng    if ( OMX_StateInvalid == mComponentState )
227b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      {
228b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        CAMHAL_LOGEA("OMX component in Invalid state");
229b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        returnFocusStatus(false);
230b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        return -EINVAL;
231b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      }
232b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng
233c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateExecuting != mComponentState )
234c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
235b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng          CAMHAL_LOGEA("OMX component not in executing state");
236b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        return NO_ERROR;
237c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
238c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
239c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( mParameters3A.Focus == OMX_IMAGE_FocusControlAutoInfinity ) {
240c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        // No need to stop focus if we are in infinity mode. Nothing to stop.
241c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        return NO_ERROR;
242c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    }
243c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
244c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
245c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
246c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        OMX_INIT_STRUCT_PTR (&focusControl, OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE);
247c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        focusControl.eFocusControl = OMX_IMAGE_FocusControlOff;
248c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
249c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
250c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                OMX_IndexConfigFocusControl,
251c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                &focusControl);
252c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( OMX_ErrorNone != eError )
253c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
254c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error while stopping focus 0x%x", eError);
25500479a8f1d791824870513b8b0b9edd67d2560ffSundar Raman            return ErrorUtils::omxToAndroidError(eError);
256c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
257c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
258c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
259c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
260c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
261c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
262c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
263c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
26485c859b69b3c003b8db810371e24fe41599fc7deSundar Ramanstatus_t OMXCameraAdapter::getFocusMode(OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE &focusMode)
26585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman{;
26685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    OMX_ERRORTYPE eError = OMX_ErrorNone;
26785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
26885c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    LOG_FUNCTION_NAME;
26985c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
27085c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    if ( OMX_StateInvalid == mComponentState ) {
27185c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        CAMHAL_LOGEA("OMX component is in invalid state");
27285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        return NO_INIT;
27385c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
27485c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
27585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    OMX_INIT_STRUCT_PTR (&focusMode, OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE);
27685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    focusMode.nPortIndex = mCameraAdapterParameters.mPrevPortIndex;
27785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
27885c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    eError =  OMX_GetConfig(mCameraAdapterParameters.mHandleComp,
27985c859b69b3c003b8db810371e24fe41599fc7deSundar Raman                            OMX_IndexConfigFocusControl,
28085c859b69b3c003b8db810371e24fe41599fc7deSundar Raman                            &focusMode);
28185c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
28285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    if ( OMX_ErrorNone != eError ) {
28385c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        CAMHAL_LOGEB("Error while retrieving focus mode 0x%x", eError);
28485c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
28585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
28685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    LOG_FUNCTION_NAME_EXIT;
28785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
28885c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    return ErrorUtils::omxToAndroidError(eError);
28985c859b69b3c003b8db810371e24fe41599fc7deSundar Raman}
29085c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
291c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::cancelAutoFocus()
292c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
293c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
294c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
29585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    OMX_IMAGE_CONFIG_FOCUSCONTROLTYPE focusMode;
296c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
297c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
298c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
29985c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    ret = getFocusMode(focusMode);
30085c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    if ( NO_ERROR != ret ) {
30185c859b69b3c003b8db810371e24fe41599fc7deSundar Raman        return ret;
30285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
30385c859b69b3c003b8db810371e24fe41599fc7deSundar Raman
3048cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman    //Stop the AF only for modes other than CAF  or Inifinity
30585c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    if ( ( focusMode.eFocusControl != OMX_IMAGE_FocusControlAuto ) &&
30685c859b69b3c003b8db810371e24fe41599fc7deSundar Raman         ( focusMode.eFocusControl != ( OMX_IMAGE_FOCUSCONTROLTYPE )
30785c859b69b3c003b8db810371e24fe41599fc7deSundar Raman                 OMX_IMAGE_FocusControlAutoInfinity ) ) {
3088cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman        stopAutoFocus();
3098a35a0ca4d30702b693c92f8cee360a8d102f49eTyler Luu    } else if (focusMode.eFocusControl == OMX_IMAGE_FocusControlAuto) {
3108a35a0ca4d30702b693c92f8cee360a8d102f49eTyler Luu       // re-apply CAF after unlocking and canceling
3118a35a0ca4d30702b693c92f8cee360a8d102f49eTyler Luu       mPending3Asettings |= SetFocus;
31285c859b69b3c003b8db810371e24fe41599fc7deSundar Raman    }
313c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
314aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    // If the apps call #cancelAutoFocus()}, the face callbacks will also resume.
315aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    pauseFaceDetection(false);
316aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu
317c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
318c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
319c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
320c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
321c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
322c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
323c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::setFocusCallback(bool enabled)
324c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
325c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
326c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
327c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_CONFIG_CALLBACKREQUESTTYPE focusRequstCallback;
328c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
329c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
330c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
331b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng    if ( OMX_StateInvalid == mComponentState )
332b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      {
333b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        CAMHAL_LOGEA("OMX component in Invalid state");
334b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        ret = -EINVAL;
335b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      }
336b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng
337c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateExecuting != mComponentState )
338c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
339b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng          CAMHAL_LOGEA("OMX component not in executing state");
340b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        ret = NO_ERROR;
341c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
342c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
343c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
344c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
345c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
346c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        OMX_INIT_STRUCT_PTR (&focusRequstCallback, OMX_CONFIG_CALLBACKREQUESTTYPE);
347c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        focusRequstCallback.nPortIndex = OMX_ALL;
348c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        focusRequstCallback.nIndex = OMX_IndexConfigCommonFocusStatus;
349c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
350c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( enabled )
351c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
352c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            focusRequstCallback.bEnable = OMX_TRUE;
353c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
354c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        else
355c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
356c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            focusRequstCallback.bEnable = OMX_FALSE;
357c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
358c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
359c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
360c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                (OMX_INDEXTYPE) OMX_IndexConfigCallbackRequest,
361c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                &focusRequstCallback);
362c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( OMX_ErrorNone != eError )
363c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
364c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error registering focus callback 0x%x", eError);
365c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            ret = -1;
366c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
367c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        else
368c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
369c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGDB("Autofocus callback for index 0x%x registered successfully",
370c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                         OMX_IndexConfigCommonFocusStatus);
371c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
372c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
373c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
374c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
375c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
376c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
377c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
378c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
379c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::returnFocusStatus(bool timeoutReached)
380c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
381c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
382c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_PARAM_FOCUSSTATUSTYPE eFocusStatus;
383057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    CameraHalEvent::FocusStatus focusStatus = CameraHalEvent::FOCUS_STATUS_FAIL;
384bbdc0fa0b8720bcfcf602861f62802c1fa1995c4Tyler Luu    BaseCameraAdapter::AdapterState state, nextState;
385c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    BaseCameraAdapter::getState(state);
386bbdc0fa0b8720bcfcf602861f62802c1fa1995c4Tyler Luu    BaseCameraAdapter::getNextState(nextState);
387c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
388c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
389c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
390c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_INIT_STRUCT(eFocusStatus, OMX_PARAM_FOCUSSTATUSTYPE);
391c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
392bbdc0fa0b8720bcfcf602861f62802c1fa1995c4Tyler Luu    if( ((AF_ACTIVE & state ) != AF_ACTIVE) && ((AF_ACTIVE & nextState ) != AF_ACTIVE) )
393c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev       {
394c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        /// We don't send focus callback if focus was not started
395bbdc0fa0b8720bcfcf602861f62802c1fa1995c4Tyler Luu       CAMHAL_LOGDA("Not sending focus callback because focus was not started");
396c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev       return NO_ERROR;
397c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev       }
398c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
399c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
400c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
401c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
402c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( !timeoutReached )
403c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
404c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            ret = checkFocus(&eFocusStatus);
405c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
406c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            if ( NO_ERROR != ret )
407c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                {
408c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                CAMHAL_LOGEA("Focus status check failed!");
409c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                }
410c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
411c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
412c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
413c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
414c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
415c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
416c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( timeoutReached )
417c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
418057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            focusStatus = CameraHalEvent::FOCUS_STATUS_FAIL;
419c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
420c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        else
421c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
422c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            switch (eFocusStatus.eFocusStatus)
423c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                {
424c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                    case OMX_FocusStatusReached:
425c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        {
426057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu                        focusStatus = CameraHalEvent::FOCUS_STATUS_SUCCESS;
427c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        break;
428c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        }
429ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev                    case OMX_FocusStatusOff: // AF got canceled
430ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev                        return NO_ERROR;
431c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                    case OMX_FocusStatusUnableToReach:
432c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                    case OMX_FocusStatusRequest:
433c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                    default:
434c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        {
435057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu                        focusStatus = CameraHalEvent::FOCUS_STATUS_FAIL;
436c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        break;
437c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                        }
438c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                }
4390e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            // Lock CAF after AF call
4400e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            if( set3ALock(mUserSetExpLock, mUserSetWbLock, OMX_TRUE) != NO_ERROR) {
4417d56715ab78f6b4be347597dc439d598cfe47dc9Sundar Raman                CAMHAL_LOGEA("Error Applying 3A locks");
4420e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            } else {
4437d56715ab78f6b4be347597dc439d598cfe47dc9Sundar Raman                CAMHAL_LOGDA("Focus locked. Applied focus locks successfully");
4440e2a9f1fabc12a1a1123f8374d0e4d6faf5a2d62Tyler Luu            }
445c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            stopAutoFocus();
446c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
447ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev
448fd705eb8b757a4f3d1d80b736cf20cade04524d7Tyler Luu        //Query current focus distance after AF is complete
449fd705eb8b757a4f3d1d80b736cf20cade04524d7Tyler Luu        updateFocusDistances(mParameters);
450fd705eb8b757a4f3d1d80b736cf20cade04524d7Tyler Luu       }
451c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
4528cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman    ret =  BaseCameraAdapter::setState(CAMERA_CANCEL_AUTOFOCUS);
453c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
454c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
4558cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman        ret = BaseCameraAdapter::commitState();
4568cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman        }
4578cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman    else
4588cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman        {
4598cb48e582f4f3c93aa25159c1116a7c83bfa388aSundar Raman        ret |= BaseCameraAdapter::rollbackState();
460c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
461c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
462c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
463c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
464c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        notifyFocusSubscribers(focusStatus);
465c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
466c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
467aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    // After focus, face detection will resume sending face callbacks
468aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu    pauseFaceDetection(false);
469aa6e62e279cb54ae76c55ba9f8d02da230ce34e7Tyler Luu
470c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
471c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
472c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
473c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
474c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
475c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::checkFocus(OMX_PARAM_FOCUSSTATUSTYPE *eFocusStatus)
476c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
477c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
478c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
479c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
480c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
481c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
482c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NULL == eFocusStatus )
483c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
484c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEA("Invalid focus status");
485c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = -EINVAL;
486c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
487c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
488b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng    if ( OMX_StateInvalid == mComponentState )
489b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      {
490b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        CAMHAL_LOGEA("OMX component in Invalid state");
491b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        ret = -EINVAL;
492b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng      }
493b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng
494c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateExecuting != mComponentState )
495c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
496c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEA("OMX component not in executing state");
497b192289737a7616f76a1cc236ed3cbc704696c03Akwasi Boateng        ret = NO_ERROR;
498c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
499c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
500c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
501c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
502c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        OMX_INIT_STRUCT_PTR (eFocusStatus, OMX_PARAM_FOCUSSTATUSTYPE);
503c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        eError = OMX_GetConfig(mCameraAdapterParameters.mHandleComp,
504c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                               OMX_IndexConfigCommonFocusStatus,
505c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                               eFocusStatus);
506c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( OMX_ErrorNone != eError )
507c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
508c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error while retrieving focus status: 0x%x", eError);
509c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            ret = -1;
510c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
511c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
512c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
513c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
514c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
515c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGDB("Focus Status: %d", eFocusStatus->eFocusStatus);
516c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
517c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
518c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
519c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
520c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
521c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
522c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
523c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::updateFocusDistances(CameraParameters &params)
524c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
525c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_U32 focusNear, focusOptimal, focusFar;
526c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
527c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
528c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
529c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
530c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    ret = getFocusDistances(focusNear, focusOptimal, focusFar);
531c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret)
532c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
533c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = addFocusDistances(focusNear, focusOptimal, focusFar, params);
534c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            if ( NO_ERROR != ret )
535c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                {
536c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                CAMHAL_LOGEB("Error in call to addFocusDistances() 0x%x", ret);
537c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                }
538c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
539c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    else
540c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
541c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEB("Error in call to getFocusDistances() 0x%x", ret);
542c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
543c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
544c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
545c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
546c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
547c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
548c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
549c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::getFocusDistances(OMX_U32 &near,OMX_U32 &optimal, OMX_U32 &far)
550c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
551c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
552c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError;
553c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
554c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_TI_CONFIG_FOCUSDISTANCETYPE focusDist;
555c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
556c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
557c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
558c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateInvalid == mComponentState )
559c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
560c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEA("OMX component is in invalid state");
561c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = UNKNOWN_ERROR;
562c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
563c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
564c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
565c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
566c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        OMX_INIT_STRUCT_PTR(&focusDist, OMX_TI_CONFIG_FOCUSDISTANCETYPE);
567c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        focusDist.nPortIndex = mCameraAdapterParameters.mPrevPortIndex;
568c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
569c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        eError = OMX_GetConfig(mCameraAdapterParameters.mHandleComp,
570c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                               ( OMX_INDEXTYPE ) OMX_TI_IndexConfigFocusDistance,
571c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                               &focusDist);
572c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( OMX_ErrorNone != eError )
573c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
574c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error while querying focus distances 0x%x", eError);
575c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            ret = UNKNOWN_ERROR;
576c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
577c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
578c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
579c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
580c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
581c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
582c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        near = focusDist.nFocusDistanceNear;
583c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        optimal = focusDist.nFocusDistanceOptimal;
584c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        far = focusDist.nFocusDistanceFar;
585c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
586c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
587c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
588c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
589c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
590c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
591c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
592c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::encodeFocusDistance(OMX_U32 dist, char *buffer, size_t length)
593c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
594c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
595c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    uint32_t focusScale = 1000;
596c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    float distFinal;
597c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
598c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
599c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
600c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if(mParameters3A.Focus == OMX_IMAGE_FocusControlAutoInfinity)
601c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
602c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        dist=0;
603c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
604c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
605c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
606c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
607c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( 0 == dist )
608c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
609c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            strncpy(buffer, CameraParameters::FOCUS_DISTANCE_INFINITY, ( length - 1 ));
610c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
611c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        else
612c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
613c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            distFinal = dist;
614c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            distFinal /= focusScale;
615c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            snprintf(buffer, ( length - 1 ) , "%5.3f", distFinal);
616c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
617c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
618c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
619c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
620c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
621c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
622c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
623c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
624c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchevstatus_t OMXCameraAdapter::addFocusDistances(OMX_U32 &near,
625c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                             OMX_U32 &optimal,
626c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                             OMX_U32 &far,
627c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                             CameraParameters& params)
628c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
629c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
630c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
631c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
632c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
633c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
634c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
635c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = encodeFocusDistance(near, mFocusDistNear, FOCUS_DIST_SIZE);
636c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( NO_ERROR != ret )
637c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
638c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error encoding near focus distance 0x%x", ret);
639c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
640c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
641c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
642c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
643c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
644c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = encodeFocusDistance(optimal, mFocusDistOptimal, FOCUS_DIST_SIZE);
645c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( NO_ERROR != ret )
646c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
647c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error encoding near focus distance 0x%x", ret);
648c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
649c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
650c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
651c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
652c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
653c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = encodeFocusDistance(far, mFocusDistFar, FOCUS_DIST_SIZE);
654c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( NO_ERROR != ret )
655c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
656c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            CAMHAL_LOGEB("Error encoding near focus distance 0x%x", ret);
657c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
658c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
659c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
660c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
661c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
662c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        snprintf(mFocusDistBuffer, ( FOCUS_DIST_BUFFER_SIZE - 1) ,"%s,%s,%s", mFocusDistNear,
663c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                                                              mFocusDistOptimal,
664c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev                                                                              mFocusDistFar);
665c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
666c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        params.set(CameraParameters::KEY_FOCUS_DISTANCES, mFocusDistBuffer);
667c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
668c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
669c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
670c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
671c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
672c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
673c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
674708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchevstatus_t OMXCameraAdapter::setTouchFocus()
675c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev{
676c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    status_t ret = NO_ERROR;
677c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    OMX_ERRORTYPE eError = OMX_ErrorNone;
678708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
679708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    OMX_ALGOAREASTYPE **focusAreas;
680708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    OMX_TI_CONFIG_SHAREDBUFFER sharedBuffer;
681708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    MemoryManager memMgr;
682708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    int areasSize = 0;
683c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
684c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME;
685c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
686c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( OMX_StateInvalid == mComponentState )
687c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
688c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        CAMHAL_LOGEA("OMX component is in invalid state");
689c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        ret = -1;
690c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
691c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
692c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    if ( NO_ERROR == ret )
693c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        {
694c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
695708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        areasSize = ((sizeof(OMX_ALGOAREASTYPE)+4095)/4096)*4096;
696708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        focusAreas = (OMX_ALGOAREASTYPE**) memMgr.allocateBuffer(0, 0, NULL, areasSize, 1);
697708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
698708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        OMXCameraPortParameters * mPreviewData = NULL;
699708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        mPreviewData = &mCameraAdapterParameters.mCameraPortParams[mCameraAdapterParameters.mPrevPortIndex];
700708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
701708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        if (!focusAreas)
702708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            {
703708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            CAMHAL_LOGEB("Error allocating buffer for focus areas %d", eError);
704708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            return -ENOMEM;
705708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            }
706708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
707708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        OMX_INIT_STRUCT_PTR (focusAreas[0], OMX_ALGOAREASTYPE);
708708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
709708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        focusAreas[0]->nPortIndex = OMX_ALL;
710708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        focusAreas[0]->nNumAreas = mFocusAreas.size();
711708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        focusAreas[0]->nAlgoAreaPurpose = OMX_AlgoAreaFocus;
712708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
713708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        // If the area is the special case of (0, 0, 0, 0, 0), then
714708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        // the algorithm needs nNumAreas to be set to 0,
715708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        // in order to automatically choose the best fitting areas.
716708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        if ( mFocusAreas.itemAt(0)->isZeroArea() )
717708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            {
718708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->nNumAreas = 0;
719708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            }
720708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
721708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        for ( unsigned int n = 0; n < mFocusAreas.size(); n++)
722708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            {
723708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            // transform the coordinates to 3A-type coordinates
724708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            mFocusAreas.itemAt(n)->transfrom((size_t)mPreviewData->mWidth,
725708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                            (size_t)mPreviewData->mHeight,
726708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                            (size_t&)focusAreas[0]->tAlgoAreas[n].nTop,
727708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                            (size_t&)focusAreas[0]->tAlgoAreas[n].nLeft,
728708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                            (size_t&)focusAreas[0]->tAlgoAreas[n].nWidth,
729708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                            (size_t&)focusAreas[0]->tAlgoAreas[n].nHeight);
730708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
731708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->tAlgoAreas[n].nLeft =
732708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    ( focusAreas[0]->tAlgoAreas[n].nLeft * TOUCH_FOCUS_RANGE ) / mPreviewData->mWidth;
733708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->tAlgoAreas[n].nTop =
734708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    ( focusAreas[0]->tAlgoAreas[n].nTop* TOUCH_FOCUS_RANGE ) / mPreviewData->mHeight;
735708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->tAlgoAreas[n].nWidth =
736708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    ( focusAreas[0]->tAlgoAreas[n].nWidth * TOUCH_FOCUS_RANGE ) / mPreviewData->mWidth;
737708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->tAlgoAreas[n].nHeight =
738708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    ( focusAreas[0]->tAlgoAreas[n].nHeight * TOUCH_FOCUS_RANGE ) / mPreviewData->mHeight;
739708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas[0]->tAlgoAreas[n].nPriority = mFocusAreas.itemAt(n)->getWeight();
740708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
741708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev             CAMHAL_LOGDB("Focus area %d : top = %d left = %d width = %d height = %d prio = %d",
742708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    n, (int)focusAreas[0]->tAlgoAreas[n].nTop, (int)focusAreas[0]->tAlgoAreas[n].nLeft,
743708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    (int)focusAreas[0]->tAlgoAreas[n].nWidth, (int)focusAreas[0]->tAlgoAreas[n].nHeight,
744708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                    (int)focusAreas[0]->tAlgoAreas[n].nPriority);
745708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev             }
746708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
747708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        OMX_INIT_STRUCT_PTR (&sharedBuffer, OMX_TI_CONFIG_SHAREDBUFFER);
748708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
749708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        sharedBuffer.nPortIndex = OMX_ALL;
750708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        sharedBuffer.nSharedBuffSize = areasSize;
751708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        sharedBuffer.pSharedBuff = (OMX_U8 *) focusAreas[0];
752708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
753708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        if ( NULL == sharedBuffer.pSharedBuff )
754708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            {
755708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            CAMHAL_LOGEA("No resources to allocate OMX shared buffer");
756708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            ret = -ENOMEM;
757708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            goto EXIT;
758708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            }
759708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
760708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            eError =  OMX_SetConfig(mCameraAdapterParameters.mHandleComp,
761708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev                                      (OMX_INDEXTYPE) OMX_TI_IndexConfigAlgoAreas, &sharedBuffer);
762708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
763c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        if ( OMX_ErrorNone != eError )
764c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
765708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            CAMHAL_LOGEB("Error while setting Focus Areas configuration 0x%x", eError);
766708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            ret = -EINVAL;
767c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
768708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev
769708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev    EXIT:
770708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev        if (NULL != focusAreas)
771c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            {
772708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            memMgr.freeBuffer((void*) focusAreas);
773708ed7306c85286aa50d05ba15e0c33106e52ed0Iliyan Malchev            focusAreas = NULL;
774c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev            }
775c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev        }
776c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
777c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    LOG_FUNCTION_NAME_EXIT;
778c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
779c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev    return ret;
780c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev}
781c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev
782057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luuvoid OMXCameraAdapter::handleFocusCallback() {
783057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    OMX_PARAM_FOCUSSTATUSTYPE eFocusStatus;
784057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    CameraHalEvent::FocusStatus focusStatus = CameraHalEvent::FOCUS_STATUS_FAIL;
785057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    status_t ret = NO_ERROR;
786057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    BaseCameraAdapter::AdapterState nextState;
787057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    BaseCameraAdapter::getNextState(nextState);
788057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
789057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    OMX_INIT_STRUCT(eFocusStatus, OMX_PARAM_FOCUSSTATUSTYPE);
790057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
791057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    ret = checkFocus(&eFocusStatus);
792057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
793057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    if (NO_ERROR != ret) {
794057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        CAMHAL_LOGEA("Focus status check failed!");
795057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        // signal and unblock doAutoFocus
796057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        if (AF_ACTIVE & nextState) {
797ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            Mutex::Autolock lock(mDoAFMutex);
798ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev            mDoAFCond.broadcast();
799057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        }
800057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        return;
801ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev    }
802ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev
803ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev    if (eFocusStatus.eFocusStatus != OMX_FocusStatusRequest) {
804057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        // signal doAutoFocus when a end of scan message comes
805057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        // ignore start of scan
806ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev        Mutex::Autolock lock(mDoAFMutex);
807ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev        mDoAFCond.broadcast();
808ac0cf36b98237ec911f49e7b1b93ef6464666e48Emilian Peev    }
809057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
810057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    if (mParameters3A.Focus != (OMX_IMAGE_FOCUSCONTROLTYPE) OMX_IMAGE_FocusControlAuto) {
811057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu       CAMHAL_LOGDA("unregistered focus callback when not in CAF or doAutoFocus... not handling");
812057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu       return;
813057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    }
814057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
815057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    // Handling for CAF Callbacks
816057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    switch (eFocusStatus.eFocusStatus) {
817057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        case OMX_FocusStatusRequest:
818057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            focusStatus = CameraHalEvent::FOCUS_STATUS_PENDING;
819057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            break;
820057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        case OMX_FocusStatusReached:
821057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        case OMX_FocusStatusOff:
822057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        case OMX_FocusStatusUnableToReach:
823057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu        default:
824057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            focusStatus = CameraHalEvent::FOCUS_STATUS_DONE;
825057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu            break;
826057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    }
827057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
828057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu    notifyFocusSubscribers(focusStatus);
829057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu}
830057f4fd59ec05ded909e9eb9a3363d9ea345b0caTyler Luu
831c322989ae6ff6769490828de1b5eda12b749cce9Iliyan Malchev};
832