]>
git.saurik.com Git - wxWidgets.git/blob - wxPython/demo/PseudoDC.py
   6 #--------------------------------------------------------------------------- 
  15 #--------------------------------------------------------------------------- 
  39 class MyCanvas(wx
.ScrolledWindow
): 
  40     def __init__(self
, parent
, id, log
, size 
= wx
.DefaultSize
): 
  41         wx
.ScrolledWindow
.__init
__(self
, parent
, id, (0, 0), size
=size
, style
=wx
.SUNKEN_BORDER
) 
  50         self
.SetBackgroundColour("WHITE") 
  51         bmp 
= images
.getTest2Bitmap() 
  52         mask 
= wx
.Mask(bmp
, wx
.BLUE
) 
  56         self
.SetVirtualSize((self
.maxWidth
, self
.maxHeight
)) 
  57         self
.SetScrollRate(20,20) 
  59         # create a PseudoDC to record our drawing 
  60         self
.pdc 
= wx
.PseudoDC() 
  63         self
.DoDrawing(self
.pdc
) 
  64         log
.write('Created PseudoDC draw list with %d operations!'%self
.pdc
.GetLen()) 
  66         self
.Bind(wx
.EVT_PAINT
, self
.OnPaint
) 
  67         self
.Bind(wx
.EVT_ERASE_BACKGROUND
, lambda x
:None) 
  69         # use timer to move one of the objects around 
  70         self
.timer 
= wx
.Timer() 
  71         self
.timer
.SetOwner(self
) 
  72         self
.Bind(wx
.EVT_TIMER
, self
.OnTimer
) 
  74         self
.movingids 
= random
.sample(self
.objids
, MOVING_COUNT
) 
  75         self
.velocitydict 
= {} 
  76         for id in self
.movingids
: 
  77             vx 
= random
.randint(1,5) * random
.choice([-1,1]) 
  78             vy 
= random
.randint(1,5) * random
.choice([-1,1]) 
  79             self
.velocitydict
[id] = (vx
,vy
) 
  81     def OnTimer(self
, event
): 
  82         # get the current position 
  83         xv
, yv 
= self
.GetViewStart() 
  84         dx
, dy 
= self
.GetScrollPixelsPerUnit() 
  85         x
, y   
= (xv 
* dx
, yv 
* dy
) 
  86         w
, h   
= self
.GetClientSizeTuple() 
  87         clip 
= wx
.Rect(x
,y
,w
,h
) 
  89         for id in self
.movingids
: 
  90             r 
= self
.pdc
.GetIdBounds(id) 
  91             # get new object position 
  92             (vx
,vy
) = self
.velocitydict
[id] 
 108             self
.velocitydict
[id] = (vx
,vy
) 
 112             # translate the object 
 113             self
.pdc
.TranslateId(id, dx
, dy
) 
 121             r
.width 
+= abs(dx
) + 40 
 122             r
.height 
+= abs(dy
) + 40 
 123             if r
.Intersects(clip
): 
 127                 self
.RefreshRect(r
, False) 
 130         c 
= random
.choice(colours
) 
 131         t 
= random
.randint(1, 4) 
 132         if not self
.pen_cache
.has_key( (c
, t
) ): 
 133             self
.pen_cache
[(c
, t
)] = wx
.Pen(c
, t
) 
 134         return self
.pen_cache
[(c
, t
)] 
 137     def RandomBrush(self
): 
 138         c 
= random
.choice(colours
) 
 139         if not self
.brush_cache
.has_key(c
): 
 140             self
.brush_cache
[c
] = wx
.Brush(c
) 
 142         return self
.brush_cache
[c
] 
 144     def RandomColor(self
): 
 145         return random
.choice(colours
) 
 148     def OnPaint(self
, event
): 
 149         # Create a buffered paint DC.  It will create the real 
 150         # wx.PaintDC and then blit the bitmap to it when dc is 
 152         dc 
= wx
.BufferedPaintDC(self
) 
 153         # we need to clear the dc BEFORE calling PrepareDC 
 154         bg 
= wx
.Brush(self
.GetBackgroundColour()) 
 157         # use PrepateDC to set position correctly 
 159         # create a clipping rect from our position and size 
 160         # and the Update Region 
 161         xv
, yv 
= self
.GetViewStart() 
 162         dx
, dy 
= self
.GetScrollPixelsPerUnit() 
 163         x
, y   
= (xv 
* dx
, yv 
* dy
) 
 164         rgn 
= self
.GetUpdateRegion() 
 167         # draw to the dc using the calculated clipping rect 
 168         self
.pdc
.DrawToDCClipped(dc
,r
) 
 170     def DoDrawing(self
, dc
): 
 175         for i 
in range(SHAPE_COUNT
): 
 178             choice 
= random
.randint(0,8) 
 180                 x 
= random
.randint(0, W
) 
 181                 y 
= random
.randint(0, H
) 
 182                 dc
.SetPen(self
.RandomPen()) 
 184                 dc
