Drawing overlay rectangle using mouse

classic Classic list List threaded Threaded
5 messages Options
Reply | Threaded
Open this post in threaded view
|

Drawing overlay rectangle using mouse

Gaurav Sharma
Dear All,

In one of my application, i need to draw multiple overlay rectangles over staticbitmap inside a scrollwindow. Displaying image is done but i am stuck at this overlay rectangles. I need to draw these rectangles using mouse pointer. I have seen few sample as below -

def OnMouseMove(self, evt):
        if not self.HasCapture():
            return       
        rect = wx.RectPP(self.startPos, evt.GetPosition())
        # Draw the rubber-band rectangle using an overlay so it
        # will manage keeping the rectangle and the former window
        # contents separate.
        dc = wx.ScreenDC()
        odc = wx.DCOverlay(self.overlay, dc)
        odc.Clear()
           
        pen = wx.Pen("black", 2)
        brush = wx.Brush(wx.Colour(192,192,192,128))
        if "wxMac" in wx.PlatformInfo:
            dc.SetPen(pen)
            dc.SetBrush(brush)
            dc.DrawRectangleRect(rect)
        else:
            # use a GC on Windows (and GTK?)
            # this crashed on the Mac
            ctx = wx.GraphicsContext_Create(dc)
            ctx.SetPen(pen)
            ctx.SetBrush(brush)
            ctx.DrawRectangle(*rect)

        del odc # work around a bug in the Python wrappers to make
                # sure the odc is destroyed before the dc is.

that draw rectangle very fine but whenever the windows is moved or scrolled up or down those rectangles gets erased.
My objective is that these rectangles should stay (or if possible move using keys) on images as long as i am not changing the image or closing the window completely and finally i need to capture the coordinates as well that i know how to do. I am attaching the source code example that also i found over internet (thanks to the author).
Please help.
Thanks in advance.

Regards
Gaurav

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.

Overlaytest2.py (3K) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: Drawing overlay rectangle using mouse

Matt Newville
Gaurav,

On Fri, Mar 3, 2017 at 3:30 AM, Gaurav Sharma <[hidden email]> wrote:
Dear All,

In one of my application, i need to draw multiple overlay rectangles over staticbitmap inside a scrollwindow. Displaying image is done but i am stuck at this overlay rectangles. I need to draw these rectangles using mouse pointer. I have seen few sample as below -

def OnMouseMove(self, evt):
        if not self.HasCapture():
            return       
        rect = wx.RectPP(self.startPos, evt.GetPosition())
        # Draw the rubber-band rectangle using an overlay so it
        # will manage keeping the rectangle and the former window
        # contents separate.
        dc = wx.ScreenDC()
        odc = wx.DCOverlay(self.overlay, dc)
        odc.Clear()
           
        pen = wx.Pen("black", 2)
        brush = wx.Brush(wx.Colour(192,192,192,128))
        if "wxMac" in wx.PlatformInfo:
            dc.SetPen(pen)
            dc.SetBrush(brush)
            dc.DrawRectangleRect(rect)
        else:
            # use a GC on Windows (and GTK?)
            # this crashed on the Mac
            ctx = wx.GraphicsContext_Create(dc)
            ctx.SetPen(pen)
            ctx.SetBrush(brush)
            ctx.DrawRectangle(*rect)

        del odc # work around a bug in the Python wrappers to make
                # sure the odc is destroyed before the dc is.

that draw rectangle very fine but whenever the windows is moved or scrolled up or down those rectangles gets erased.
My objective is that these rectangles should stay (or if possible move using keys) on images as long as i am not changing the image or closing the window completely and finally i need to capture the coordinates as well that i know how to do. I am attaching the source code example that also i found over internet (thanks to the author).
Please help.
Thanks in advance.

I believe you need to bind a function to wx.EVT_PAINT and have that function redraw the entire panel, including the static bitmap and the overlays (say from saved coordinates for the rubber-band box drawn by the user).  I think you'd probably also want to bind wx.EVT_SIZE to function that eventually calls self.Refresh(), which will generate a "needs repainting" event.

FWIW, when I do such things (taking a bitmap from a live camera source, and drawing that plus user-defined overlays), I do this in the Panel.onPaint method of a wx.Panel, which has been bound the wx.EVT_PAINT, roughly as:

    dc = wx.AutoBufferedPaintDC(self)
    dc.Clear()
    dc.DrawBitmap(bitmap, pad_width, pad_height, useMask=True)
    dc.SetBrush(wx.Brush('Black', wx.BRUSHSTYLE_TRANSPARENT))
    dc.SetPen(rect_color, 1.0, wx.SOLID))
    dc.DrawRectangle(*rect_coords)

I know that's not complete, but I think you have the dc drawing stuff understood.  Using AutoBufferedPaintDC gives pretty good, flicker-free drawing.
   
Hope that helps,

--Matt

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: Drawing overlay rectangle using mouse

