2 * Copyright 2012 Samsung Electronics Co., Ltd
\r
4 * Licensed under the Flora License, Version 1.1 (the "License");
\r
5 * you may not use this file except in compliance with the License.
\r
6 * You may obtain a copy of the License at
\r
8 * http://floralicense.org/license/
\r
10 * Unless required by applicable law or agreed to in writing, software
\r
11 * distributed under the License is distributed on an "AS IS" BASIS,
\r
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
\r
13 * See the License for the specific language governing permissions and
\r
14 * limitations under the License.
\r
23 #include <sys/time.h>
\r
24 #include <pthread.h>
\r
26 #include "cam_error.h"
\r
27 #include "cam_debug.h"
\r
29 #include "cam_face_detection_focus.h"
\r
31 static pthread_mutex_t face_detecton_mutex = PTHREAD_MUTEX_INITIALIZER;
\r
32 static gboolean is_face_zoom = FALSE; /*note: the flag: now is in face zoom state or not*/
\r
33 static CamFaceInfo face_info;
\r
36 #define RECT_CORRECTION_VALUE (20)
\r
39 /*note:check point whether in rect, @correction_value for enhance/weaken the condition*/
\r
40 static gboolean __check_point_whether_in_rect(int point_x,
\r
42 CamVideoRectangle rect,
\r
43 int correction_value)
\r
46 if (point_x > (rect.x - correction_value)
\r
47 && point_y > (rect.y - correction_value)
\r
48 && point_x < (rect.w + rect.x + correction_value)
\r
49 && point_y < (rect.h + rect.y + correction_value)) {
\r
50 DEBUG_TRACE("point is in rect");
\r
56 void cam_face_detection_focus_start_stream(camera_preview_data_s *preview_frame, void *user_data)
\r
59 cam_retm_if(user_data == NULL, "data is null");
\r
60 cam_retm_if(preview_frame == NULL, "data is null");
\r
61 struct appdata *ad = (struct appdata *)user_data;
\r
62 CamAppData *camapp = ad->camapp_handle;
\r
63 cam_retm_if(camapp == NULL, "camapp is null");
\r
65 if (cam_app_is_skip_video_stream()) {
\r
68 if (cam_utils_set_guide_rect_color(ad) ==FALSE) {
\r
69 DEBUG_TRACE("cam_utils_set_guide_rect_color failed");
\r
72 switch (preview_frame->num_of_planes) {
\r
74 frame = preview_frame->data.single_plane.yuv;
\r
77 /*TODO: now do not support two planes*/
\r
80 /*TODO: now do not support three planes*/
\r
85 pthread_mutex_lock(&face_detecton_mutex);
\r
87 for(i = 0; i < face_info.count; i++ ) {
\r
90 camapp->guide_rect_color = camapp->guide_rect_green;
\r
92 camapp->guide_rect_color = camapp->guide_rect_white;
\r
95 cam_utils_draw_guide_rectangle(ad,
\r
97 face_info.faces[i].x,
\r
98 face_info.faces[i].y,
\r
99 face_info.faces[i].width,
\r
100 face_info.faces[i].height);
\r
103 pthread_mutex_unlock(&face_detecton_mutex);
\r
108 gboolean cam_face_detection_focus_init()
\r
111 err = pthread_mutex_init(&(face_detecton_mutex), NULL);
\r
113 cam_critical(LOG_CAM, "Create face detection mutex failed");
\r
119 gboolean cam_face_detection_focus_finish()
\r
121 pthread_mutex_destroy(&face_detecton_mutex);
\r
126 /*note: in face detection focus mode, when face deteced , callback will be called*/
\r
127 void cam_face_detection_focus_face_detected_cb(camera_detected_face_s *faces, int count, void *user_data)
\r
129 pthread_mutex_lock(&face_detecton_mutex);
\r
131 if(count > MAX_FACE_COUNT)
\r
132 count = MAX_FACE_COUNT;
\r
135 for(i = 0; i < count; i++ ) {
\r
137 face_info.faces[i].height = faces->height;
\r
138 face_info.faces[i].id = faces->id;
\r
139 face_info.faces[i].score = faces->score;
\r
140 face_info.faces[i].width = faces->width;
\r
141 face_info.faces[i].x = faces->x;
\r
142 face_info.faces[i].y = faces->y;
\r
145 face_info.count = count;
\r
146 pthread_mutex_unlock(&face_detecton_mutex);
\r
151 void cam_common_set_mouse_double_click_xy(Evas_Coord x, Evas_Coord y)
\r
153 struct appdata *ad = (struct appdata *)cam_appdata_get();
\r
154 cam_retm_if(ad == NULL, "appdata is NULL");
\r
156 CamAppData *camapp = NULL;
\r
157 camapp = ad->camapp_handle;
\r
158 cam_retm_if(camapp == NULL, "camapp is NULL");
\r
160 if (is_face_zoom) {
\r
162 cam_critical(LOG_CAM, "cancel face zoom");
\r
163 if (cam_mm_camera_cancel_face_zoom())
\r
164 is_face_zoom = FALSE;
\r
168 pthread_mutex_lock(&face_detecton_mutex);
\r
170 if(face_info.count < 1 )
\r
172 cam_debug(LOG_CAM, "not detected face");
\r
173 pthread_mutex_unlock(&face_detecton_mutex);
\r
177 cam_debug(LOG_CAM, "x = %d, y = %d", x, y);
\r
181 for(i=0; i<face_info.count; i++)
\r
183 CamVideoRectangle src;
\r
184 src.x = face_info.faces[i].x;
\r
185 src.y = face_info.faces[i].y;
\r
186 src.w = face_info.faces[i].width;
\r
187 src.h = face_info.faces[i].height;
\r
189 CamVideoRectangle dest;
\r
190 cam_utils_set_videos_xy_to_windows_xy(src, &dest,(void *)ad);
\r
192 cam_debug(LOG_CAM, "_x = %d, _y = %d", face_info.faces[i].x, face_info.faces[i].y);
\r
193 cam_debug(LOG_CAM, "cam_face_x = %d, cam_face_y = %d", dest.x, dest.y);
\r
195 gboolean point_in_rect = FALSE;
\r
196 point_in_rect = __check_point_whether_in_rect(x, y, dest, RECT_CORRECTION_VALUE);
\r
198 if (point_in_rect) {
\r
199 cam_debug(LOG_CAM, "in rect");
\r
200 if (is_face_zoom || (camapp->zoom_mode != camapp->zoom_min)) {
\r
201 if (cam_mm_camera_cancel_face_zoom()){
\r
202 is_face_zoom = FALSE;
\r
203 camapp->zoom_mode = ZOOM_DEFAULT;
\r
206 if (cam_mm_set_camera_face_zoom(face_info.faces[i].id)) {
\r
207 is_face_zoom = TRUE;
\r
211 cam_debug(LOG_CAM, "not matcing");
\r
214 pthread_mutex_unlock(&face_detecton_mutex);
\r
218 void cam_face_detection_reset()
\r
220 face_info.count = 0;
\r