.SetIdBounds(id,wx
.Rect(x
,y
,1,1)) 
 185             elif choice 
in (2,3): 
 186                 x1 
= random
.randint(0, W
-SW
) 
 187                 y1 
= random
.randint(0, H
-SH
) 
 188                 x2 
= random
.randint(x1
, x1
+SW
) 
 189                 y2 
= random
.randint(y1
, y1
+SH
) 
 190                 dc
.SetPen(self
.RandomPen()) 
 191                 dc
.DrawLine(x1
,y1
,x2
,y2
) 
 192                 dc
.SetIdBounds(id,wx
.Rect(x1
,y1
,x2
-x1
,y2
-y1
)) 
 193             elif choice 
in (4,5): 
 194                 w 
= random
.randint(10, SW
) 
 195                 h 
= random
.randint(10, SH
) 
 196                 x 
= random
.randint(0, W 
- w
) 
 197                 y 
= random
.randint(0, H 
- h
) 
 198                 dc
.SetPen(self
.RandomPen()) 
 199                 dc
.SetBrush(self
.RandomBrush()) 
 200                 dc
.DrawRectangle(x
,y
,w
,h
) 
 201                 dc
.SetIdBounds(id,wx
.Rect(x
,y
,w
,h
)) 
 202                 self
.objids
.append(id) 
 204                 Np 
= 8 # number of characters in text 
 207                     c 
= chr( random
.randint(48, 122) ) 
 210                 w
,h 
= self
.GetFullTextExtent(word
)[0:2] 
 211                 x 
= random
.randint(0, W
-w
) 
 212                 y 
= random
.randint(0, H
-h
) 
 213                 dc
.SetTextForeground(self
.RandomColor()) 
 214                 dc
.SetTextBackground(self
.RandomColor()) 
 215                 dc
.DrawText(word
, x
, y
) 
 216                 dc
.SetIdBounds(id,wx
.Rect(x
,y
,w
,h
)) 
 217                 self
.objids
.append(id) 
 219                 Np 
= 8 # number of points per polygon 
 226                     x 
= random
.randint(0, SW
) 
 227                     y 
= random
.randint(0, SH
) 
 228                     if x 
< minx
: minx 
= x
 
 229                     if x 
> maxx
: maxx 
= x
 
 230                     if y 
< miny
: miny 
= y
 
 231                     if y 
> maxy
: maxy 
= y
 
 232                     poly
.append(wx
.Point(x
,y
)) 
 233                 x 
= random
.randint(0, W
-SW
) 
 234                 y 
= random
.randint(0, H
-SH
) 
 235                 dc
.SetPen(self
.RandomPen()) 
 236                 dc
.SetBrush(self
.RandomBrush()) 
 237                 dc
.DrawPolygon(poly
, x
,y
) 
 238                 dc
.SetIdBounds(id,wx
.Rect(minx
+x
,miny
+y
,maxx
-minx
+x
,maxy
-miny
+y
)) 
 239                 self
.objids
.append(id) 
 241                 w
,h 
= self
.bmp
.GetSize() 
 242                 x 
= random
.randint(0, W
-w
) 
 243                 y 
= random
.randint(0, H
-h
) 
 244                 dc
.DrawBitmap(self
.bmp
,x
,y
,True) 
 245                 dc
.SetIdBounds(id,wx
.Rect(x
,y
,w
,h
)) 
 246                 self
.objids
.append(id) 
 249     def ShutdownDemo(self
): 
 253 #--------------------------------------------------------------------------- 
 255 def runTest(frame
, nb
, log
): 
 256     win 
= MyCanvas(nb
, wx
.ID_ANY
, log
) 
 259 #--------------------------------------------------------------------------- 
 268 The wx.PseudoDC class provides a way to record operations on a DC and then 
 269 play them back later.  The PseudoDC can be passed to a drawing routine as 
 270 if it were a real DC.  All Drawing methods are supported except Blit but 
 271 GetXXX methods are not supported and none of the drawing methods return 
 272 a value. The PseudoDC records the drawing to an operation 
 273 list.  The operations can be played back to a real DC using:<pre> 
 276 The operations can be tagged with an id in order to associated them with a 
 277 specific object.  To do this use:<pre> 
 280 Every operation after this will be associated with id until SetId is called 
 281 again.  The PseudoDC also supports object level clipping.  To enable this use:<pre> 
 284 for each object that should be clipped.  Then use:<pre> 
 285     DrawToDCClipped(dc, clippingRect) 
 287 To draw the PseudoDC to a real dc. This is useful for large scrolled windows  
 288 where many objects are offscreen. 
 290 Objects can be moved around without re-drawing using:<pre> 
 291     TranslateId(id, dx, dy) 
 294 To re-draw an object use:<pre> 
 298 and then re-draw the object. 
 304 if __name__ 
== '__main__': 
 307     run
.main(['', os
.path
.basename(sys
.argv
[0])] + sys
.argv
[1:])