Chris Barker - NOAA Federal
A few notes:

        if "wxMac" in wx.PlatformInfo:
            dc.SetPen(pen)
            dc.SetBrush(brush)
            dc.DrawRectangleRect(rect)
        else:
            # use a GC on Windows (and GTK?)
            # this crashed on the Mac
            ctx = wx.GraphicsContext_Create(dc)
            ctx.SetPen(pen)
            ctx.SetBrush(brush)
            ctx.DrawRectangle(*rect)

I'd just use a DC everywhere, then -- this use case doesn't make use of the GCs advantages, anyway.

that draw rectangle very fine but whenever the windows is moved or scrolled up or down those rectangles gets erased.

scrolling is an issue -- what coordinates do you want teh overlay to be in? i.e., should it scroll with the contents? IF so, I think you may not be able to do that with an overlay.
 
I believe you need to bind a function to wx.EVT_PAINT and have that function redraw the entire panel, including the static bitmap and the overlays (say from saved coordinates for the rubber-band box drawn by the user). 

whic pretty much defeats the whole point of an overlay -- if you meed to mange drawing it, you might as well simply draw the rect normally.

That being said, I so recall al ot of frustration with Overlays not really doing what I think they should :-)

You may want to take a look at these examples:

I haven't tested them for ages, but maybe there is something useful there?


there are a couple Overlay examples in there.

And a bunch of other useful drawing code.

-CHB


 
I think you'd probably also want to bind wx.EVT_SIZE to function that eventually calls self.Refresh(), which will generate a "needs repainting" event.

FWIW, when I do such things (taking a bitmap from a live camera source, and drawing that plus user-defined overlays), I do this in the Panel.onPaint method of a wx.Panel, which has been bound the wx.EVT_PAINT, roughly as:

    dc = wx.AutoBufferedPaintDC(self)
    dc.Clear()
    dc.DrawBitmap(bitmap, pad_width, pad_height, useMask=True)
    dc.SetBrush(wx.Brush('Black', wx.BRUSHSTYLE_TRANSPARENT))
    dc.SetPen(rect_color, 1.0, wx.SOLID))
    dc.DrawRectangle(*rect_coords)

I know that's not complete, but I think you have the dc drawing stuff understood.  Using AutoBufferedPaintDC gives pretty good, flicker-free drawing.
   
Hope that helps,

--Matt

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.



--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

[hidden email]

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: Drawing overlay rectangle using mouse

Gaurav Sharma
Hello Chris,

First of all thanks for your reply and all others.

I have tried many things from replies of your and many other users but no success. I would explain what i want to do -
I have a bitmap image inside a scrolled window. Now i need a feature to draw a one or more rectangle over the image. These rectangles must not change the original image and just stay over image temporarily as long as i don't close the app. I don't want to get them erased by scrolling action. i should be able to move them over image using mouse. Behind the scene i would be recording the coordinates of rectangles in some file. I am not sure if i need overlay or not. I am not well versed in wxpython now as i am a beginner.
If you can suggest some way then it would be great help.

Thanks
-Gaurav



On Saturday, 4 March 2017 03:04:28 UTC+5:30, Chris Barker wrote:
A few notes:

        if "wxMac" in wx.PlatformInfo:
            dc.SetPen(pen)
            dc.SetBrush(brush)
            dc.DrawRectangleRect(rect)
        else:
            # use a GC on Windows (and GTK?)
            # this crashed on the Mac
            ctx = wx.GraphicsContext_Create(dc)
            ctx.SetPen(pen)
            ctx.SetBrush(brush)
            ctx.DrawRectangle(*rect)

I'd just use a DC everywhere, then -- this use case doesn't make use of the GCs advantages, anyway.

that draw rectangle very fine but whenever the windows is moved or scrolled up or down those rectangles gets erased.

scrolling is an issue -- what coordinates do you want teh overlay to be in? i.e., should it scroll with the contents? IF so, I think you may not be able to do that with an overlay.
 
I believe you need to bind a function to wx.EVT_PAINT and have that function redraw the entire panel, including the static bitmap and the overlays (say from saved coordinates for the rubber-band box drawn by the user). 

whic pretty much defeats the whole point of an overlay -- if you meed to mange drawing it, you might as well simply draw the rect normally.

That being said, I so recall al ot of frustration with Overlays not really doing what I think they should :-)

You may want to take a look at these examples:

I haven't tested them for ages, but maybe there is something useful there?

<a href="https://github.com/PythonCHB/wxPythonDemos" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fgithub.com%2FPythonCHB%2FwxPythonDemos\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNG_UmoRVNR-9jZ_tTRs7pU3D4OL7g&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fgithub.com%2FPythonCHB%2FwxPythonDemos\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNG_UmoRVNR-9jZ_tTRs7pU3D4OL7g&#39;;return true;">https://github.com/PythonCHB/wxPythonDemos

there are a couple Overlay examples in there.

And a bunch of other useful drawing code.

-CHB


 
I think you'd probably also want to bind wx.EVT_SIZE to function that eventually calls self.Refresh(), which will generate a "needs repainting" event.

