Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    primarykey
    data
    text
    <p>If it helps, here is my code for drawing rectangles on multiple sized video streams</p> <pre><code>#include "stdafx.h" #include "opencv2/imgproc/imgproc.hpp" #include "opencv2/highgui/highgui.hpp" #include &lt;stdlib.h&gt; #include &lt;stdio.h&gt; #include &lt;iostream&gt; #define SSTR( x ) dynamic_cast&lt; std::ostringstream &amp; &gt;(( std::ostringstream() &lt;&lt; std::dec &lt;&lt; x ) ).str() using namespace std; using namespace cv; Rect box; //global structures needed for drawing bool drawing_box = false; struct mousecallbackstruct{ Mat* src; Mat* overlay; string windowname; }; Mat srcoverlay,smallsrcoverlay; //an overlay must be created for each window you want to draw on void onMouse(int event, int x, int y, int flags, void* param) //it seems the only way to use this is by keeping different globals for different windows - meaning you have to set up all thise ahead of time, and keep track of it and not mix/match windows/frames!! horrible design here. { cout &lt;&lt; event; mousecallbackstruct mousestruct; mousestruct = *((mousecallbackstruct*)param); Mat* srcp = mousestruct.src; Mat* overlayp = mousestruct.overlay; // yeah, yeah, i use 7 lines where I could use 3, so sue me Mat src = *srcp; Mat overlay = *overlayp; if(!src.data){ cout &lt;&lt; "your void * cast didn't work :(\n"; return; } switch( event ){ case CV_EVENT_MOUSEMOVE: if( drawing_box ){ box.width = x-box.x; box.height = y-box.y; } break; case CV_EVENT_LBUTTONDOWN: //start drawing drawing_box = true; box = cvRect( x, y, 0, 0 ); break; case CV_EVENT_LBUTTONDBLCLK: //double click to clear drawing_box = false; overlay.setTo(cv::Scalar::all(0)); //clear it break; case CV_EVENT_LBUTTONUP: //draw what we created with Lbuttondown drawing_box = false; if( box.width &lt; 0 ){ box.x += box.width; box.width *= -1; } if( box.height &lt; 0 ){ box.y += box.height; box.height *= -1; } rectangle( overlay, Point(box.x, box.y), Point(box.x+box.width,box.y+box.height),CV_RGB(100,200,100),4); //draw rectangle. You can change this to line or circle or whatever. Maybe with the Right mouse button. break; } } void iimshow(mousecallbackstruct* mystructp){ //this is where we add the text/drawing created in the mouse handler to the actual image (since mouse handler events do not coincide with the drawing events) mousecallbackstruct mystruct = *mystructp; //custom struct made for the mouse callback - very handy for other functions too Mat overlay, src; Mat* srcp = mystruct.src; Mat* overlayp = mystruct.overlay; src = *srcp; // yeah, yeah, i use 9 lines where I could use 3, so sue me overlay = *overlayp; string name = mystruct.windowname; Mat added,imageROI; try{ //cout &lt;&lt; "tch:" &lt;&lt; overlay.rows &lt;&lt; "," &lt;&lt; src.rows &lt;&lt; ";" &lt;&lt; overlay.cols &lt;&lt; "," &lt;&lt; src.cols &lt;&lt; ";" &lt;&lt; src.channels() &lt;&lt; "," &lt;&lt; overlay.channels() &lt;&lt;"," &lt;&lt; src.type() &lt;&lt; "," &lt;&lt; overlay.type() &lt;&lt; "\n"; if(overlay.data &amp;&amp; overlay.rows == src.rows &amp;&amp; overlay.cols == src.cols &amp;&amp; overlay.channels() == src.channels()){ //basic error checking add(src,overlay,added); }else{ //try to resize it imageROI= overlay(Rect(0,0,src.cols,src.rows)); add(src,imageROI,added); } imshow(name,added);// the actual draw moment }catch(...){ //if resize didn't work then this should catch it and you can see what didn't match up cout &lt;&lt; "Error. Mismatch:" &lt;&lt; overlay.rows &lt;&lt; "," &lt;&lt; src.rows &lt;&lt; ";" &lt;&lt; overlay.cols &lt;&lt; "," &lt;&lt; src.cols &lt;&lt; ";" &lt;&lt; src.channels() &lt;&lt; "," &lt;&lt; overlay.channels() &lt;&lt;"," &lt;&lt; src.type() &lt;&lt; "," &lt;&lt; overlay.type() &lt;&lt; "\n"; imshow(name + "overlay",overlay); imshow(name+"source",src); } } int _tmain(int argc, _TCHAR* argv[]){ VideoCapture cap(0); // open the default camera if(!cap.isOpened()) { // check if we succeeded cout &lt;&lt; "NO camera found \n"; return -1; } Mat src,smallsrc,overlay; cap &gt;&gt; src; //grab 1 frame to build our preliminary Mats and overlays srcoverlay.create(src.rows,src.cols,src.type()); //create overlays smallsrcoverlay.create(src.rows,src.cols,src.type()); srcoverlay.setTo(cv::Scalar::all(0)); //clear it smallsrcoverlay.setTo(cv::Scalar::all(0)); //clear it namedWindow( "smallsrc", CV_WINDOW_AUTOSIZE ); namedWindow( "source", CV_WINDOW_AUTOSIZE ); //these must be created early for the setmousecallback, AND you have to know what Mats will be using them and not switch them around :( moveWindow("smallsrc",1000,100); //create a small original capture off to the side of screen ////////////// for each window/mat that uses a mouse handler, you must create one of these structures for it and pass it into the mouse handler, and add a global mat for overlays (at top of code) mousecallbackstruct srcmousestruct,smallsrcmousestruct; //these get passed into the mouse callback function. Hopefully they update their contents automatically for the callback? :( srcmousestruct.overlay = &amp;srcoverlay; //fill our custom struct srcmousestruct.src = &amp;src; srcmousestruct.windowname = "source"; smallsrcmousestruct.overlay = &amp;smallsrcoverlay; //the small window smallsrcmousestruct.src = &amp;smallsrc; smallsrcmousestruct.windowname = "smallsrc"; setMouseCallback(smallsrcmousestruct.windowname, onMouse, (void*)&amp;smallsrcmousestruct); //the actual 'set mouse callback' call setMouseCallback(srcmousestruct.windowname, onMouse, (void*)&amp;srcmousestruct); for(;;){ //main loop /// Load an image cap &gt;&gt; src; if( !src.data ) { return -1; } resize(src,smallsrc,Size(),.5,.5); //smaller scale window of original overlay = *srcmousestruct.overlay; src = *srcmousestruct.src; iimshow(&amp;srcmousestruct); //my imshow replacement. uses structs iimshow(&amp;smallsrcmousestruct); if(waitKey(30) == 27) cin.get(); //esc pauses } cin.get(); return 0; } </code></pre>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload