c710b4ee4aedab91bc30b6d8efd4e694276803d2
[ozzloy@gmail.com/oble] / oble.cpp
1 //use the camera to aid the decision to sleep.
2 //Copyright 2009 Daniel Watson
3 /*
4 use a camera to prevent screensaver
5 Copyright (C) 2009 daniel watson, ozzloy@gmail.com
6
7 This program is free software: you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation, either version 3 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
19 */
20 /*
21 This file is part of oble.
22
23 oble is free software: you can redistribute it and/or modify
24 it under the terms of the GNU General Public License as published by
25 the Free Software Foundation, either version 3 of the License, or
26 (at your option) any later version.
27
28 oble is distributed in the hope that it will be useful,
29 but WITHOUT ANY WARRANTY; without even the implied warranty of
30 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
31 GNU General Public License for more details.
32
33 You should have received a copy of the GNU General Public License
34 along with oble. If not, see <http://www.gnu.org/licenses/>.
35
36 */
37 #include <cv.h>
38 #include <highgui.h>
39 #include <stdio.h>
40 #include <iostream>
41 #include <time.h>
42
43 static time_t t_last = time(NULL);
44 static time_t t_current = time(NULL);
45 static time_t t_tmp = time(NULL);
46
47 using namespace std;
48
49 // argument for cvFlip(src, dest, FLIP_TYPE)
50 #define MIRROR 1
51
52 CvHaarClassifierCascade* load_object_detector(const char* cascade_path)
53 {
54 return (CvHaarClassifierCascade*)cvLoad(cascade_path);
55 }
56
57 void detect_and_draw_objects(IplImage* image,
58 CvHaarClassifierCascade* cascade,
59 int do_pyramids)
60 {
61 IplImage* small_image = image;
62 CvMemStorage* storage = cvCreateMemStorage(0);
63 CvSeq* faces;
64 int i, scale = 1;
65
66 /* if the flag is specified, down-scale the input image to get a
67 performance boost w/o loosing quality (perhaps) */
68 if(do_pyramids)
69 {
70 small_image = cvCreateImage(cvSize(image->width/2,image->height/2),
71 IPL_DEPTH_8U, 3);
72 cvPyrDown(image, small_image, CV_GAUSSIAN_5x5);
73 scale = 2;
74 }
75
76 /* use the fastest variant */
77 faces = cvHaarDetectObjects(small_image, cascade, storage, 1.2, 2,
78 CV_HAAR_DO_CANNY_PRUNING);
79
80 if(0 < faces->total)
81 {
82 t_current = time(NULL);
83 }
84
85 /* draw all the rectangles */
86 for(i = 0; i < faces->total; i++)
87 {
88 /* extract the rectangles only */
89 CvRect face = *(CvRect*)cvGetSeqElem(faces, i);
90 CvPoint upperLeft = cvPoint(face.x * scale, face.y * scale);
91 CvPoint bottomRight = cvPoint((face.x + face.width) * scale,
92 (face.y + face.height) * scale);
93 cvRectangle(image, upperLeft, bottomRight, CV_RGB(255,0,0), 3);
94 }
95
96 if(small_image != image)
97 cvReleaseImage(&small_image);
98 cvReleaseMemStorage(&storage);
99 }
100
101 void screensave(time_t t_current)
102 {
103 static int last_elapse = 0;
104 static int activated = 0;
105 int elapse = difftime(time(NULL), t_current);
106 int timeout = 10;
107 if(elapse > timeout && elapse != last_elapse)
108 {
109 last_elapse = elapse;
110 printf("elapse = %d\n", elapse);
111 if(!activated)
112 {
113 printf("activated\n");
114 activated = 1;
115 system("gnome-screensaver-command -a");
116 }
117 }
118 if(elapse < timeout && activated)
119 {
120 printf("deactivated\n");
121 activated = 0;
122 system("gnome-screensaver-command -d");
123 }
124 }
125
126 // A Simple Camera Capture Framework.
127 int main(int argc, char** argv)
128 {
129 CvHaarClassifierCascade* cascade = load_object_detector(argv[1]);
130
131 CvCapture* capture = cvCaptureFromCAM(CV_CAP_ANY);
132 if(!capture) {
133 cerr << "ERROR: capture is NULL " << endl;
134 getchar();
135 return -1;
136 }
137
138 // Create a window in which the captured images will be presented
139 cvNamedWindow("mywindow", CV_WINDOW_AUTOSIZE);
140
141 IplImage* frame = cvQueryFrame(capture);
142 if(!frame) {
143 cerr << "ERROR: frame is null..." << endl;
144 getchar();
145 return -1;
146 }
147 IplImage* mirrored =
148 cvCreateImage(cvGetSize(frame), frame->depth, frame->nChannels);
149 t_current = time(NULL);
150 // Show the image captured from the camera in the window and repeat
151 while(1) {
152 // Get one frame
153 frame = cvQueryFrame(capture);
154 if(!frame) {
155 cerr << "ERROR: frame is null..." << endl;
156 getchar();
157 break;
158 }
159
160 //flip the image so displayed right/left corresponds to physical right/left
161 cvFlip(frame, mirrored, MIRROR);
162
163 detect_and_draw_objects(mirrored, cascade, 1);
164 cvShowImage("mywindow", mirrored);
165 // Do not release the frame!
166 screensave(t_current);
167
168 //If ESC key pressed, Key=0x10001B under OpenCV 0.9.7(linux version),
169 //remove higher bits using AND operator
170 if((cvWaitKey(100) & 255) == 27) break;
171 }
172
173 // Release the capture device housekeeping
174 cvReleaseCapture(&capture);
175 cvDestroyWindow("mywindow");
176 cvReleaseImage(&mirrored);
177 return 0;
178 }