1 /*M///////////////////////////////////////////////////////////////////////////////////////
2 //
3 // IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING.
4 //
5 // By downloading, copying, installing or using the software you agree to this license.
6 // If you do not agree to this license, do not download, install,
7 // copy or use the software.
8 //
9 //
10 // Intel License Agreement
11 // For Open Source Computer Vision Library
12 //
13 // Copyright (C) 2000, Intel Corporation, all rights reserved.
14 // Third party copyrights are property of their respective owners.
15 //
16 // Redistribution and use in source and binary forms, with or without modification,
17 // are permitted provided that the following conditions are met:
18 //
19 // * Redistribution's of source code must retain the above copyright notice,
20 // this list of conditions and the following disclaimer.
21 //
22 // * Redistribution's in binary form must reproduce the above copyright notice,
23 // this list of conditions and the following disclaimer in the documentation
24 // and/or other materials provided with the distribution.
25 //
26 // * The name of Intel Corporation may not be used to endorse or promote products
27 // derived from this software without specific prior written permission.
28 //
29 // This software is provided by the copyright holders and contributors "as is" and
30 // any express or implied warranties, including, but not limited to, the implied
31 // warranties of merchantability and fitness for a particular purpose are disclaimed.
32 // In no event shall the Intel Corporation or contributors be liable for any direct,
33 // indirect, incidental, special, exemplary, or consequential damages
34 // (including, but not limited to, procurement of substitute goods or services;
35 // loss of use, data, or profits; or business interruption) however caused
36 // and on any theory of liability, whether in contract, strict liability,
37 // or tort (including negligence or otherwise) arising in any way out of
38 // the use of this software, even if advised of the possibility of such damage.
39 //
40 //M*/
41
42 #include "precomp.hpp"
43
44 #include <Carbon/Carbon.h>
45 #include <Quicktime/Quicktime.h>//YV
46
47 #include <unistd.h>
48 #include <cstdio>
49 #include <cmath>
50
51 //#define MS_TO_TICKS(a) a*3/50
52
53 #define LABELWIDTH 64
54 #define INTERWIDGETSPACE 16
55 #define WIDGETHEIGHT 32
56 #define NO_KEY -1
57
58 struct CvWindow;
59
60 typedef struct CvTrackbar
61 {
62 int signature;
63
64 ControlRef trackbar;
65 ControlRef label;
66
67 char* name;
68 CvTrackbar* next;
69 CvWindow* parent;
70 int* data;
71 int pos;
72 int maxval;
73 int labelSize;//Yannick Verdie
74 CvTrackbarCallback notify;
75 CvTrackbarCallback2 notify2;
76 void* userdata;
77 }
78 CvTrackbar;
79
80
81 typedef struct CvWindow
82 {
83 int signature;
84
85 char* name;
86 CvWindow* prev;
87 CvWindow* next;
88
89 WindowRef window;
90 WindowRef oldwindow;//YV
91 CGImageRef imageRef;
92 int imageWidth;//FD
93 int imageHeight;//FD
94
95 CvMat* image;
96 CvMat* dst_image;
97 int converted;
98 int last_key;
99 int flags;
100 int status;//YV
101 Ptr restoreState;//YV
102
103 CvMouseCallback on_mouse;
104 void* on_mouse_param;
105
106 struct {
107 int pos;
108 int rows;
109 CvTrackbar* first;
110 }
111 toolbar;
112 int trackbarheight;
113 }
114 CvWindow;
115
116 static CvWindow* hg_windows = 0;
117
118 #define Assert(exp) \
119 if( !(exp) ) \
120 { \
121 printf("Assertion: %s %s: %d\n", #exp, __FILE__, __LINE__);\
122 assert(exp); \
123 }
124
125 static int wasInitialized = 0;
126 static char lastKey = NO_KEY;
127 OSStatus keyHandler(EventHandlerCallRef hcr, EventRef theEvent, void* inUserData);
128 static pascal OSStatus windowEventHandler(EventHandlerCallRef nextHandler, EventRef theEvent, void *inUserData);
129
130 static const EventTypeSpec applicationKeyboardEvents[] =
131 {
132 { kEventClassKeyboard, kEventRawKeyDown },
133 };
134
cvInitSystem(int argc,char ** argv)135 CV_IMPL int cvInitSystem( int argc, char** argv )
136 {
137 OSErr err = noErr;
138 if( !wasInitialized )
139 {
140
141 hg_windows = 0;
142 err = InstallApplicationEventHandler(NewEventHandlerUPP( keyHandler),GetEventTypeCount(applicationKeyboardEvents),applicationKeyboardEvents,NULL,NULL);
143 if (err != noErr)
144 {
145 fprintf(stderr,"InstallApplicationEventHandler was not ok\n");
146 }
147 wasInitialized = 1;
148 }
149 setlocale(LC_NUMERIC,"C");
150
151 return 0;
152 }
153
154 // TODO: implement missing functionality
cvStartWindowThread()155 CV_IMPL int cvStartWindowThread()
156 {
157 return 0;
158 }
159
icvCountTrackbarInWindow(const CvWindow * window)160 static int icvCountTrackbarInWindow( const CvWindow* window)
161 {
162 CvTrackbar* trackbar = window->toolbar.first;
163 int count = 0;
164 while (trackbar != 0) {
165 count++;
166 trackbar = trackbar->next;
167 }
168 return count;
169 }
170
icvTrackbarByHandle(void * handle)171 static CvTrackbar* icvTrackbarByHandle( void * handle )
172 {
173 CvWindow* window = hg_windows;
174 CvTrackbar* trackbar = NULL;
175 while( window != 0 && window->window != handle) {
176 trackbar = window->toolbar.first;
177 while (trackbar != 0 && trackbar->trackbar != handle)
178 trackbar = trackbar->next;
179 if (trackbar != 0 && trackbar->trackbar == handle)
180 break;
181 window = window->next;
182 }
183 return trackbar;
184 }
185
icvWindowByHandle(void * handle)186 static CvWindow* icvWindowByHandle( void * handle )
187 {
188 CvWindow* window = hg_windows;
189
190 while( window != 0 && window->window != handle)
191 window = window->next;
192
193 return window;
194 }
195
icvFindWindowByName(const char * name)196 CV_IMPL CvWindow * icvFindWindowByName( const char* name)
197 {
198 CvWindow* window = hg_windows;
199 while( window != 0 && strcmp(name, window->name) != 0 )
200 window = window->next;
201
202 return window;
203 }
204
icvFindTrackbarByName(const CvWindow * window,const char * name)205 static CvTrackbar* icvFindTrackbarByName( const CvWindow* window, const char* name )
206 {
207 CvTrackbar* trackbar = window->toolbar.first;
208
209 while (trackbar != 0 && strcmp( trackbar->name, name ) != 0)
210 trackbar = trackbar->next;
211
212 return trackbar;
213 }
214
215 //FD
216 /* draw image to frame */
icvDrawImage(CvWindow * window)217 static void icvDrawImage( CvWindow* window )
218 {
219 Assert( window != 0 );
220 if( window->imageRef == 0 ) return;
221
222 CGContextRef myContext;
223 CGRect rect;
224 Rect portrect;
225 int width = window->imageWidth;
226 int height = window->imageHeight;
227
228 GetWindowPortBounds(window->window, &portrect);
229
230 if(!( window->flags & CV_WINDOW_AUTOSIZE) ) //YV
231 {
232 CGPoint origin = {0,0};
233 CGSize size = {portrect.right-portrect.left, portrect.bottom-portrect.top-window->trackbarheight};
234 rect.origin = origin; rect.size = size;
235 }
236 else
237 {
238 CGPoint origin = {0, portrect.bottom - height - window->trackbarheight};
239 CGSize size = {width, height};
240 rect.origin = origin; rect.size = size;
241 }
242
243 /* To be sybnchronous we are using this, better would be to susbcribe to the draw event and process whenever requested, we might save SOME CPU cycles*/
244 SetPortWindowPort (window->window);
245 QDBeginCGContext (GetWindowPort (window->window), &myContext);
246 CGContextSetInterpolationQuality (myContext, kCGInterpolationLow);
247 CGContextDrawImage(myContext,rect,window->imageRef);
248 CGContextFlush(myContext);// 4
249 QDEndCGContext (GetWindowPort(window->window), &myContext);// 5
250 }
251
252 //FD
253 /* update imageRef */
icvPutImage(CvWindow * window)254 static void icvPutImage( CvWindow* window )
255 {
256 Assert( window != 0 );
257 if( window->image == 0 ) return;
258
259 CGColorSpaceRef colorspace = NULL;
260 CGDataProviderRef provider = NULL;
261 int width = window->imageWidth = window->image->cols;
262 int height = window->imageHeight = window->image->rows;
263
264 colorspace = CGColorSpaceCreateDeviceRGB();
265
266 int size = 8;
267 int nbChannels = 3;
268
269 provider = CGDataProviderCreateWithData(NULL, window->image->data.ptr, width * height , NULL );
270
271 if (window->imageRef != NULL){
272 CGImageRelease(window->imageRef);
273 window->imageRef = NULL;
274 }
275
276 window->imageRef = CGImageCreate( width, height, size , size*nbChannels , window->image->step, colorspace, kCGImageAlphaNone , provider, NULL, true, kCGRenderingIntentDefault );
277 icvDrawImage( window );
278
279 /* release the provider's memory */
280 CGDataProviderRelease( provider );
281 }
282
icvUpdateWindowSize(const CvWindow * window)283 static void icvUpdateWindowSize( const CvWindow* window )
284 {
285 int width = 0, height = 240; /* init à al taille de base de l'image*/
286 Rect globalBounds;
287
288 GetWindowBounds(window->window, kWindowContentRgn, &globalBounds);
289
290 int minWidth = 320;
291
292 if( window->image ) {
293 width = MAX(MAX(window->image->width, width), minWidth);
294 height = window->image->height;
295 } else
296 width = minWidth;
297
298 height += window->trackbarheight;
299
300 //height +=WIDGETHEIGHT; /* 32 pixels are spearating tracbars from the video display */
301
302 globalBounds.right = globalBounds.left + width;
303 globalBounds.bottom = globalBounds.top + height;
304 SetWindowBounds(window->window, kWindowContentRgn, &globalBounds);
305 }
306
icvDeleteWindow(CvWindow * window)307 static void icvDeleteWindow( CvWindow* window )
308 {
309 CvTrackbar* trackbar;
310
311 if( window->prev )
312 window->prev->next = window->next;
313 else
314 hg_windows = window->next;
315
316 if( window->next )
317 window->next->prev = window->prev;
318
319 window->prev = window->next = 0;
320
321 cvReleaseMat( &window->image );
322 cvReleaseMat( &window->dst_image );
323
324 for( trackbar = window->toolbar.first; trackbar != 0; )
325 {
326 CvTrackbar* next = trackbar->next;
327 cvFree( (void**)&trackbar );
328 trackbar = next;
329 }
330
331 if (window->imageRef != NULL)
332 CGImageRelease(window->imageRef);
333
334 DisposeWindow (window->window);//YV
335
336 cvFree( (void**)&window );
337 }
338
339
cvDestroyWindow(const char * name)340 CV_IMPL void cvDestroyWindow( const char* name)
341 {
342 CV_FUNCNAME( "cvDestroyWindow" );
343
344 __BEGIN__;
345
346 CvWindow* window;
347
348 if(!name)
349 CV_ERROR( CV_StsNullPtr, "NULL name string" );
350
351 window = icvFindWindowByName( name );
352 if( !window )
353 EXIT;
354
355 icvDeleteWindow( window );
356
357 __END__;
358 }
359
360
cvDestroyAllWindows(void)361 CV_IMPL void cvDestroyAllWindows( void )
362 {
363 while( hg_windows )
364 {
365 CvWindow* window = hg_windows;
366 icvDeleteWindow( window );
367 }
368 }
369
370
cvShowImage(const char * name,const CvArr * arr)371 CV_IMPL void cvShowImage( const char* name, const CvArr* arr)
372 {
373 CV_FUNCNAME( "cvShowImage" );
374
375 __BEGIN__;
376
377 CvWindow* window;
378 int origin = 0;
379 int resize = 0;
380 CvMat stub, *image;
381
382 if( !name )
383 CV_ERROR( CV_StsNullPtr, "NULL name" );
384
385 window = icvFindWindowByName(name);
386 if(!window)
387 {
388 cvNamedWindow(name, 1);
389 window = icvFindWindowByName(name);
390 }
391
392 if( !window || !arr )
393 EXIT; // keep silence here.
394
395 if( CV_IS_IMAGE_HDR( arr ))
396 origin = ((IplImage*)arr)->origin;
397
398 CV_CALL( image = cvGetMat( arr, &stub ));
399
400 /*
401 if( !window->image )
402 cvResizeWindow( name, image->cols, image->rows );
403 */
404
405 if( window->image &&
406 !CV_ARE_SIZES_EQ(window->image, image) ) {
407 if ( ! (window->flags & CV_WINDOW_AUTOSIZE) )//FD
408 resize = 1;
409 cvReleaseMat( &window->image );
410 }
411
412 if( !window->image ) {
413 resize = 1;//FD
414 window->image = cvCreateMat( image->rows, image->cols, CV_8UC3 );
415 }
416
417 cvConvertImage( image, window->image, (origin != 0 ? CV_CVTIMG_FLIP : 0) + CV_CVTIMG_SWAP_RB );
418 icvPutImage( window );
419 if ( resize )//FD
420 icvUpdateWindowSize( window );
421
422 __END__;
423 }
424
cvResizeWindow(const char * name,int width,int height)425 CV_IMPL void cvResizeWindow( const char* name, int width, int height)
426 {
427 CV_FUNCNAME( "cvResizeWindow" );
428
429 __BEGIN__;
430
431 CvWindow* window;
432 //CvTrackbar* trackbar;
433
434 if( !name )
435 CV_ERROR( CV_StsNullPtr, "NULL name" );
436
437 window = icvFindWindowByName(name);
438 if(!window)
439 EXIT;
440
441 SizeWindow(window->window, width, height, true);
442
443 __END__;
444 }
445
cvMoveWindow(const char * name,int x,int y)446 CV_IMPL void cvMoveWindow( const char* name, int x, int y)
447 {
448 CV_FUNCNAME( "cvMoveWindow" );
449
450 __BEGIN__;
451
452 CvWindow* window;
453 //CvTrackbar* trackbar;
454
455 if( !name )
456 CV_ERROR( CV_StsNullPtr, "NULL name" );
457
458 window = icvFindWindowByName(name);
459 if(!window)
460 EXIT;
461
462 MoveWindow(window->window, x, y, true);
463
464 __END__;
465 }
466
TrackbarActionProcPtr(ControlRef theControl,ControlPartCode partCode)467 void TrackbarActionProcPtr (ControlRef theControl, ControlPartCode partCode)
468 {
469 CvTrackbar * trackbar = icvTrackbarByHandle (theControl);
470
471 if (trackbar == NULL)
472 {
473 fprintf(stderr,"Error getting trackbar\n");
474 return;
475 }
476 else
477 {
478 int pos = GetControl32BitValue (theControl);
479 if ( trackbar->data )
480 *trackbar->data = pos;
481 if ( trackbar->notify )
482 trackbar->notify(pos);
483 else if ( trackbar->notify2 )
484 trackbar->notify2(pos, trackbar->userdata);
485
486 //--------YV---------------------------
487 CFStringEncoding encoding = kCFStringEncodingASCII;
488 CFAllocatorRef alloc_default = kCFAllocatorDefault; // = NULL;
489
490 char valueinchar[20];
491 sprintf(valueinchar, " (%d)", *trackbar->data);
492
493 // create an empty CFMutableString
494 CFIndex maxLength = 256;
495 CFMutableStringRef cfstring = CFStringCreateMutable(alloc_default,maxLength);
496
497 // append some c strings into it.
498 CFStringAppendCString(cfstring,trackbar->name,encoding);
499 CFStringAppendCString(cfstring,valueinchar,encoding);
500
501 SetControlData(trackbar->label, kControlEntireControl,kControlStaticTextCFStringTag, sizeof(cfstring), &cfstring);
502 DrawControls(trackbar->parent->window);
503 //-----------------------------------------
504 }
505 }
506
507
icvCreateTrackbar(const char * trackbar_name,const char * window_name,int * val,int count,CvTrackbarCallback on_notify,CvTrackbarCallback2 on_notify2,void * userdata)508 static int icvCreateTrackbar (const char* trackbar_name,
509 const char* window_name,
510 int* val, int count,
511 CvTrackbarCallback on_notify,
512 CvTrackbarCallback2 on_notify2,
513 void* userdata)
514 {
515 int result = 0;
516
517 CV_FUNCNAME( "icvCreateTrackbar" );
518 __BEGIN__;
519
520 /*char slider_name[32];*/
521 CvWindow* window = 0;
522 CvTrackbar* trackbar = 0;
523 Rect stboundsRect;
524 ControlRef outControl;
525 ControlRef stoutControl;
526 Rect bounds;
527
528 if( !window_name || !trackbar_name )
529 CV_ERROR( CV_StsNullPtr, "NULL window or trackbar name" );
530
531 if( count <= 0 )
532 CV_ERROR( CV_StsOutOfRange, "Bad trackbar maximal value" );
533
534 window = icvFindWindowByName(window_name);
535 if( !window )
536 EXIT;
537
538 trackbar = icvFindTrackbarByName(window,trackbar_name);
539 if( !trackbar )
540 {
541 int len = strlen(trackbar_name);
542 trackbar = (CvTrackbar*)cvAlloc(sizeof(CvTrackbar) + len + 1);
543 memset( trackbar, 0, sizeof(*trackbar));
544 trackbar->signature = CV_TRACKBAR_MAGIC_VAL;
545 trackbar->name = (char*)(trackbar+1);
546 memcpy( trackbar->name, trackbar_name, len + 1 );
547 trackbar->parent = window;
548 trackbar->next = window->toolbar.first;
549 window->toolbar.first = trackbar;
550
551 if( val )
552 {
553 int value = *val;
554 if( value < 0 )
555 value = 0;
556 if( value > count )
557 value = count;
558 trackbar->pos = value;
559 trackbar->data = val;
560 }
561
562 trackbar->maxval = count;
563
564 //----------- YV ----------------------
565 //get nb of digits
566 int nbDigit = 0;
567 while((count/=10)>10){
568 nbDigit++;
569 }
570
571 //pad size maxvalue in pixel
572 Point qdSize;
573 char valueinchar[strlen(trackbar_name)+1 +1 +1+nbDigit+1];//length+\n +space +(+nbDigit+)
574 sprintf(valueinchar, "%s (%d)",trackbar_name, trackbar->maxval);
575 SInt16 baseline;
576 CFStringRef text = CFStringCreateWithCString(NULL,valueinchar,kCFStringEncodingASCII);
577 GetThemeTextDimensions( text, kThemeCurrentPortFont, kThemeStateActive, false, &qdSize, &baseline );
578 trackbar->labelSize = qdSize.h;
579 //--------------------------------------
580
581 int c = icvCountTrackbarInWindow(window);
582
583 GetWindowBounds(window->window,kWindowContentRgn,&bounds);
584
585 stboundsRect.top = (INTERWIDGETSPACE +WIDGETHEIGHT)* (c-1)+INTERWIDGETSPACE;
586 stboundsRect.left = INTERWIDGETSPACE;
587 stboundsRect.bottom = stboundsRect.top + WIDGETHEIGHT;
588 stboundsRect.right = stboundsRect.left+LABELWIDTH;
589
590 //fprintf(stdout,"create trackabar bounds (%d %d %d %d)\n",stboundsRect.top,stboundsRect.left,stboundsRect.bottom,stboundsRect.right);
591 //----------- YV ----------------------
592 sprintf(valueinchar, "%s (%d)",trackbar_name, trackbar->pos);
593 CreateStaticTextControl (window->window,&stboundsRect,CFStringCreateWithCString(NULL,valueinchar,kCFStringEncodingASCII),NULL,&stoutControl);
594 //--------------------------------------
595
596 stboundsRect.top = (INTERWIDGETSPACE +WIDGETHEIGHT)* (c-1)+INTERWIDGETSPACE;
597 stboundsRect.left = INTERWIDGETSPACE*2+LABELWIDTH;
598 stboundsRect.bottom = stboundsRect.top + WIDGETHEIGHT;
599 stboundsRect.right = bounds.right-INTERWIDGETSPACE;
600
601 CreateSliderControl (window->window,&stboundsRect, trackbar->pos,0,trackbar->maxval,kControlSliderLiveFeedback,0,true,NewControlActionUPP(TrackbarActionProcPtr),&outControl);
602
603 bounds.bottom += INTERWIDGETSPACE + WIDGETHEIGHT;
604 SetControlVisibility (outControl,true,true);
605 SetControlVisibility (stoutControl,true,true);
606
607 trackbar->trackbar = outControl;
608 trackbar->label = stoutControl;
609 if (c == 1)
610 window->trackbarheight = INTERWIDGETSPACE*2 + WIDGETHEIGHT;
611 else
612 window->trackbarheight += INTERWIDGETSPACE + WIDGETHEIGHT;
613 icvUpdateWindowSize( window );
614 }
615
616 trackbar->notify = on_notify;
617 trackbar->notify2 = on_notify2;
618 trackbar->userdata = userdata;
619
620 result = 1;
621
622 __END__;
623 return result;
624 }
625
626
cvCreateTrackbar(const char * trackbar_name,const char * window_name,int * val,int count,CvTrackbarCallback on_notify)627 CV_IMPL int cvCreateTrackbar (const char* trackbar_name,
628 const char* window_name,
629 int* val, int count,
630 CvTrackbarCallback on_notify)
631 {
632 return icvCreateTrackbar(trackbar_name, window_name, val, count, on_notify, 0, 0);
633 }
634
635
cvCreateTrackbar2(const char * trackbar_name,const char * window_name,int * val,int count,CvTrackbarCallback2 on_notify2,void * userdata)636 CV_IMPL int cvCreateTrackbar2(const char* trackbar_name,
637 const char* window_name,
638 int* val, int count,
639 CvTrackbarCallback2 on_notify2,
640 void* userdata)
641 {
642 return icvCreateTrackbar(trackbar_name, window_name, val,
643 count, 0, on_notify2, userdata);
644 }
645
646
647 CV_IMPL void
cvSetMouseCallback(const char * name,CvMouseCallback function,void * info)648 cvSetMouseCallback( const char* name, CvMouseCallback function, void* info)
649 {
650 CvWindow* window = icvFindWindowByName( name );
651 if (window != NULL)
652 {
653 window->on_mouse = function;
654 window->on_mouse_param = info;
655 }
656 else
657 {
658 fprintf(stdout,"Error with cvSetMouseCallback. Window not found : %s\n",name);
659 }
660 }
661
cvGetTrackbarPos(const char * trackbar_name,const char * window_name)662 CV_IMPL int cvGetTrackbarPos( const char* trackbar_name, const char* window_name )
663 {
664 int pos = -1;
665
666 CV_FUNCNAME( "cvGetTrackbarPos" );
667
668 __BEGIN__;
669
670 CvWindow* window;
671 CvTrackbar* trackbar = 0;
672
673 if( trackbar_name == 0 || window_name == 0 )
674 CV_ERROR( CV_StsNullPtr, "NULL trackbar or window name" );
675
676 window = icvFindWindowByName( window_name );
677 if( window )
678 trackbar = icvFindTrackbarByName( window, trackbar_name );
679
680 if( trackbar )
681 pos = trackbar->pos;
682
683 __END__;
684
685 return pos;
686 }
687
cvSetTrackbarPos(const char * trackbar_name,const char * window_name,int pos)688 CV_IMPL void cvSetTrackbarPos(const char* trackbar_name, const char* window_name, int pos)
689 {
690 CV_FUNCNAME( "cvSetTrackbarPos" );
691
692 __BEGIN__;
693
694 CvWindow* window;
695 CvTrackbar* trackbar = 0;
696
697 if( trackbar_name == 0 || window_name == 0 )
698 CV_ERROR( CV_StsNullPtr, "NULL trackbar or window name" );
699
700 window = icvFindWindowByName( window_name );
701 if( window )
702 trackbar = icvFindTrackbarByName( window, trackbar_name );
703
704 if( trackbar )
705 {
706 if( pos < 0 )
707 pos = 0;
708
709 if( pos > trackbar->maxval )
710 pos = trackbar->maxval;
711
712 // Set new value and redraw the trackbar
713 SetControlValue( trackbar->trackbar, pos );
714 Draw1Control( trackbar->trackbar );
715 }
716
717 __END__;
718 return ;
719 }
720
cvGetWindowHandle(const char * name)721 CV_IMPL void* cvGetWindowHandle( const char* name )
722 {
723 WindowRef result = 0;
724
725 __BEGIN__;
726
727 CvWindow* window;
728 window = icvFindWindowByName( name );
729 if (window != NULL)
730 result = window->window;
731 else
732 result = NULL;
733
734 __END__;
735
736 return result;
737 }
738
739
cvGetWindowName(void * window_handle)740 CV_IMPL const char* cvGetWindowName( void* window_handle )
741 {
742 const char* window_name = "";
743
744 CV_FUNCNAME( "cvGetWindowName" );
745
746 __BEGIN__;
747
748 CvWindow* window;
749
750 if( window_handle == 0 )
751 CV_ERROR( CV_StsNullPtr, "NULL window" );
752 window = icvWindowByHandle(window_handle );
753 if( window )
754 window_name = window->name;
755
756 __END__;
757
758 return window_name;
759 }
760
cvGetModeWindow_CARBON(const char * name)761 double cvGetModeWindow_CARBON(const char* name)//YV
762 {
763 double result = -1;
764
765 CV_FUNCNAME( "cvGetModeWindow_QT" );
766
767 __BEGIN__;
768
769 CvWindow* window;
770
771 if(!name)
772 CV_ERROR( CV_StsNullPtr, "NULL name string" );
773
774 window = icvFindWindowByName( name );
775 if( !window )
776 CV_ERROR( CV_StsNullPtr, "NULL window" );
777
778 result = window->status;
779
780 __END__;
781 return result;
782 }
783
cvSetModeWindow_CARBON(const char * name,double prop_value)784 void cvSetModeWindow_CARBON( const char* name, double prop_value)//Yannick Verdie
785 {
786 OSStatus err = noErr;
787
788
789 CV_FUNCNAME( "cvSetModeWindow_QT" );
790
791 __BEGIN__;
792
793 CvWindow* window;
794
795 if(!name)
796 CV_ERROR( CV_StsNullPtr, "NULL name string" );
797
798 window = icvFindWindowByName( name );
799 if( !window )
800 CV_ERROR( CV_StsNullPtr, "NULL window" );
801
802 if(window->flags & CV_WINDOW_AUTOSIZE)//if the flag CV_WINDOW_AUTOSIZE is set
803 EXIT;
804
805 if (window->status==CV_WINDOW_FULLSCREEN && prop_value==CV_WINDOW_NORMAL)
806 {
807 err = EndFullScreen(window->restoreState,0);
808 if (err != noErr)
809 fprintf(stdout,"Error EndFullScreen\n");
810 window->window = window->oldwindow;
811 ShowWindow( window->window );
812
813 window->status=CV_WINDOW_NORMAL;
814 EXIT;
815 }
816
817 if (window->status==CV_WINDOW_NORMAL && prop_value==CV_WINDOW_FULLSCREEN)
818 {
819 GDHandle device;
820 err = GetWindowGreatestAreaDevice(window->window, kWindowTitleBarRgn, &device, NULL);
821 if (err != noErr)
822 fprintf(stdout,"Error GetWindowGreatestAreaDevice\n");
823
824 HideWindow(window->window);
825 window->oldwindow = window->window;
826 err = BeginFullScreen(&(window->restoreState), device, 0, 0, &window->window, 0, fullScreenAllowEvents | fullScreenDontSwitchMonitorResolution);
827 if (err != noErr)
828 fprintf(stdout,"Error BeginFullScreen\n");
829
830 window->status=CV_WINDOW_FULLSCREEN;
831 EXIT;
832 }
833
834 __END__;
835 }
836
setWindowTitle(const String & winname,const String & title)837 void cv::setWindowTitle(const String& winname, const String& title)
838 {
839 CvWindow* window = icvFindWindowByName(winname.c_str());
840
841 if (!window)
842 {
843 namedWindow(winname);
844 window = icvFindWindowByName(winname.c_str());
845 }
846
847 if (!window)
848 CV_Error(Error::StsNullPtr, "NULL window");
849
850 if (noErr != SetWindowTitleWithCFString(window->window, CFStringCreateWithCString(NULL, title.c_str(), kCFStringEncodingASCII)))
851 CV_Error_(Error::StsError, ("Failed to set \"%s\" window title to \"%s\"", winname.c_str(), title.c_str()));
852 }
853
cvNamedWindow(const char * name,int flags)854 CV_IMPL int cvNamedWindow( const char* name, int flags )
855 {
856 int result = 0;
857 CV_FUNCNAME( "cvNamedWindow" );
858 if (!wasInitialized)
859 cvInitSystem(0, NULL);
860
861 // to be able to display a window, we need to be a 'faceful' application
862 // http://lists.apple.com/archives/carbon-dev/2005/Jun/msg01414.html
863 static bool switched_to_faceful = false;
864 if (! switched_to_faceful)
865 {
866 ProcessSerialNumber psn = { 0, kCurrentProcess };
867 OSStatus ret = TransformProcessType (&psn, kProcessTransformToForegroundApplication );
868
869 if (ret == noErr)
870 {
871 SetFrontProcess( &psn );
872 switched_to_faceful = true;
873 }
874 else
875 {
876 fprintf(stderr, "Failed to tranform process type: %d\n", (int) ret);
877 fflush (stderr);
878 }
879 }
880
881 __BEGIN__;
882
883 WindowRef outWindow = NULL;
884 OSStatus err = noErr;
885 Rect contentBounds = {100,100,320,440};
886
887 CvWindow* window;
888 UInt wAttributes = 0;
889
890 int len;
891
892 const EventTypeSpec genericWindowEventHandler[] = {
893 { kEventClassMouse, kEventMouseMoved},
894 { kEventClassMouse, kEventMouseDragged},
895 { kEventClassMouse, kEventMouseUp},
896 { kEventClassMouse, kEventMouseDown},
897 { kEventClassWindow, kEventWindowClose },
898 { kEventClassWindow, kEventWindowBoundsChanged }//FD
899 };
900
901 if( !name )
902 CV_ERROR( CV_StsNullPtr, "NULL name string" );
903
904 if( icvFindWindowByName( name ) != 0 ){
905 result = 1;
906 EXIT;
907 }
908 len = strlen(name);
909 CV_CALL( window = (CvWindow*)cvAlloc(sizeof(CvWindow) + len + 1));
910 memset( window, 0, sizeof(*window));
911 window->name = (char*)(window + 1);
912 memcpy( window->name, name, len + 1 );
913 window->flags = flags;
914 window->status = CV_WINDOW_NORMAL;//YV
915 window->signature = CV_WINDOW_MAGIC_VAL;
916 window->image = 0;
917 window->last_key = 0;
918 window->on_mouse = 0;
919 window->on_mouse_param = 0;
920
921 window->next = hg_windows;
922 window->prev = 0;
923 if( hg_windows )
924 hg_windows->prev = window;
925 hg_windows = window;
926 wAttributes = kWindowStandardDocumentAttributes | kWindowStandardHandlerAttribute | kWindowLiveResizeAttribute;
927
928
929 if (window->flags & CV_WINDOW_AUTOSIZE)//Yannick verdie, remove the handler at the bottom-right position of the window in AUTORESIZE mode
930 {
931 wAttributes = 0;
932 wAttributes = kWindowCloseBoxAttribute | kWindowFullZoomAttribute | kWindowCollapseBoxAttribute | kWindowStandardHandlerAttribute | kWindowLiveResizeAttribute;
933 }
934
935 err = CreateNewWindow ( kDocumentWindowClass,wAttributes,&contentBounds,&outWindow);
936 if (err != noErr)
937 fprintf(stderr,"Error while creating the window\n");
938
939 SetWindowTitleWithCFString(outWindow,CFStringCreateWithCString(NULL,name,kCFStringEncodingASCII));
940 if (err != noErr)
941 fprintf(stdout,"Error SetWindowTitleWithCFString\n");
942
943 window->window = outWindow;
944 window->oldwindow = 0;//YV
945
946 err = InstallWindowEventHandler(outWindow, NewEventHandlerUPP(windowEventHandler), GetEventTypeCount(genericWindowEventHandler), genericWindowEventHandler, outWindow, NULL);
947
948 ShowWindow( outWindow );
949 result = 1;
950
951 __END__;
952 return result;
953 }
954
windowEventHandler(EventHandlerCallRef nextHandler,EventRef theEvent,void * inUserData)955 static pascal OSStatus windowEventHandler(EventHandlerCallRef nextHandler, EventRef theEvent, void *inUserData)
956 {
957 CvWindow* window = NULL;
958 UInt32 eventKind, eventClass;
959 OSErr err = noErr;
960 int event = 0;
961 UInt32 count = 0;
962 HIPoint point = {0,0};
963 EventMouseButton eventMouseButton = 0;//FD
964 UInt32 modifiers;//FD
965
966 WindowRef theWindow = (WindowRef)inUserData;
967 if (theWindow == NULL)
968 return eventNotHandledErr;
969 window = icvWindowByHandle(theWindow);
970 if ( window == NULL)
971 return eventNotHandledErr;
972
973 eventKind = GetEventKind(theEvent);
974 eventClass = GetEventClass(theEvent);
975
976 switch (eventClass) {
977 case kEventClassMouse : {
978 switch (eventKind){
979 case kEventMouseUp :
980 case kEventMouseDown :
981 case kEventMouseMoved :
982 case kEventMouseDragged : {
983 err = CallNextEventHandler(nextHandler, theEvent);
984 if (err != eventNotHandledErr)
985 return err;
986 err = GetEventParameter(theEvent, kEventParamMouseButton, typeMouseButton, NULL, sizeof(eventMouseButton), NULL, &eventMouseButton);
987 err = GetEventParameter(theEvent, kEventParamKeyModifiers, typeUInt32, NULL, sizeof(modifiers), NULL, &modifiers);
988 err = GetEventParameter(theEvent,kEventParamClickCount,typeUInt32,NULL,sizeof(UInt32),NULL,&count);
989 if (err == noErr){
990 if (count >1) event += 6;
991 } else {
992 event = CV_EVENT_MOUSEMOVE;
993 }
994
995 if (eventKind == kEventMouseUp)
996 event +=4;
997 if (eventKind == kEventMouseDown)
998 event +=1;
999
1000 unsigned int flags = 0;
1001
1002 err = GetEventParameter(theEvent, kEventParamWindowMouseLocation, typeHIPoint, NULL, sizeof(point), NULL, &point);
1003 if (eventKind != kEventMouseMoved){
1004 switch(eventMouseButton){
1005 case kEventMouseButtonPrimary:
1006 if (modifiers & controlKey){
1007 flags += CV_EVENT_FLAG_RBUTTON;
1008 event += 1;
1009 } else {
1010 flags += CV_EVENT_FLAG_LBUTTON;
1011 }
1012 break;
1013 case kEventMouseButtonSecondary:
1014 flags += CV_EVENT_FLAG_RBUTTON;
1015 event += 1;
1016 break;
1017 case kEventMouseButtonTertiary:
1018 flags += CV_EVENT_FLAG_MBUTTON;
1019 event += 2;
1020 break;
1021 }
1022 }
1023
1024 if (modifiers&controlKey) flags += CV_EVENT_FLAG_CTRLKEY;
1025 if (modifiers&shiftKey) flags += CV_EVENT_FLAG_SHIFTKEY;
1026 if (modifiers& cmdKey ) flags += CV_EVENT_FLAG_ALTKEY;
1027
1028 if (window->on_mouse != NULL){
1029 int lx,ly;
1030 Rect structure, content;
1031 GetWindowBounds(theWindow, kWindowStructureRgn, &structure);
1032 GetWindowBounds(theWindow, kWindowContentRgn, &content);
1033 lx = (int)point.x - content.left + structure.left;
1034 ly = (int)point.y - window->trackbarheight - content.top + structure.top; /* minus la taille des trackbars */
1035 if (window->flags & CV_WINDOW_AUTOSIZE) {//FD
1036 //printf("was %d,%d\n", lx, ly);
1037 /* scale the mouse coordinates */
1038 lx = lx * window->imageWidth / (content.right - content.left);
1039 ly = ly * window->imageHeight / (content.bottom - content.top - window->trackbarheight);
1040 }
1041
1042 if (lx>0 && ly >0){ /* a remettre dans les coordonnées locale */
1043 window->on_mouse (event, lx, ly, flags, window->on_mouse_param);
1044 return noErr;
1045 }
1046 }
1047 }
1048 default : return eventNotHandledErr;
1049 }
1050 }
1051 case kEventClassWindow : {//FD
1052 switch (eventKind){
1053 case kEventWindowBoundsChanged :
1054 {
1055 /* resize the trackbars */
1056 CvTrackbar *t;
1057 Rect bounds;
1058 GetWindowBounds(window->window,kWindowContentRgn,&bounds);
1059 for ( t = window->toolbar.first; t != 0; t = t->next )
1060 SizeControl(t->trackbar,bounds.right - bounds.left - INTERWIDGETSPACE*3 - LABELWIDTH , WIDGETHEIGHT);
1061 }
1062 /* redraw the image */
1063 icvDrawImage(window);
1064 break;
1065 default :
1066 return eventNotHandledErr;
1067 }
1068 }
1069 default:
1070 return eventNotHandledErr;
1071 }
1072
1073 return eventNotHandledErr;
1074 }
1075
keyHandler(EventHandlerCallRef hcr,EventRef theEvent,void * inUserData)1076 OSStatus keyHandler(EventHandlerCallRef hcr, EventRef theEvent, void* inUserData)
1077 {
1078 UInt32 eventKind;
1079 UInt32 eventClass;
1080 OSErr err = noErr;
1081
1082 eventKind = GetEventKind (theEvent);
1083 eventClass = GetEventClass (theEvent);
1084 err = GetEventParameter(theEvent, kEventParamKeyMacCharCodes, typeChar, NULL, sizeof(lastKey), NULL, &lastKey);
1085 if (err != noErr)
1086 lastKey = NO_KEY;
1087
1088 return noErr;
1089 }
1090
cvWaitKey(int maxWait)1091 CV_IMPL int cvWaitKey (int maxWait)
1092 {
1093 EventRecord theEvent;
1094
1095 // wait at least for one event (to allow mouse, etc. processing), exit if maxWait milliseconds passed (nullEvent)
1096 UInt32 start = TickCount();
1097 int iters=0;
1098 do
1099 {
1100 // remaining time until maxWait is over
1101 UInt32 wait = EventTimeToTicks (maxWait / 1000.0) - (TickCount() - start);
1102 if ((int)wait <= 0)
1103 {
1104 if( maxWait > 0 && iters > 0 )
1105 break;
1106 wait = 1;
1107 }
1108 iters++;
1109 WaitNextEvent (everyEvent, &theEvent, maxWait > 0 ? wait : kDurationForever, NULL);
1110 }
1111 while (lastKey == NO_KEY && theEvent.what != nullEvent);
1112
1113 int key = lastKey;
1114 lastKey = NO_KEY;
1115 return key;
1116 }
1117
1118 /* End of file. */
1119