FWIW, when I do such things (taking a bitmap from a live camera source, and drawing that plus user-defined overlays), I do this in the Panel.onPaint method of a wx.Panel, which has been bound the wx.EVT_PAINT, roughly as:

    dc = wx.AutoBufferedPaintDC(self)
    dc.Clear()
    dc.DrawBitmap(bitmap, pad_width, pad_height, useMask=True)
    dc.SetBrush(wx.Brush('Black', wx.BRUSHSTYLE_TRANSPARENT))
    dc.SetPen(rect_color, 1.0, wx.SOLID))
    dc.DrawRectangle(*rect_coords)

I know that's not complete, but I think you have the dc drawing stuff understood.  Using AutoBufferedPaintDC gives pretty good, flicker-free drawing.
   
Hope that helps,

--Matt

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="MBIywrfeAwAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">wxpython-user...@googlegroups.com.
For more options, visit <a href="https://groups.google.com/d/optout" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;">https://groups.google.com/d/optout.



--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

<a href="javascript:" target="_blank" gdf-obfuscated-mailto="MBIywrfeAwAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">Chris....@...

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: Drawing overlay rectangle using mouse

Chris Barker - NOAA Federal


On Wed, Mar 15, 2017 at 2:01 AM, Gaurav Sharma <[hidden email]> wrote:
I have a bitmap image inside a scrolled window. Now i need a feature to draw a one or more rectangle over the image. These rectangles must not change the original image and just stay over image temporarily as long as i don't close the app. I don't want to get them erased by scrolling action.

If you want them to stay in the same "virtual position", then try the enclosed.

(you'll need to edit the file to point to an image file of your own...)

This code can be found here also:


along with a bunch of other demos

In this case, it's a single hard-coded rectangle -- I'll leave it as an exercise for the reader to add code to update the position of the  rectangle...

This is the simple, no-overlay way to do it.

-CHB

 
i should be able to move them over image using mouse. Behind the scene i would be recording the coordinates of rectangles in some file. I am not sure if i need overlay or not. I am not well versed in wxpython now as i am a beginner.
If you can suggest some way then it would be great help.

Thanks
-Gaurav




On Saturday, 4 March 2017 03:04:28 UTC+5:30, Chris Barker wrote:
A few notes:

        if "wxMac" in wx.PlatformInfo:
            dc.SetPen(pen)
            dc.SetBrush(brush)
            dc.DrawRectangleRect(rect)
        else:
            # use a GC on Windows (and GTK?)
            # this crashed on the Mac
            ctx = wx.GraphicsContext_Create(dc)
            ctx.SetPen(pen)
            ctx.SetBrush(brush)
            ctx.DrawRectangle(*rect)

I'd just use a DC everywhere, then -- this use case doesn't make use of the GCs advantages, anyway.

that draw rectangle very fine but whenever the windows is moved or scrolled up or down those rectangles gets erased.

scrolling is an issue -- what coordinates do you want teh overlay to be in? i.e., should it scroll with the contents? IF so, I think you may not be able to do that with an overlay.
 
I believe you need to bind a function to wx.EVT_PAINT and have that function redraw the entire panel, including the static bitmap and the overlays (say from saved coordinates for the rubber-band box drawn by the user). 

whic pretty much defeats the whole point of an overlay -- if you meed to mange drawing it, you might as well simply draw the rect normally.

That being said, I so recall al ot of frustration with Overlays not really doing what I think they should :-)

You may want to take a look at these examples:

I haven't tested them for ages, but maybe there is something useful there?


there are a couple Overlay examples in there.

And a bunch of other useful drawing code.

-CHB


 
I think you'd probably also want to bind wx.EVT_SIZE to function that eventually calls self.Refresh(), which will generate a "needs repainting" event.

FWIW, when I do such things (taking a bitmap from a live camera source, and drawing that plus user-defined overlays), I do this in the Panel.onPaint method of a wx.Panel, which has been bound the wx.EVT_PAINT, roughly as:

    dc = wx.AutoBufferedPaintDC(self)
    dc.Clear()
    dc.DrawBitmap(bitmap, pad_width, pad_height, useMask=True)
    dc.SetBrush(wx.Brush('Black', wx.BRUSHSTYLE_TRANSPARENT))
    dc.SetPen(rect_color, 1.0, wx.SOLID))
    dc.DrawRectangle(*rect_coords)

I know that's not complete, but I think you have the dc drawing stuff understood.  Using AutoBufferedPaintDC gives pretty good, flicker-free drawing.
   
Hope that helps,

--Matt

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to wxpython-user...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.



--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            <a href="tel:(206)%20526-6959" value="+12065266959" target="_blank">(206) 526-6959   voice
7600 Sand Point Way NE   <a href="tel:(206)%20526-6329" value="+12065266329" target="_blank">(206) 526-6329   fax
Seattle, WA  98115       <a href="tel:(206)%20526-6317" value="+12065266317" target="_blank">(206) 526-6317   main reception

[hidden email]

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.



--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

[hidden email]

--
You received this message because you are subscribed to the Google Groups "wxPython-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
For more options, visit https://groups.google.com/d/optout.

ScrolledBitmap.py (1K) Download Attachment