Mercurial > pygame
comparison src/_camera.c @ 1849:301bc61643a9 math_module
merged changes from trunk
| author | lorenz |
|---|---|
| date | Mon, 16 Nov 2009 18:31:40 +0000 |
| parents | 19a59d1c410b |
| children |
comparison
equal
deleted
inserted
replaced
| 1848:bbc21cd6faeb | 1849:301bc61643a9 |
|---|---|
| 33 * functions to convert the format to packed RGB, YUV, and HSV. | 33 * functions to convert the format to packed RGB, YUV, and HSV. |
| 34 */ | 34 */ |
| 35 | 35 |
| 36 #include "camera.h" | 36 #include "camera.h" |
| 37 | 37 |
| 38 #if defined(__unix__) | 38 /* |
| 39 #if defined(__unix__) || !defined(__APPLE__) | |
| 39 #else | 40 #else |
| 40 #define V4L2_PIX_FMT_RGB24 1 | 41 #define V4L2_PIX_FMT_RGB24 1 |
| 41 #define V4L2_PIX_FMT_RGB444 1 | 42 #define V4L2_PIX_FMT_RGB444 1 |
| 42 #endif | 43 #endif |
| 44 */ | |
| 45 | |
| 43 | 46 |
| 44 /* functions available to pygame users */ | 47 /* functions available to pygame users */ |
| 45 PyObject* surf_colorspace (PyObject* self, PyObject* arg); | 48 PyObject* surf_colorspace (PyObject* self, PyObject* arg); |
| 46 PyObject* list_cameras (PyObject* self, PyObject* arg); | 49 PyObject* list_cameras (PyObject* self, PyObject* arg); |
| 47 PyObject* camera_start (PyCameraObject* self); | 50 PyObject* camera_start (PyCameraObject* self); |
| 60 * functions, but it could check something like self->cameratype and depending | 63 * functions, but it could check something like self->cameratype and depending |
| 61 * on the result, call v4l, v4l2, vfw, or other functions. | 64 * on the result, call v4l, v4l2, vfw, or other functions. |
| 62 */ | 65 */ |
| 63 | 66 |
| 64 /* colorspace() - Surface colorspace conversion */ | 67 /* colorspace() - Surface colorspace conversion */ |
| 65 PyObject* surf_colorspace (PyObject* self, PyObject* arg) | 68 PyObject* surf_colorspace (PyObject* self, PyObject* arg) { |
| 66 { | |
| 67 PyObject *surfobj, *surfobj2; | 69 PyObject *surfobj, *surfobj2; |
| 68 SDL_Surface* surf, *newsurf; | 70 SDL_Surface* surf, *newsurf; |
| 69 char* color; | 71 char* color; |
| 70 int cspace; | 72 int cspace; |
| 71 surfobj2 = NULL; | 73 surfobj2 = NULL; |
| 123 else | 125 else |
| 124 return PySurface_New (newsurf); | 126 return PySurface_New (newsurf); |
| 125 } | 127 } |
| 126 | 128 |
| 127 /* list_cameras() - lists cameras available on the computer */ | 129 /* list_cameras() - lists cameras available on the computer */ |
| 128 PyObject* list_cameras (PyObject* self, PyObject* arg) | 130 PyObject* list_cameras (PyObject* self, PyObject* arg) { |
| 129 { | 131 #if defined(__unix__) || defined (__APPLE__) |
| 130 #if defined(__unix__) | |
| 131 PyObject* ret_list; | 132 PyObject* ret_list; |
| 132 PyObject* string; | 133 PyObject* string; |
| 133 char** devices; | 134 char** devices; |
| 134 int num_devices, i; | 135 int num_devices, i; |
| 135 | 136 |
| 136 num_devices = 0; | 137 num_devices = 0; |
| 137 ret_list = NULL; | 138 ret_list = NULL; |
| 138 ret_list = PyList_New (0); | 139 ret_list = PyList_New (0); |
| 139 if (!ret_list) | 140 if (!ret_list) |
| 140 return NULL; | 141 return NULL; |
| 141 | 142 |
| 143 #if defined(__unix__) | |
| 142 devices = v4l2_list_cameras(&num_devices); | 144 devices = v4l2_list_cameras(&num_devices); |
| 145 # elif defined(__APPLE__) | |
| 146 devices = mac_list_cameras(&num_devices); | |
| 147 # endif | |
| 143 | 148 |
| 144 for(i = 0; i < num_devices; i++) { | 149 for(i = 0; i < num_devices; i++) { |
| 145 string = PyString_FromString(devices[i]); | 150 string = PyString_FromString(devices[i]); |
| 146 PyList_Append(ret_list, string); | 151 PyList_Append(ret_list, string); |
| 147 Py_DECREF(string); | 152 Py_DECREF(string); |
| 154 Py_RETURN_NONE; | 159 Py_RETURN_NONE; |
| 155 #endif | 160 #endif |
| 156 } | 161 } |
| 157 | 162 |
| 158 /* start() - opens, inits, and starts capturing on the camera */ | 163 /* start() - opens, inits, and starts capturing on the camera */ |
| 159 PyObject* camera_start (PyCameraObject* self) | 164 PyObject* camera_start (PyCameraObject* self) { |
| 160 { | |
| 161 #if defined(__unix__) | 165 #if defined(__unix__) |
| 162 if (v4l2_open_device(self) == 0) { | 166 if (v4l2_open_device(self) == 0) { |
| 163 if (v4l_open_device(self) == 0) { | 167 if (v4l_open_device(self) == 0) { |
| 164 v4l2_close_device(self); | 168 v4l2_close_device(self); |
| 165 return NULL; | 169 return NULL; |
| 183 if (v4l2_start_capturing(self) == 0) { | 187 if (v4l2_start_capturing(self) == 0) { |
| 184 v4l2_close_device(self); | 188 v4l2_close_device(self); |
| 185 return NULL; | 189 return NULL; |
| 186 } | 190 } |
| 187 } | 191 } |
| 192 #elif defined(__APPLE__) | |
| 193 if (! (mac_open_device(self) == 1 && mac_init_device(self) == 1 && mac_start_capturing(self) == 1)) { | |
| 194 mac_close_device(self); | |
| 195 return NULL; | |
| 196 } | |
| 188 #endif | 197 #endif |
| 189 Py_RETURN_NONE; | 198 Py_RETURN_NONE; |
| 190 } | 199 } |
| 191 | 200 |
| 192 /* stop() - stops capturing, uninits, and closes the camera */ | 201 /* stop() - stops capturing, uninits, and closes the camera */ |
| 193 PyObject* camera_stop (PyCameraObject* self) | 202 PyObject* camera_stop (PyCameraObject* self) { |
| 194 { | |
| 195 #if defined(__unix__) | 203 #if defined(__unix__) |
| 196 if (v4l2_stop_capturing(self) == 0) | 204 if (v4l2_stop_capturing(self) == 0) |
| 197 return NULL; | 205 return NULL; |
| 198 if (v4l2_uninit_device(self) == 0) | 206 if (v4l2_uninit_device(self) == 0) |
| 199 return NULL; | 207 return NULL; |
| 200 if (v4l2_close_device(self) == 0) | 208 if (v4l2_close_device(self) == 0) |
| 201 return NULL; | 209 return NULL; |
| 210 #elif defined(__APPLE__) | |
| 211 if (mac_stop_capturing(self) == 0) | |
| 212 return NULL; | |
| 213 if (mac_close_device(self) == 0) | |
| 214 return NULL; | |
| 202 #endif | 215 #endif |
| 203 Py_RETURN_NONE; | 216 Py_RETURN_NONE; |
| 204 } | 217 } |
| 205 | 218 |
| 206 /* get_controls() - gets current values of user controls */ | 219 /* get_controls() - gets current values of user controls */ |
| 207 /* TODO: Support brightness, contrast, and other common controls */ | 220 /* TODO: Support brightness, contrast, and other common controls */ |
| 208 PyObject* camera_get_controls (PyCameraObject* self) | 221 PyObject* camera_get_controls (PyCameraObject* self) { |
| 209 { | 222 #if defined(__unix__) |
| 210 int value; | 223 int value; |
| 211 #if defined(__unix__) | |
| 212 if (v4l2_get_control(self->fd, V4L2_CID_HFLIP, &value)) | 224 if (v4l2_get_control(self->fd, V4L2_CID_HFLIP, &value)) |
| 213 self->hflip = value; | 225 self->hflip = value; |
| 214 | 226 |
| 215 if (v4l2_get_control(self->fd, V4L2_CID_VFLIP, &value)) | 227 if (v4l2_get_control(self->fd, V4L2_CID_VFLIP, &value)) |
| 216 self->vflip = value; | 228 self->vflip = value; |
| 217 | 229 |
| 218 if (v4l2_get_control(self->fd, V4L2_CID_BRIGHTNESS, &value)) | 230 if (v4l2_get_control(self->fd, V4L2_CID_BRIGHTNESS, &value)) |
| 219 self->brightness = value; | 231 self->brightness = value; |
| 220 #endif | 232 |
| 221 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(self->brightness)); | 233 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(self->brightness)); |
| 234 #elif defined(__APPLE__) | |
| 235 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(-1)); | |
| 236 #endif | |
| 237 Py_RETURN_NONE; | |
| 222 } | 238 } |
| 223 | 239 |
| 224 /* set_controls() - changes camera settings if supported by the camera */ | 240 /* set_controls() - changes camera settings if supported by the camera */ |
| 225 PyObject* camera_set_controls (PyCameraObject* self, PyObject* arg, PyObject *kwds) | 241 PyObject* camera_set_controls (PyCameraObject* self, PyObject* arg, PyObject *kwds) { |
| 226 { | 242 #if defined(__unix__) |
| 227 int hflip = 0, vflip = 0, brightness = 0; | 243 int hflip = 0, vflip = 0, brightness = 0; |
| 228 char *kwids[] = {"hflip", "vflip", "brightness", NULL}; | 244 char *kwids[] = {"hflip", "vflip", "brightness", NULL}; |
| 229 | 245 |
| 230 camera_get_controls(self); | 246 camera_get_controls(self); |
| 231 hflip = self->hflip; | 247 hflip = self->hflip; |
| 232 vflip = self->vflip; | 248 vflip = self->vflip; |
| 233 brightness = self->brightness; | 249 brightness = self->brightness; |
| 234 | 250 |
| 235 if (!PyArg_ParseTupleAndKeywords(arg, kwds, "|iii", kwids, &hflip, &vflip, &brightness)) | 251 if (!PyArg_ParseTupleAndKeywords(arg, kwds, "|iii", kwids, &hflip, &vflip, &brightness)) |
| 236 return NULL; | 252 return NULL; |
| 237 #if defined(__unix__) | 253 |
| 254 /* #if defined(__unix__) */ | |
| 238 if (v4l2_set_control(self->fd, V4L2_CID_HFLIP, hflip)) | 255 if (v4l2_set_control(self->fd, V4L2_CID_HFLIP, hflip)) |
| 239 self->hflip = hflip; | 256 self->hflip = hflip; |
| 240 | 257 |
| 241 if (v4l2_set_control(self->fd, V4L2_CID_VFLIP, vflip)) | 258 if (v4l2_set_control(self->fd, V4L2_CID_VFLIP, vflip)) |
| 242 self->vflip = vflip; | 259 self->vflip = vflip; |
| 243 | 260 |
| 244 if (v4l2_set_control(self->fd, V4L2_CID_BRIGHTNESS, brightness)) | 261 if (v4l2_set_control(self->fd, V4L2_CID_BRIGHTNESS, brightness)) |
| 245 self->brightness = brightness; | 262 self->brightness = brightness; |
| 246 #endif | 263 |
| 247 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(self->brightness)); | 264 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(self->brightness)); |
| 265 | |
| 266 #elif defined(__APPLE__) | |
| 267 int hflip = 0, vflip = 0, brightness = 0; | |
| 268 char *kwids[] = {"hflip", "vflip", "brightness", NULL}; | |
| 269 | |
| 270 camera_get_controls(self); | |
| 271 hflip = self->hflip; | |
| 272 vflip = self->vflip; | |
| 273 brightness = -1; | |
| 274 | |
| 275 if (!PyArg_ParseTupleAndKeywords(arg, kwds, "|iii", kwids, &hflip, &vflip, &brightness)) | |
| 276 return NULL; | |
| 277 | |
| 278 self->hflip = hflip; | |
| 279 self->vflip = vflip; | |
| 280 | |
| 281 return Py_BuildValue ("(NNN)", PyBool_FromLong(self->hflip), PyBool_FromLong(self->vflip), PyInt_FromLong(-1)); | |
| 282 #endif | |
| 283 Py_RETURN_NONE; | |
| 248 } | 284 } |
| 249 | 285 |
| 250 /* get_size() - returns the dimensions of the images being recorded */ | 286 /* get_size() - returns the dimensions of the images being recorded */ |
| 251 PyObject* camera_get_size (PyCameraObject* self) | 287 PyObject* camera_get_size (PyCameraObject* self) { |
| 252 { | 288 #if defined(__unix__) |
| 253 return Py_BuildValue ("(ii)", self->width, self->height); | 289 return Py_BuildValue ("(ii)", self->width, self->height); |
| 290 #elif defined(__APPLE__) | |
| 291 return Py_BuildValue ("(ii)", self->boundsRect.right, self->boundsRect.bottom); | |
| 292 #endif | |
| 293 Py_RETURN_NONE; | |
| 254 } | 294 } |
| 255 | 295 |
| 256 /* query_image() - checks if a frame is ready */ | 296 /* query_image() - checks if a frame is ready */ |
| 257 PyObject* camera_query_image (PyCameraObject* self) | 297 PyObject* camera_query_image(PyCameraObject* self) { |
| 258 { | |
| 259 #if defined(__unix__) | 298 #if defined(__unix__) |
| 260 return PyBool_FromLong(v4l2_query_buffer(self)); | 299 return PyBool_FromLong(v4l2_query_buffer(self)); |
| 261 #endif | 300 #endif |
| 262 Py_RETURN_NONE; | 301 Py_RETURN_TRUE; |
| 263 } | 302 } |
| 264 | 303 |
| 265 /* get_image() - returns an RGB Surface */ | 304 /* get_image() - returns an RGB Surface */ |
| 266 /* code to reuse Surface from René Dudfield */ | 305 /* code to reuse Surface from René Dudfield */ |
| 267 PyObject* camera_get_image (PyCameraObject* self, PyObject* arg) | 306 PyObject* camera_get_image (PyCameraObject* self, PyObject* arg) { |
| 268 { | 307 #if defined(__unix__) |
| 269 SDL_Surface* surf = NULL; | 308 SDL_Surface* surf = NULL; |
| 270 PyObject *surfobj = NULL; | 309 PyObject *surfobj = NULL; |
| 271 | 310 |
| 272 if (!PyArg_ParseTuple (arg, "|O!", &PySurface_Type, &surfobj)) | 311 if (!PyArg_ParseTuple (arg, "|O!", &PySurface_Type, &surfobj)) |
| 273 return NULL; | 312 return NULL; |
| 284 | 323 |
| 285 if (surf->w != self->width || surf->h != self->height) { | 324 if (surf->w != self->width || surf->h != self->height) { |
| 286 return RAISE (PyExc_ValueError, | 325 return RAISE (PyExc_ValueError, |
| 287 "Destination surface not the correct width or height."); | 326 "Destination surface not the correct width or height."); |
| 288 } | 327 } |
| 289 #if defined(__unix__) | 328 |
| 290 Py_BEGIN_ALLOW_THREADS; | 329 Py_BEGIN_ALLOW_THREADS; |
| 291 if (!v4l2_read_frame(self, surf)) | 330 if (!v4l2_read_frame(self, surf)) |
| 292 return NULL; | 331 return NULL; |
| 293 Py_END_ALLOW_THREADS; | 332 Py_END_ALLOW_THREADS; |
| 294 #endif | 333 |
| 295 if (!surf) | 334 if (!surf) |
| 296 return NULL; | 335 return NULL; |
| 297 | 336 |
| 298 if (surfobj) { | 337 if (surfobj) { |
| 299 Py_INCREF (surfobj); | 338 Py_INCREF (surfobj); |
| 300 return surfobj; | 339 return surfobj; |
| 301 } else { | 340 } else { |
| 302 return PySurface_New (surf); | 341 return PySurface_New (surf); |
| 303 } | 342 } |
| 343 #elif defined(__APPLE__) | |
| 344 SDL_Surface* surf = NULL; | |
| 345 PyObject *surfobj = NULL; | |
| 346 | |
| 347 if (!PyArg_ParseTuple (arg, "|O!", &PySurface_Type, &surfobj)) | |
| 348 return NULL; | |
| 349 | |
| 350 if (!surfobj) { | |
| 351 surf = SDL_CreateRGBSurface( | |
| 352 0, | |
| 353 self->boundsRect.right, | |
| 354 self->boundsRect.bottom, | |
| 355 24, | |
| 356 0xFF<<16, | |
| 357 0xFF<<8, | |
| 358 0xFF, | |
| 359 0); | |
| 360 | |
| 361 } else { | |
| 362 surf = PySurface_AsSurface(surfobj); | |
| 363 } | |
| 364 | |
| 365 if (!surf) | |
| 366 return NULL; | |
| 367 | |
| 368 if (surf->w != self->boundsRect.right || surf->h != self->boundsRect.bottom) { | |
| 369 return RAISE (PyExc_ValueError, | |
| 370 "Destination surface not the correct width or height."); | |
| 371 } | |
| 372 /*is dit nodig op osx... */ | |
| 373 Py_BEGIN_ALLOW_THREADS; | |
| 374 | |
| 375 if (!mac_read_frame(self, surf)) | |
| 376 return NULL; | |
| 377 Py_END_ALLOW_THREADS; | |
| 378 if (!surf) | |
| 379 return NULL; | |
| 380 | |
| 381 if (surfobj) { | |
| 382 Py_INCREF (surfobj); | |
| 383 return surfobj; | |
| 384 } else { | |
| 385 return PySurface_New (surf); | |
| 386 } | |
| 387 #endif | |
| 388 Py_RETURN_NONE; | |
| 304 } | 389 } |
| 305 | 390 |
| 306 /* get_raw() - returns an unmodified image as a string from the buffer */ | 391 /* get_raw() - returns an unmodified image as a string from the buffer */ |
| 307 PyObject* camera_get_raw(PyCameraObject* self) | 392 PyObject* camera_get_raw(PyCameraObject* self) { |
| 308 { | |
| 309 #if defined(__unix__) | 393 #if defined(__unix__) |
| 310 return v4l2_read_raw(self); | 394 return v4l2_read_raw(self); |
| 395 #elif defined(__APPLE__) | |
| 396 return mac_read_raw(self); | |
| 311 #endif | 397 #endif |
| 312 Py_RETURN_NONE; | 398 Py_RETURN_NONE; |
| 313 } | 399 } |
| 314 | 400 |
| 315 /* | 401 /* |
| 316 * Pixelformat conversion functions | 402 * Pixelformat conversion functions |
| 317 */ | 403 */ |
| 318 | 404 |
| 319 /* converts from rgb Surface to yuv or hsv */ | 405 /* converts from rgb Surface to yuv or hsv */ |
| 320 /* TODO: Allow for conversion from yuv and hsv to all */ | 406 /* TODO: Allow for conversion from yuv and hsv to all */ |
| 321 void colorspace (SDL_Surface *src, SDL_Surface *dst, int cspace) | 407 void colorspace (SDL_Surface *src, SDL_Surface *dst, int cspace) { |
| 322 { | |
| 323 switch (cspace) { | 408 switch (cspace) { |
| 324 case YUV_OUT: | 409 case YUV_OUT: |
| 325 rgb_to_yuv (src->pixels, dst->pixels, src->h * src->w, 0, src->format); | 410 rgb_to_yuv (src->pixels, dst->pixels, src->h * src->w, 0, src->format); |
| 326 break; | 411 break; |
| 327 case HSV_OUT: | 412 case HSV_OUT: |
| 669 } | 754 } |
| 670 } | 755 } |
| 671 } | 756 } |
| 672 | 757 |
| 673 /* Converts from rgb444 (R444) to rgb24 (RGB3) */ | 758 /* Converts from rgb444 (R444) to rgb24 (RGB3) */ |
| 674 void rgb444_to_rgb (const void* src, void* dst, int length, SDL_PixelFormat* format) | 759 void rgb444_to_rgb (const void* src, void* dst, int length, SDL_PixelFormat* format) { |
| 675 { | |
| 676 Uint8 *s, *d8; | 760 Uint8 *s, *d8; |
| 677 Uint16 *d16; | 761 Uint16 *d16; |
| 678 Uint32 *d32; | 762 Uint32 *d32; |
| 679 Uint8 p1, p2, r, g, b; | 763 Uint8 p1, p2, r, g, b; |
| 680 int rshift, gshift, bshift, rloss, gloss, bloss; | 764 int rshift, gshift, bshift, rloss, gloss, bloss; |
| 729 } | 813 } |
| 730 | 814 |
| 731 /* convert from 4:2:2 YUYV interlaced to RGB */ | 815 /* convert from 4:2:2 YUYV interlaced to RGB */ |
| 732 /* colorspace conversion routine from libv4l. Licensed LGPL 2.1 | 816 /* colorspace conversion routine from libv4l. Licensed LGPL 2.1 |
| 733 (C) 2008 Hans de Goede <j.w.r.degoede@hhs.nl> */ | 817 (C) 2008 Hans de Goede <j.w.r.degoede@hhs.nl> */ |
| 734 void yuyv_to_rgb (const void* src, void* dst, int length, SDL_PixelFormat* format) | 818 void yuyv_to_rgb (const void* src, void* dst, int length, SDL_PixelFormat* format) { |
| 735 { | |
| 736 Uint8 *s, *d8; | 819 Uint8 *s, *d8; |
| 737 Uint16 *d16; | 820 Uint16 *d16; |
| 738 Uint32 *d32; | 821 Uint32 *d32; |
| 739 int i; | 822 int i; |
| 740 int r1, g1, b1, r2, b2, g2; | 823 int r1, g1, b1, r2, b2, g2; |
| 800 } | 883 } |
| 801 } | 884 } |
| 802 } | 885 } |
| 803 | 886 |
| 804 /* turn yuyv into packed yuv. */ | 887 /* turn yuyv into packed yuv. */ |
| 805 void yuyv_to_yuv (const void* src, void* dst, int length, SDL_PixelFormat* format) | 888 void yuyv_to_yuv (const void* src, void* dst, int length, SDL_PixelFormat* format) { |
| 806 { | |
| 807 Uint8 *s, *d8; | 889 Uint8 *s, *d8; |
| 808 Uint8 y1, u, y2, v; | 890 Uint8 y1, u, y2, v; |
| 809 Uint16 *d16; | 891 Uint16 *d16; |
| 810 Uint32 *d32; | 892 Uint32 *d32; |
| 811 int i = length >> 1; | 893 int i = length >> 1; |
| 894 * SUCH DAMAGE. | 976 * SUCH DAMAGE. |
| 895 */ | 977 */ |
| 896 /* FIXME: Seems to be grayscale and kind of dark on the OLPC XO | 978 /* FIXME: Seems to be grayscale and kind of dark on the OLPC XO |
| 897 Maybe the result of a different Bayer color order on the screen? */ | 979 Maybe the result of a different Bayer color order on the screen? */ |
| 898 /* TODO: Certainly not the most efficient way of doing this conversion. */ | 980 /* TODO: Certainly not the most efficient way of doing this conversion. */ |
| 899 void sbggr8_to_rgb (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) | 981 void sbggr8_to_rgb (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) { |
| 900 { | |
| 901 Uint8 *rawpt, *d8; | 982 Uint8 *rawpt, *d8; |
| 902 Uint16 *d16; | 983 Uint16 *d16; |
| 903 Uint32 *d32; | 984 Uint32 *d32; |
| 904 Uint8 r, g, b; | 985 Uint8 r, g, b; |
| 905 int rshift, gshift, bshift, rloss, gloss, bloss; | 986 int rshift, gshift, bshift, rloss, gloss, bloss; |
| 997 } | 1078 } |
| 998 | 1079 |
| 999 | 1080 |
| 1000 /* convert from YUV 4:2:0 (YU12) to RGB24 */ | 1081 /* convert from YUV 4:2:0 (YU12) to RGB24 */ |
| 1001 /* based on v4lconvert_yuv420_to_rgb24 in libv4l (C) 2008 Hans de Goede. LGPL */ | 1082 /* based on v4lconvert_yuv420_to_rgb24 in libv4l (C) 2008 Hans de Goede. LGPL */ |
| 1002 void yuv420_to_rgb (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) | 1083 void yuv420_to_rgb (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) { |
| 1003 { | |
| 1004 int rshift, gshift, bshift, rloss, gloss, bloss, i, j, u1, v1, rg, y; | 1084 int rshift, gshift, bshift, rloss, gloss, bloss, i, j, u1, v1, rg, y; |
| 1005 const Uint8 *y1, *y2, *u, *v; | 1085 const Uint8 *y1, *y2, *u, *v; |
| 1006 Uint8 *d8_1, *d8_2; | 1086 Uint8 *d8_1, *d8_2; |
| 1007 Uint16 *d16_1, *d16_2; | 1087 Uint16 *d16_1, *d16_2; |
| 1008 Uint32 *d32_1, *d32_2; | 1088 Uint32 *d32_1, *d32_2; |
| 1188 break; | 1268 break; |
| 1189 } | 1269 } |
| 1190 } | 1270 } |
| 1191 | 1271 |
| 1192 /* turn yuv420 into packed yuv. */ | 1272 /* turn yuv420 into packed yuv. */ |
| 1193 void yuv420_to_yuv (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) | 1273 void yuv420_to_yuv (const void* src, void* dst, int width, int height, SDL_PixelFormat* format) { |
| 1194 { | |
| 1195 const Uint8 *y1, *y2, *u, *v; | 1274 const Uint8 *y1, *y2, *u, *v; |
| 1196 Uint8 *d8_1, *d8_2; | 1275 Uint8 *d8_1, *d8_2; |
| 1197 Uint16 *d16_1, *d16_2; | 1276 Uint16 *d16_1, *d16_2; |
| 1198 Uint32 *d32_1, *d32_2; | 1277 Uint32 *d32_1, *d32_2; |
| 1199 int rshift, gshift, bshift, rloss, gloss, bloss, j, i; | 1278 int rshift, gshift, bshift, rloss, gloss, bloss, j, i; |
| 1288 break; | 1367 break; |
| 1289 } | 1368 } |
| 1290 | 1369 |
| 1291 } | 1370 } |
| 1292 | 1371 |
| 1372 | |
| 1373 | |
| 1293 /* | 1374 /* |
| 1294 * Python API stuff | 1375 * Python API stuff |
| 1295 */ | 1376 */ |
| 1296 | 1377 |
| 1297 PyMethodDef cameraobj_builtins[] = | 1378 /* Camera class definition */ |
| 1298 { | 1379 PyMethodDef cameraobj_builtins[] = { |
| 1299 { "start", (PyCFunction) camera_start, METH_NOARGS, DOC_CAMERASTART }, | 1380 { "start", (PyCFunction) camera_start, METH_NOARGS, DOC_CAMERASTART }, |
| 1300 { "stop", (PyCFunction) camera_stop, METH_NOARGS, DOC_CAMERASTOP }, | 1381 { "stop", (PyCFunction) camera_stop, METH_NOARGS, DOC_CAMERASTOP }, |
| 1301 { "get_controls", (PyCFunction) camera_get_controls, METH_NOARGS, DOC_CAMERAGETCONTROLS }, | 1382 { "get_controls", (PyCFunction) camera_get_controls, METH_NOARGS, DOC_CAMERAGETCONTROLS }, |
| 1302 { "set_controls", (PyCFunction) camera_set_controls, METH_KEYWORDS, DOC_CAMERASETCONTROLS }, | 1383 { "set_controls", (PyCFunction) camera_set_controls, METH_KEYWORDS, DOC_CAMERASETCONTROLS }, |
| 1303 { "get_size", (PyCFunction) camera_get_size, METH_NOARGS, DOC_CAMERAGETSIZE }, | 1384 { "get_size", (PyCFunction) camera_get_size, METH_NOARGS, DOC_CAMERAGETSIZE }, |
| 1305 { "get_image", (PyCFunction) camera_get_image, METH_VARARGS, DOC_CAMERAGETIMAGE }, | 1386 { "get_image", (PyCFunction) camera_get_image, METH_VARARGS, DOC_CAMERAGETIMAGE }, |
| 1306 { "get_raw", (PyCFunction) camera_get_raw, METH_NOARGS, DOC_CAMERAGETRAW }, | 1387 { "get_raw", (PyCFunction) camera_get_raw, METH_NOARGS, DOC_CAMERAGETRAW }, |
| 1307 { NULL, NULL, 0, NULL } | 1388 { NULL, NULL, 0, NULL } |
| 1308 }; | 1389 }; |
| 1309 | 1390 |
| 1310 void camera_dealloc (PyObject* self) | 1391 void camera_dealloc (PyObject* self) { |
| 1311 { | |
| 1312 free(((PyCameraObject*) self)->device_name); | 1392 free(((PyCameraObject*) self)->device_name); |
| 1313 PyObject_DEL (self); | 1393 PyObject_DEL (self); |
| 1314 } | 1394 } |
| 1315 | 1395 |
| 1316 PyObject* camera_getattr(PyObject* self, char* attrname) | 1396 PyObject* camera_getattr(PyObject* self, char* attrname) { |
| 1317 { | |
| 1318 return Py_FindMethod(cameraobj_builtins, self, attrname); | 1397 return Py_FindMethod(cameraobj_builtins, self, attrname); |
| 1319 } | 1398 } |
| 1320 | 1399 |
| 1321 PyTypeObject PyCamera_Type = | 1400 PyTypeObject PyCamera_Type = { |
| 1322 { | |
| 1323 PyObject_HEAD_INIT(NULL) | 1401 PyObject_HEAD_INIT(NULL) |
| 1324 0, | 1402 0, |
| 1325 "Camera", | 1403 "Camera", |
| 1326 sizeof(PyCameraObject), | 1404 sizeof(PyCameraObject), |
| 1327 0, | 1405 0, |
| 1328 camera_dealloc, | 1406 camera_dealloc, |
| 1329 0, | 1407 0, |
| 1330 camera_getattr, | 1408 camera_getattr, |
| 1331 NULL, /*setattr*/ | 1409 NULL, /*setattr*/ |
| 1332 NULL, /*compare*/ | 1410 NULL, /*compare*/ |
| 1333 NULL, /*repr*/ | 1411 NULL, /*repr*/ |
| 1334 NULL, /*as_number*/ | 1412 NULL, /*as_number*/ |
| 1335 NULL, /*as_sequence*/ | 1413 NULL, /*as_sequence*/ |
| 1336 NULL, /*as_mapping*/ | 1414 NULL, /*as_mapping*/ |
| 1337 (hashfunc)NULL, /*hash*/ | 1415 (hashfunc)NULL, /*hash*/ |
| 1338 (ternaryfunc)NULL, /*call*/ | 1416 (ternaryfunc)NULL, /*call*/ |
| 1339 (reprfunc)NULL, /*str*/ | 1417 (reprfunc)NULL, /*str*/ |
| 1340 0L,0L,0L,0L, | 1418 0L,0L,0L,0L, |
| 1341 DOC_PYGAMECAMERACAMERA /* Documentation string */ | 1419 DOC_PYGAMECAMERACAMERA /* Documentation string */ |
| 1342 }; | 1420 }; |
| 1343 | 1421 |
| 1344 PyObject* Camera (PyCameraObject* self, PyObject* arg) | 1422 PyObject* Camera (PyCameraObject* self, PyObject* arg) { |
| 1345 { | 1423 # if defined(__unix__) |
| 1346 int w, h; | 1424 int w, h; |
| 1347 char* dev_name = NULL; | 1425 char* dev_name = NULL; |
| 1348 char* color = NULL; | 1426 char* color = NULL; |
| 1349 PyCameraObject *cameraobj; | 1427 PyCameraObject *cameraobj; |
| 1350 | 1428 |
| 1382 cameraobj->brightness = 0; | 1460 cameraobj->brightness = 0; |
| 1383 cameraobj->fd = -1; | 1461 cameraobj->fd = -1; |
| 1384 } | 1462 } |
| 1385 | 1463 |
| 1386 return (PyObject*)cameraobj; | 1464 return (PyObject*)cameraobj; |
| 1387 } | 1465 |
| 1388 | 1466 # elif defined(__APPLE__) |
| 1389 PyMethodDef camera_builtins[] = | 1467 int w, h; |
| 1390 { | 1468 char* dev_name = NULL; |
| 1391 { "colorspace", surf_colorspace, METH_VARARGS, DOC_PYGAMECAMERACOLORSPACE }, | 1469 char* color = NULL; |
| 1392 { "list_cameras", list_cameras, METH_NOARGS, DOC_PYGAMECAMERALISTCAMERAS }, | 1470 PyCameraObject *cameraobj; |
| 1393 { "Camera", (PyCFunction) Camera, METH_VARARGS, DOC_PYGAMECAMERACAMERA }, | 1471 |
| 1394 { NULL, NULL, 0, NULL } | 1472 w = DEFAULT_WIDTH; |
| 1473 h = DEFAULT_HEIGHT; | |
| 1474 | |
| 1475 if (!PyArg_ParseTuple(arg, "s|(ii)s", &dev_name, &w, &h, &color)) | |
| 1476 return NULL; | |
| 1477 | |
| 1478 cameraobj = PyObject_NEW (PyCameraObject, &PyCamera_Type); | |
| 1479 | |
| 1480 if (cameraobj) { | |
| 1481 cameraobj->device_name = (char*) malloc((strlen(dev_name)+1)*sizeof(char)); | |
| 1482 strcpy(cameraobj->device_name, dev_name); | |
| 1483 if (color) { | |
| 1484 if (!strcmp(color, "YUV")) { | |
| 1485 cameraobj->color_out = YUV_OUT; | |
| 1486 } else if (!strcmp(color, "HSV")) { | |
| 1487 cameraobj->color_out = HSV_OUT; | |
| 1488 } else { | |
| 1489 cameraobj->color_out = RGB_OUT; | |
| 1490 } | |
| 1491 } else { | |
| 1492 cameraobj->color_out = RGB_OUT; | |
| 1493 } | |
| 1494 cameraobj->component = NULL; | |
| 1495 cameraobj->channel = NULL; | |
| 1496 cameraobj->gworld = NULL; | |
| 1497 cameraobj->boundsRect.top = 0; | |
| 1498 cameraobj->boundsRect.left = 0; | |
| 1499 cameraobj->boundsRect.bottom = h; | |
| 1500 cameraobj->boundsRect.right = w; | |
| 1501 cameraobj->size = w * h; | |
| 1502 cameraobj->hflip = 0; | |
| 1503 cameraobj->vflip = 0; | |
| 1504 } | |
| 1505 | |
| 1506 return (PyObject*)cameraobj; | |
| 1507 # endif | |
| 1508 } | |
| 1509 | |
| 1510 /* Camera module definition */ | |
| 1511 PyMethodDef camera_builtins[] = { | |
| 1512 {"colorspace", surf_colorspace, METH_VARARGS, DOC_PYGAMECAMERACOLORSPACE }, | |
| 1513 {"list_cameras", list_cameras, METH_NOARGS, DOC_PYGAMECAMERALISTCAMERAS }, | |
| 1514 {"Camera", (PyCFunction) Camera, METH_VARARGS, DOC_PYGAMECAMERACAMERA }, | |
| 1515 {NULL, NULL, 0, NULL } | |
| 1395 }; | 1516 }; |
| 1396 | 1517 |
| 1397 void init_camera(void) | 1518 void init_camera(void) { |
| 1398 { | 1519 PyObject *module, *dict; |
| 1399 PyObject *module, *dict; | 1520 /* imported needed apis; Do this first so if there is an error |
| 1400 /* imported needed apis; Do this first so if there is an error | 1521 * the module is not loaded. |
| 1401 the module is not loaded. | 1522 */ |
| 1402 */ | 1523 import_pygame_base(); |
| 1403 import_pygame_base (); | 1524 if (PyErr_Occurred()) { |
| 1404 if (PyErr_Occurred ()) { | 1525 return; |
| 1405 return; | 1526 } |
| 1406 } | 1527 import_pygame_surface(); |
| 1407 import_pygame_surface (); | 1528 if (PyErr_Occurred()) { |
| 1408 if (PyErr_Occurred ()) { | 1529 return; |
| 1409 return; | 1530 } |
| 1410 } | 1531 |
| 1411 | 1532 /* type preparation */ |
| 1412 /* type preparation */ | 1533 PyType_Init(PyCamera_Type); |
| 1413 PyType_Init(PyCamera_Type); | |
| 1414 | 1534 |
| 1415 /* create the module */ | 1535 /* create the module */ |
| 1416 module = Py_InitModule3("_camera", camera_builtins, DOC_PYGAMECAMERA); | 1536 module = Py_InitModule3("_camera", camera_builtins, DOC_PYGAMECAMERA); |
| 1417 dict = PyModule_GetDict(module); | 1537 dict = PyModule_GetDict(module); |
| 1418 PyDict_SetItemString(dict, "CameraType", (PyObject *)&PyCamera_Type); | 1538 PyDict_SetItemString(dict, "CameraType", (PyObject *)&PyCamera_Type); |
| 1419 } | 1539 } |
