-
+#!/usr/bin/env python2.3
try:
import Numeric
import RandomArray
if __name__ == "__main__": # parse options if run stand-alone
# check options:
import sys, getopt
- optlist, args = getopt.getopt(sys.argv[1:],'l',["local","all","text","map","stext","hit","hitf","animate","speed","temp"])
+ optlist, args = getopt.getopt(sys.argv[1:],'l',["local","all","text","map","stext","hit","hitf","animate","speed","temp","props"])
for opt in optlist:
if opt[0] == "--all":
StartUpDemo = "speed"
elif opt[0] == "--temp":
StartUpDemo = "temp"
+ elif opt[0] == "--props":
+ StartUpDemo = "props"
import wx
import time, random
self.Bind(wx.EVT_MENU, self.Clear, item)
item = draw_menu.Append(-1, "&Hit Test","Run a test of the hit test code")
self.Bind(wx.EVT_MENU, self.TestHitTest, item)
- item = draw_menu.Append(-1, "&Hit Test Foreground","Run a test of the hit test code with a foreground Object")
+ item = draw_menu.Append(-1, "Hit Test &Foreground","Run a test of the hit test code with a foreground Object")
self.Bind(wx.EVT_MENU, self.TestHitTestForeground, item)
item = draw_menu.Append(-1, "&Animation","Run a test of Animation")
self.Bind(wx.EVT_MENU, self.TestAnimation, item)
item = draw_menu.Append(-1, "&Speed","Run a test of Drawing Speed")
self.Bind(wx.EVT_MENU, self.SpeedTest, item)
+ item = draw_menu.Append(-1, "Change &Properties","Run a test of Changing Object Properties")
+ self.Bind(wx.EVT_MENU, self.PropertiesChangeTest, item)
MenuBar.Append(draw_menu, "&Tests")
view_menu = wx.Menu()
self.Canvas = NavCanvas.NavCanvas(self,
-1,
(500,500),
- Debug = 1,
+ Debug = 0,
BackgroundColor = "DARK SLATE BLUE")
wx.EVT_CLOSE(self, self.OnCloseWindow)
self.Destroy()
def DrawTest(self,event=None):
+ wx.GetApp().Yield()
# import random
# import RandomArray
Range = (-10,10)
cf = random.randint(0,len(colors)-1)
h = random.randint(1,5)
w = random.randint(1,5)
- Canvas.AddRectangle(x,y,h,w,LineWidth = lw,FillColor = colors[cf])
+ Canvas.AddRectangle(x,y,w,h,LineWidth = lw,FillColor = colors[cf])
# Ellipses
for i in range(3):
w = random.randint(1,5)
Canvas.AddEllipse(x,y,h,w,LineWidth = lw,FillColor = colors[cf])
-## # Dots -- Does anyone need this?
-## for i in range(5):
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## D = random.randint(1,50)
-## lw = random.randint(1,5)
-## cf = random.randint(0,len(colors)-1)
-## cl = random.randint(0,len(colors)-1)
-## Canvas.AddDot(x,y,D,LineWidth = lw,LineColor = colors[cl],FillColor = colors[cf])
+ # Points
+ for i in range(5):
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ D = random.randint(1,50)
+ cf = random.randint(0,len(colors)-1)
+ Canvas.AddPoint((x,y), Color = colors[cf], Diameter = D)
# Circles
for i in range(5):
having to re-draw the whole background.
"""
- print "Running TestAnimation"
+ wx.GetApp().Yield()
Range = (-10,10)
self.Range = Range
# Now the Foreground Object:
C = Canvas.AddCircle(0,0,7,LineWidth = 2,LineColor = "Black",FillColor = "Red", InForeground = True)
- T = Canvas.AddScaledText("Click to Move",0,0, Size = 0.8, Position = 'cc', InForeground = True)
+ T = Canvas.AddScaledText("Click to Move",0,0, Size = 0.6, Position = 'cc', InForeground = True)
C.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.MoveMe)
C.Text = T
Object.Text.Move( (self.dx,self.dy))
self.Canvas.Draw()
self.TimeStep += 1
+ wx.GetApp().Yield(True)
else:
self.Timer.Stop()
self.dy = random.uniform(Range[0]/4,Range[1]/4)
#import time
#start = time.time()
- self.NumTimeSteps = 500
+ self.NumTimeSteps = 200
self.TimeStep = 1
self.Timer.Start(self.FrameDelay)
#print "Did %i frames in %f seconds"%(N, (time.time() - start) )
def TestHitTest(self,event=None):
+ wx.GetApp().Yield()
self.UnBindAllMouseEvents()
Canvas = self.Canvas
dx = 80
dy = 40
x,y = 20, 20
+ FontSize = 8
#Add one that is not HitAble
Canvas.AddRectangle(x, y, w, h, LineWidth = 2)
- Canvas.AddText("Not Hit-able", x, y, Position = "bl")
+ Canvas.AddText("Not Hit-able", x, y, Size = FontSize, Position = "bl")
x += dx
- R = Canvas.AddRectangle(x, y, w, h,LineWidth = 2)
+ R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2)
R.Name = "Line Rectangle"
R.HitFill = False
+ R.HitLineWidth = 5 # Makes it a little easier to hit
R.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHit)
- Canvas.AddText("Left Click Line", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
-
+ Canvas.AddText("Left Click Line", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "Red"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + "Rectangle"
R.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHit)
- Canvas.AddText("Left Click Fill", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Left Click Fill", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_RIGHT_DOWN, self.RectGotHit)
Canvas.AddText("Right Click Fill", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "Grey"
R = Canvas.AddEllipse(x, y, w, h,LineWidth = 2,FillColor = color)
R.Name = color +" Ellipse"
R.Bind(FloatCanvas.EVT_FC_RIGHT_DOWN, self.RectGotHit)
- Canvas.AddText("Right Click Fill", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Right Click Fill", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "Brown"
R.Name = color + " Circle"
R.HitFill = True
R.Bind(FloatCanvas.EVT_FC_LEFT_DCLICK, self.RectGotHit)
- Canvas.AddText("Left D-Click Fill", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Left D-Click Fill", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
R = Canvas.AddCircle(x+dx/2, y+dy/2, dx/4, LineWidth = 2,FillColor = color)
R.Name = color + " Circle"
R.Bind(FloatCanvas.EVT_FC_LEFT_UP, self.RectGotHit)
- Canvas.AddText("Left Up Fill", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Left Up Fill", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "White"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_MIDDLE_DOWN, self.RectGotHit)
- Canvas.AddText("Middle Down", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Middle Down", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "AQUAMARINE"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_MIDDLE_UP, self.RectGotHit)
- Canvas.AddText("Middle Up", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Middle Up", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_MIDDLE_DCLICK, self.RectGotHit)
- Canvas.AddText("Middle DoubleClick", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Middle DoubleClick", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "CYAN"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_RIGHT_UP, self.RectGotHit)
- Canvas.AddText("Right Up", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Right Up", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "LIME GREEN"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_RIGHT_DCLICK, self.RectGotHit)
- Canvas.AddText("Right Double Click", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Right Double Click", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
R.Name = color
R.Bind(FloatCanvas.EVT_FC_RIGHT_DOWN, self.RectGotHitRight)
R.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHitLeft)
- Canvas.AddText("L and R Click", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("L and R Click", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "SALMON"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color + " Rectangle"
R.Bind(FloatCanvas.EVT_FC_ENTER_OBJECT, self.RectMouseOver)
- Canvas.AddText("Mouse Enter", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Mouse Enter", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "MEDIUM VIOLET RED"
R = Canvas.AddRectangle(x, y, w, h, LineWidth = 2, FillColor = color)
R.Name = color
R.Bind(FloatCanvas.EVT_FC_LEAVE_OBJECT, self.RectMouseLeave)
- Canvas.AddText("Mouse Leave", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Mouse Leave", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
R.Name = color
R.Bind(FloatCanvas.EVT_FC_ENTER_OBJECT, self.RectMouseOver)
R.Bind(FloatCanvas.EVT_FC_LEAVE_OBJECT, self.RectMouseLeave)
- Canvas.AddText("Enter and Leave", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Enter and Leave", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "WHEAT"
R.Name = color
R.Bind(FloatCanvas.EVT_FC_ENTER_OBJECT, self.RectMouseOver)
R.Bind(FloatCanvas.EVT_FC_LEAVE_OBJECT, self.RectMouseLeave)
- Canvas.AddText("Mouse Enter&Leave", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Mouse Enter&Leave", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "KHAKI"
R.Name = color
R.Bind(FloatCanvas.EVT_FC_ENTER_OBJECT, self.RectMouseOver)
R.Bind(FloatCanvas.EVT_FC_LEAVE_OBJECT, self.RectMouseLeave)
- Canvas.AddText("Mouse ENter&Leave", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Mouse ENter&Leave", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
L = Canvas.AddLine(( (x, y), (x+10, y+10), (x+w, y+h) ), LineWidth = 2, LineColor = "Red")
L.Name = "A Line"
L.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHitLeft)
- Canvas.AddText("Left Down", x, y, Position = "bl")
- Canvas.AddText(L.Name, x, y+h, Position = "tl")
+ Canvas.AddText("Left Down", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(L.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "SEA GREEN"
R = Canvas.AddPolygon(Points, LineWidth = 2, FillColor = color)
R.Name = color + " Polygon"
R.Bind(FloatCanvas.EVT_FC_RIGHT_DOWN, self.RectGotHitRight)
- Canvas.AddText("RIGHT_DOWN", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("RIGHT_DOWN", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x += dx
color = "Red"
R = Canvas.AddPointSet(Points, Diameter = 4, Color = color)
R.Name = "PointSet"
R.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.PointSetGotHit)
- Canvas.AddText("LEFT_DOWN", x, y, Position = "bl")
- Canvas.AddText(R.Name, x, y+h, Position = "tl")
+ Canvas.AddText("LEFT_DOWN", x, y, Size = FontSize, Position = "bl")
+ Canvas.AddText(R.Name, x, y+h, Size = FontSize, Position = "tl")
x = 20
y += dy
T = Canvas.AddText("Hit-able Text", x, y, Size = 15, Color = "Red", Position = 'tl')
T.Name = "Hit-able Text"
T.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHitLeft)
- Canvas.AddText("Left Down", x, y, Position = "bl")
+ Canvas.AddText("Left Down", x, y, Size = FontSize, Position = "bl")
x += dx
T = Canvas.AddScaledText("Scaled Text", x, y, Size = 1./2*h, Color = "Pink", Position = 'bl')
Canvas.AddPointSet( (x, y), Diameter = 3)
T.Name = "Scaled Text"
T.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.RectGotHitLeft)
- Canvas.AddText("Left Down", x, y, Position = "tl")
+ Canvas.AddText("Left Down", x, y, Size = FontSize, Position = "tl")
self.Canvas.ZoomToBB()
def TestHitTestForeground(self,event=None):
- print "Running: TestHitTestForeground"
+ wx.GetApp().Yield()
self.UnBindAllMouseEvents()
Canvas = self.Canvas
def TestText(self, event= None):
+ wx.GetApp().Yield()
self.BindAllMouseEvents()
Canvas = self.Canvas
# Text
String = "Some text"
-## for i in range(10):
-## ts = random.randint(10,40)
-## cf = random.randint(0,len(colors)-1)
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
self.Canvas.AddText("Top Left",x,y,Size = 14,Color = "Yellow",BackgroundColor = "Blue", Position = "tl")
self.Canvas.AddText("Bottom Left",x,y,Size = 14,Color = "Cyan",BackgroundColor = "Black",Position = "bl")
self.Canvas.AddText("Top Right",x,y,Size = 14,Color = "Black",BackgroundColor = "Cyan",Position = "tr")
self.Canvas.ZoomToBB()
def TestScaledText(self, event= None):
+ wx.GetApp().Yield()
self.BindAllMouseEvents()
Canvas = self.Canvas
self.Canvas.ZoomToBB()
def DrawMap(self,event = None):
+ wx.GetApp().Yield()
import os, time
self.BindAllMouseEvents()
def LineTest(self,event = None):
+ wx.GetApp().Yield()
import os, time
# import random
colors = self.colors
#print "It took %f seconds to draw %i lines"%(time.clock() - start,len(linepoints) )
def SpeedTest(self,event=None):
-# import random
-# import RandomArray
+ wx.GetApp().Yield()
BigRange = (-1000,1000)
colors = self.colors
Canvas.ClearAll()
Canvas.SetProjectionFun(None)
- # Lots of Text
- String = "Unscaled text"
+ # Pointset
coords = []
- text = []
- for i in range(5000):
+ for i in range(1000):
x,y = (random.uniform(BigRange[0],BigRange[1]),random.uniform(BigRange[0],BigRange[1]))
coords.append( (x,y) )
- print "Drawing the Numbers"
+ print "Drawing the Points"
start = time.clock()
- for i in xrange( len(coords) ):
- Canvas.AddText("%i"%(i),
- coords[i][0],
- coords[i][1],
- Size = 12,
- Position = "cc",
- BackgroundColor = "White")
- print "It took %s seconds to add the numbers"%(time.clock() - start)
-
-
-## ObjectList = []
-
-## print "Building a list of lots of random objects"
-## ## Random tests of everything:
-## def MakeRange():
-## while True:
-## Range = ( random.randint(BigRange[0],BigRange[1]), random.randint(BigRange[0],BigRange[1]) )
-## if abs (Range[0] - Range[1]) < 10:
-## continue
-## if Range[0] > Range[1]:
-## Range = ( Range[1], Range[0] )
-## break
-## return Range
-
-## # Rectangles
-## for i in range(300):
-## Range = MakeRange()
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## lw = random.randint(1,5)
-## cf = random.randint(0,len(colors)-1)
-## h = random.randint(1, Range[1] - Range[0])
-## w = random.randint(1, Range[1] - Range[0])
-## ObjectList.append(FloatCanvas.Rectangle(x,y,h,w,LineWidth = lw,FillColor = colors[cf]))
+ for Point in coords:
+ Canvas.AddPoint(Point, Diameter = 4)
+ print "It took %s seconds to add the points"%(time.clock() - start)
+ Canvas.ZoomToBB()
+
+ def PropertiesChangeTest(self,event=None):
+ wx.GetApp().Yield()
+
+ Range = (-10,10)
+ colors = self.colors
+
+ self.UnBindAllMouseEvents()
+ Canvas = self.Canvas
+
+ Canvas.ClearAll()
+ Canvas.SetProjectionFun(None)
+
+ self.ColorObjectsAll = []
+ self.ColorObjectsLine = []
+ self.ColorObjectsColor = []
+ self.ColorObjectsText = []
+ ##One of each object:
+ # Rectangle
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ lw = random.randint(1,5)
+ cf = random.randint(0,len(colors)-1)
+ h = random.randint(1,5)
+ w = random.randint(1,5)
+ self.Rectangle = Canvas.AddRectangle(x,y,w,h,LineWidth = lw,FillColor = colors[cf])
+ self.ColorObjectsAll.append(self.Rectangle)
-## # Ellipses
-## for i in range(300):
-## Range = MakeRange()
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## lw = random.randint(1,5)
-## cf = random.randint(0,len(colors)-1)
-## h = random.randint(1, Range[1] - Range[0])
-## w = random.randint(1, Range[1] - Range[0])
-## ObjectList.append(FloatCanvas.Ellipse(x,y,h,w,LineWidth = lw,FillColor = colors[cf]))
+ # Ellipse
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ lw = random.randint(1,5)
+ cf = random.randint(0,len(colors)-1)
+ h = random.randint(1,5)
+ w = random.randint(1,5)
+ self.Ellipse = Canvas.AddEllipse(x,y,h,w,LineWidth = lw,FillColor = colors[cf])
+ self.ColorObjectsAll.append(self.Ellipse)
-
-## # Circles
-## for i in range(500):
-## Range = MakeRange()
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## D = random.randint(1, (Range[1] - Range[0]) / 2)
-## lw = random.randint(1,5)
-## cf = random.randint(0,len(colors)-1)
-## cl = random.randint(0,len(colors)-1)
-## ObjectList.append(FloatCanvas.Circle(x,y,D,LineWidth = lw,LineColor = colors[cl],FillColor = colors[cf]))
-## #ObjectList.append(FloatCanvas.Text("Circle # %i"%(i),x,y,Size = 12,BackgroundColor = None,Position = "cc"))
+ # Point
+ xy = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ D = random.randint(1,50)
+ lw = random.randint(1,5)
+ cf = random.randint(0,len(colors)-1)
+ cl = random.randint(0,len(colors)-1)
+ self.ColorObjectsColor.append(Canvas.AddPoint(xy, colors[cf], D))
-## # Lines
-## for i in range(500):
-## Range = MakeRange()
-## points = []
-## for j in range(random.randint(2,100)):
-## point = (random.randint(Range[0],Range[1]),random.randint(Range[0],Range[1]))
-## points.append(point)
-## lw = random.randint(1,10)
-## cf = random.randint(0,len(colors)-1)
-## cl = random.randint(0,len(colors)-1)
-## ObjectList.append(FloatCanvas.Line(points, LineWidth = lw, LineColor = colors[cl]) )
+ # Circle
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ D = random.randint(1,5)
+ lw = random.randint(1,5)
+ cf = random.randint(0,len(colors)-1)
+ cl = random.randint(0,len(colors)-1)
+ self.Circle = Canvas.AddCircle(x,y,D,LineWidth = lw,LineColor = colors[cl],FillColor = colors[cf])
+ self.ColorObjectsAll.append(self.Circle)
+
+ # Line
+ points = []
+ for j in range(random.randint(2,10)):
+ point = (random.randint(Range[0],Range[1]),random.randint(Range[0],Range[1]))
+ points.append(point)
+ lw = random.randint(1,10)
+ cf = random.randint(0,len(colors)-1)
+ cl = random.randint(0,len(colors)-1)
+ self.ColorObjectsLine.append(Canvas.AddLine(points, LineWidth = lw, LineColor = colors[cl]))
-## # Polygons
-## for i in range(300):
-## Range = MakeRange()
-## points = []
-## for j in range(random.randint(2,60)):
-## point = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## points.append(point)
-## lw = random.randint(1,6)
-## cf = random.randint(0,len(colors)-1)
-## cl = random.randint(0,len(colors)-1)
-## ObjectList.append(FloatCanvas.Polygon(points,
-## LineWidth = lw,
-## LineColor = colors[cl],
-## FillColor = colors[cf],
-## FillStyle = 'Solid') )
-## random.shuffle(ObjectList)
-## print "Adding lots of random objects"
-## start = time.clock()
-## for Object in ObjectList:
-## Canvas.AddObject(Object)
-## print "It took %s Seconds to add %i objects "%(time.clock() - start, len(ObjectList) )
-
-## ## Pointset
-## for i in range(100):
-## points = []
-## points = RandomArray.uniform(Range[0],Range[1],(100,2))
-## cf = random.randint(0,len(colors)-1)
-## D = random.randint(1,4)
-## Canvas.AddPointSet(points, Color = colors[cf], Diameter = D)
+ # Polygon
+## points = []
+## for j in range(random.randint(2,6)):
+## point = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+## points.append(point)
+ points = RandomArray.uniform(Range[0],Range[1],(6,2))
+ lw = random.randint(1,6)
+ cf = random.randint(0,len(colors)-1)
+ cl = random.randint(0,len(colors)-1)
+ self.ColorObjectsAll.append(Canvas.AddPolygon(points,
+ LineWidth = lw,
+ LineColor = colors[cl],
+ FillColor = colors[cf],
+ FillStyle = 'Solid'))
+
+ ## Pointset
+ points = RandomArray.uniform(Range[0],Range[1],(100,2))
+ cf = random.randint(0,len(colors)-1)
+ D = random.randint(1,4)
+ self.PointSet = Canvas.AddPointSet(points, Color = colors[cf], Diameter = D)
+ self.ColorObjectsColor.append(self.PointSet)
+ ## Point
+ point = RandomArray.uniform(Range[0],Range[1],(2,))
+ cf = random.randint(0,len(colors)-1)
+ D = random.randint(1,4)
+ self.Point = Canvas.AddPoint(point, Color = colors[cf], Diameter = D)
+ self.ColorObjectsColor.append(self.Point)
+
+ # Text
+ String = "Unscaled text"
+ ts = random.randint(10,40)
+ cf = random.randint(0,len(colors)-1)
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ self.ColorObjectsText.append(Canvas.AddText(String, x, y, Size = ts, Color = colors[cf], Position = "cc"))
+
+ # Scaled Text
+ String = "Scaled text"
+ ts = random.random()*3 + 0.2
+ cf = random.randint(0,len(colors)-1)
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ self.ColorObjectsText.append(Canvas.AddScaledText(String, x, y, Size = ts, Color = colors[cf], Position = "cc"))
-## # Scaled Text
-## String = "Scaled text"
-## for i in range(30):
-## ts = random.random()*3 + 0.2
-## cf = random.randint(0,len(colors)-1)
-## x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
-## Canvas.AddScaledText(String, x, y, Size = ts, Color = colors[cf], Position = "cc")
+ # A "Button"
+ Button = Canvas.AddRectangle(-10, -12, 20, 3, LineStyle = None, FillColor = "Red")
+ Canvas.AddScaledText("Click Here To Change Properties",
+ 0, -10.5,
+ Size = 0.7,
+ Color = "Black",
+ Position = "cc")
+
+ Button.Bind(FloatCanvas.EVT_FC_LEFT_DOWN, self.ChangeProperties)
Canvas.ZoomToBB()
+ def ChangeProperties(self, Object = None):
+ colors = self.colors
+ Range = (-10,10)
+
+ for Object in self.ColorObjectsAll:
+ pass
+ Object.SetFillColor(colors[random.randint(0,len(colors)-1)])
+ Object.SetLineColor(colors[random.randint(0,len(colors)-1)])
+ Object.SetLineWidth(random.randint(1,7))
+ Object.SetLineStyle(FloatCanvas.DrawObject.LineStyleList.keys()[random.randint(0,5)])
+ for Object in self.ColorObjectsLine:
+ Object.SetLineColor(colors[random.randint(0,len(colors)-1)])
+ Object.SetLineWidth(random.randint(1,7))
+ Object.SetLineStyle(FloatCanvas.DrawObject.LineStyleList.keys()[random.randint(0,5)])
+ for Object in self.ColorObjectsColor:
+ Object.SetColor(colors[random.randint(0,len(colors)-1)])
+ for Object in self.ColorObjectsText:
+ Object.SetColor(colors[random.randint(0,len(colors)-1)])
+ Object.SetBackgroundColor(colors[random.randint(0,len(colors)-1)])
+ self.Circle.SetDiameter(random.randint(1,10))
+ self.PointSet.SetDiameter(random.randint(1,8))
+ self.Point.SetDiameter(random.randint(1,8))
+ for Object in (self.Rectangle, self.Ellipse):
+ x,y = (random.uniform(Range[0],Range[1]),random.uniform(Range[0],Range[1]))
+ w,h = random.randint(1,5), random.randint(1,5)
+ Object.SetShape(x,y,w,h)
+
+ self.Canvas.Draw(Force = True)
def TempTest(self, event= None):
- "Running the Temporary test"
+ wx.GetApp().Yield()
self.UnBindAllMouseEvents()
Canvas = self.Canvas
Canvas.ClearAll()
Canvas.SetProjectionFun(None)
-# import random
-# import RandomArray
Range = (-10,10)
# Create a random Polygon
elif StartUpDemo == "temp":
"starting temp Test"
frame.TempTest()
+ elif StartUpDemo == "props":
+ "starting PropertiesChange Test"
+ frame.PropertiesChangeTest()
return True
-
try:
- from Numeric import array,asarray,Float,cos,pi,sum,minimum,maximum,Int32,zeros
+ from Numeric import array,asarray,Float,cos,pi,sum,minimum,maximum,Int32,zeros, ones, concatenate, sqrt, argmin, power, absolute
except ImportError:
- from numarray import array, asarray, Float, cos, pi, sum, minimum, maximum, Int32, zeros
+ from numarray import array, asarray, Float, cos, pi, sum, minimum, maximum, Int32, zeros, concatenate
from time import clock, sleep
import types
import os
-import Resources
-
## A global variable to hold the Pixels per inch that wxWindows thinks is in use
## This is used for scaling fonts.
## This can't be computed on module __init__, because a wx.App might not have iniitalized yet.
-global ScreenPPI
+global ScreenPPI
## a custom Exceptions:
class FloatCanvasException(Exception):
pass
-## All the mouse events
+## Create all the mouse events
#EVT_FC_ENTER_WINDOW = wx.NewEventType()
#EVT_FC_LEAVE_WINDOW = wx.NewEventType()
EVT_FC_LEFT_DOWN = wx.NewEventType()
EVT_FC_ENTER_OBJECT = wx.NewEventType()
EVT_FC_LEAVE_OBJECT = wx.NewEventType()
+##Create all mouse event binding functions
#def EVT_ENTER_WINDOW( window, function ):
# window.Connect( -1, -1, EVT_FC_ENTER_WINDOW, function )
#def EVT_LEAVE_WINDOW( window, function ):
def EVT_MOUSEWHEEL( window, function ):
window.Connect( -1, -1,EVT_FC_MOUSEWHEEL , function )
-class MouseEvent(wx.PyCommandEvent):
+class _MouseEvent(wx.PyCommandEvent):
"""
GetCoords() , which returns and (x,y) tuple in world coordinates.
- Another differnce is that it is a CommandEvent, which propagates up
+ Another difference is that it is a CommandEvent, which propagates up
the window hierarchy until it is handled.
"""
#return eval(self.NativeEvent.__getattr__(name) )
return getattr(self._NativeEvent, name)
-#### ColorGEnerator class is now obsolete. I'm using a python generator function instead.
-##class ColorGenerator:
+def _cycleidxs(indexcount, maxvalue, step):
-## """
-
-## An instance of this class generates a unique color each time
-## GetNextColor() is called. Someday I will use a proper Python
-## generator for this class.
-
-## The point of this generator is for the hit-test bitmap, each object
-## needs to be a unique color. Also, each system can be running a
-## different number of colors, and it doesn't appear to be possible to
-## have a wxMemDC with a different colordepth as the screen so this
-## generates colors far enough apart that they can be distinguished on
-## a 16bit screen. Anything less than 16bits won't work. It could, but
-## I havn't written the code that way. You also wouldn't get many
-## distict colors
-
-## """
+ """
+ Utility function used by _colorGenerator
-## def __init__(self):
-## import sys
-## ## figure out the color depth of the screen
-## ## for some bizare reason, thisdoesn't work on OS-X
-## if sys.platform == 'darwin':
-## depth = 24
-## else:
-## b = wx.EmptyBitmap(1,1)
-## depth = b.GetDepth()
-## self.r = 0
-## self.g = 0
-## self.b = 0
-## if depth == 16:
-## self.step = 8
-## elif depth >= 24:
-## self.step = 1
-## else:
-## raise FloatCanvasException("ColorGenerator does not work with depth = %s"%depth )
-
-## def GetNextColor(self):
-## step = self.step
-## ##r,g,b = self.r,self.g,self.b
-## self.r += step
-## if self.r > 255:
-## self.r = step
-## self.g += step
-## if self.g > 255:
-## self.g = step
-## self.b += step
-## if self.b > 255:
-## ## fixme: this should be a derived exception
-## raise FloatCanvasException("Too many objects in colorgenerator for HitTest")
-## return (self.r,self.g,self.b)
-
-## def Reset(self):
-## self.r = 0
-## self.g = 0
-## self.b = 0
-
-def cycleidxs(indexcount, maxvalue, step):
+ """
if indexcount == 0:
yield ()
else:
for idx in xrange(0, maxvalue, step):
- for tail in cycleidxs(indexcount - 1, maxvalue, step):
+ for tail in _cycleidxs(indexcount - 1, maxvalue, step):
yield (idx, ) + tail
-def colorGenerator():
+def _colorGenerator():
+
+ """
+
+ Generates a seris of unique colors used to do hit-tests with the HIt
+ Test bitmap
+
+ """
import sys
if sys.platform == 'darwin':
depth = 24
step = 1
else:
raise "ColorGenerator does not work with depth = %s" % depth
- return cycleidxs(indexcount=3, maxvalue=256, step=step)
+ return _cycleidxs(indexcount=3, maxvalue=256, step=step)
-#### I don't know if the Set objects are useful, beyond the pointset object
-#### The problem is that when zoomed in, the BB is checked to see whether to draw the object.
-#### A Set object can defeat this
+#### I don't know if the Set objects are useful, beyond the pointset
+#### object The problem is that when zoomed in, the BB is checked to see
+#### whether to draw the object. A Set object can defeat this. ONe day
+#### I plan to write some custon C++ code to draw sets of objects
##class ObjectSetMixin:
## """
## if length == 1:
## self.Pens = self.Pens[0]
-
-
class DrawObject:
"""
This is the base class for all the objects that can be drawn.
+ One must subclass from this (and an assortment of Mixins) to create
+ a new DrawObject.
+
"""
def __init__(self,InForeground = False):
self.HitFill = True
self.MinHitLineWidth = 3
self.HitLineWidth = 3 ## this gets re-set by the subclasses if necessary
+
+ self.Brush = None
+ self.Pen = None
+
+ self.FillStyle = "Solid"
# I pre-define all these as class variables to provide an easier
# interface, and perhaps speed things up by caching all the Pens
self._Canvas.MakeNewHTdc()
if not self.HitColor:
if not self._Canvas.HitColorGenerator:
- self._Canvas.HitColorGenerator = colorGenerator()
+ self._Canvas.HitColorGenerator = _colorGenerator()
self._Canvas.HitColorGenerator.next() # first call to prevent the background color from being used.
self.HitColor = self._Canvas.HitColorGenerator.next()
self.SetHitPen(self.HitColor,self.HitLineWidth)
pass
self.HitAble = False
+
def SetBrush(self,FillColor,FillStyle):
if FillColor is None or FillStyle is None:
self.Brush = wx.TRANSPARENT_BRUSH
if not self.HitLine:
self.HitPen = wx.TRANSPARENT_PEN
else:
- self.HitPen = self.PenList.setdefault( (HitColor, "solid", LineWidth), wx.Pen(HitColor, LineWidth, self.LineStyleList["Solid"]) )
+ self.HitPen = self.PenList.setdefault( (HitColor, "solid", self.HitLineWidth), wx.Pen(HitColor, self.HitLineWidth, self.LineStyleList["Solid"]) )
def PutInBackground(self):
if self._Canvas and self.InForeground:
self._Canvas._BackgroundDirty = True
self.InForeground = True
+class ColorOnlyMixin:
+ """
+
+ Mixin class for objects that have just one color, rather than a fill
+ color and line color
+
+ """
+
+ def SetColor(self, Color):
+ self.SetPen(Color,"Solid",1)
+ self.SetBrush(Color,"Solid")
+
+ SetFillColor = SetColor # Just to provide a consistant interface
+
+class LineOnlyMixin:
+ """
+
+ Mixin class for objects that have just one color, rather than a fill
+ color and line color
+
+ """
+
+ def SetLineColor(self, LineColor):
+ self.LineColor = LineColor
+ self.SetPen(LineColor,self.LineStyle,self.LineWidth)
+
+ def SetLineStyle(self, LineStyle):
+ self.LineStyle = LineStyle
+ self.SetPen(self.LineColor,LineStyle,self.LineWidth)
+
+ def SetLineWidth(self, LineWidth):
+ self.LineWidth = LineWidth
+ self.SetPen(self.LineColor,self.LineStyle,LineWidth)
+
+class LineAndFillMixin(LineOnlyMixin):
+ """
+
+ Mixin class for objects that have both a line and a fill color and
+ style.
+
+ """
+ def SetFillColor(self, FillColor):
+ self.FillColor = FillColor
+ self.SetBrush(FillColor,self.FillStyle)
+
+ def SetFillStyle(self, FillStyle):
+ self.FillStyle = FillStyle
+ self.SetBrush(self.FillColor,FillStyle)
+
class XYObjectMixin:
"""
if self._Canvas:
self._Canvas.BoundingBoxDirty = True
+ def SetXY(self, x, y):
+ self.XY = array( (x, y), Float)
+ self.CalcBoundingBox()
+
+ def SetPoint(self, xy):
+ self.XY = array( xy, Float)
+ self.XY.shape = (2,)
+ self.CalcBoundingBox()
+
class PointsObjectMixin:
"""
"""
-## This is code for the XYMixin object, it needs to be adapeted and tested.
+
+## This is code for the PointsObjectMixin object, it needs to be adapted and tested.
+## Is the neccesary at all: you can always do:
+## Object.SetPoints( Object.Points + delta, copy = False)
## def Move(self, Delta ):
## """
## Move(Delta): moves the object by delta, where delta is an (dx,
-## dy) pair. Ideally a Numpy array or shape (2,)
+## dy) pair. Ideally a Numpy array of shape (2,)
## """
## if self._Canvas:
## self._Canvas.BoundingBoxDirty = True
- def SetPoints(self,Points):
- self.Points = Points
- self.BoundingBox = array(((min(self.Points[:,0]),min(self.Points[:,1])),(max(self.Points[:,0]),max(self.Points[:,1]))),Float)
+ def CalcBoundingBox(self):
+ self.BoundingBox = array(((min(self.Points[:,0]),
+ min(self.Points[:,1]) ),
+ (max(self.Points[:,0]),
+ max(self.Points[:,1]) ) ), Float )
if self._Canvas:
self._Canvas.BoundingBoxDirty = True
+ def SetPoints(self, Points, copy = True):
+ """
+ Sets the coordinates of the points of the object to Points (NX2 array).
+
+ By default, a copy is made, if copy is set to False, a reference
+ is used, iff Points is a NumPy array of Floats. This allows you
+ to change some or all of the points without making any copies.
+
+ For example:
+
+ Points = Object.Points
+ Points += (5,10) # shifts the points 5 in the x dir, and 10 in the y dir.
+ Object.SetPoints(Points, False) # Sets the points to the same array as it was
+
+ """
+ if copy:
+ self.Points = array(Points, Float)
+ self.Points.shape = (-1,2) # Make sure it is a NX2 array, even if there is only one point
+ else:
+ self.Points = asarray(Points, Float)
+ self.CalcBoundingBox()
-class Polygon(DrawObject,PointsObjectMixin):
+class Polygon(DrawObject,PointsObjectMixin,LineAndFillMixin):
"""
x-coordinate of point N and Points[N,1] is the y-coordinate for
arrays.
+ The other parameters specify various properties of the Polygon, and
+ should be self explanatory.
+
"""
def __init__(self,
Points,
InForeground = False):
DrawObject.__init__(self,InForeground)
self.Points = array(Points,Float) # this DOES need to make a copy
- self.BoundingBox = array(((min(self.Points[:,0]),min(self.Points[:,1])),(max(self.Points[:,0]),max(self.Points[:,1]))),Float)
+ self.CalcBoundingBox()
self.LineColor = LineColor
self.LineStyle = LineStyle
## dc.DrawLineList(Points,self.Pens)
-class Line(DrawObject,PointsObjectMixin):
+class Line(DrawObject,PointsObjectMixin,LineOnlyMixin):
"""
- The Line class takes a list of 2-tuples, or a NX2 NumPy array of point coordinates.
- so that Points[N][0] is the x-coordinate of point N and Points[N][1] is the y-coordinate
- or Points[N,0] is the x-coordinate of point N and Points[N,1] is the y-coordinate for arrays.
- It will draw a straight line if there are two points, and a polyline if there are more than two.
+ The Line class takes a list of 2-tuples, or a NX2 NumPy Float array
+ of point coordinates.
+
+ It will draw a straight line if there are two points, and a polyline
+ if there are more than two.
"""
def __init__(self,Points,
self.Points = array(Points,Float)
- self.BoundingBox = array(((min(self.Points[:,0]),min(self.Points[:,1])),(max(self.Points[:,0]),max(self.Points[:,1]))),Float)
+ self.CalcBoundingBox()
self.LineColor = LineColor
self.LineStyle = LineStyle
## Points.shape = (-1,4)
## dc.DrawLineList(Points,self.Pens)
-class PointSet(DrawObject):
+class PointSet(DrawObject,PointsObjectMixin, ColorOnlyMixin):
"""
- The PointSet class takes a list of 2-tuples, or a NX2 NumPy array of point coordinates.
- so that Points[N][0] is the x-coordinate of point N and Points[N][1] is the y-coordinate
- or Points[N,0] is the x-coordinate of point N and Points[N,1] is the y-coordinate for arrays.
- Each point will be drawn the same color and Diameter. The Diameter is in screen points,
- not world coordinates.
+ The PointSet class takes a list of 2-tuples, or a NX2 NumPy array of
+ point coordinates.
+
+ If Points is a sequence of tuples: Points[N][0] is the x-coordinate of
+ point N and Points[N][1] is the y-coordinate.
+
+ If Points is a NumPy array: Points[N,0] is the x-coordinate of point
+ N and Points[N,1] is the y-coordinate for arrays.
+
+ Each point will be drawn the same color and Diameter. The Diameter
+ is in screen pixels, not world coordinates.
- At this point, the hit-test code does not distingish between the
- points, you will only know that one of the poins got hit, not which
- one.
+ The hit-test code does not distingish between the points, you will
+ only know that one of the points got hit, not which one. You can use
+ PointSet.FindClosestPoint(WorldPoint) to find out which one
In the case of points, the HitLineWidth is used as diameter.
self.Points = array(Points,Float)
self.Points.shape = (-1,2) # Make sure it is a NX2 array, even if there is only one point
- self.BoundingBox = array(((min(self.Points[:,0]),
- min(self.Points[:,1])),
- (max(self.Points[:,0]),
- max(self.Points[:,1]))),Float)
-
- self.Color = Color
+ self.CalcBoundingBox()
self.Diameter = Diameter
self.HitLineWidth = self.MinHitLineWidth
- self.SetPen(Color,"Solid",1)
- self.SetBrush(Color,"Solid")
+ self.SetColor(Color)
- def SetPoints(self,Points):
- self.Points = array(Points, Float)
- self.Points.shape = (-1,2) # Make sure it is a NX2 array, even if there is only one point
- self.BoundingBox = array(((min(self.Points[:,0]),
- min(self.Points[:,1]) ),
- (max(self.Points[:,0]),
- max(self.Points[:,1]) ) ) )
- if self._Canvas:
- self._Canvas.BoundingBoxDirty = True
+ def SetDiameter(self,Diameter):
+ self.Diameter = Diameter
+
+
+ def FindClosestPoint(self, XY):
+ """
+
+ Returns the index of the closest point to the point, XY, given
+ in World coordinates. It's essentially random which you get if
+ there are more than one that are the same.
+
+ This can be used to figure out which point got hit in a mouse
+ binding callback, for instance. It's a lot faster that using a
+ lot of separate points.
+
+ """
+ ## kind of ugly to minimize data copying
+ d = self.Points - XY
+ d = sum( power(d,2,d), 1 )
+ d = absolute( d, d ) # don't need the real distance, just which is smallest
+ #dist = sqrt( sum( (self.Points - XY)**2), 1) )
+ return argmin(d)
def DrawD2(self, dc, Points):
# A Little optimization for a diameter2 - point
else:
dc.SetBrush(self.Brush)
radius = int(round(self.Diameter/2))
- for xy in Points:
- dc.DrawEllipsePointSize( (xy - radius), (self.Diameter, self.Diameter) )
+ if len(Points) > 100:
+ xy = Points
+ xywh = concatenate((xy-radius, ones(xy.shape) * self.Diameter ), 1 )
+ dc.DrawEllipseList(xywh)
+ else:
+ for xy in Points:
+ dc.DrawCircle(xy[0],xy[1], radius)
if HTdc and self.HitAble:
HTdc.SetPen(self.HitPen)
+ HTdc.SetBrush(self.HitBrush)
if self.Diameter <= 1:
HTdc.DrawPointList(Points)
elif self.Diameter <= 2:
self.DrawD2(HTdc, Points)
else:
- HTdc.SetBrush(self.HitBrush)
- radius = int(round(self.Diameter/2))
- for xy in Points:
- HTdc.DrawEllipsePointSize( (xy - radius), (self.Diameter, self.Diameter) )
-
-#### Does anyone need this?
-##class Dot(DrawObject):
-## """
-## The Dot class takes an x.y coordinate pair, and the Diameter of the circle.
-## The Diameter is in pixels, so it won't change with zoom.
+ if len(Points) > 100:
+ xy = Points
+ xywh = concatenate((xy-radius, ones(xy.shape) * self.Diameter ), 1 )
+ HTdc.DrawEllipseList(xywh)
+ else:
+ for xy in Points:
+ HTdc.DrawCircle(xy[0],xy[1], radius)
-## Also Fill and line data
+class Point(DrawObject,XYObjectMixin,ColorOnlyMixin):
+ """
+
+ The Point class takes a 2-tuple, or a (2,) NumPy array of point
+ coordinates.
-## """
-## def __init__(self,x,y,Diameter,LineColor,LineStyle,LineWidth,FillColor,FillStyle,InForeground = False):
-## DrawObject.__init__(self,InForeground)
+ The Diameter is in screen points, not world coordinates, So the
+ Bounding box is just the point, and doesn't include the Diameter.
+
+ The HitLineWidth is used as diameter for the
+ Hit Test.
+
+ """
+ def __init__(self, XY, Color = "Black", Diameter = 1, InForeground = False):
+ DrawObject.__init__(self, InForeground)
-## self.X = x
-## self.Y = y
-## self.Diameter = Diameter
-## # NOTE: the bounding box does not include the diameter of the dot, as that is in pixel coords.
-## # If this is a problem, perhaps you should use a circle, instead!
-## self.BoundingBox = array(((x,y),(x,y)),Float)
+ self.XY = array(XY, Float)
+ self.XY.shape = (2,) # Make sure it is a 1X2 array, even if there is only one point
+ self.CalcBoundingBox()
+ self.SetColor(Color)
+ self.Diameter = Diameter
-## self.LineColor = LineColor
-## self.LineStyle = LineStyle
-## self.LineWidth = LineWidth
-## self.FillColor = FillColor
-## self.FillStyle = FillStyle
+ self.HitLineWidth = self.MinHitLineWidth
-## self.SetPen(LineColor,LineStyle,LineWidth)
-## self.SetBrush(FillColor,FillStyle)
+ def SetDiameter(self,Diameter):
+ self.Diameter = Diameter
-## def _Draw(self, dc , WorldToPixel, ScaleWorldToPixel, HTdc=None):
-## #def _Draw(self,dc,WorldToPixel,ScaleWorldToPixel):
-## dc.SetPen(self.Pen)
-## dc.SetBrush(self.Brush)
-## radius = int(round(self.Diameter/2))
-## (X,Y) = WorldToPixel((self.X,self.Y))
-## dc.DrawEllipse((X - radius), (Y - radius), self.Diameter, self.Diameter)
+ def CalcBoundingBox(self):
+ self.BoundingBox = array( (self.XY, self.XY), Float )
-class RectEllipse(DrawObject, XYObjectMixin):
+ def _Draw(self, dc , WorldToPixel, ScaleWorldToPixel, HTdc=None):
+ dc.SetPen(self.Pen)
+ xy = WorldToPixel(self.XY)
+ if self.Diameter <= 1:
+ dc.DrawPoint(xy[0], xy[1])
+ else:
+ dc.SetBrush(self.Brush)
+ radius = int(round(self.Diameter/2))
+ dc.DrawCircle(xy[0],xy[1], radius)
+ if HTdc and self.HitAble:
+ HTdc.SetPen(self.HitPen)
+ if self.Diameter <= 1:
+ HTdc.DrawPoint(xy[0], xy[1])
+ else:
+ HTdc.SetBrush(self.HitBrush)
+ HTdc.DrawCircle(xy[0],xy[1], radius)
+
+class RectEllipse(DrawObject, XYObjectMixin,LineAndFillMixin):
def __init__(self,x,y,width,height,
LineColor = "Black",
LineStyle = "Solid",
self.SetPen(LineColor,LineStyle,LineWidth)
self.SetBrush(FillColor,FillStyle)
+ def SetShape(self,x,y,width,height):
+ self.XY = array( (x, y), Float)
+ self.WH = array( (width, height), Float )
+ self.CalcBoundingBox()
+
def SetUpDraw(self, dc , WorldToPixel, ScaleWorldToPixel, HTdc):
dc.SetPen(self.Pen)
return ( WorldToPixel(self.XY),
ScaleWorldToPixel(self.WH) )
- def SetXY(self, x, y):
- self.XY = array( (x, y), Float)
+ def CalcBoundingBox(self):
self.BoundingBox = array((self.XY, (self.XY + self.WH) ), Float)
- if self._Canvas:
- self._Canvas.BoundingBoxDirty = True
+ self._Canvas.BoundingBoxDirty = True
class Rectangle(RectEllipse):
class Circle(Ellipse):
def __init__(self, x ,y, Diameter, **kwargs):
+ self.Center = array((x,y),Float)
RectEllipse.__init__(self ,
x-Diameter/2.,
y-Diameter/2.,
Diameter,
Diameter,
**kwargs)
+
+ def SetDiameter(self, Diameter):
+ x,y = self.Center - (Diameter/2.)
+ self.SetShape(x,
+ y,
+ Diameter,
+ Diameter)
-class TextObjectMixin:
+class TextObjectMixin(XYObjectMixin):
"""
A mix in class that holds attributes and methods that are needed by
FaceName) )
return self.Font
+ def SetColor(self, Color):
+ self.Color = Color
+
+ def SetBackgroundColor(self, BackgroundColor):
+ self.BackgroundColor = BackgroundColor
+
## store the function that shift the coords for drawing text. The
## "c" parameter is the correction for world coordinates, rather
## than pixel coords as the y axis is reversed
self.XY = ( x,y )
- # use a memDC -- ScreenDC doesn't work with 2.5.1 and GTK2
- #dc = wx.MemoryDC()
- #bitmap = wx.EmptyBitmap(1, 1)
- #dc.SelectObject(bitmap)
- #dc.SetFont(self.Font)
- #(self.TextWidth, self.TextHeight) = dc.GetTextExtent(self.String)
(self.TextWidth, self.TextHeight) = (None, None)
self.ShiftFun = self.ShiftFunDict[Position]
- def SetXY(self, x, y):
- self.XY = ( x,y )
+ def CalcBoundingBox(self):
self.BoundingBox = array((self.XY, self.XY),Float)
- if self._Canvas:
- self._Canvas.BoundingBoxDirty = True
+
def _Draw(self, dc , WorldToPixel, ScaleWorldToPixel, HTdc=None):
XY = WorldToPixel(self.XY)
HTdc.SetBrush(self.HitBrush)
HTdc.DrawRectanglePointSize(XY, (self.TextWidth, self.TextHeight) )
-class ScaledText(DrawObject, TextObjectMixin, XYObjectMixin):
+class ScaledText(DrawObject, TextObjectMixin):
"""
This class creates a text object that is scaled when zoomed. It is
placed at the coordinates, x,y. the "Position" argument is a two
Family:
Font family, a generic way of referring to fonts without
- specifying actual facename. One of::
+ specifying actual facename. One of:
wx.DEFAULT: Chooses a default font.
wx.DECORATI: A decorative font.
wx.ROMAN: A formal, serif font.
wx.SCRIPT: A handwriting font.
wx.SWISS: A sans-serif font.
wx.MODERN: A fixed pitch font.
-
NOTE: these are only as good as the wxWindows defaults, which aren't so good.
-
Style:
One of wx.NORMAL, wx.SLANT and wx.ITALIC.
-
Weight:
One of wx.NORMAL, wx.LIGHT and wx.BOLD.
-
Underline:
The value can be True or False. At present this may have an an
effect on Windows only.
self.Weight = Font.GetWeight()
# Experimental max font size value on wxGTK2: this works OK on
- # my system If it's any larger, there is a crash, with the
- # message: The application 'FloatCanvasDemo.py' lost its
+ # my system. If it's a lot larger, there is a crash, with the
+ # message:
+ #
+ # The application 'FloatCanvasDemo.py' lost its
# connection to the display :0.0; most likely the X server was
# shut down or you killed/destroyed the application.
- self.MaxSize = 2750
+ #
+ # Windows and OS-X seem to be better behaved in this regard.
+ # They may not draw it, but they don't crash either!
+ self.MaxFontSize = 1000
self.ShiftFun = self.ShiftFunDict[Position]
- ## Compute the BB
+ self.CalcBoundingBox()
+
+
+ def CalcBoundingBox(self):
## this isn't exact, as fonts don't scale exactly.
dc = wx.MemoryDC()
bitmap = wx.EmptyBitmap(1, 1)
dc.SelectObject(bitmap) #wxMac needs a Bitmap selected for GetTextExtent to work.
DrawingSize = 40 # pts This effectively determines the resolution that the BB is computed to.
- ScaleFactor = float(Size) / DrawingSize
+ ScaleFactor = float(self.Size) / DrawingSize
dc.SetFont(self.SetFont(DrawingSize, self.Family, self.Style, self.Weight, self.Underline, self.FaceName) )
(w,h) = dc.GetTextExtent(self.String)
w = w * ScaleFactor
h = h * ScaleFactor
- x, y = self.ShiftFun(x, y, w, h, world = 1)
+ x, y = self.ShiftFun(self.XY[0], self.XY[1], w, h, world = 1)
self.BoundingBox = array(((x, y-h ),(x + w, y)),Float)
-
- # the new coords are set to the corner of the BB:
- #self.X = self.BoundingBox[0,0]
- #self.Y = self.BoundingBox[1,1]
+
def _Draw(self, dc , WorldToPixel, ScaleWorldToPixel, HTdc=None):
(X,Y) = WorldToPixel( (self.XY) )
## Check to see if the font size is large enough to blow up the X font server
## If so, limit it. Would it be better just to not draw it?
## note that this limit is dependent on how much memory you have, etc.
- if Size > self.MaxSize:
- Size = self.MaxSize
+ Size = min(Size, self.MaxFontSize)
dc.SetFont(self.SetFont(Size, self.Family, self.Style, self.Weight, self.Underline, self.FaceName))
dc.SetTextForeground(self.Color)
if self.BackgroundColor:
EVT_FC_LEAVE_OBJECT: {},
}
- def RaiseMouseEvent(self, Event, EventType):
+ def _RaiseMouseEvent(self, Event, EventType):
"""
This is called in various other places to raise a Mouse Event
"""
#print "in Raise Mouse Event", Event
pt = self.PixelToWorld( Event.GetPosition() )
- evt = MouseEvent(EventType, Event, self.GetId(), pt)
+ evt = _MouseEvent(EventType, Event, self.GetId(), pt)
self.GetEventHandler().ProcessEvent(evt)
def HitTest(self, event, HitEvent):
if self.GUIMode == "Mouse":
EventType = EVT_FC_LEFT_DCLICK
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def MiddleDownEvent(self,event):
if self.GUIMode == "Mouse":
EventType = EVT_FC_MIDDLE_DOWN
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def MiddleUpEvent(self,event):
if self.GUIMode == "Mouse":
EventType = EVT_FC_MIDDLE_UP
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def MiddleDoubleClickEvent(self,event):
if self.GUIMode == "Mouse":
EventType = EVT_FC_MIDDLE_DCLICK
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def RightUpEvent(self,event):
if self.GUIMode == "Mouse":
EventType = EVT_FC_RIGHT_UP
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def RightDoubleCLickEvent(self,event):
if self.GUIMode == "Mouse":
EventType = EVT_FC_RIGHT_DCLICK
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
def WheelEvent(self,event):
if self.GUIMode == "Mouse":
- self.RaiseMouseEvent(event, EVT_FC_MOUSEWHEEL)
+ self._RaiseMouseEvent(event, EVT_FC_MOUSEWHEEL)
def LeftDownEvent(self,event):
elif self.GUIMode == "Mouse":
## check for a hit
if not self.HitTest(event, EVT_FC_LEFT_DOWN):
- self.RaiseMouseEvent(event,EVT_FC_LEFT_DOWN)
+ self._RaiseMouseEvent(event,EVT_FC_LEFT_DOWN)
else:
pass
elif self.GUIMode == "Mouse":
EventType = EVT_FC_LEFT_UP
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
else:
pass
## Only do something if there are mouse over events bound
if self.HitDict and (self.HitDict[ EVT_FC_ENTER_OBJECT ] or self.HitDict[ EVT_FC_LEAVE_OBJECT ] ):
if not self.MouseOverTest(event):
- self.RaiseMouseEvent(event,EVT_FC_MOTION)
+ self._RaiseMouseEvent(event,EVT_FC_MOTION)
else:
pass
- self.RaiseMouseEvent(event,EVT_FC_MOTION)
+ self._RaiseMouseEvent(event,EVT_FC_MOTION)
else:
pass
elif self.GUIMode == "Mouse":
EventType = EVT_FC_RIGHT_DOWN
if not self.HitTest(event, EventType):
- self.RaiseMouseEvent(event, EventType)
+ self._RaiseMouseEvent(event, EventType)
else:
pass
"""
#print "In Draw"
- if self.PanelSize < (1,1):
+ if self.PanelSize < (1,1): # it's possible for this to get called before being properly initialized.
return
if self.Debug: start = clock()
ScreenDC = wx.ClientDC(self)
a 2-tuple, or sequence of 2-tuples.
"""
#Note: this can be called by users code for various reasons, so asarray is needed.
- return (((asarray(Coordinates,Float) - self.ViewPortCenter)*self.TransformVector)+(self.HalfPanelSize)).astype('i')
+ return (((asarray(Coordinates,Float) -
+ self.ViewPortCenter)*self.TransformVector)+
+ (self.HalfPanelSize)).astype('i')
def ScaleWorldToPixel(self,Lengths):
"""
def _makeFloatCanvasAddMethods(): ## lrk's code for doing this in module __init__
classnames = ["Circle", "Ellipse", "Rectangle", "ScaledText", "Polygon",
- "Line", "Text", "PointSet"]
+ "Line", "Text", "PointSet","Point"]
for classname in classnames:
klass = globals()[classname]
def getaddshapemethod(klass=klass):
addshapemethod = getaddshapemethod()
methodname = "Add" + classname
setattr(FloatCanvas, methodname, addshapemethod)
- docstring = " Creates %s and adds its reference to the canvas.\n" % classname
- docstring += " Argument protocol same as %s class" % classname
+ docstring = "Creates %s and adds its reference to the canvas.\n" % classname
+ docstring += "Argument protocol same as %s class" % classname
if klass.__doc__:
docstring += ", whose docstring is:\n%s" % klass.__doc__
FloatCanvas.__dict__[methodname].__doc__ = docstring