python-box2d-2.0.2+svn20100109.244/ 0000755 0000000 0000000 00000000000 11414467240 014500 5 ustar root root python-box2d-2.0.2+svn20100109.244/setup.py 0000644 0000000 0000000 00000006346 11151077147 016224 0 ustar root root #!/usr/bin/env python """ Setup script for pyBox2D distribution. For installation instructions, see INSTALL. Basic install steps: setup.py build If that worked, then: setup.py install """ import os from glob import glob try: from setuptools import (setup, Extension) print 'Using setuptools.' except: from distutils.core import (setup, Extension) print 'Setuptools not found; falling back on distutils.' # release version number box2d_version = '2.0.2' release_number = 1 # create the version string version_str = "%sb%s" % (box2d_version, str(release_number)) def write_init(): # read in the license header license_header = open(os.path.join('Box2D', 'pybox2d_license_header.txt')).read() # create the source code for the file init_source = [ "", "from Box2D import *", "__version__ = '%s'" % version_str, "__version_info__ = (%s,%d)" % (box2d_version.replace('.', ','), release_number), ] # and create the __init__ file with the appropriate version string f=open('__init__.py', 'w') f.write(license_header) f.write( '\n'.join(init_source) ) f.close() source_paths = [ 'Box2D/Dynamics/', 'Box2D/Dynamics/Contacts/', 'Box2D/Dynamics/Controllers/', 'Box2D/Dynamics/Joints/', 'Box2D/Common/', 'Box2D/Collision/', 'Box2D/Collision/Shapes/', ] # glob all of the paths and then flatten the list into one box2d_source_files = ['Box2D/Box2D.i'] + \ sum( [glob(os.path.join(path, "*.cpp")) for path in source_paths], []) # arguments to pass to SWIG. for old versions of SWIG, -O (optimize) might not be present. swig_arguments = '-c++ -IBox2D -O -includeall -ignoremissing -w201 -outdir .' pybox2d_extension = \ Extension('Box2D._Box2D', box2d_source_files, extra_compile_args=['-I.'], language='c++') LONG_DESCRIPTION = \ """ 2D physics library Box2D %s for usage in Python. After installing please be sure to try out the testbed demos. They require either pygame or pyglet and are available on the homepage. pybox2d homepage: http://pybox2d.googlecode.com Box2D's homepage: http://www.box2d.org """ % (box2d_version,) CLASSIFIERS = [ "Development Status :: 4 - Beta", "Intended Audience :: Developers", "License :: OSI Approved :: zlib/libpng License", "Operating System :: Microsoft :: Windows", "Operating System :: MacOS :: MacOS X", "Operating System :: POSIX", "Programming Language :: Python", "Games :: Physics Libraries" ] write_init() setup_dict = dict( name = "Box2D", version = version_str, author = "Ken Lauer", author_email = "sirkne at gmail dot com", description = "Python Box2D", license = "zlib", url ="http://pybox2d.googlecode.com/", long_description = LONG_DESCRIPTION, classifiers = CLASSIFIERS, packages = ['Box2D'], package_dir = {'Box2D': '.'}, options = { 'build_ext': { 'swig_opts' : swig_arguments } }, ext_modules = [ pybox2d_extension ] ) # run the actual setup from distutils setup( **setup_dict ) python-box2d-2.0.2+svn20100109.244/README 0000644 0000000 0000000 00000002661 11151113531 015352 0 ustar root root pyBox2D Python Box2D Bindings -- 2D Physics Library http://pybox2d.googlecode.com/ What is it? ----------- pyBox2D is a 2D physics library for your games and simulation. It's based on the Box2D library, written in C++. It supports several shape types (circle, polygon, thin line segments), quite a few joint types (revolute, prismatic, etc.), and even controllers (buoyancy, gravity, etc.). Getting Started --------------- For building instructions, see INSTALL or the wiki on the homepage. Once installed, check out the testbed demos to see what pyBox2D can do (located in testbed/ ). Then read the manual located on the Box2D wiki, here: http://www.box2d.org/wiki/index.php?title=Python_Manual A possibly outdated local copy is included in this distribution in docs/ . For more information on some caveats and key differences between the C++ version of Box2D, please see: http://www.box2d.org/wiki/index.php?title=Box2D_with_Python On the wiki, you will also find more useful things of varying quality. Epydoc output for pyBox2D: http://pybox2d.googlecode.com/svn/epydoc/html/index.html It's by no means perfect, but it can come in handy. Bugs ---- Please submit any bugs that you find to: http://code.google.com/p/pybox2d/issues/list Contact ------- You can contact the team on the Box2D forums: http://www.box2d.org/forum/ or by e-mail: sirkne at gmail com python-box2d-2.0.2+svn20100109.244/testbed/ 0000755 0000000 0000000 00000000000 11414467240 016132 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/test_Pulleys.py 0000644 0000000 0000000 00000005255 11136402204 021175 0 ustar root root #!/usr/bin/python # # C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com # Python version Copyright (c) 2008 kne / sirkne at gmail dot com # # Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com) # # This software is provided 'as-is', without any express or implied # warranty. In no event will the authors be held liable for any damages # arising from the use of this software. # Permission is granted to anyone to use this software for any purpose, # including commercial applications, and to alter it and redistribute it # freely, subject to the following restrictions: # 1. The origin of this software must not be misrepresented; you must not # claim that you wrote the original software. If you use this software # in a product, an acknowledgment in the product documentation would be # appreciated but is not required. # 2. Altered source versions must be plainly marked as such, and must not be # misrepresented as being the original software. # 3. This notice may not be removed or altered from any source distribution. from test_main import * class Pulleys (Framework): name="Pulleys" joint1=None _pickle_vars=['joint1'] def __init__(self): super(Pulleys, self).__init__() sd=box2d.b2PolygonDef() sd.SetAsBox(50.0, 10.0) bd=box2d.b2BodyDef() bd.position = (0.0, -10.0) ground = self.world.CreateBody(bd) ground.CreateShape(sd) a = 2.0 b = 4.0 y = 16.0 L = 12.0 sd=box2d.b2PolygonDef() sd.SetAsBox(a, b) sd.density = 5.0 bd=box2d.b2BodyDef() bd.position = (-10.0, y) body1 = self.world.CreateBody(bd) body1.CreateShape(sd) body1.SetMassFromShapes() bd.position = (10.0, y) body2 = self.world.CreateBody(bd) body2.CreateShape(sd) body2.SetMassFromShapes() pulleyDef=box2d.b2PulleyJointDef() anchor1 =(-10.0, y + b) anchor2 =( 10.0, y + b) groundAnchor1=(-10.0, y + b + L) groundAnchor2=( 10.0, y + b + L) pulleyDef.Initialize(body1, body2, groundAnchor1, groundAnchor2, anchor1, anchor2, 2.0) self.joint1 = self.world.CreateJoint(pulleyDef).getAsType() def Step(self, settings): super(Pulleys, self).Step(settings) if not self.joint1: return ratio = self.joint1.GetRatio() L = self.joint1.GetLength1() + ratio * self.joint1.GetLength2() self.DrawStringCR("L1 + %.2f * L2 = %.2f" % (ratio, L)) if __name__=="__main__": main(Pulleys) python-box2d-2.0.2+svn20100109.244/testbed/test_MotorsAndLimits.py 0000644 0000000 0000000 00000011100 11136402204 022612 0 ustar root root #!/usr/bin/python # # C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com # Python version Copyright (c) 2008 kne / sirkne at gmail dot com # # Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com) # # This software is provided 'as-is', without any express or implied # warranty. In no event will the authors be held liable for any damages # arising from the use of this software. # Permission is granted to anyone to use this software for any purpose, # including commercial applications, and to alter it and redistribute it # freely, subject to the following restrictions: # 1. The origin of this software must not be misrepresented; you must not # claim that you wrote the original software. If you use this software # in a product, an acknowledgment in the product documentation would be # appreciated but is not required. # 2. Altered source versions must be plainly marked as such, and must not be # misrepresented as being the original software. # 3. This notice may not be removed or altered from any source distribution. from test_main import * class MotorsAndLimits (Framework): name="MotorsAndLimits" joint1=None joint2=None joint3=None _pickle_vars = ['joint1', 'joint2', 'joint3'] def __init__(self): super(MotorsAndLimits, self).__init__() sd=box2d.b2PolygonDef() sd.SetAsBox(50.0, 10.0) bd=box2d.b2BodyDef() bd.position = (0.0, -10.0) ground = self.world.CreateBody(bd) ground.CreateShape(sd) sd=box2d.b2PolygonDef() sd.SetAsBox(2.0, 0.5) sd.density = 5.0 sd.friction = 0.05 bd=box2d.b2BodyDef() rjd=box2d.b2RevoluteJointDef() prevBody=ground y = 8.0 bd.position = (3.0, y) body = self.world.CreateBody(bd) body.CreateShape(sd) body.SetMassFromShapes() rjd.Initialize(prevBody, body, (0.0, y)) rjd.motorSpeed = 1.0 * box2d.b2_pi rjd.maxMotorTorque = 10000.0 rjd.enableMotor = True self.joint1 = self.world.CreateJoint(rjd).getAsType() prevBody = body bd.position = (9.0, y) body = self.world.CreateBody(bd) body.CreateShape(sd) body.SetMassFromShapes() rjd.Initialize(prevBody, body, (6.0, y)) rjd.motorSpeed = 0.5 * box2d.b2_pi rjd.maxMotorTorque = 2000.0 rjd.enableMotor = True rjd.lowerAngle = - 0.5 * box2d.b2_pi rjd.upperAngle = 0.5 * box2d.b2_pi rjd.enableLimit = True self.joint2 = self.world.CreateJoint(rjd).getAsType() bd.position = (-10.0, 10.0) bd.angle = 0.5 * box2d.b2_pi body = self.world.CreateBody(bd) body.CreateShape(sd) body.SetMassFromShapes() pjd=box2d.b2PrismaticJointDef() pjd.Initialize(ground, body, (-10.0, 10.0), (1.0, 0.0)) pjd.motorSpeed = 10.0 pjd.maxMotorForce = 1000.0 pjd.enableMotor = True pjd.lowerTranslation = 0.0 pjd.upperTranslation = 20.0 pjd.enableLimit = True self.joint3 = self.world.CreateJoint(pjd).getAsType() def Keyboard(self, key): if not self.joint1 or not self.joint2 or not self.joint3: return if key==K_l: self.joint2.EnableLimit(not self.joint2.IsLimitEnabled()) self.joint3.EnableLimit(not self.joint3.IsLimitEnabled()) self.joint2.GetBody1().WakeUp() self.joint3.GetBody2().WakeUp() elif key==K_m: self.joint1.EnableMotor(not self.joint1.IsMotorEnabled()) self.joint2.EnableMotor(not self.joint2.IsMotorEnabled()) self.joint3.EnableMotor(not self.joint3.IsMotorEnabled()) self.joint2.GetBody1().WakeUp() self.joint3.GetBody2().WakeUp() elif key==K_p: self.joint3.GetBody2().WakeUp() self.joint3.SetMotorSpeed(-self.joint3.GetMotorSpeed()) def Step(self, settings): self.DrawStringCR("Keys: (l) limits, (m) motors, (p) prismatic speed") if self.joint1 and self.joint2 and self.joint3: torque1 = self.joint1.GetMotorTorque() torque2 = self.joint2.GetMotorTorque() force3 = self.joint3.GetMotorForce() self.DrawStringCR("Motor Torque = %.0f, %.0f : Motor Force = %.0f" % (torque1,torque2, force3)) super(MotorsAndLimits, self).Step(settings) if __name__=="__main__": main(MotorsAndLimits) python-box2d-2.0.2+svn20100109.244/testbed/test_DynamicEdges.py 0000644 0000000 0000000 00000021456 11135461416 022106 0 ustar root root #!/usr/bin/python # # C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com # Python version Copyright (c) 2008 kne / sirkne at gmail dot com # # Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com) # # This software is provided 'as-is', without any express or implied # warranty. In no event will the authors be held liable for any damages # arising from the use of this software. # Permission is granted to anyone to use this software for any purpose, # including commercial applications, and to alter it and redistribute it # freely, subject to the following restrictions: # 1. The origin of this software must not be misrepresented; you must not # claim that you wrote the original software. If you use this software # in a product, an acknowledgment in the product documentation would be # appreciated but is not required. # 2. Altered source versions must be plainly marked as such, and must not be # misrepresented as being the original software. # 3. This notice may not be removed or altered from any source distribution. from test_main import * class DynamicEdges (Framework): name="DynamicEdges" def __init__(self): super(DynamicEdges, self).__init__() bd=box2d.b2BodyDef() bd.position = (0.0, -10.0) body = self.world.CreateBody(bd) sd=box2d.b2PolygonDef() sd.SetAsBox(50.0, 10.0) body.CreateShape(sd) sd1=box2d.b2CircleDef() sd1.radius = 0.5 sd1.localPosition = (-0.5, 0.5) sd1.density = 2.0 sd2=box2d.b2CircleDef() sd2.radius = 0.5 sd2.localPosition = (0.5, 0.5) sd2.density = 0.0 # massless for i in range(10): x = box2d.b2Random(-0.1, 0.1) bd=box2d.b2BodyDef() bd.position = (x + 5.0, 1.05 + 2.5 * i) bd.angle = box2d.b2Random(-box2d.b2_pi, box2d.b2_pi) body = self.world.CreateBody(bd) body.CreateShape(sd1) body.CreateShape(sd2) body.SetMassFromShapes() sd1=box2d.b2PolygonDef() sd1.SetAsBox(0.25, 0.5) sd1.density = 2.0 sd2=box2d.b2PolygonDef() sd2.SetAsBox(0.25, 0.5, (0.0, -0.5), 0.5 * box2d.b2_pi) sd2.density = 2.0 for i in range(10): x = box2d.b2Random(-0.1, 0.1) bd=box2d.b2BodyDef() bd.position = (x - 5.0, 1.05 + 2.5 * i) bd.angle = box2d.b2Random(-box2d.b2_pi, box2d.b2_pi) body = self.world.CreateBody(bd) body.CreateShape(sd1) body.CreateShape(sd2) body.SetMassFromShapes() xf1=box2d.b2XForm() xf1.R.Set(0.3524 * box2d.b2_pi) xf1.position = box2d.b2Mul(xf1.R, (1.0, 0.0)) sd1=box2d.b2PolygonDef() sd1.vertexCount = 3 sd1.setVertex(0, box2d.b2Mul(xf1, (-1.0, 0.0))) sd1.setVertex(1, box2d.b2Mul(xf1, (1.0, 0.0))) sd1.setVertex(2, box2d.b2Mul(xf1, (0.0, 0.5))) sd1.density = 2.0 xf2=box2d.b2XForm() xf2.R.Set(-0.3524 * box2d.b2_pi) xf2.position = box2d.b2Mul(xf2.R, (-1.0, 0.0)) sd2=box2d.b2PolygonDef() sd2.vertexCount = 3 sd2.setVertex(0, box2d.b2Mul(xf2, (-1.0, 0.0))) sd2.setVertex(1, box2d.b2Mul(xf2, (1.0, 0.0))) sd2.setVertex(2, box2d.b2Mul(xf2, (0.0, 0.5))) sd2.density = 2.0 for i in range(10): x = box2d.b2Random(-0.1, 0.1) bd=box2d.b2BodyDef() bd.position = (x, 2.05 + 2.5 * i) bd.angle = 0.0 body = self.world.CreateBody(bd) body.CreateShape(sd1) body.CreateShape(sd2) body.SetMassFromShapes() sd_bottom=box2d.b2PolygonDef() sd_bottom.SetAsBox( 1.5, 0.15 ) sd_bottom.density = 4.0 sd_left=box2d.b2PolygonDef() sd_left.SetAsBox(0.15, 2.7, (-1.45, 2.35), 0.2) sd_left.density = 4.0 sd_right=box2d.b2PolygonDef() sd_right.SetAsBox(0.15, 2.7, (1.45, 2.35), -0.2) sd_right.density = 4.0 bd=box2d.b2BodyDef() bd.position = ( 0.0, 2.0 ) body = self.world.CreateBody(bd) body.CreateShape(sd_bottom) body.CreateShape(sd_left) body.CreateShape(sd_right) body.SetMassFromShapes() loop1=[ (0.063134534,8.3695248), (0.94701801,9.3165428), (0.0,9.0640047), (-0.12626907,10.326695), (1.4520943,11.77879), (2.2728432,10.137292), (2.3991123,11.147444), (3.5986685,10.958041), (3.9143411,7.3593722), (4.1668793,9.4428119), (5.4295699,9.3165428), (6.2503189,8.3063903), (6.6922606,10.137292), (4.9876282,9.8216191), (4.7350901,10.958041), (7.2604714,11.652521), (10.732871,11.147444), (10.480333,10.642368), (10.732871,9.8216191), (11.55362,9.4428119), (12.374369,9.3796773), (13.005714,9.8216191), (13.195118,10.38983), (13.005714,10.768637), (12.626907,10.894906), (12.753176,11.526252), (13.573925,11.715655), (14.836616,11.399982), (16.351844,10.768637), (17.867073,11.399982), (17.803939,10.263561), (17.361997,8.3063903), (17.803939,8.1801212), (18.056477,9.5059464), (18.182746,11.336848), (18.561553,11.210579), (18.561553,9.6322155), (18.561553,7.7381795), (18.687822,5.5284708), (19.382302,5.6547398), (19.066629,8.1801212), (19.003495,10.263561), (19.066629,11.463117), (19.887378,11.841924), (20.708127,11.273713), (21.0238,10.011023), (20.708127,7.2962377), (21.086934,6.2860852), (21.150069,3.7607038), (20.392455,2.5611476), (18.624688,2.5611476), (20.771262,2.1192059), (20.771262,0.22516988), (18.624688,-0.2799064), (13.826463,0.16203534), (14.015867,1.7403987), (13.195118,2.1823404), (12.626907,1.5509951), (12.879445,0.85651522), (12.626907,0.35143895), (10.543467,1.298457), (11.490485,3.9501074), (13.889598,3.6344347), (13.889598,2.9399549), (14.584077,3.8869729), (11.932427,5.2127981), (9.7227183,4.0132419), (10.796005,3.5081657), (9.7858528,3.2556275), (10.796005,2.4980131), (7.9549513,1.7403987), (9.6595837,1.424726), (9.217642,0.66711162), (8.270624,-0.090502792), (7.0079333,0.85651522), (6.1240498,-0.15363733), (6.1240498,3.192493), (5.6821081,2.4348786), (4.9876282,2.1192059), (4.1037447,1.8666678), (3.0304576,1.8666678), (2.0834396,2.245475), (1.6414979,2.6242822), (1.3258252,3.5081657), (1.2626907,0.47770802), (0.63134534,0.035766276), (0.063134534,0.9827842), ] loop2 = [ (8.270624,6.1598161), (8.270624,5.3390672), (8.7757003,5.086529), (9.4701801,5.5284708), (9.217642,6.033547), (8.7757003,6.412354), ] b2Loop1 = [(loop[0] + 10.0, loop[1]+1.0) for loop in loop1] b2Loop2 = [(loop[0] - 10.0, loop[1]) for loop in loop2] b2Loop1.reverse() bd=box2d.b2BodyDef() bd.position = ( 0.0, 0.0 ) body = self.world.CreateBody(bd) weight=box2d.b2CircleDef() weight.filter.maskBits = 0 weight.density = 4.0 weight.radius = 0.5 weight.localPosition = (8.9, 5.75) body.CreateShape(weight) edgeDef=box2d.b2EdgeChainDef() edgeDef.setVertices(b2Loop2) body.CreateShape(edgeDef) body.SetMassFromShapes() body = self.world.CreateBody(bd) weight.radius = 5.0 weight.localPosition = (20.5, 7.0) body.CreateShape(weight) edgeDef.setVertices(b2Loop1) body.CreateShape(edgeDef) body.SetMassFromShapes() if __name__=="__main__": main(DynamicEdges) python-box2d-2.0.2+svn20100109.244/testbed/pgu/ 0000755 0000000 0000000 00000000000 11414467240 016725 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/ 0000755 0000000 0000000 00000000000 11414467240 017511 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/button.py 0000644 0000000 0000000 00000023567 11130023047 021377 0 ustar root root """ """ from pygame.locals import * from const import * import widget, surface import basic class _button(widget.Widget): def __init__(self,**params): widget.Widget.__init__(self,**params) self.state = 0 def event(self,e): if e.type == ENTER: self.repaint() elif e.type == EXIT: self.repaint() elif e.type == FOCUS: self.repaint() elif e.type == BLUR: self.repaint() elif e.type == KEYDOWN: if e.key == K_SPACE or e.key == K_RETURN: self.state = 1 self.repaint() elif e.type == MOUSEBUTTONDOWN: self.state = 1 self.repaint() elif e.type == KEYUP: if self.state == 1: sub = pygame.event.Event(CLICK,{'pos':(0,0),'button':1}) #self.send(sub.type,sub) self._event(sub) self.state = 0 self.repaint() elif e.type == MOUSEBUTTONUP: self.state = 0 self.repaint() elif e.type == CLICK: self.click() self.pcls = "" if self.state == 0 and self.container.myhover is self: self.pcls = "hover" if self.state == 1 and self.container.myhover is self: self.pcls = "down" def click(self): pass class Button(_button): """A button, buttons can be clicked, they are usually used to set up callbacks.
Button(value=None)
w = gui.Button("Click Me")
w.connect(gui.CLICK,fnc,value)
"""
def __init__(self,value=None,**params):
params.setdefault('cls','button')
_button.__init__(self,**params)
self.value = value
def __setattr__(self,k,v):
if k == 'value' and type(v) == str: v = basic.Label(v,cls=self.cls+".label")
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and v != None:
pass
if k == 'value' and _v != NOATTR and _v != None and _v != v:
self.send(CHANGE)
self.chsize()
def resize(self,width=None,height=None):
self.value.rect.x,self.value.rect.y = 0,0
self.value.rect.w,self.value.rect.h = self.value.resize(width,height)
return self.value.rect.w,self.value.rect.h
#
# self.value._resize()
# self.rect.w,self.rect.h = self.value.rect_margin.w,self.value.rect_margin.h
#
# if self.style.width: self.rect.w = max(self.rect.w,self.style.width)
# if self.style.height: self.rect.w = max(self.rect.w,self.style.height)
#
# xt,xr,xb,xl = self.value.getspacing()
#
# self.value._resize(self.rect.w-(xl+xr),self.rect.h-(xt+xb))
#
def paint(self,s):
self.value.pcls = self.pcls
self.value.paint(surface.subsurface(s,self.value.rect))
class Switch(_button):
"""A switch can have two states, True or False.
Switch(value=False)
w = gui.Switch(True)
w.connect(gui.CHANGE,fnc,value)
"""
def __init__(self,value=False,**params):
params.setdefault('cls','switch')
_button.__init__(self,**params)
self.value = value
img = self.style.off
self.style.width = img.get_width()
self.style.height = img.get_height()
def paint(self,s):
#self.pcls = ""
#if self.container.myhover is self: self.pcls = "hover"
if self.value: img = self.style.on
else: img = self.style.off
s.blit(img,(0,0))
def __setattr__(self,k,v):
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
def click(self):
self.value = not self.value
class Checkbox(_button):
"""Within a Group of Checkbox widgets several may be selected at a time.
Checkbox(group,value=None)
g = gui.Group(name='colors',value=['r','b'])
t = gui.Table()
t.tr()
t.td(gui.Label('Red'))
t.td(gui.Checkbox(g,'r'))
t.tr()
t.td(gui.Label('Green'))
t.td(gui.Checkbox(g,'g'))
t.tr()
t.td(gui.Label('Blue'))
t.td(gui.Checkbox(g,'b'))
"""
def __init__(self,group,value=None,**params):
params.setdefault('cls','checkbox')
_button.__init__(self,**params)
self.group = group
self.group.add(self)
if self.group.value == None:
self.group.value = []
self.value = value
img = self.style.off
self.style.width = img.get_width()
self.style.height = img.get_height()
def paint(self,s):
#self.pcls = ""
#if self.container.myhover is self: self.pcls = "hover"
if self.value in self.group.value: img = self.style.on
else: img = self.style.off
s.blit(img,(0,0))
def click(self):
if self.value in self.group.value:
self.group.value.remove(self.value)
else:
self.group.value.append(self.value)
self.group._change()
class Radio(_button):
"""Within a Group of Radio widgets only one may be selected at a time.
Radio(group,value=None)
g = gui.Group(name='colors',value='g')
t = gui.Table()
t.tr()
t.td(gui.Label('Red'))
t.td(gui.Radio(g,'r'))
t.tr()
t.td(gui.Label('Green'))
t.td(gui.Radio(g,'g'))
t.tr()
t.td(gui.Label('Blue'))
t.td(gui.Radio(g,'b'))
"""
def __init__(self,group=None,value=None,**params):
params.setdefault('cls','radio')
_button.__init__(self,**params)
self.group = group
self.group.add(self)
self.value = value
img = self.style.off
self.style.width = img.get_width()
self.style.height = img.get_height()
def paint(self,s):
#self.pcls = ""
#if self.container.myhover is self: self.pcls = "hover"
if self.group.value == self.value: img = self.style.on
else: img = self.style.off
s.blit(img,(0,0))
def click(self):
self.group.value = self.value
class Tool(_button):
"""Within a Group of Tool widgets only one may be selected at a time.
Tool(group,widget=None,value=None)
g = gui.Group(name='colors',value='g')
t = gui.Table()
t.tr()
t.td(gui.Tool(g,'Red','r'))
t.tr()
t.td(gui.Tool(g,'Green','g'))
t.tr()
t.td(gui.Tool(g,'Blue','b'))
"""
def __init__(self,group,widget=None,value=None,**params): #TODO widget= could conflict with module widget
params.setdefault('cls','tool')
_button.__init__(self,**params)
self.group = group
self.group.add(self)
self.value = value
if widget:
self.setwidget(widget)
if self.group.value == self.value: self.pcls = "down"
def setwidget(self,w):
self.widget = w
def resize(self,width=None,height=None):
self.widget.rect.w,self.widget.rect.h = self.widget.resize()
#self.widget._resize()
#self.rect.w,self.rect.h = self.widget.rect_margin.w,self.widget.rect_margin.h
return self.widget.rect.w,self.widget.rect.h
def event(self,e):
_button.event(self,e)
if self.group.value == self.value: self.pcls = "down"
def paint(self,s):
if self.group.value == self.value: self.pcls = "down"
self.widget.paint(surface.subsurface(s,self.widget.rect))
def click(self):
self.group.value = self.value
for w in self.group.widgets:
if w != self: w.pcls = ""
class Icon(_button):
"""TODO - might be deprecated
"""
def __init__(self,cls,**params):
params['cls'] = cls
_button.__init__(self,**params)
s = self.style.image
self.style.width = s.get_width()
self.style.height = s.get_height()
self.state = 0
def paint(self,s):
#self.pcls = ""
#if self.state == 0 and hasattr(self.container,'myhover') and self.container.myhover is self: self.pcls = "hover"
#if self.state == 1 and hasattr(self.container,'myhover') and self.container.myhover is self: self.pcls = "down"
s.blit(self.style.image,(0,0))
class Link(_button):
"""A link, links can be clicked, they are usually used to set up callbacks.
Basically the same as the button widget, just text only with a different cls. Made for
convenience.
Link(value=None)
w = gui.Link("Click Me")
w.connect(gui.CLICK,fnc,value)
"""
def __init__(self,value,**params):
params.setdefault('focusable',True)
params.setdefault('cls','link')
_button.__init__(self,**params)
self.value = value
self.font = self.style.font
self.style.width, self.style.height = self.font.size(self.value)
def paint(self,s):
s.blit(self.font.render(self.value, 1, self.style.color),(0,0))
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/misc.py 0000644 0000000 0000000 00000002207 11130023047 021003 0 ustar root root from const import *
import widget
import app
class ProgressBar(widget.Widget):
"""A progress bar.
ProgressBar(value,min,max)
w = gui.ProgressBar(0,0,100)
w.value = 25
"""
def __init__(self,value,min,max,**params):
params.setdefault('cls','progressbar')
widget.Widget.__init__(self,**params)
self.min,self.max,self.value = min,max,value
def paint(self,s):
r = pygame.rect.Rect(0,0,self.rect.w,self.rect.h)
r.w = r.w*(self.value-self.min)/(self.max-self.min)
self.bar = r
app.App.app.theme.render(s,self.style.bar,r)
def __setattr__(self,k,v):
if k == 'value':
v = int(v)
v = max(v,self.min)
v = min(v,self.max)
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint() python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/style.py 0000644 0000000 0000000 00000002640 11130023047 021211 0 ustar root root """
"""
class Style:
"""The class used by widget for the widget.style
This object is used mainly as a dictionary, accessed via widget.style.attr, as opposed to widget.style['attr']. It automatically grabs information from the theme via value = theme.get(widget.cls,widget.pcls,attr).
""" def __init__(self,o,dict): self.obj = o for k,v in dict.items(): self.__dict__[k]=v self._cache = {} def __getattr__(self,k): key = self.obj.cls,self.obj.pcls,k if key not in self._cache: #import app #self._cache[key] = app.App.app.theme.get(self.obj.cls, self.obj.pcls, k) self._cache[key] = Style_get(self.obj.cls,self.obj.pcls,k) v = self._cache[key] if k in ( 'border_top','border_right','border_bottom','border_left', 'padding_top','padding_right','padding_bottom','padding_left', 'margin_top','margin_right','margin_bottom','margin_left', 'align','valign','width','height', ): self.__dict__[k] = v return v def __setattr__(self,k,v): self.__dict__[k] = v Style_cache = {} def Style_get(cls,pcls,k): key = cls,pcls,k if key not in Style_cache: import app Style_cache[key] = app.App.app.theme.get(cls,pcls,k) return Style_cache[key] python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/select.py 0000644 0000000 0000000 00000013443 11130023047 021333 0 ustar root root """ """ from const import * import table import basic, button class Select(table.Table): """A select input.Select(value=None)
w = Select(value="goats")
w.add("Cats","cats")
w.add("Goats","goats")
w.add("Dogs","Dogs")
w.value = 'dogs' #changes the value from goats to dogs
"""
def __init__(self,value=None,**params):
params.setdefault('cls','select')
table.Table.__init__(self,**params)
self.top_selected = button.Button(cls=self.cls+".selected")
table.Table.add(self,self.top_selected) #,hexpand=1,vexpand=1)#,0,0)
self.top_selected.value = basic.Label(" ",cls=self.cls+".option.label")
self.top_arrow = button.Button(basic.Image(self.style.arrow),cls=self.cls+".arrow")
table.Table.add(self,self.top_arrow) #,hexpand=1,vexpand=1) #,1,0)
self.options = table.Table() #style={'border':3})
self.options_first = None
self.options.tr()
self.spacer_top = basic.Spacer(0,0)
self.options.add(self.spacer_top)
self.options.tr()
self._options = table.Table(cls=self.cls+".options")
self.options.add(self._options)
self.options.tr()
self.spacer_bottom = basic.Spacer(0,0)
self.options.add(self.spacer_bottom)
self.options.connect(BLUR,self._close,None)
self.spacer_top.connect(CLICK,self._close,None)
self.spacer_bottom.connect(CLICK,self._close,None)
self.values = []
self.value = value
def resize(self,width=None,height=None):
max_w,max_h = 0,0
for w in self._options.widgets:
w.rect.w,w.rect.h = w.resize()
max_w,max_h = max(max_w,w.rect.w),max(max_h,w.rect.h)
#xt,xr,xb,xl = self.top_selected.getspacing()
self.top_selected.style.width = max_w #+ xl + xr
self.top_selected.style.height = max_h #+ xt + xb
self.top_arrow.connect(CLICK,self._open,None)
self.top_selected.connect(CLICK,self._open,None)
w,h = table.Table.resize(self,width,height)
self.spacer_top.style.width, self.spacer_top.style.height = w,h
self.spacer_bottom.style.width, self.spacer_bottom.style.height = w,h
self._options.style.width = w
#HACK: sort of, but not a big one..
self._options.resize()
return w,h
def _open(self,value):
sh = self.rect.h #spacer height
opts = self.options
self.spacer_top.style.height = 0
self.spacer_bottom.style.height = 0
opts.rect.w, opts.rect.h = opts.resize()
h = opts.rect.h
y = self.rect.y
c = self.container
while hasattr(c,'container'):
y += c.rect.y
if c.container == None: break
c = c.container
if y + sh + h <= c.rect.h: #down
self.spacer_top.style.height = sh
dy = self.rect.y
else: #up
self.spacer_bottom.style.height = sh
dy = self.rect.y - h
opts.rect.w, opts.rect.h = opts.resize()
self.container.open(opts,self.rect.x,dy)
self.options_first.focus()
def _close(self,value):
# print 'my close!'
self.options.close()
self.top_selected.focus()
# self.blur()
# self.focus()
# print self.container.myfocus == self
def _setvalue(self,value):
self.value = value._value
if hasattr(self,'container'):
#self.chsize()
#HACK: improper use of resize()
#self.resize() #to recenter the new value, etc.
pass
# #self._resize()
self._close(None)
#self.repaint() #this will happen anyways
def __setattr__(self,k,v):
mywidget = None
if k == 'value':
for w in self.values:
if w._value == v:
mywidget = w
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
if k == 'value':
if not mywidget:
mywidget = basic.Label(" ",cls=self.cls+".option.label")
self.top_selected.value = mywidget
def add(self,w,value=None):
"""Add a widget, value item to the Select.
Select.add(widget,value=None)
w = Select()
w.add("Goat") #adds a Label
w.add("Goat","goat") #adds a Label with the value goat
w.add(gui.Label("Cuzco"),"goat") #adds a Label with value goat
"""
if type(w) == str: w = basic.Label(w,cls=self.cls+".option.label")
w.style.align = -1
b = button.Button(w,cls=self.cls+".option")
b.connect(CLICK,self._setvalue,w)
#b = w
#w.cls = self.cls+".option"
#w.cls = self.cls+".option"
self._options.tr()
self._options.add(b) #,align=-1)
if self.options_first == None:
self.options_first = b
#self._options.td(b, align=-1, cls=self.cls+".option")
#self._options.td(_List_Item(w,value=value),align=-1)
if value != None: w._value = value
else: w._value = w
if self.value == w._value:
self.top_selected.value = w
self.values.append(w)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/area.py 0000644 0000000 0000000 00000036770 11130023047 020774 0 ustar root root """
"""
import os
from const import *
import surface
import container, table
import group
import basic, button, slider
class SlideBox(container.Container):
"""A scrollable area with no scrollbars.
SlideBox(widget,width,height)
c = SlideBox(w,100,100)
c.offset = (10,10)
c.repaint()
"""
def __init__(self, widget, width, height, **params):
params.setdefault('width', width)
params.setdefault('height', height)
container.Container.__init__(self, **params)
self.offset = [0, 0]
self.widget = widget
def __setattr__(self,k,v):
if k == 'widget':
if hasattr(self,'widget'):
self.remove(self.widget)
self.add(v,0,0)
self.__dict__[k] = v
def paint(self, s):
#if not hasattr(self,'surface'):
self.surface = pygame.Surface((self.max_rect.w,self.max_rect.h),0,s)
#self.surface.fill((0,0,0,0))
import app
app.App.app.theme.render(self.surface,self.style.background,pygame.Rect(0,0,self.max_rect.w,self.max_rect.h))
self.bkgr = pygame.Surface((s.get_width(),s.get_height()),0,s)
self.bkgr.blit(s,(0,0))
container.Container.paint(self,self.surface)
s.blit(self.surface,(-self.offset[0],-self.offset[1]))
self._offset = self.offset[:]
return
def paint_for_when_pygame_supports_other_tricks(self,s):
#this would be ideal if pygame had support for it!
#and if pgu also had a paint(self,s,rect) method to paint small parts
sr = (self.offset[0],self.offset[1],self.max_rect.w,self.max_rect.h)
cr = (-self.offset[0],-self.offset[1],s.get_width(),s.get_height())
s2 = s.subsurface(sr)
s2.set_clip(cr)
container.Container.paint(self,s2)
def proxy_paint(self, s):
container.Container.paint(self, surface.ProxySurface(parent=None,
rect=self.max_rect,
real_surface=s,
offset=self.offset))
def update(self, s):
rects = container.Container.update(self,self.surface)
rets = []
s_rect = pygame.Rect(0,0,s.get_width(),s.get_height())
if self.offset == self._offset:
for r in rects:
r2 = r.move((-self.offset[0],-self.offset[1]))
if r2.colliderect(s_rect):
s.blit(self.surface.subsurface(r),r2)
rets.append(r2)
else:
s.blit(self.bkgr,(0,0))
sub = pygame.Rect(self.offset[0],self.offset[1],min(s.get_width(),self.max_rect.w-self.offset[0]),min(s.get_height(),self.max_rect.h-self.offset[1]))
# print sub
# print self.surface.get_width(),self.surface.get_height()
# print s.get_width(),s.get_height()
# print self.offset
# print self.style.width,self.style.height
s.blit(self.surface.subsurface(sub),(0,0))
rets.append(s_rect)
self._offset = self.offset[:]
return rets
def proxy_update(self, s):
rects = container.Container.update(self, surface.ProxySurface(parent=None,
rect=self.max_rect,
real_surface=s,
offset=self.offset))
result = []
for r in rects: result.append(pygame.Rect(r).move(self.offset))
return result
def resize(self, width=None, height=None):
container.Container.resize(self)
self.max_rect = pygame.Rect(self.widget.rect)
#self.max_rect.w = max(self.max_rect.w,self.style.width)
#self.max_rect.h = max(self.max_rect.h,self.style.height)
return self.style.width,self.style.height
#self.rect = pygame.Rect(self.rect[0], self.rect[1], self.style.width, self.style.height)
def event(self, e):
if e.type in [MOUSEBUTTONDOWN, MOUSEBUTTONUP, MOUSEMOTION]:
pos = (e.pos[0] + self.offset[0], e.pos[1] + self.offset[1])
if self.max_rect.collidepoint(pos):
e_params = {'pos': pos }
if e.type == MOUSEMOTION:
e_params['buttons'] = e.buttons
e_params['rel'] = e.rel
else:
e_params['button'] = e.button
e = pygame.event.Event(e.type, e_params)
container.Container.event(self, e)
#class SlideBox(Area):
# def __init__(self,*args,**params):
# print 'gui.SlideBox','Scheduled to be renamed to Area.'
# Area.__init__(self,*args,**params)
class ScrollArea(table.Table):
"""A scrollable area with scrollbars.
ScrollArea(widget,width,height,hscrollbar=True)
This widget can be a form element, it has a value set to whatever item is selected.
List(width,height)""" def _change(self, value): self.value = self.group.value self.send(CHANGE) def __init__(self, width, height, **params): params.setdefault('cls', 'list') self.table = table.Table(width=width) ScrollArea.__init__(self, self.table, width, height,hscrollbar=False ,**params) self.items = [] g = group.Group() self.group = g g.connect(CHANGE,self._change,None) self.value = self.group.value = None self.add = self._add self.remove = self._remove def clear(self): """Clear the list.
List.clear()""" self.items = [] self.group = group.Group() self.group.connect(CHANGE,self._change,None) self.table.clear() self.set_vertical_scroll(0) self.blur(self.myfocus) def _docs(self): #HACK: nasty hack to get the docs in "my way" def add(self, label, image=None, value=None): """Add an item to the list.
List.add(label,image=None,value=None)
List.remove(value)
Input(value="",size=20)
w = Input(value="Cuzco the Goat",size=20)
w = Input("Marbles")
"""
def __init__(self,value="",size=20,**params):
params.setdefault('cls','input')
widget.Widget.__init__(self,**params)
self.value = value
self.pos = len(str(value))
self.vpos = 0
self.font = self.style.font
w,h = self.font.size("e"*size)
if not self.style.height: self.style.height = h
if not self.style.width: self.style.width = w
#self.style.height = max(self.style.height,h)
#self.style.width = max(self.style.width,w)
#self.rect.w=w+self.style.padding_left+self.style.padding_right;
#self.rect.h=h+self.style.padding_top+self.style.padding_bottom;
def paint(self,s):
r = pygame.Rect(0,0,self.rect.w,self.rect.h)
cs = 2 #NOTE: should be in a style
w,h = self.font.size(self.value[0:self.pos])
x = w-self.vpos
if x < 0: self.vpos -= -x
if x+cs > s.get_width(): self.vpos += x+cs-s.get_width()
s.blit(self.font.render(self.value, 1, self.style.color),(-self.vpos,0))
if self.container.myfocus is self:
w,h = self.font.size(self.value[0:self.pos])
r.x = w-self.vpos
r.w = cs
r.h = h
s.fill(self.style.color,r)
def _setvalue(self,v):
self.__dict__['value'] = v
self.send(CHANGE)
def event(self,e):
used = None
if e.type == KEYDOWN:
if e.key == K_BACKSPACE:
if self.pos:
self._setvalue(self.value[:self.pos-1] + self.value[self.pos:])
self.pos -= 1
elif e.key == K_DELETE:
if len(self.value) > self.pos:
self._setvalue(self.value[:self.pos] + self.value[self.pos+1:])
elif e.key == K_HOME:
self.pos = 0
elif e.key == K_END:
self.pos = len(self.value)
elif e.key == K_LEFT:
if self.pos > 0: self.pos -= 1
used = True
elif e.key == K_RIGHT:
if self.pos < len(self.value): self.pos += 1
used = True
elif e.key == K_RETURN:
self.next()
elif e.key == K_TAB:
pass
else:
#c = str(e.unicode)
try:
c = (e.unicode).encode('latin-1')
if c:
self._setvalue(self.value[:self.pos] + c + self.value[self.pos:])
self.pos += 1
except: #ignore weird characters
pass
self.repaint()
elif e.type == FOCUS:
self.repaint()
elif e.type == BLUR:
self.repaint()
self.pcls = ""
if self.container.myfocus is self: self.pcls = "focus"
return used
def __setattr__(self,k,v):
if k == 'value':
if v == None: v = ''
v = str(v)
self.pos = len(v)
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
class Password(Input):
"""A password input, text is *-ed out.
Password(value="",size=20)
w = Password(value="password",size=20)
w = Password("53[r3+")
"""
def paint(self,s):
hidden="*"
show=len(self.value)*hidden
#print "self.value:",self.value
if self.pos == None: self.pos = len(self.value)
r = pygame.Rect(0,0,self.rect.w,self.rect.h)
cs = 2 #NOTE: should be in a style
w,h = self.font.size(show)
x = w-self.vpos
if x < 0: self.vpos -= -x
if x+cs > s.get_width(): self.vpos += x+cs-s.get_width()
s.blit(self.font.render(show, 1, self.style.color),(-self.vpos,0))
if self.container.myfocus is self:
#w,h = self.font.size(self.value[0:self.pos])
w,h = self.font.size(show[0:self.pos])
r.x = w-self.vpos
r.w = cs
r.h = h
s.fill(self.style.color,r)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/basic.py 0000644 0000000 0000000 00000005436 11130023047 021140 0 ustar root root """These widgets are all grouped together because they are non-interactive widgets.
"""
import pygame
from const import *
import widget
class Spacer(widget.Widget):
"""A invisible space.
Spacer(width,height)""" def __init__(self,width,height,**params): params.setdefault('focusable',False) widget.Widget.__init__(self,width=width,height=height,**params) class Color(widget.Widget): """A block of color.
The color can be changed at run-time.
Color(value=None)Example
c = Color()
c.value = (255,0,0)
c.value = (0,255,0)
"""
def __init__(self,value=None,**params):
params.setdefault('focusable',False)
if value != None: params['value']=value
widget.Widget.__init__(self,**params)
def paint(self,s):
if hasattr(self,'value'): s.fill(self.value)
def __setattr__(self,k,v):
if k == 'value' and type(v) == str: v = pygame.Color(v)
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
class Label(widget.Widget):
"""A text label.
Label(value)
w = Label(value="I own a rubber chicken!")
w = Label("3 rubber chickens")
"""
def __init__(self,value,**params):
params.setdefault('focusable',False)
params.setdefault('cls','label')
widget.Widget.__init__(self,**params)
self.value = value
self.font = self.style.font
self.style.width, self.style.height = self.font.size(self.value)
def paint(self,s):
s.blit(self.font.render(self.value, 1, self.style.color),(0,0))
class Image(widget.Widget):
"""An image.
Image(value)
from pygame
gui specific
Menus(data)
data = [
('File/Save',fnc_save,None),
('File/New',fnc_new,None),
('Edit/Copy',fnc_copy,None),
('Edit/Cut',fnc_cut,None),
('Help/About',fnc_help,help_about_content),
('Help/Reference',fnc_help,help_reference_content),
]
w = Menus(data)
"""
def __init__(self,data,menu_cls='menu',**params):
params.setdefault('cls','menus')
table.Table.__init__(self,**params)
self.value = None
n,m,mt = 0,None,None
for path,cmd,value in data:
parts = path.split("/")
if parts[0] != mt:
mt = parts[0]
m = _Menu(self,basic.Label(mt,cls=menu_cls+".label"),cls=menu_cls)
self.add(m,n,0)
n += 1
m.add(basic.Label(parts[1],cls=m.cls+".option.label"),cmd,value)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/keysym.py 0000644 0000000 0000000 00000004153 11130023047 021373 0 ustar root root """
"""
import pygame
from pygame.locals import *
from const import *
import widget
class Keysym(widget.Widget):
"""A keysym input.
This widget records the keysym of the key pressed while this widget is in focus.
Keysym(value=None)
- value
- initial keysym, see pygame keysyms
Example
w = Input(value=pygame.locals.K_g)
w = Input(pygame.locals.K_g)
w = Input()
"""
def __init__(self,value=None,**params):
params.setdefault('cls','keysym')
widget.Widget.__init__(self,**params)
self.value = value
self.font = self.style.font
w,h = self.font.size("Right Super") #"Right Shift")
self.style.width,self.style.height = w,h
#self.rect.w=w+self.style.padding_left+self.style.padding_right
#self.rect.h=h+self.style.padding_top+self.style.padding_bottom
def event(self,e):
used = None
if e.type == FOCUS or e.type == BLUR: self.repaint()
elif e.type == KEYDOWN:
if e.key != K_TAB:
self.value = e.key
self.repaint()
self.send(CHANGE)
used = True
self.next()
self.pcls = ""
if self.container.myfocus is self: self.pcls = "focus"
return used
def paint(self,s):
r = pygame.rect.Rect(0,0,self.rect.w,self.rect.h)
#render_box(s,self.style.background,r)
if self.value == None: return
name = ""
for p in pygame.key.name(self.value).split(): name += p.capitalize()+" "
#r.x = self.style.padding_left;
#r.y = self.style.padding_bottom;
s.blit(self.style.font.render(name, 1, self.style.color), r)
def __setattr__(self,k,v):
if k == 'value' and v != None:
v = int(v)
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/widget.py 0000644 0000000 0000000 00000024474 11130023047 021345 0 ustar root root """
"""
import pygame
import style
class Widget:
"""Template object - base for all widgets.
Widget(**params)
A number of optional params may be passed to the Widget initializer.
- decorate
- defaults to True. If true, will call theme.decorate(self) to allow the theme a chance to decorate the widget.
- style
- a dict of style parameters.
- x, y, width, height
- position and size parameters, passed along to style
- align, valign
- alignment parameters, passed along to style
- font, color, background
- other common parameters that are passed along to style
- cls
- class name as used by Theme
- name
- name of widget as used by Form. If set, will call form.add(self,name) to add the widget to the most recently created Form.
- focusable
- True if this widget can receive focus via Tab, etc. Defaults to True.
- disabled
- True of this widget is disabled. Defaults to False.
- value
- initial value
Example - Creating your own Widget
This example shows which methods are template methods.
class Draw(gui.Widget):
def paint(self,s):
#paint the pygame.Surface
return
def update(self,s):
#update the pygame.Surface and return the update rects
return [pygame.Rect(0,0,self.rect.w,self.rect.h)]
def event(self,e):
#handle the pygame.Event
return
def resize(self,width=None,height=None):
#return the width and height of this widget
return 256,256
"""
def __init__(self,**params):
#object.Object.__init__(self)
self.connects = {}
params.setdefault('decorate',True)
params.setdefault('style',{})
params.setdefault('focusable',True)
params.setdefault('disabled',False)
self.focusable = params['focusable']
self.disabled = params['disabled']
self.rect = pygame.Rect(params.get('x',0),params.get('y',0),params.get('width',0),params.get('height',0))
s = params['style']
#some of this is a bit "theme-ish" but it is very handy, so these
#things don't have to be put directly into the style.
for att in ('align','valign','x','y','width','height','color','font','background'):
if att in params: s[att] = params[att]
self.style = style.Style(self,s)
self.cls = 'default'
if 'cls' in params: self.cls = params['cls']
if 'name' in params:
import form
self.name = params['name']
if hasattr(form.Form,'form') and form.Form.form != None:
form.Form.form.add(self)
self.form = form.Form.form
if 'value' in params: self.value = params['value']
self.pcls = ""
if params['decorate'] != False:
import app
if not hasattr(app.App,'app'):
print 'gui.widget: creating an App'
app.App.app = app.App()
app.App.app.theme.decorate(self,params['decorate'])
def focus(self):
"""Focus this Widget.
Widget.focus()
"""
if getattr(self,'container',None) != None:
if self.container.myfocus != self: ## by Gal Koren
self.container.focus(self)
def blur(self):
"""Blur this Widget.
Widget.blur()
"""
if getattr(self,'container',None) != None: self.container.blur(self)
def open(self):
"""Open this Widget as a modal dialog.
Widget.open()
"""
if getattr(self,'container',None) != None: self.container.open(self)
def close(self):
"""Close this Widget (if it is a modal dialog.)
Widget.close()
"""
if getattr(self,'container',None) != None: self.container.close(self)
def resize(self,width=None,height=None):
"""Template method - return the size and width of this widget.
Responsible for also resizing all sub-widgets.
Widget.resize(width,height): return width,height
- width
- suggested width
- height
- suggested height
If not overridden, will return self.style.width, self.style.height
"""
return self.style.width, self.style.height
def chsize(self):
"""Change the size of this widget.
Calling this method will cause a resize on all the widgets,
including this one.
Widget.chsize()
"""
if not hasattr(self,'_painted'): return
if not hasattr(self,'container'): return
import app
if hasattr(app.App,'app'):
if app.App.app._chsize: return
app.App.app.chsize()
return
#if hasattr(app.App,'app'):
# w,h = self.rect.w,self.rect.h
# w2,h2 = self.resize()
# if w2 != w or h2 != h:
# app.App.app.chsize()
# else:
# self.repaint()
def update(self,s):
"""Template method - update the surface
Widget.update(s): return list of pygame.Rect(s)
- s
- pygame.Surface to update
return - a list of the updated areas as pygame.Rect(s).
"""
return
def paint(self,s):
"""Template method - paint the surface
Widget.paint(s)
- s
- pygame.Surface to paint
"""
return
def repaint(self):
"""Request a repaint of this Widget.
Widget.repaint()
"""
if getattr(self,'container',None) != None: self.container.repaint(self)
def repaintall(self):
"""Request a repaint of all Widgets.
Widget.repaintall()
"""
if getattr(self,'container',None) != None: self.container.repaintall()
def reupdate(self):
"""Request a reupdate of this Widget
Widget.reupdate()
"""
if getattr(self,'container',None) != None: self.container.reupdate(self)
def next(self):
"""Pass focus to next Widget.
Widget order determined by the order they were added to their container.
Widget.next()
"""
if getattr(self,'container',None) != None: self.container.next(self)
def previous(self):
"""Pass focus to previous Widget.
Widget order determined by the order they were added to their container.
Widget.previous()
"""
if getattr(self,'container',None) != None: self.container.previous(self)
def get_abs_rect(self):
"""Get the absolute rect of this widget on the App screen
Widget.get_abs_rect(): return pygame.Rect
"""
x, y = self.rect.x , self.rect.y
x += self._rect_content.x
y += self._rect_content.y
c = getattr(self,'container',None)
while c:
x += c.rect.x
y += c.rect.y
if hasattr(c,'_rect_content'):
x += c._rect_content.x
y += c._rect_content.y
c = getattr(c,'container',None)
return pygame.Rect(x, y, self.rect.w, self.rect.h)
def connect(self,code,fnc,*values):
"""Connect a event code to a callback function.
There may only be one callback per event code.
Object.connect(code,fnc,value)
- code
- event type [[gui-const]]
- fnc
- callback function
- *values
- values to pass to callback. Please note that callbacks may also have "magicaly" parameters. Such as:
- _event
- receive the event
- _code
- receive the event code
- _widget
- receive the sending widget
Example
def onclick(value):
print 'click',value
w = Button("PGU!")
w.connect(gui.CLICK,onclick,'PGU Button Clicked')
"""
self.connects[code] = {'fnc':fnc,'values':values}
def send(self,code,event=None):
"""Send a code, event callback trigger.
Object.send(code,event=None)
- code
- event code
- event
- event
"""
if code in self.connects:
con = self.connects[code]
#con['fnc'](*con['values'])
fnc = con['fnc']
values = list(con['values'])
nargs = fnc.func_code.co_argcount
names = list(fnc.func_code.co_varnames)[:nargs]
if hasattr(fnc,'im_class'): names.pop(0)
args = []
magic = {'_event':event,'_code':code,'_widget':self}
for name in names:
if name in magic.keys():
args.append(magic[name])
elif len(values):
args.append(values.pop(0))
else:
break
args.extend(values)
fnc(*args)
def _event(self,e):
if self.disabled: return
self.send(e.type,e)
return self.event(e)
# return
# import app
# if hasattr(app.App,'app'):
# app.App.app.events.append((self,e))
def event(self,e):
"""Template method - called when an event is passed to this object.
Please note that if you use an event, returning the value True
will stop parent containers from also using the event. (For example, if
your widget handles TABs or arrow keys, and you don't want those to
also alter the focus.)
- e
- event
"""
return
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/group.py 0000644 0000000 0000000 00000002167 11130023047 021211 0 ustar root root """
"""
from const import *
import widget
class Group(widget.Widget):
"""An object for grouping together Form elements.
Group(name=None,value=None)
- name
- name as used in the Form
- value
- values that are currently selected in the group
See [[gui-button]] for several examples.
When the value changes, an gui.CHANGE event is sent.
Although note, that when the value is a list, it may have to be sent by hand via
g.send(gui.CHANGE)
"""
def __init__(self,name=None,value=None):
widget.Widget.__init__(self,name=name,value=value)
self.widgets = []
def add(self,w):
"""Add a widget to this group.
Group.add(w)
"""
self.widgets.append(w)
def __setattr__(self,k,v):
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k] = v
if k == 'value' and _v != NOATTR and _v != v:
self._change()
def _change(self):
self.send(CHANGE)
for w in self.widgets:
w.repaint()
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/container.py 0000644 0000000 0000000 00000035447 11130023047 022046 0 ustar root root """
"""
import pygame
from pygame.locals import *
from const import *
import widget, surface
class Container(widget.Widget):
"""The base container widget, can be used as a template as well as stand alone.
Container()
"""
def __init__(self,**params):
widget.Widget.__init__(self,**params)
self.myfocus = None
self.mywindow = None
self.myhover = None
#self.background = 0
self.widgets = []
self.windows = []
self.toupdate = {}
self.topaint = {}
def update(self,s):
updates = []
if self.myfocus: self.toupdate[self.myfocus] = self.myfocus
for w in self.topaint:
if w is self.mywindow:
continue
else:
sub = surface.subsurface(s,w.rect)
sub.blit(w._container_bkgr,(0,0))
w.paint(sub)
updates.append(pygame.rect.Rect(w.rect))
for w in self.toupdate:
if w is self.mywindow:
continue
else:
us = w.update(surface.subsurface(s,w.rect))
if us:
for u in us:
updates.append(pygame.rect.Rect(u.x + w.rect.x,u.y+w.rect.y,u.w,u.h))
for w in self.topaint:
if w is self.mywindow:
w.paint(self.top_surface(s,w))
updates.append(pygame.rect.Rect(w.rect))
else:
continue
for w in self.toupdate:
if w is self.mywindow:
us = w.update(self.top_surface(s,w))
else:
continue
if us:
for u in us:
updates.append(pygame.rect.Rect(u.x + w.rect.x,u.y+w.rect.y,u.w,u.h))
self.topaint = {}
self.toupdate = {}
return updates
def repaint(self,w=None):
if not w:
return widget.Widget.repaint(self)
self.topaint[w] = w
self.reupdate()
def reupdate(self,w=None):
if not w:
return widget.Widget.reupdate(self)
self.toupdate[w] = w
self.reupdate()
def paint(self,s):
self.toupdate = {}
self.topaint = {}
for w in self.widgets:
ok = False
try:
sub = surface.subsurface(s,w.rect)
ok = True
except:
print 'container.paint(): %s not in %s'%(w.__class__.__name__,self.__class__.__name__)
print s.get_width(),s.get_height(),w.rect
ok = False
if ok:
if not (hasattr(w,'_container_bkgr') and w._container_bkgr.get_width() == sub.get_width() and w._container_bkgr.get_height() == sub.get_height()):
w._container_bkgr = sub.copy()
w._container_bkgr.fill((0,0,0,0))
w._container_bkgr.blit(sub,(0,0))
w.paint(sub)
for w in self.windows:
w.paint(self.top_surface(s,w))
def top_surface(self,s,w):
x,y = s.get_abs_offset()
s = s.get_abs_parent()
return surface.subsurface(s,(x+w.rect.x,y+w.rect.y,w.rect.w,w.rect.h))
def event(self,e):
used = False
if self.mywindow and e.type == MOUSEBUTTONDOWN:
w = self.mywindow
if self.myfocus is w:
if not w.rect.collidepoint(e.pos): self.blur(w)
if not self.myfocus:
if w.rect.collidepoint(e.pos): self.focus(w)
if not self.mywindow:
#### by Gal Koren
##
## if e.type == FOCUS:
if e.type == FOCUS and not self.myfocus:
#self.first()
pass
elif e.type == EXIT:
if self.myhover: self.exit(self.myhover)
elif e.type == BLUR:
if self.myfocus: self.blur(self.myfocus)
elif e.type == MOUSEBUTTONDOWN:
h = None
for w in self.widgets:
if not w.disabled: #focusable not considered, since that is only for tabs
if w.rect.collidepoint(e.pos):
h = w
if self.myfocus is not w: self.focus(w)
if not h and self.myfocus:
self.blur(self.myfocus)
elif e.type == MOUSEMOTION:
if 1 in e.buttons:
if self.myfocus: ws = [self.myfocus]
else: ws = []
else: ws = self.widgets
h = None
for w in ws:
if w.rect.collidepoint(e.pos):
h = w
if self.myhover is not w: self.enter(w)
if not h and self.myhover:
self.exit(self.myhover)
w = self.myhover
if w and w is not self.myfocus:
sub = pygame.event.Event(e.type,{
'buttons':e.buttons,
'pos':(e.pos[0]-w.rect.x,e.pos[1]-w.rect.y),
'rel':e.rel})
used = w._event(sub)
w = self.myfocus
if w:
sub = e
if e.type == MOUSEBUTTONUP or e.type == MOUSEBUTTONDOWN:
sub = pygame.event.Event(e.type,{
'button':e.button,
'pos':(e.pos[0]-w.rect.x,e.pos[1]-w.rect.y)})
used = w._event(sub)
elif e.type == CLICK and self.myhover is w:
sub = pygame.event.Event(e.type,{
'button':e.button,
'pos':(e.pos[0]-w.rect.x,e.pos[1]-w.rect.y)})
used = w._event(sub)
elif e.type == CLICK: #a dead click
pass
elif e.type == MOUSEMOTION:
sub = pygame.event.Event(e.type,{
'buttons':e.buttons,
'pos':(e.pos[0]-w.rect.x,e.pos[1]-w.rect.y),
'rel':e.rel})
used = w._event(sub)
else:
used = w._event(sub)
if not used:
if e.type is KEYDOWN:
if e.key is K_TAB and self.myfocus:
if (e.mod&KMOD_SHIFT) == 0:
self.myfocus.next()
else:
self.myfocus.previous()
return True
elif e.key == K_UP:
self._move_focus(0,-1)
return True
elif e.key == K_RIGHT:
self._move_focus(1,0)
return True
elif e.key == K_DOWN:
self._move_focus(0,1)
return True
elif e.key == K_LEFT:
self._move_focus(-1,0)
return True
return used
def _move_focus(self,dx_,dy_):
myfocus = self.myfocus
if not self.myfocus: return
from pgu.gui import App
widgets = self._get_widgets(App.app)
#if myfocus not in widgets: return
#widgets.remove(myfocus)
if myfocus in widgets:
widgets.remove(myfocus)
rect = myfocus.get_abs_rect()
fx,fy = rect.centerx,rect.centery
def sign(v):
if v < 0: return -1
if v > 0: return 1
return 0
dist = []
for w in widgets:
wrect = w.get_abs_rect()
wx,wy = wrect.centerx,wrect.centery
dx,dy = wx-fx,wy-fy
if dx_ > 0 and wrect.left < rect.right: continue
if dx_ < 0 and wrect.right > rect.left: continue
if dy_ > 0 and wrect.top < rect.bottom: continue
if dy_ < 0 and wrect.bottom > rect.top: continue
dist.append((dx*dx+dy*dy,w))
if not len(dist): return
dist.sort()
d,w = dist.pop(0)
w.focus()
def _get_widgets(self,c):
widgets = []
if c.mywindow:
widgets.extend(self._get_widgets(c.mywindow))
else:
for w in c.widgets:
if isinstance(w,Container):
widgets.extend(self._get_widgets(w))
elif not w.disabled and w.focusable:
widgets.append(w)
return widgets
def remove(self,w):
"""Remove a widget from the container.
Container.remove(w)
"""
self.blur(w)
self.widgets.remove(w)
#self.repaint()
self.chsize()
def add(self,w,x,y):
"""Add a widget to the container.
Container.add(w,x,y)
- x, y
- position of the widget
"""
w.style.x = x
w.style.y = y
w.container = self
#NOTE: this might fix it, sort of...
#but the thing is, we don't really want to resize
#something if it is going to get resized again later
#for no reason...
#w.rect.x,w.rect.y = w.style.x,w.style.y
#w.rect.w, w.rect.h = w.resize()
self.widgets.append(w)
self.chsize()
def open(self,w=None,x=None,y=None):
from app import App #HACK: I import it here to prevent circular importing
if not w:
if (not hasattr(self,'container') or not self.container) and self is not App.app:
self.container = App.app
#print 'top level open'
return widget.Widget.open(self)
if self.container:
if x != None: return self.container.open(w,self.rect.x+x,self.rect.y+y)
return self.container.open(w)
w.container = self
if w.rect.w == 0 or w.rect.h == 0: #this might be okay, not sure if needed.
#_chsize = App.app._chsize #HACK: we don't want this resize to trigger a chsize.
w.rect.w,w.rect.h = w.resize()
#App.app._chsize = _chsize
if x == None or y == None: #auto center the window
#w.style.x,w.style.y = 0,0
w.rect.x = (self.rect.w-w.rect.w)/2
w.rect.y = (self.rect.h-w.rect.h)/2
#w.resize()
#w._resize(self.rect.w,self.rect.h)
else: #show it where we want it
w.rect.x = x
w.rect.y = y
#w._resize()
self.windows.append(w)
self.mywindow = w
self.focus(w)
self.repaint(w)
w.send(OPEN)
def close(self,w=None):
if not w:
return widget.Widget.close(self)
if self.container: #make sure we're in the App
return self.container.close(w)
if self.myfocus is w: self.blur(w)
if w not in self.windows: return #no need to remove it twice! happens.
self.windows.remove(w)
self.mywindow = None
if self.windows:
self.mywindow = self.windows[-1]
self.focus(self.mywindow)
if not self.mywindow:
self.myfocus = self.widget #HACK: should be done fancier, i think..
if not self.myhover:
self.enter(self.widget)
self.repaintall()
w.send(CLOSE)
def focus(self,w=None):
widget.Widget.focus(self) ### by Gal koren
# if not w:
# return widget.Widget.focus(self)
if not w: return
if self.myfocus: self.blur(self.myfocus)
if self.myhover is not w: self.enter(w)
self.myfocus = w
w._event(pygame.event.Event(FOCUS))
#print self.myfocus,self.myfocus.__class__.__name__
def blur(self,w=None):
if not w:
return widget.Widget.blur(self)
if self.myfocus is w:
if self.myhover is w: self.exit(w)
self.myfocus = None
w._event(pygame.event.Event(BLUR))
def enter(self,w):
if self.myhover: self.exit(self.myhover)
self.myhover = w
w._event(pygame.event.Event(ENTER))
def exit(self,w):
if self.myhover and self.myhover is w:
self.myhover = None
w._event(pygame.event.Event(EXIT))
# def first(self):
# for w in self.widgets:
# if w.focusable:
# self.focus(w)
# return
# if self.container: self.container.next(self)
# def next(self,w):
# if w not in self.widgets: return #HACK: maybe. this happens in windows for some reason...
#
# for w in self.widgets[self.widgets.index(w)+1:]:
# if w.focusable:
# self.focus(w)
# return
# if self.container: return self.container.next(self)
def _next(self,orig=None):
start = 0
if orig in self.widgets: start = self.widgets.index(orig)+1
for w in self.widgets[start:]:
if not w.disabled and w.focusable:
if isinstance(w,Container):
if w._next():
return True
else:
self.focus(w)
return True
return False
def _previous(self,orig=None):
end = len(self.widgets)
if orig in self.widgets: end = self.widgets.index(orig)
ws = self.widgets[:end]
ws.reverse()
for w in ws:
if not w.disabled and w.focusable:
if isinstance(w,Container):
if w._previous():
return True
else:
self.focus(w)
return True
return False
def next(self,w=None):
if w != None and w not in self.widgets: return #HACK: maybe. this happens in windows for some reason...
if self._next(w): return True
if self.container: return self.container.next(self)
def previous(self,w=None):
if w != None and w not in self.widgets: return #HACK: maybe. this happens in windows for some reason...
if self._previous(w): return True
if self.container: return self.container.previous(self)
def resize(self,width=None,height=None):
#r = self.rect
#r.w,r.h = 0,0
ww,hh = 0,0
if self.style.width: ww = self.style.width
if self.style.height: hh = self.style.height
for w in self.widgets:
#w.rect.w,w.rect.h = 0,0
w.rect.x,w.rect.y = w.style.x,w.style.y
w.rect.w, w.rect.h = w.resize()
#w._resize()
ww = max(ww,w.rect.right)
hh = max(hh,w.rect.bottom)
return ww,hh
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/slider.py 0000644 0000000 0000000 00000023073 11130023047 021336 0 ustar root root """All sliders and scroll bar widgets have the same parameters.
Slider(value,min,max,size)
- value
- initial value
- min
- minimum value
- max
- maximum value
- size
- size of bar in pixels
"""
import pygame
from pygame.locals import *
from const import *
import widget
import app
import table
import basic
_SLIDER_HORIZONTAL = 0
_SLIDER_VERTICAL = 1
class _slider(widget.Widget):
def __init__(self,value,orient,min,max,size,step=1,**params):
params.setdefault('cls','slider')
widget.Widget.__init__(self,**params)
self.min,self.max,self.value,self.orient,self.size,self.step = min,max,value,orient,size,step
def paint(self,s):
self.value = self.value
r = pygame.rect.Rect(0,0,self.style.width,self.style.height)
if self.orient == _SLIDER_HORIZONTAL:
r.x = (self.value-self.min) * (r.w-self.size) / max(1,self.max-self.min);
r.w = self.size;
else:
r.y = (self.value-self.min) * (r.h-self.size) / max(1,self.max-self.min);
r.h = self.size;
self.bar = r
app.App.app.theme.render(s,self.style.bar,r)
def event(self,e):
used = None
r = pygame.rect.Rect(0,0,self.style.width,self.style.height)
adj = 0
if e.type == ENTER: self.repaint()
elif e.type == EXIT: self.repaint()
elif e.type == MOUSEBUTTONDOWN:
if self.bar.collidepoint(e.pos):
self.grab = e.pos[0],e.pos[1]
self.grab_value = self.value
else:
x,y,adj = e.pos[0],e.pos[1],1
self.grab = None
self.repaint()
elif e.type == MOUSEBUTTONUP:
#x,y,adj = e.pos[0],e.pos[1],1
self.repaint()
elif e.type == MOUSEMOTION:
if 1 in e.buttons and self.container.myfocus is self:
if self.grab != None:
rel = e.pos[0]-self.grab[0],e.pos[1]-self.grab[1]
if self.orient == _SLIDER_HORIZONTAL:
d = (r.w - self.size)
if d != 0: self.value = self.grab_value + ((self.max-self.min) * rel[0] / d)
else:
d = (r.h - self.size)
if d != 0: self.value = self.grab_value + ((self.max-self.min) * rel[1] / d)
else:
x,y,adj = e.pos[0],e.pos[1],1
elif e.type is KEYDOWN:
if self.orient == _SLIDER_HORIZONTAL and e.key == K_LEFT:
self.value -= self.step
used = True
elif self.orient == _SLIDER_HORIZONTAL and e.key == K_RIGHT:
self.value += self.step
used = True
elif self.orient == _SLIDER_VERTICAL and e.key == K_UP:
self.value -= self.step
used = True
elif self.orient == _SLIDER_VERTICAL and e.key == K_DOWN:
self.value += self.step
used = True
if adj:
if self.orient == _SLIDER_HORIZONTAL:
d = self.size/2 - (r.w/(self.max-self.min+1))/2
self.value = (x-d) * (self.max-self.min) / (r.w-self.size+1) + self.min
else:
d = self.size/2 - (r.h/(self.max-self.min+1))/2
self.value = (y-d) * (self.max-self.min) / (r.h-self.size+1) + self.min
self.pcls = ""
if self.container.myhover is self: self.pcls = "hover"
if (self.container.myfocus is self and 1 in pygame.mouse.get_pressed()): self.pcls = "down"
return used
def __setattr__(self,k,v):
if k == 'value':
v = int(v)
v = max(v,self.min)
v = min(v,self.max)
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.send(CHANGE)
self.repaint()
if hasattr(self,'size'):
sz = min(self.size,max(self.style.width,self.style.height))
sz = max(sz,min(self.style.width,self.style.height))
self.__dict__['size'] = sz
if hasattr(self,'max') and hasattr(self,'min'):
if self.max < self.min: self.max = self.min
class VSlider(_slider):
"""A verticle slider.
VSlider(value,min,max,size)
"""
def __init__(self,value,min,max,size,step=1,**params):
params.setdefault('cls','vslider')
_slider.__init__(self,value,_SLIDER_VERTICAL,min,max,size,step,**params)
class HSlider(_slider):
"""A horizontal slider.
HSlider(value,min,max,size)
"""
def __init__(self,value,min,max,size,step=1,**params):
params.setdefault('cls','hslider')
_slider.__init__(self,value,_SLIDER_HORIZONTAL,min,max,size,step,**params)
class HScrollBar(table.Table):
"""A horizontal scroll bar.
HScrollBar(value,min,max,size,step=1)
"""
def __init__(self,value,min,max,size,step=1,**params):
params.setdefault('cls','hscrollbar')
table.Table.__init__(self,**params)
self.slider = _slider(value,_SLIDER_HORIZONTAL,min,max,size,step=step,cls=self.cls+'.slider')
self.minus = basic.Image(self.style.minus)
self.minus.connect(MOUSEBUTTONDOWN,self._click,-1)
self.slider.connect(CHANGE,self.send,CHANGE)
self.minus2 = basic.Image(self.style.minus)
self.minus2.connect(MOUSEBUTTONDOWN,self._click,-1)
self.plus = basic.Image(self.style.plus)
self.plus.connect(MOUSEBUTTONDOWN,self._click,1)
self.size = size
def _click(self,value):
self.slider.value += self.slider.step*value
def resize(self,width=None,height=None):
self.clear()
self.tr()
w = self.style.width
h = self.slider.style.height
ww = 0
if w > (h*2 + self.minus.style.width+self.plus.style.width):
self.td(self.minus)
ww += self.minus.style.width
self.td(self.slider)
if w > (h*2 + self.minus.style.width+self.minus2.style.width+self.plus.style.width):
self.td(self.minus2)
ww += self.minus2.style.width
if w > (h*2 + self.minus.style.width+self.plus.style.width):
self.td(self.plus)
ww += self.plus.style.width
#HACK: handle theme sizing properly
from app import App
xt,xr,xb,xl = App.app.theme.getspacing(self.slider)
ww += xr+xl
self.slider.style.width = self.style.width - ww
setattr(self.slider,'size',self.size * self.slider.style.width / max(1,self.style.width))
return table.Table.resize(self,width,height)
def __setattr__(self,k,v):
if k in ('min','max','value','step'):
return setattr(self.slider,k,v)
self.__dict__[k]=v
def __getattr__(self,k):
if k in ('min','max','value','step'):
return getattr(self.slider,k)
return table.Table.__getattr__(self,k) #self.__dict__[k]
class VScrollBar(table.Table):
"""A vertical scroll bar.
VScrollBar(value,min,max,size,step=1)
"""
def __init__(self,value,min,max,size,step=1,**params):
params.setdefault('cls','vscrollbar')
table.Table.__init__(self,**params)
self.minus = basic.Image(self.style.minus)
self.minus.connect(MOUSEBUTTONDOWN,self._click,-1)
self.minus2 = basic.Image(self.style.minus)
self.minus2.connect(MOUSEBUTTONDOWN,self._click,-1)
self.plus = basic.Image(self.style.plus)
self.plus.connect(MOUSEBUTTONDOWN,self._click,1)
self.slider = _slider(value,_SLIDER_VERTICAL,min,max,size,step=step,cls=self.cls+'.slider')
self.slider.connect(CHANGE,self.send,CHANGE)
self.size = size
def _click(self,value):
self.slider.value += self.slider.step*value
def resize(self,width=None,height=None):
self.clear()
h = self.style.height
w = self.slider.style.width
hh = 0
if h > (w*2 + self.minus.style.height+self.plus.style.height):
self.tr()
self.td(self.minus)
hh += self.minus.style.height
self.tr()
self.td(self.slider)
if h > (w*2 + self.minus.style.height+self.minus2.style.height+self.plus.style.height):
self.tr()
self.td(self.minus2)
hh += self.minus2.style.height
if h > (w*2 + self.minus.style.height+self.plus.style.height):
self.tr()
self.td(self.plus)
hh += self.plus.style.height
#HACK: handle theme sizing properly
from app import App
xt,xr,xb,xl = App.app.theme.getspacing(self.slider)
hh += xt+xb
self.slider.style.height = self.style.height - hh
setattr(self.slider,'size',self.size * self.slider.style.height / max(1,self.style.height))
return table.Table.resize(self,width,height)
def __setattr__(self,k,v):
if k in ('min','max','value','step'):
return setattr(self.slider,k,v)
self.__dict__[k]=v
def __getattr__(self,k):
if k in ('min','max','value','step'):
return getattr(self.slider,k)
return table.Table.__getattr__(self,k)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/form.py 0000644 0000000 0000000 00000003711 11130023047 021014 0 ustar root root """
"""
import widget
class Form(widget.Widget):
"""A form that automatically will contain all named widgets.
After a form is created, all named widget that are subsequently created are added
to that form. You may use dict style access to access named widgets.
Form()
Example
f = gui.Form()
w = gui.Input("Phil",name="firstname")
w = gui.Input("Hassey",name="lastname")
print f.results()
print ''
print f.items()
print ''
print f['firstname'].value
print f['lastname'].value
"""
def __init__(self):
widget.Widget.__init__(self,decorate=False)
self._elist = []
self._emap = {}
self._dirty = 0
Form.form = self
def add(self,e,name=None,value=None):
if name != None: e.name = name
if value != None: e.value = value
self._elist.append(e)
self._dirty = 1
def _clean(self):
for e in self._elist[:]:
if not hasattr(e,'name') or e.name == None:
self._elist.remove(e)
self._emap = {}
for e in self._elist:
self._emap[e.name] = e
self._dirty = 0
def __getitem__(self,k):
if self._dirty: self._clean()
return self._emap[k]
def __contains__(self,k):
if self._dirty: self._clean()
if k in self._emap: return True
return False
def results(self):
"""Return a dict of name => values.
Form.results(): return dict
"""
if self._dirty: self._clean()
r = {}
for e in self._elist:
r[e.name] = e.value
return r
def items(self):
"""Return a list of name, value keys.
Form.items(): return list
"""
return self.results().items()
#def start(self):
# Object.start(self,-1)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/readme.txt 0000644 0000000 0000000 00000000144 11130023047 021472 0 ustar root root This is the GUI module from Phil's pyGame Utilities:
http://www.imitationpickles.org/pgu/wiki/index python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/document.py 0000644 0000000 0000000 00000005771 11130023047 021677 0 ustar root root """
"""
import pygame
import container
import layout
class _document_widget:
def __init__(self,w,align=None):
#w.rect.w,w.rect.h = w.resize()
#self.rect = w.rect
self.widget = w
if align != None: self.align = align
class Document(container.Container):
"""A document container contains many widgets strung together in a document format. (How informative!)
Document()
"""
def __init__(self,**params):
params.setdefault('cls','document')
container.Container.__init__(self,**params)
self.layout = layout.Layout(pygame.Rect(0,0,self.rect.w,self.rect.h))
def add(self,e,align=None):
"""Add a widget.
Document.add(e,align=None)
- e
- widget
- align
- alignment (None,-1,0,1)
"""
dw = _document_widget(e,align)
self.layout.add(dw)
e.container = self
e._c_dw = dw
self.widgets.append(e)
self.chsize()
def remove(self,e):
self.layout._widgets.remove(e._c_dw)
self.widgets.remove(e)
self.chsize()
def block(self,align):
"""Start a new block.
Document.block(align)
- align
- alignment of block (-1,0,1)
"""
self.layout.add(align)
def space(self,e):
"""Add a spacer.
Document.space(e)
- e
- a (w,h) size for the spacer
"""
self.layout.add(e)
def br(self,height):
"""Add a line break.
Document.br(height)
- height
- height of line break
"""
self.layout.add((0,height))
def resize(self,width=None,height=None):
if self.style.width: width = self.style.width
if self.style.height: height = self.style.height
for w in self.widgets:
w.rect.w,w.rect.h = w.resize()
if (width != None and w.rect.w > width) or (height != None and w.rect.h > height):
w.rect.w,w.rect.h = w.resize(width,height)
dw = w._c_dw
dw.rect = pygame.Rect(0,0,w.rect.w,w.rect.h)
if width == None: width = 65535
self.layout.rect = pygame.Rect(0,0,width,0)
self.layout.resize()
_max_w = 0
for w in self.widgets:
#xt,xl,xb,xr = w.getspacing()
dw = w._c_dw
w.style.x,w.style.y,w.rect.w,w.rect.h = dw.rect.x,dw.rect.y,dw.rect.w,dw.rect.h
#w.resize()
w.rect.x,w.rect.y = w.style.x,w.style.y
_max_w = max(_max_w,w.rect.right)
#self.rect.w = _max_w #self.layout.rect.w
#self.rect.h = self.layout.rect.h
#print 'document',_max_w,self.layout.rect.h
return _max_w,self.layout.rect.h
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/dialog.py 0000644 0000000 0000000 00000011617 11130023047 021314 0 ustar root root """
"""
import os
from const import *
import table, area
import basic, input, button
class Dialog(table.Table):
"""A dialog window with a title bar and an "close" button on the bar.
Dialog(title,main)
- title
- title widget, usually a label
- main
- main widget, usually a container
Example
title = gui.Label("My Title")
main = gui.Container()
#add stuff to the container...
d = gui.Dialog(title,main)
d.open()
"""
def __init__(self,title,main,**params):
params.setdefault('cls','dialog')
table.Table.__init__(self,**params)
self.tr()
self.td(title,align=-1,cls=self.cls+'.bar')
clos = button.Icon(self.cls+".bar.close")
clos.connect(CLICK,self.close,None)
self.td(clos,align=1,cls=self.cls+'.bar')
self.tr()
self.td(main,colspan=2,cls=self.cls+".main")
# self.tr()
#
#
# t = table.Table(cls=self.cls+".bar")
# t.tr()
# t.td(title)
# clos = button.Icon(self.cls+".bar.close")
# t.td(clos,align=1)
# clos.connect(CLICK,self.close,None)
# self.add(t,0,0)
#
# main.rect.w,main.rect.h = main.resize()
# clos.rect.w,clos.rect.h = clos.resize()
# title.container.style.width = main.rect.w - clos.rect.w
#
# self.tr()
# self.td(main,cls=self.cls+".main")
#
class FileDialog(Dialog):
"""A file picker dialog window.
FileDialog()
Some optional parameters:
- title_txt
- title text
- button_txt
- button text
- path
- initial path
"""
def __init__(self, title_txt="File Browser", button_txt="Okay", cls="dialog", path=None):
cls1 = 'filedialog'
if not path: self.curdir = os.getcwd()
else: self.curdir = path
import app
self.dir_img = basic.Image(app.App.app.theme.get(cls1+'.folder', '', 'image'))
td_style = {'padding_left': 4,
'padding_right': 4,
'padding_top': 2,
'padding_bottom': 2}
self.title = basic.Label(title_txt, cls=cls+".title.label")
self.body = table.Table()
self.list = area.List(width=350, height=150)
self.input_dir = input.Input()
self.input_file = input.Input()
self._list_dir_()
self.button_ok = button.Button(button_txt)
self.body.tr()
self.body.td(basic.Label("Folder"), style=td_style, align=-1)
self.body.td(self.input_dir, style=td_style)
self.body.tr()
self.body.td(self.list, colspan=3, style=td_style)
self.list.connect(CHANGE, self._item_select_changed_, None)
self.button_ok.connect(CLICK, self._button_okay_clicked_, None)
self.body.tr()
self.body.td(basic.Label("File"), style=td_style, align=-1)
self.body.td(self.input_file, style=td_style)
self.body.td(self.button_ok, style=td_style)
self.value = None
Dialog.__init__(self, self.title, self.body)
def _list_dir_(self):
self.input_dir.value = self.curdir
self.input_dir.pos = len(self.curdir)
self.input_dir.vpos = 0
dirs = []
files = []
try:
for i in os.listdir(self.curdir):
if os.path.isdir(os.path.join(self.curdir, i)): dirs.append(i)
else: files.append(i)
except:
self.input_file.value = "Opps! no access"
#if '..' not in dirs: dirs.append('..')
dirs.sort()
dirs = ['..'] + dirs
files.sort()
for i in dirs:
#item = ListItem(image=self.dir_img, text=i, value=i)
self.list.add(i,image=self.dir_img,value=i)
for i in files:
#item = ListItem(image=None, text=i, value=i)
self.list.add(i,value=i)
#self.list.resize()
self.list.set_vertical_scroll(0)
#self.list.repaintall()
def _item_select_changed_(self, arg):
self.input_file.value = self.list.value
fname = os.path.abspath(os.path.join(self.curdir, self.input_file.value))
if os.path.isdir(fname):
self.input_file.value = ""
self.curdir = fname
self.list.clear()
self._list_dir_()
def _button_okay_clicked_(self, arg):
if self.input_dir.value != self.curdir:
if os.path.isdir(self.input_dir.value):
self.input_file.value = ""
self.curdir = os.path.abspath(self.input_dir.value)
self.list.clear()
self._list_dir_()
else:
self.value = os.path.join(self.curdir, self.input_file.value)
self.send(CHANGE)
self.close() python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/app.py 0000644 0000000 0000000 00000014064 11130023047 020634 0 ustar root root """
"""
import pygame
from pygame.locals import *
import container
from const import *
class App(container.Container):
"""The top-level widget for an application.
App(theme=None)
- theme
- an instance of a Theme, optional as it will use the default Theme class.
Basic Example
app = gui.App()
app.run(widget=widget,screen=screen)
Integrated Example
app = gui.App()
gui.init(widget=widget)
while 1:
for e in pygame.event.get():
app.event(e)
app.update(screen)
"""
def __init__(self,theme=None,**params):
App.app = self
if theme == None:
from theme import Theme
theme = Theme()
self.theme = theme
params['decorate'] = 'app'
container.Container.__init__(self,**params)
self._quit = False
self.widget = None
self._chsize = False
self._repaint = False
self.screen = None
self.container = None
self.events = []
def resize(self):
screen = self.screen
w = self.widget
wsize = 0
#5 cases
#input screen is already set use its size
if screen:
self.screen = screen
width,height = screen.get_width(),screen.get_height()
#display.screen
elif pygame.display.get_surface():
screen = pygame.display.get_surface()
self.screen = screen
width,height = screen.get_width(),screen.get_height()
#app has width,height
elif self.style.width != 0 and self.style.height != 0:
screen = pygame.display.set_mode((self.style.width,self.style.height),SWSURFACE)
self.screen = screen
width,height = screen.get_width(),screen.get_height()
#widget has width,height, or its own size..
else:
wsize = 1
width,height = w.rect.w,w.rect.h = w.resize()
#w._resize()
screen = pygame.display.set_mode((width,height),SWSURFACE)
self.screen = screen
#use screen to set up size of this widget
self.style.width,self.style.height = width,height
self.rect.w,self.rect.h = width,height
self.rect.x,self.rect.y = 0,0
w.rect.x,w.rect.y = 0,0
w.rect.w,w.rect.h = w.resize(width,height)
for w in self.windows:
w.rect.w,w.rect.h = w.resize()
self._chsize = False
def init(self,widget=None,screen=None): #TODO widget= could conflict with module widget
"""Initialize the application.
App.init(widget=None,screen=None)
- widget
- main widget
- screen
- pygame.Surface to render to
"""
App.app = self
if widget: self.widget = widget
if screen: self.screen = screen
self.resize()
w = self.widget
self.widgets = []
self.widgets.append(w)
w.container = self
self.focus(w)
pygame.key.set_repeat(500,30)
self._repaint = True
self._quit = False
self.send(INIT)
def event(self,e):
"""Pass an event to the main widget.
App.event(e)
- e
- event
"""
App.app = self
#NOTE: might want to deal with ACTIVEEVENT in the future.
self.send(e.type,e)
container.Container.event(self,e)
if e.type == MOUSEBUTTONUP:
if e.button not in (4,5): #ignore mouse wheel
sub = pygame.event.Event(CLICK,{
'button':e.button,
'pos':e.pos})
self.send(sub.type,sub)
container.Container.event(self,sub)
def loop(self):
App.app = self
s = self.screen
for e in pygame.event.get():
if not (e.type == QUIT and self.mywindow):
self.event(e)
us = self.update(s)
pygame.display.update(us)
def paint(self,screen):
self.screen = screen
if self._chsize:
self.resize()
self._chsize = False
if hasattr(self,'background'):
self.background.paint(screen)
container.Container.paint(self,screen)
def update(self,screen):
"""Update the screen.
- screen
- pygame surface
"""
self.screen = screen
if self._chsize:
self.resize()
self._chsize = False
if self._repaint:
self.paint(screen)
self._repaint = False
return [pygame.Rect(0,0,screen.get_width(),screen.get_height())]
else:
us = container.Container.update(self,screen)
return us
def run(self,widget=None,screen=None):
"""Run an application.
Automatically calls App.init and then forever loops App.event and App.update
- widget
- main widget
- screen
- pygame.Surface to render to
"""
self.init(widget,screen)
while not self._quit:
self.loop()
pygame.time.wait(10)
def reupdate(self,w=None): pass
def repaint(self,w=None): self._repaint = True
def repaintall(self): self._repaint = True
def chsize(self):
self._chsize = True
self._repaint = True
def quit(self,value=None): self._quit = True
class Desktop(App):
"""Create an App using the desktop theme class.
Desktop()
"""
def __init__(self,**params):
params.setdefault('cls','desktop')
App.__init__(self,**params) python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/layout.py 0000644 0000000 0000000 00000011643 11130023047 021371 0 ustar root root """document layout engine."""
class Layout:
"""the document layout engine
.widgets -- elements are kept in this list. read-only, use add to add items to it.
"""
def __init__(self,rect=None):
"""initialize the object with the size of the box."""
self._widgets = []
self.rect = rect
def add(self,e):
"""add a document element to the layout.
a document element may be
- a tuple (w,h) if it is a whitespace element
- a tuple (0,h) if it is a linebreak element
- an integer -1,0,1 if it is a command to start a new block of elements that are aligned either left,center, or right.
- an object with a .rect (for size) -- such as a word element
- an object with a .rect (for size) and .align -- such as an image element
"""
self._widgets.append(e)
def resize(self):
"""resize the layout
this method recalculates the position of all document elements
after they have been added to the document. .rect.x,y will be updated for all
objects.
"""
self.init()
self.widgets = []
for e in self._widgets:
if type(e) is tuple and e[0] != 0:
self.do_space(e)
elif type(e) is tuple and e[0] == 0:
self.do_br(e[1])
elif type(e) is int:
self.do_block(align=e)
elif hasattr(e,'align'):
self.do_align(e)
else:
self.do_item(e)
self.line()
self.rect.h = max(self.y,self.left_bottom,self.right_bottom)
def init(self):
self.x,self.y = self.rect.x,self.rect.y
self.left = self.rect.left
self.right = self.rect.right
self.left_bottom = 0
self.right_bottom = 0
self.y = self.rect.y
self.x = self.rect.x
self.h = 0
self.items = []
self.align = -1
def getleft(self):
if self.y > self.left_bottom:
self.left = self.rect.left
return self.left
def getright(self):
if self.y > self.right_bottom:
self.right = self.rect.right
return self.right
def do_br(self,h):
self.line()
self.h = h
def do_block(self,align=-1):
self.line()
self.align = align
def do_align(self,e):
align = e.align
ox,oy,oh = self.x,self.y,self.h
w,h = e.rect.w,e.rect.h
if align == 0:
self.line()
self.x = self.rect.left + (self.rect.width-w)/2
self.fit = 0
elif align == -1:
self.line()
self.y = max(self.left_bottom,self.y + self.h)
self.h = 0
self.x = self.rect.left
elif align == 1:
self.line()
self.y = max(self.right_bottom,self.y + self.h)
self.h = 0
self.x = self.rect.left + (self.rect.width-w)
e.rect.x,e.rect.y = self.x,self.y
self.x = self.x + w
self.y = self.y
if align == 0:
self.h = max(self.h,h)
self.y = self.y + self.h
self.x = self.getleft()
self.h = 0
elif align == -1:
self.left = self.x
self.left_bottom = self.y + h
self.x,self.y,self.h = ox + w,oy,oh
elif align == 1:
self.right = self.x - w
self.right_bottom = self.y + h
self.x,self.y,self.h = ox,oy,oh
self.widgets.append(e)
def do_space(self,e):
w,h = e
if self.x+w >= self.getright():
self.line()
else:
self.items.append(e)
self.h = max(self.h,h)
self.x += w
def do_item(self,e):
w,h = e.rect.w,e.rect.h
if self.x+w >= self.getright():
self.line()
self.items.append(e)
self.h = max(self.h,h)
self.x += w
def line(self):
x1 = self.getleft()
x2 = self.getright()
align = self.align
y = self.y
if len(self.items) != 0 and type(self.items[-1]) == tuple:
del self.items[-1]
w = 0
for e in self.items:
if type(e) == tuple: w += e[0]
else: w += e.rect.w
if align == -1: x = x1
elif align == 0:
x = x1 + ((x2-x1)-w)/2
self.fit = 0
elif align == 1: x = x2 - w
for e in self.items:
if type(e) == tuple: x += e[0]
else:
e.rect.x,e.rect.y = x,y
self.widgets.append(e)
x += e.rect.w
self.items = []
self.y = self.y + self.h
self.x = self.getleft()
self.h = 0
# vim: set filetype=python sts=4 sw=4 noet si :
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/surface.py 0000644 0000000 0000000 00000012023 11130023047 021475 0 ustar root root """
"""
import pygame
def subsurface(s,r):
"""Return the subsurface of a surface, with some help, checks.
subsurface(s,r): return surface
"""
r = pygame.Rect(r)
if r.x < 0 or r.y < 0:
raise "gui.subsurface: %d %d %s"%(s.get_width(),s.get_height(),r)
w,h = s.get_width(),s.get_height()
if r.right > w:
r.w -= r.right-w
if r.bottom > h:
r.h -= r.bottom-h
return s.subsurface(r)
class ProxySurface:
"""
A surface-like object which smartly handle out-of-area blitting.
ProxySurface(parent, rect, real_surface=None, offset=(0, 0))
only one of parent and real_surface should be supplied (non None)
- parent
- a ProxySurface object
- real_surface
- a pygame Surface object
Variables
- mysubsurface
- a real and valid pygame.Surface object to be used
for blitting.
- x, y
- if the proxy surface is lefter or higher than the parent,
x, y hold the diffs.
- offset
- an optional feature which let you scroll the whole blitted
content.
"""
def __init__(self, parent, rect, real_surface, offset=(0, 0)):
self.offset = offset
self.x = self.y = 0
if rect[0] < 0: self.x = rect[0]
if rect[1] < 0: self.y = rect[1]
self.real_surface = real_surface
if real_surface == None:
self.mysubsurface = parent.mysubsurface.subsurface(parent.mysubsurface.get_rect().clip(rect))
else:
self.mysubsurface = real_surface.subsurface(real_surface.get_rect().clip(rect))
rect[0], rect[1] = 0, 0
self.rect = rect
def blit(self, s, pos, rect=None):
if rect == None: rect = s.get_rect()
pos = (pos[0] + self.offset[0] + self.x, pos[1] + self.offset[1] + self.y)
self.mysubsurface.blit(s, pos, rect)
def subsurface(self, rect): return ProxySurface(self, pygame.Rect(rect).move(self.offset[0] + self.x, self.offset[1] + self.y),self.real_surface)
def fill(self, color, rect=None):
if rect != None: self.mysubsurface.fill(color, rect)
else: self.mysubsurface.fill(color)
def get_rect(self): return self.rect
def get_width(self): return self.rect[2]
def get_height(self): return self.rect[3]
def get_abs_offset(): return self.rect[:2]
def get_abs_parent(): return self.mysubsurface.get_abs_parent()
def set_clip(self, rect=None):
if rect == None: self.mysubsurface.set_clip()
else:
rect = [rect[0] + self.offset[0] + self.x, rect[1] + self.offset[0] + self.y, rect[2], rect[3]]
self.mysubsurface.set_clip(rect)
class xProxySurface:
"""
A surface-like object which smartly handle out-of-area blitting.
ProxySurface(parent, rect, real_surface=None, offset=(0, 0))
only one of parent and real_surface should be supplied (non None)
- parent
- a ProxySurface object
- real_surface
- a pygame Surface object
Variables
- mysubsurface
- a real and valid pygame.Surface object to be used
for blitting.
- x, y
- if the proxy surface is lefter or higher than the parent,
x, y hold the diffs.
- offset
- an optional feature which let you scroll the whole blitted
content.
"""
def __init__(self, parent, rect, real_surface, offset=(0, 0)):
self.offset = offset
self.x = self.y = 0
if rect[0] < 0: self.x = rect[0]
if rect[1] < 0: self.y = rect[1]
self.real_surface = real_surface
if real_surface == None:
self.mysubsurface = parent.mysubsurface.subsurface(parent.mysubsurface.get_rect().clip(rect))
else:
self.mysubsurface = real_surface.subsurface(real_surface.get_rect().clip(rect))
rect[0], rect[1] = 0, 0
self.rect = rect
def blit(self, s, pos, rect=None):
if rect == None: rect = s.get_rect()
pos = (pos[0] + self.offset[0] + self.x, pos[1] + self.offset[1] + self.y)
self.mysubsurface.blit(s, pos, rect)
def subsurface(self, rect): return ProxySurface(self, pygame.Rect(rect).move(self.offset[0] + self.x, self.offset[1] + self.y),self.real_surface)
def fill(self, color, rect=None):
if rect != None: self.mysubsurface.fill(color, rect)
else: self.mysubsurface.fill(color)
def get_rect(self): return self.rect
def get_width(self): return self.rect[2]
def get_height(self): return self.rect[3]
def get_abs_offset(): return self.rect[:2]
def get_abs_parent(): return self.mysubsurface.get_abs_parent()
def set_clip(self, rect=None):
if rect == None: self.mysubsurface.set_clip()
else:
rect = [rect[0] + self.offset[0] + self.x, rect[1] + self.offset[0] + self.y, rect[2], rect[3]]
self.mysubsurface.set_clip(rect)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/theme.py 0000644 0000000 0000000 00000037432 11130023047 021162 0 ustar root root """
"""
import os, re
import pygame
from const import *
import surface
def _list_themes(dir):
d = {}
for entry in os.listdir(dir):
if os.path.exists(os.path.join(dir, entry, 'config.txt')):
d[entry] = os.path.join(dir, entry)
return d
class Theme:
"""Theme interface.
If you wish to create your own theme, create a class with this interface, and
pass it to gui.App via gui.App(theme=MyTheme()).
Default Theme
Theme(dirs='default')
- dirs
- Name of the theme dir to load a theme from. May be an absolute path to a theme, if pgu is not installed, or if you created your own theme. May include several dirs in a list if data is spread across several themes.
Example
theme = gui.Theme("default")
theme = gui.Theme(["mytheme","mytheme2"])
"""
def __init__(self,dirs='default'):
self.config = {}
self.dict = {}
self._loaded = []
self.cache = {}
self._preload(dirs)
pygame.font.init()
def _preload(self,ds):
if not isinstance(ds, list):
ds = [ds]
for d in ds:
if d not in self._loaded:
self._load(d)
self._loaded.append(d)
def _load(self, name):
#theme_dir = themes[name]
#try to load the local dir, or absolute path
dnames = [name]
#if the package isn't installed and people are just
#trying out the scripts or examples
dnames.append(os.path.join(os.path.dirname(__file__),"..","..","data","themes",name))
#if the package is installed, and the package is installed
#in /usr/lib/python2.3/site-packages/pgu/
#or c:\python23\lib\site-packages\pgu\
#the data is in ... lib/../share/ ...
dnames.append(os.path.join(os.path.dirname(__file__),"..","..","..","..","share","pgu","themes",name))
dnames.append(os.path.join(os.path.dirname(__file__),"..","..","..","..","..","share","pgu","themes",name))
for dname in dnames:
if os.path.isdir(dname): break
if not os.path.isdir(dname):
raise 'could not find theme '+name
fname = os.path.join(dname,"config.txt")
if os.path.isfile(fname):
try:
f = open(fname)
for line in f.readlines():
vals = line.strip().split()
if len(vals) < 3: continue
cls = vals[0]
del vals[0]
pcls = ""
if cls.find(":")>=0:
cls,pcls = cls.split(":")
attr = vals[0]
del vals[0]
self.config[cls+":"+pcls+" "+attr] = (dname, vals)
finally:
f.close()
fname = os.path.join(dname,"style.ini")
if os.path.isfile(fname):
import ConfigParser
cfg = ConfigParser.ConfigParser()
f = open(fname,'r')
cfg.readfp(f)
for section in cfg.sections():
cls = section
pcls = ''
if cls.find(":")>=0:
cls,pcls = cls.split(":")
for attr in cfg.options(section):
vals = cfg.get(section,attr).strip().split()
self.config[cls+':'+pcls+' '+attr] = (dname,vals)
is_image = re.compile('\.(gif|jpg|bmp|png|tga)$', re.I)
def _get(self,key):
if not key in self.config: return
if key in self.dict: return self.dict[key]
dvals = self.config[key]
dname, vals = dvals
#theme_dir = themes[name]
v0 = vals[0]
if v0[0] == '#':
v = pygame.color.Color(v0)
elif v0.endswith(".ttf") or v0.endswith(".TTF"):
v = pygame.font.Font(os.path.join(dname, v0),int(vals[1]))
elif self.is_image.search(v0) is not None:
v = pygame.image.load(os.path.join(dname, v0))
else:
try: v = int(v0)
except: v = pygame.font.SysFont(v0, int(vals[1]))
self.dict[key] = v
return v
def get(self,cls,pcls,attr):
"""Interface method -- get the value of a style attribute.
Theme.get(cls,pcls,attr): return value
- cls
- class, for example "checkbox", "button", etc.
- pcls
- pseudo class, for example "hover", "down", etc.
- attr
- attribute, for example "image", "background", "font", "color", etc.
returns the value of the attribute.
This method is called from [[gui-style]].
"""
if not self._loaded: self._preload("default")
o = cls+":"+pcls+" "+attr
#if not hasattr(self,'_count'):
# self._count = {}
#if o not in self._count: self._count[o] = 0
#self._count[o] += 1
if o in self.cache:
return self.cache[o]
v = self._get(cls+":"+pcls+" "+attr)
if v:
self.cache[o] = v
return v
pcls = ""
v = self._get(cls+":"+pcls+" "+attr)
if v:
self.cache[o] = v
return v
cls = "default"
v = self._get(cls+":"+pcls+" "+attr)
if v:
self.cache[o] = v
return v
v = 0
self.cache[o] = v
return v
def box(self,w,s):
style = w.style
c = (0,0,0)
if style.border_color != 0: c = style.border_color
w,h = s.get_width(),s.get_height()
s.fill(c,(0,0,w,style.border_top))
s.fill(c,(0,h-style.border_bottom,w,style.border_bottom))
s.fill(c,(0,0,style.border_left,h))
s.fill(c,(w-style.border_right,0,style.border_right,h))
def getspacing(self,w):
# return the top, right, bottom, left spacing around the widget
if not hasattr(w,'_spacing'): #HACK: assume spacing doesn't change re pcls
s = w.style
xt = s.margin_top+s.border_top+s.padding_top
xr = s.padding_right+s.border_right+s.margin_right
xb = s.padding_bottom+s.border_bottom+s.margin_bottom
xl = s.margin_left+s.border_left+s.padding_left
w._spacing = xt,xr,xb,xl
return w._spacing
def resize(self,w,m):
def func(width=None,height=None):
#ww,hh = m(width,height)
ow,oh = width,height
s = w.style
pt,pr,pb,pl = s.padding_top,s.padding_right,s.padding_bottom,s.padding_left
bt,br,bb,bl = s.border_top,s.border_right,s.border_bottom,s.border_left
mt,mr,mb,ml = s.margin_top,s.margin_right,s.margin_bottom,s.margin_left
xt = pt+bt+mt
xr = pr+br+mr
xb = pb+bb+mb
xl = pl+bl+ml
ttw = xl+xr
tth = xt+xb
ww,hh = None,None
if width != None: ww = width-ttw
if height != None: hh = height-tth
ww,hh = m(ww,hh)
rect = pygame.Rect(0 + xl, 0 + xt, ww, hh)
w._rect_content = rect #pygame.Rect(0 + xl, 0 + xt, width, height)
#r = rect
if width == None: width = ww
if height == None: height = hh
#if the widget hasn't respected the style.width,
#style height, we'll add in the space for it...
width = max(width-ttw,ww,w.style.width)
height = max(height-tth,hh,w.style.height)
#width = max(ww,w.style.width-tw)
#height = max(hh,w.style.height-th)
r = pygame.Rect(rect.x,rect.y,width,height)
w._rect_padding = pygame.Rect(r.x-pl,r.y-pt,r.w+pl+pr,r.h+pt+pb)
r = w._rect_padding
w._rect_border = pygame.Rect(r.x-bl,r.y-bt,r.w+bl+br,r.h+bt+bb)
r = w._rect_border
w._rect_margin = pygame.Rect(r.x-ml,r.y-mt,r.w+ml+mr,r.h+mt+mb)
#align it within it's zone of power.
dx = width-rect.w
dy = height-rect.h
#rect.x += (1)*dx/2
#rect.y += (1)*dy/2
rect.x += (w.style.align+1)*dx/2
rect.y += (w.style.valign+1)*dy/2
#print w,ow, w._rect_margin.w, ttw
return w._rect_margin.w,w._rect_margin.h
return func
def paint(self,w,m):
def func(s):
# if w.disabled:
# if not hasattr(w,'_disabled_bkgr'):
# w._disabled_bkgr = s.convert()
# orig = s
# s = w._disabled_bkgr.convert()
# if not hasattr(w,'_theme_paint_bkgr'):
# w._theme_paint_bkgr = s.convert()
# else:
# s.blit(w._theme_paint_bkgr,(0,0))
#
# if w.disabled:
# orig = s
# s = w._theme_paint_bkgr.convert()
if w.disabled:
if not (hasattr(w,'_theme_bkgr') and w._theme_bkgr.get_width() == s.get_width() and w._theme_bkgr.get_height() == s.get_height()):
w._theme_bkgr = s.copy()
orig = s
s = w._theme_bkgr
s.fill((0,0,0,0))
s.blit(orig,(0,0))
if hasattr(w,'background'):
w.background.paint(surface.subsurface(s,w._rect_border))
self.box(w,surface.subsurface(s,w._rect_border))
r = m(surface.subsurface(s,w._rect_content))
if w.disabled:
s.set_alpha(128)
orig.blit(s,(0,0))
# if w.disabled:
# orig.blit(w._disabled_bkgr,(0,0))
# s.set_alpha(128)
# orig.blit(s,(0,0))
w._painted = True
return r
return func
def event(self,w,m):
def func(e):
rect = w._rect_content
if e.type == MOUSEBUTTONUP or e.type == MOUSEBUTTONDOWN:
sub = pygame.event.Event(e.type,{
'button':e.button,
'pos':(e.pos[0]-rect.x,e.pos[1]-rect.y)})
elif e.type == CLICK:
sub = pygame.event.Event(e.type,{
'button':e.button,
'pos':(e.pos[0]-rect.x,e.pos[1]-rect.y)})
elif e.type == MOUSEMOTION:
sub = pygame.event.Event(e.type,{
'buttons':e.buttons,
'pos':(e.pos[0]-rect.x,e.pos[1]-rect.y),
'rel':e.rel})
else:
sub = e
r = m(sub)
return r
return func
def update(self,w,m):
def func(s):
if w.disabled: return []
r = m(surface.subsurface(s,w._rect_content))
if type(r) == list:
dx,dy = w._rect_content.topleft
for rr in r:
rr.x,rr.y = rr.x+dx,rr.y+dy
return r
return func
def open(self,w,m):
def func(widget=None,x=None,y=None):
if not hasattr(w,'_rect_content'): w.rect.w,w.rect.h = w.resize() #HACK: so that container.open won't resize again!
rect = w._rect_content
##print w.__class__.__name__, rect
if x != None: x += rect.x
if y != None: y += rect.y
return m(widget,x,y)
return func
#def open(self,w,m):
# def func(widget=None):
# return m(widget)
# return func
def decorate(self,widget,level):
"""Interface method -- decorate a widget.
The theme system is given the opportunity to decorate a widget methods at the
end of the Widget initializer.
Theme.decorate(widget,level)
- widget
- the widget to be decorated
- level
- the amount of decoration to do, False for none, True for normal amount, 'app' for special treatment of App objects.
"""
w = widget
if level == False: return
if type(w.style.background) != int:
w.background = Background(w,self)
if level == 'app': return
for k,v in w.style.__dict__.items():
if k in ('border','margin','padding'):
for kk in ('top','bottom','left','right'):
setattr(w.style,'%s_%s'%(k,kk),v)
w.paint = self.paint(w,w.paint)
w.event = self.event(w,w.event)
w.update = self.update(w,w.update)
w.resize = self.resize(w,w.resize)
w.open = self.open(w,w.open)
def render(self,s,box,r):
"""Interface method - render a special widget feature.
Theme.render(s,box,r)
- s
- pygame.Surface
- box
- box data, a value returned from Theme.get, typically a pygame.Surface
- r
- pygame.Rect with the size that the box data should be rendered
"""
if box == 0: return
if not isinstance(box,pygame.Surface):
s.fill(box,r)
return
x,y,w,h=r.x,r.y,r.w,r.h
ww,hh=box.get_width()/3,box.get_height()/3
xx,yy=x+w,y+h
src = pygame.rect.Rect(0,0,ww,hh)
dest = pygame.rect.Rect(0,0,ww,hh)
s.set_clip(pygame.Rect(x+ww,y+hh,w-ww*2,h-hh*2))
src.x,src.y = ww,hh
for dest.y in xrange(y+hh,yy-hh,hh):
for dest.x in xrange(x+ww,xx-ww,ww): s.blit(box,dest,src)
s.set_clip(pygame.Rect(x+ww,y,w-ww*3,hh))
src.x,src.y,dest.y = ww,0,y
for dest.x in xrange(x+ww,xx-ww*2,ww): s.blit(box,dest,src)
dest.x = xx-ww*2
s.set_clip(pygame.Rect(x+ww,y,w-ww*2,hh))
s.blit(box,dest,src)
s.set_clip(pygame.Rect(x+ww,yy-hh,w-ww*3,hh))
src.x,src.y,dest.y = ww,hh*2,yy-hh
for dest.x in xrange(x+ww,xx-ww*2,ww): s.blit(box,dest,src)
dest.x = xx-ww*2
s.set_clip(pygame.Rect(x+ww,yy-hh,w-ww*2,hh))
s.blit(box,dest,src)
s.set_clip(pygame.Rect(x,y+hh,xx,h-hh*3))
src.y,src.x,dest.x = hh,0,x
for dest.y in xrange(y+hh,yy-hh*2,hh): s.blit(box,dest,src)
dest.y = yy-hh*2
s.set_clip(pygame.Rect(x,y+hh,xx,h-hh*2))
s.blit(box,dest,src)
s.set_clip(pygame.Rect(xx-ww,y+hh,xx,h-hh*3))
src.y,src.x,dest.x=hh,ww*2,xx-ww
for dest.y in xrange(y+hh,yy-hh*2,hh): s.blit(box,dest,src)
dest.y = yy-hh*2
s.set_clip(pygame.Rect(xx-ww,y+hh,xx,h-hh*2))
s.blit(box,dest,src)
s.set_clip()
src.x,src.y,dest.x,dest.y = 0,0,x,y
s.blit(box,dest,src)
src.x,src.y,dest.x,dest.y = ww*2,0,xx-ww,y
s.blit(box,dest,src)
src.x,src.y,dest.x,dest.y = 0,hh*2,x,yy-hh
s.blit(box,dest,src)
src.x,src.y,dest.x,dest.y = ww*2,hh*2,xx-ww,yy-hh
s.blit(box,dest,src)
import pygame
import widget
class Background(widget.Widget):
def __init__(self,value,theme,**params):
params['decorate'] = False
widget.Widget.__init__(self,**params)
self.value = value
self.theme = theme
def paint(self,s):
r = pygame.Rect(0,0,s.get_width(),s.get_height())
v = self.value.style.background
if not isinstance(v,pygame.Surface):
s.fill(v)
else:
self.theme.render(s,v,r)
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/table.py 0000644 0000000 0000000 00000030741 11130023047 021143 0 ustar root root """
"""
from const import *
import container
class Table(container.Container):
"""A table style container.
If you know HTML, this should all work roughly how you would expect. If you are not
familiar with HTML, please read Tables in HTML Documents. Pay attention to TABLE, TR, TD related parts of the document.
Table()
Example
t = gui.Table()
t.tr()
t.td(gui.Label("First Name"), align=-1)
t.td(gui.Input())
t.tr()
t.td(gui.Label("Last Name"), align=-1)
t.td(gui.Input())
"""
def __init__(self, **params):
params.setdefault('cls','table')
container.Container.__init__(self, **params)
self._rows = []
self._curRow = 0
self._trok = False
def getRows(self):
return len(self._rows)
def getColumns(self):
if self._rows:
return len(self._rows[0])
else:
return 0
def remove_row(self, n): #NOTE: won't work in all cases.
if n >= self.getRows():
print "Trying to remove a nonexistant row:", n, "there are only", self.getRows(), "rows"
return
for cell in self._rows[n]:
if isinstance(cell, dict) and cell["widget"] in self.widgets:
#print 'removing widget'
self.widgets.remove(cell["widget"])
del self._rows[n]
#print "got here"
for w in self.widgets:
if w.style.row > n: w.style.row -= 1
if self._curRow >= n:
self._curRow -= 1
#self.rect.w, self.rect.h = self.resize()
#self.repaint()
self.chsize()
def clear(self):
self._rows = []
self._curRow = 0
self._trok = False
self.widgets = []
self.chsize()
#print 'clear',self,self._rows
def _addRow(self):
self._rows.append([None for x in xrange(self.getColumns())])
def tr(self):
"""Start on the next row."""
if not self._trok:
self._trok = True
return
self._curRow += 1
if self.getRows() <= self._curRow:
self._addRow()
def _addColumn(self):
if not self._rows:
self._addRow()
for row in self._rows:
row.append(None)
def _setCell(self, w, col, row, colspan=1, rowspan=1):
#make room for the widget by adding columns and rows
while self.getColumns() < col + colspan:
self._addColumn()
while self.getRows() < row + rowspan:
self._addRow()
#print w.__class__.__name__,col,row,colspan,rowspan
#actual widget setting and modification stuff
w.container = self
w.style.row = row #HACK - to work with gal's list
w.style.col = col #HACK - to work with gal's list
self._rows[row][col] = {"widget":w, "colspan":colspan, "rowspan":rowspan}
self.widgets.append(self._rows[row][col]["widget"])
#set the spanned columns
#for acell in xrange(col + 1, col + colspan):
# self._rows[row][acell] = True
#set the spanned rows and the columns on them
#for arow in xrange(row + 1, row + rowspan):
# for acell in xrange(col, col + colspan): #incorrect?
# self._rows[arow][acell] = True
for arow in xrange(row, row + rowspan):
for acell in xrange(col, col + colspan): #incorrect?
if row != arow or col != acell:
self._rows[arow][acell] = True
def td(self, w, col=None, row=None, colspan=1, rowspan=1, **params):
"""Add a widget to a table after wrapping it in a TD container.
Table.td(w,col=None,row=None,colspan=1,rowspan=1,**params)
- w
- widget
- col
- column
- row
- row
- colspan
- colspan
- rowspan
- rowspan
- align
- horizontal alignment (-1,0,1)
- valign
- vertical alignment (-1,0,1)
- params
- other params for the TD container, style information, etc
"""
Table.add(self,_Table_td(w, **params), col=col, row=row, colspan=colspan, rowspan=rowspan)
def add(self, w, col=None, row=None, colspan=1, rowspan=1):
"""Add a widget directly into the table, without wrapping it in a TD container.
Table.add(w,col=None,row=None,colspan=1,rowspan=1)
See Table.td for an explanation of the parameters.
"""
self._trok = True
#if no row was specifically specified, set it to the current row
if row is None:
row = self._curRow
#print row
#if its going to be a new row, have it be on the first column
if row >= self.getRows():
col = 0
#try to find an open cell for the widget
if col is None:
for cell in xrange(self.getColumns()):
if col is None and not self._rows[row][cell]:
col = cell
break
#otherwise put the widget in a new column
if col is None:
col = self.getColumns()
self._setCell(w, col, row, colspan=colspan, rowspan=rowspan)
self.chsize()
return
def remove(self,w):
if hasattr(w,'_table_td'): w = w._table_td
row,col = w.style.row,w.style.col
cell = self._rows[row][col]
colspan,rowspan = cell['colspan'],cell['rowspan']
for arow in xrange(row , row + rowspan):
for acell in xrange(col, col + colspan): #incorrect?
self._rows[arow][acell] = False
self.widgets.remove(w)
self.chsize()
def resize(self, width=None, height=None):
#if 1 or self.getRows() == 82:
#print ''
#print 'resize',self.getRows(),self.getColumns(),width,height
#import inspect
#for obj,fname,line,fnc,code,n in inspect.stack()[9:20]:
# print fname,line,':',fnc,code[0].strip()
#resize the widgets to their smallest size
for w in self.widgets:
w.rect.w, w.rect.h = w.resize()
#calculate row heights and column widths
rowsizes = [0 for y in xrange(self.getRows())]
columnsizes = [0 for x in xrange(self.getColumns())]
for row in xrange(self.getRows()):
for cell in xrange(self.getColumns()):
if self._rows[row][cell] and self._rows[row][cell] is not True:
if not self._rows[row][cell]["colspan"] > 1:
columnsizes[cell] = max(columnsizes[cell], self._rows[row][cell]["widget"].rect.w)
if not self._rows[row][cell]["rowspan"] > 1:
rowsizes[row] = max(rowsizes[row], self._rows[row][cell]["widget"].rect.h)
#distribute extra space if necessary for wide colspanning/rowspanning
for row in xrange(self.getRows()):
for cell in xrange(self.getColumns()):
if self._rows[row][cell] and self._rows[row][cell] is not True:
if self._rows[row][cell]["colspan"] > 1:
columns = xrange(cell, cell + self._rows[row][cell]["colspan"])
totalwidth = 0
for acol in columns:
totalwidth += columnsizes[acol]
if totalwidth < self._rows[row][cell]["widget"].rect.w:
for acol in columns:
columnsizes[acol] += _table_div(self._rows[row][cell]["widget"].rect.w - totalwidth, self._rows[row][cell]["colspan"],acol)
if self._rows[row][cell]["rowspan"] > 1:
rows = xrange(row, row + self._rows[row][cell]["rowspan"])
totalheight = 0
for arow in rows:
totalheight += rowsizes[arow]
if totalheight < self._rows[row][cell]["widget"].rect.h:
for arow in rows:
rowsizes[arow] += _table_div(self._rows[row][cell]["widget"].rect.h - totalheight, self._rows[row][cell]["rowspan"],arow)
#make everything fill out to self.style.width, self.style.heigh, not exact, but pretty close...
w, h = sum(columnsizes), sum(rowsizes)
if w > 0 and w < self.style.width and len(columnsizes):
d = (self.style.width - w)
for n in xrange(0, len(columnsizes)):
v = columnsizes[n]
columnsizes[n] += v * d / w
if h > 0 and h < self.style.height and len(rowsizes):
d = (self.style.height - h) / len(rowsizes)
for n in xrange(0, len(rowsizes)):
v = rowsizes[n]
rowsizes[n] += v * d / h
#set the widget's position by calculating their row/column x/y offset
cellpositions = [[[sum(columnsizes[0:cell]), sum(rowsizes[0:row])] for cell in xrange(self.getColumns())] for row in xrange(self.getRows())]
for row in xrange(self.getRows()):
for cell in xrange(self.getColumns()):
if self._rows[row][cell] and self._rows[row][cell] is not True:
x, y = cellpositions[row][cell]
w = sum(columnsizes[cell:cell+self._rows[row][cell]["colspan"]])
h = sum(rowsizes[row:row+self._rows[row][cell]["rowspan"]])
widget = self._rows[row][cell]["widget"]
widget.rect.x = x
widget.rect.y = y
if 1 and (w,h) != (widget.rect.w,widget.rect.h):
# if h > 20:
# print widget.widget.__class__.__name__, (widget.rect.w,widget.rect.h),'=>',(w,h)
widget.rect.w, widget.rect.h = widget.resize(w, h)
#print self._rows[row][cell]["widget"].rect
#print columnsizes
#print sum(columnsizes)
#size = sum(columnsizes), sum(rowsizes); print size
#return the tables final size
return sum(columnsizes),sum(rowsizes)
def _table_div(a,b,c):
v,r = a/b, a%b
if r != 0 and (c%b) self.style.width) or (self.style.height!=0 and w.rect.h > self.style.height):
# ww,hh = None,None
# if self.style.width: ww = self.style.width
# if self.style.height: hh = self.style.height
# w.rect.w,w.rect.h = w.resize(ww,hh)
#in the case that the widget is too big, we try to resize it
if (width != None and width < w.rect.w) or (height != None and height < w.rect.h):
w.rect.w,w.rect.h = w.resize(width,height)
width = max(width,w.rect.w,self.style.width) #,self.style.cell_width)
height = max(height,w.rect.h,self.style.height) #,self.style.cell_height)
dx = width-w.rect.w
dy = height-w.rect.h
w.rect.x = (self.style.align+1)*dx/2
w.rect.y = (self.style.valign+1)*dy/2
return width,height
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/deprecated.py 0000644 0000000 0000000 00000004447 11130023047 022160 0 ustar root root import pygame
from const import *
import table
import group
import button, basic
def action_open(value):
print 'gui.action_open',"Scheduled to be deprecated."
value.setdefault('x',None)
value.setdefault('y',None)
value['container'].open(value['window'],value['x'],value['y'])
def action_setvalue(value):
print 'gui.action_setvalue',"Scheduled to be deprecated."
a,b = value
b.value = a.value
def action_quit(value):
print 'gui.action_quit',"Scheduled to be deprecated."
value.quit()
def action_exec(value):
print 'gui.action_exec',"Scheduled to be deprecated."
exec(value['script'],globals(),value['dict'])
class Toolbox(table.Table):
def __setattr__(self,k,v):
_v = self.__dict__.get(k,NOATTR)
self.__dict__[k]=v
if k == 'value' and _v != NOATTR and _v != v:
self.group.value = v
for w in self.group.widgets:
if w.value != v: w.pcls = ""
else: w.pcls = "down"
self.repaint()
def _change(self,value):
self.value = self.group.value
self.send(CHANGE)
def __init__(self,data,cols=0,rows=0,tool_cls='tool',value=None,**params):
print 'gui.Toolbox','Scheduled to be deprecated.'
params.setdefault('cls','toolbox')
table.Table.__init__(self,**params)
if cols == 0 and rows == 0: cols = len(data)
if cols != 0 and rows != 0: rows = 0
self.tools = {}
_value = value
g = group.Group()
self.group = g
g.connect(CHANGE,self._change,None)
self.group.value = _value
x,y,p,s = 0,0,None,1
for ico,value in data:
#from __init__ import theme
import app
img = app.App.app.theme.get(tool_cls+"."+ico,"","image")
if img:
i = basic.Image(img)
else: i = basic.Label(ico,cls=tool_cls+".label")
p = button.Tool(g,i,value,cls=tool_cls)
self.tools[ico] = p
#p.style.hexpand = 1
#p.style.vexpand = 1
self.add(p,x,y)
s = 0
if cols != 0: x += 1
if cols != 0 and x == cols: x,y = 0,y+1
if rows != 0: y += 1
if rows != 0 and y == rows: x,y = x+1,0
python-box2d-2.0.2+svn20100109.244/testbed/pgu/gui/__init__.py 0000644 0000000 0000000 00000001505 11130023047 021607 0 ustar root root import pygame
from pygame.locals import *
from theme import Theme
from style import Style
from widget import Widget
from surface import subsurface, ProxySurface
from const import *
from container import Container
from app import App, Desktop
from table import Table
from document import Document
#html
from area import SlideBox, ScrollArea, List
from form import Form
from group import Group
from basic import Spacer, Color, Label, Image
from button import Icon, Button, Switch, Checkbox, Radio, Tool, Link
from input import Input, Password
from keysym import Keysym
from slider import VSlider, HSlider, VScrollBar, HScrollBar
from select import Select
from misc import ProgressBar
from menus import Menus
from dialog import Dialog, FileDialog
from deprecated import Toolbox, action_open, action_setvalue, action_quit, action_exec python-box2d-2.0.2+svn20100109.244/testbed/pgu/__init__.py 0000644 0000000 0000000 00000000151 11130023047 021017 0 ustar root root """Phil's pyGame Utilities
"""
__version__ = '0.10.6'
# vim: set filetype=python sts=4 sw=4 noet si :
python-box2d-2.0.2+svn20100109.244/testbed/test_Dominos.py 0000644 0000000 0000000 00000012416 11135471136 021156 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class Dominos (Framework):
name="Dominos"
def __init__(self):
super(Dominos, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
b1 = self.world.CreateBody(bd)
b1.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(6.0, 0.25)
bd=box2d.b2BodyDef()
bd.position = (-1.5, 10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.1, 1.0)
sd.density = 20.0
sd.friction = 0.1
for i in range(10):
bd=box2d.b2BodyDef()
bd.position = (-6.0 + 1.0 * i, 11.25)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
sd=box2d.b2PolygonDef()
sd.SetAsBox(7.0, 0.25, (0,0), 0.3)
bd=box2d.b2BodyDef()
bd.position = (1.0, 6.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.25, 1.5)
bd=box2d.b2BodyDef()
bd.position = (-7.0, 4.0)
b2 = self.world.CreateBody(bd)
b2.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(6.0, 0.125)
sd.density = 10.0
bd=box2d.b2BodyDef()
bd.position = (-0.9, 1.0)
bd.angle = -0.15
b3 = self.world.CreateBody(bd)
b3.CreateShape(sd)
b3.SetMassFromShapes()
jd=box2d.b2RevoluteJointDef()
anchor=(-2.0, 1.0)
jd.Initialize(b1, b3, anchor)
jd.collideConnected = True
self.world.CreateJoint(jd).getAsType()
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.25, 0.25)
sd.density = 10.0
bd=box2d.b2BodyDef()
bd.position = (-10.0, 15.0)
b4 = self.world.CreateBody(bd)
b4.CreateShape(sd)
b4.SetMassFromShapes()
anchor = (-7.0, 15.0)
jd.Initialize(b2, b4, anchor)
self.world.CreateJoint(jd).getAsType()
bd=box2d.b2BodyDef()
bd.position = (6.5, 3.0)
b5 = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.density = 10.0
sd.friction = 0.1
sd.SetAsBox(1.0, 0.1, (0.0, -0.9), 0.0)
b5.CreateShape(sd)
sd.SetAsBox(0.1, 1.0, (-0.9, 0.0), 0.0)
b5.CreateShape(sd)
sd.SetAsBox(0.1, 1.0, (0.9, 0.0), 0.0)
b5.CreateShape(sd)
b5.SetMassFromShapes()
anchor = (6.0, 2.0)
jd.Initialize(b1, b5, anchor)
self.world.CreateJoint(jd).getAsType()
sd=box2d.b2PolygonDef()
sd.SetAsBox(1.0, 0.1)
sd.density = 30.0
sd.friction = 0.2
bd=box2d.b2BodyDef()
bd.position = (6.5, 4.1)
b6 = self.world.CreateBody(bd)
b6.CreateShape(sd)
b6.SetMassFromShapes()
anchor = (7.5, 4.0)
jd.Initialize(b5, b6, anchor)
self.world.CreateJoint(jd).getAsType()
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.1, 1.0)
sd.density = 10.0
bd=box2d.b2BodyDef()
bd.position = (7.4, 1.0)
b7 = self.world.CreateBody(bd)
b7.CreateShape(sd)
b7.SetMassFromShapes()
djd=box2d.b2DistanceJointDef()
djd.body1 = b3
djd.body2 = b7
djd.localAnchor1 = (6.0, 0.0)
djd.localAnchor2 = (0.0, -1.0)
d = djd.body2.GetWorldPoint(djd.localAnchor2) - djd.body1.GetWorldPoint(djd.localAnchor1)
djd.length = d.Length()
self.world.CreateJoint(djd).getAsType()
sd=box2d.b2CircleDef()
sd.radius = 0.2
sd.density = 10.0
for i in range(4):
bd=box2d.b2BodyDef()
bd.position = (5.9 + 2.0 * sd.radius * i, 2.4)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
if __name__=="__main__":
main(Dominos)
python-box2d-2.0.2+svn20100109.244/testbed/test_empty.py 0000644 0000000 0000000 00000005770 11136402204 020700 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class Empty(Framework):
"""You can use this class as an outline for your tests.
"""
name = "Empty" # Name of the class to display
_pickle_vars=[] # variables to pickle (save/load). e.g., ['name', 'var1', 'var2']
def __init__(self):
"""
Initialize all of your objects here.
Be sure to call the Framework's initializer first.
"""
super(Empty, self).__init__()
# Initialize all of the objects
def Keyboard(self, key):
"""
The key is from pygame.locals.K_*
(e.g., if key == K_z: ... )
If you are using the pyglet backend, you should be able to use the same
K_[a-z], see pyglet_keymapper.py
"""
pass
def Step(self, settings):
"""Called upon every step.
You should always call
-> super(Your_Test_Class, self).Step(settings)
at the beginning or end of your function.
If placed at the beginning, it will cause the actual physics step to happen first.
If placed at the end, it will cause the physics step to happen after your code.
"""
super(Empty, self).Step(settings)
# do stuff
# Placed after the physics step, it will draw on top of physics objects
self.DrawStringCR("*** Base your own testbeds on me! ***")
def ShapeDestroyed(self, shape):
"""
Callback indicating 'shape' has been destroyed.
"""
pass
def JointDestroyed(self, joint):
"""
The joint passed in was removed.
"""
pass
#def BoundaryViolated(self, body):
# """
# The body went out of the world's extents.
# """
# See pygame_main's implementation of BoundaryViolated for more information
# about pickling and general stability.
if __name__=="__main__":
main(Empty)
python-box2d-2.0.2+svn20100109.244/testbed/test_Biped.py 0000644 0000000 0000000 00000060404 11135461416 020571 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
global k_scale
k_scale = 3.0
class Test_Biped(Framework):
name = "Biped"
biped = None
_pickle_vars=[]
def __init__(self):
super(Test_Biped, self).__init__()
k_restitution = 1.4
bd=box2d.b2BodyDef()
bd.position = (0.0, 20.0)
body = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.density = 0.0
sd.restitution = k_restitution
sd.SetAsBox(0.1, 10.0, (-10.0, 0.0), 0.0)
body.CreateShape(sd)
sd.SetAsBox(0.1, 10.0, (10.0, 0.0), 0.0)
body.CreateShape(sd)
sd.SetAsBox(0.1, 10.0, (0.0, -10.0), 0.5 * box2d.b2_pi)
body.CreateShape(sd)
sd.SetAsBox(0.1, 10.0, (0.0, 10.0), -0.5 * box2d.b2_pi)
body.CreateShape(sd)
self.biped = Biped(self.world, box2d.b2Vec2(0.0, 20.0))
for i in range(8):
bd=box2d.b2BodyDef()
bd.position = (5.0, 20.0 + i)
bd.isBullet = True
body = self.world.CreateBody(bd)
body.SetLinearVelocity(box2d.b2Vec2(0.0, -100.0))
body.SetAngularVelocity(box2d.b2Random(-50.0, 50.0))
sd=box2d.b2CircleDef()
sd.radius = 0.25
sd.density = 15.0
sd.restitution = k_restitution
body.CreateShape(sd)
body.SetMassFromShapes()
class Biped(object):
world = None
LFoot=None
RFoot=None
LCalf=None
RCalf=None
LThigh=None
RThigh=None
Pelvis=None
Stomach=None
Chest=None
Neck=None
Head=None
LUpperArm=None
RUpperArm=None
LForearm=None
RForearm=None
LHand=None
RHand=None
LAnkle=None
RAnkle=None
LKnee=None
RKnee=None
LHip=None
RHip=None
LowerAbs=None
UpperAbs=None
LowerNeck=None
UpperNeck=None
LShoulder=None
RShoulder=None
LElbow=None
RElbow=None
LWrist=None
RWrist=None
def __init__(self, world, position):
self.world = world
bdef = BipedDef()
bd=box2d.b2BodyDef()
# create body parts
bd = bdef.LFootDef
bd.position += position
self.LFoot = self.world.CreateBody(bd)
self.LFoot.CreateShape(bdef.LFootPoly)
self.LFoot.SetMassFromShapes()
bd = bdef.RFootDef
bd.position += position
self.RFoot = self.world.CreateBody(bd)
self.RFoot.CreateShape(bdef.RFootPoly)
self.RFoot.SetMassFromShapes()
bd = bdef.LCalfDef
bd.position += position
self.LCalf = self.world.CreateBody(bd)
self.LCalf.CreateShape(bdef.LCalfPoly)
self.LCalf.SetMassFromShapes()
bd = bdef.RCalfDef
bd.position += position
self.RCalf = self.world.CreateBody(bd)
self.RCalf.CreateShape(bdef.RCalfPoly)
self.RCalf.SetMassFromShapes()
bd = bdef.LThighDef
bd.position += position
self.LThigh = self.world.CreateBody(bd)
self.LThigh.CreateShape(bdef.LThighPoly)
self.LThigh.SetMassFromShapes()
bd = bdef.RThighDef
bd.position += position
self.RThigh = self.world.CreateBody(bd)
self.RThigh.CreateShape(bdef.RThighPoly)
self.RThigh.SetMassFromShapes()
bd = bdef.PelvisDef
bd.position += position
self.Pelvis = self.world.CreateBody(bd)
self.Pelvis.CreateShape(bdef.PelvisPoly)
self.Pelvis.SetMassFromShapes()
bd = bdef.StomachDef
bd.position += position
self.Stomach = self.world.CreateBody(bd)
self.Stomach.CreateShape(bdef.StomachPoly)
self.Stomach.SetMassFromShapes()
bd = bdef.ChestDef
bd.position += position
self.Chest = self.world.CreateBody(bd)
self.Chest.CreateShape(bdef.ChestPoly)
self.Chest.SetMassFromShapes()
bd = bdef.NeckDef
bd.position += position
self.Neck = self.world.CreateBody(bd)
self.Neck.CreateShape(bdef.NeckPoly)
self.Neck.SetMassFromShapes()
bd = bdef.HeadDef
bd.position += position
self.Head = self.world.CreateBody(bd)
self.Head.CreateShape(bdef.HeadCirc)
self.Head.SetMassFromShapes()
bd = bdef.LUpperArmDef
bd.position += position
self.LUpperArm = self.world.CreateBody(bd)
self.LUpperArm.CreateShape(bdef.LUpperArmPoly)
self.LUpperArm.SetMassFromShapes()
bd = bdef.RUpperArmDef
bd.position += position
self.RUpperArm = self.world.CreateBody(bd)
self.RUpperArm.CreateShape(bdef.RUpperArmPoly)
self.RUpperArm.SetMassFromShapes()
bd = bdef.LForearmDef
bd.position += position
self.LForearm = self.world.CreateBody(bd)
self.LForearm.CreateShape(bdef.LForearmPoly)
self.LForearm.SetMassFromShapes()
bd = bdef.RForearmDef
bd.position += position
self.RForearm = self.world.CreateBody(bd)
self.RForearm.CreateShape(bdef.RForearmPoly)
self.RForearm.SetMassFromShapes()
bd = bdef.LHandDef
bd.position += position
self.LHand = self.world.CreateBody(bd)
self.LHand.CreateShape(bdef.LHandPoly)
self.LHand.SetMassFromShapes()
bd = bdef.RHandDef
bd.position += position
self.RHand = self.world.CreateBody(bd)
self.RHand.CreateShape(bdef.RHandPoly)
self.RHand.SetMassFromShapes()
# link body parts
bdef.LAnkleDef.body1 = self.LFoot
bdef.LAnkleDef.body2 = self.LCalf
bdef.RAnkleDef.body1 = self.RFoot
bdef.RAnkleDef.body2 = self.RCalf
bdef.LKneeDef.body1 = self.LCalf
bdef.LKneeDef.body2 = self.LThigh
bdef.RKneeDef.body1 = self.RCalf
bdef.RKneeDef.body2 = self.RThigh
bdef.LHipDef.body1 = self.LThigh
bdef.LHipDef.body2 = self.Pelvis
bdef.RHipDef.body1 = self.RThigh
bdef.RHipDef.body2 = self.Pelvis
bdef.LowerAbsDef.body1 = self.Pelvis
bdef.LowerAbsDef.body2 = self.Stomach
bdef.UpperAbsDef.body1 = self.Stomach
bdef.UpperAbsDef.body2 = self.Chest
bdef.LowerNeckDef.body1 = self.Chest
bdef.LowerNeckDef.body2 = self.Neck
bdef.UpperNeckDef.body1 = self.Chest
bdef.UpperNeckDef.body2 = self.Head
bdef.LShoulderDef.body1 = self.Chest
bdef.LShoulderDef.body2 = self.LUpperArm
bdef.RShoulderDef.body1 = self.Chest
bdef.RShoulderDef.body2 = self.RUpperArm
bdef.LElbowDef.body1 = self.LForearm
bdef.LElbowDef.body2 = self.LUpperArm
bdef.RElbowDef.body1 = self.RForearm
bdef.RElbowDef.body2 = self.RUpperArm
bdef.LWristDef.body1 = self.LHand
bdef.LWristDef.body2 = self.LForearm
bdef.RWristDef.body1 = self.RHand
bdef.RWristDef.body2 = self.RForearm
# create joints
self.LAnkle = self.world.CreateJoint(bdef.LAnkleDef).getAsType()
self.RAnkle = self.world.CreateJoint(bdef.RAnkleDef).getAsType()
self.LKnee = self.world.CreateJoint(bdef.LKneeDef).getAsType()
self.RKnee = self.world.CreateJoint(bdef.RKneeDef).getAsType()
self.LHip = self.world.CreateJoint(bdef.LHipDef).getAsType()
self.RHip = self.world.CreateJoint(bdef.RHipDef).getAsType()
self.LowerAbs = self.world.CreateJoint(bdef.LowerAbsDef).getAsType()
self.UpperAbs = self.world.CreateJoint(bdef.UpperAbsDef).getAsType()
self.LowerNeck = self.world.CreateJoint(bdef.LowerNeckDef).getAsType()
self.UpperNeck = self.world.CreateJoint(bdef.UpperNeckDef).getAsType()
self.LShoulder = self.world.CreateJoint(bdef.LShoulderDef).getAsType()
self.RShoulder = self.world.CreateJoint(bdef.RShoulderDef).getAsType()
self.LElbow = self.world.CreateJoint(bdef.LElbowDef).getAsType()
self.RElbow = self.world.CreateJoint(bdef.RElbowDef).getAsType()
self.LWrist = self.world.CreateJoint(bdef.LWristDef).getAsType()
self.RWrist = self.world.CreateJoint(bdef.RWristDef).getAsType()
class BipedDef(object):
# BodyDefs
LFootDef=box2d.b2BodyDef()
RFootDef=box2d.b2BodyDef()
LCalfDef=box2d.b2BodyDef()
RCalfDef=box2d.b2BodyDef()
LThighDef=box2d.b2BodyDef()
RThighDef=box2d.b2BodyDef()
PelvisDef=box2d.b2BodyDef()
StomachDef=box2d.b2BodyDef()
ChestDef=box2d.b2BodyDef()
NeckDef=box2d.b2BodyDef()
HeadDef=box2d.b2BodyDef()
LUpperArmDef=box2d.b2BodyDef()
RUpperArmDef=box2d.b2BodyDef()
LForearmDef=box2d.b2BodyDef()
RForearmDef=box2d.b2BodyDef()
LHandDef=box2d.b2BodyDef()
RHandDef=box2d.b2BodyDef()
# Polygons
LFootPoly=box2d.b2PolygonDef()
RFootPoly=box2d.b2PolygonDef()
LCalfPoly=box2d.b2PolygonDef()
RCalfPoly=box2d.b2PolygonDef()
LThighPoly=box2d.b2PolygonDef()
RThighPoly=box2d.b2PolygonDef()
PelvisPoly=box2d.b2PolygonDef()
StomachPoly=box2d.b2PolygonDef()
ChestPoly=box2d.b2PolygonDef()
NeckPoly=box2d.b2PolygonDef()
LUpperArmPoly=box2d.b2PolygonDef()
RUpperArmPoly=box2d.b2PolygonDef()
LForearmPoly=box2d.b2PolygonDef()
RForearmPoly=box2d.b2PolygonDef()
LHandPoly=box2d.b2PolygonDef()
RHandPoly=box2d.b2PolygonDef()
# Circles
HeadCirc=box2d.b2CircleDef()
# Revolute Joints
LAnkleDef=box2d.b2RevoluteJointDef()
RAnkleDef=box2d.b2RevoluteJointDef()
LKneeDef=box2d.b2RevoluteJointDef()
RKneeDef=box2d.b2RevoluteJointDef()
LHipDef=box2d.b2RevoluteJointDef()
RHipDef=box2d.b2RevoluteJointDef()
LowerAbsDef=box2d.b2RevoluteJointDef()
UpperAbsDef=box2d.b2RevoluteJointDef()
LowerNeckDef=box2d.b2RevoluteJointDef()
UpperNeckDef=box2d.b2RevoluteJointDef()
LShoulderDef=box2d.b2RevoluteJointDef()
RShoulderDef=box2d.b2RevoluteJointDef()
LElbowDef=box2d.b2RevoluteJointDef()
RElbowDef=box2d.b2RevoluteJointDef()
LWristDef=box2d.b2RevoluteJointDef()
RWristDef=box2d.b2RevoluteJointDef()
count = 0
def __init__(self):
# So much cleaner in Python than C++ :)
self.iter_polys = ( self.LFootPoly, self.RFootPoly, self.LCalfPoly, self.RCalfPoly, self.LThighPoly, self.RThighPoly,
self.PelvisPoly, self.StomachPoly, self.ChestPoly, self.NeckPoly,
self.LUpperArmPoly, self.RUpperArmPoly, self.LForearmPoly, self.RForearmPoly, self.LHandPoly, self.RHandPoly ,
self.HeadCirc )
self.iter_defs = ( self.LFootDef, self.RFootDef, self.LCalfDef, self.RCalfDef, self.LThighDef, self.RThighDef,
self.PelvisDef, self.StomachDef, self.ChestDef, self.NeckDef, self.HeadDef,
self.LUpperArmDef, self.RUpperArmDef, self.LForearmDef, self.RForearmDef, self.LHandDef, self.RHandDef )
self.iter_joints=( self.LAnkleDef, self.RAnkleDef, self.LKneeDef, self.RKneeDef, self.LHipDef, self.RHipDef,
self.LowerAbsDef, self.UpperAbsDef, self.LowerNeckDef, self.UpperNeckDef,
self.LShoulderDef, self.RShoulderDef, self.LElbowDef, self.RElbowDef, self.LWristDef, self.RWristDef )
self.SetMotorTorque(2.0)
self.SetMotorSpeed(0.0)
self.SetDensity(20.0)
self.SetRestitution(0.0)
self.SetLinearDamping(0.0)
self.SetAngularDamping(0.005)
self.count -= 1
self.SetGroupIndex(self.count)
self.EnableMotor()
self.EnableLimit()
self.DefaultVertices()
self.DefaultPositions()
self.DefaultJoints()
self.LFootPoly.friction = self.RFootPoly.friction = 0.85
def IsFast(self, b):
pass
def SetGroupIndex(self, i):
for o in self.iter_polys:
o.filter.groupIndex = i
def SetLinearDamping(self, f):
for d in self.iter_defs:
d.linearDamping = f
def SetAngularDamping(self, f):
for d in self.iter_defs:
d.angularDamping = f
def SetMotorTorque(self, f):
for j in self.iter_joints:
j.maxMotorTorque = f
def SetMotorSpeed(self, f):
for j in self.iter_joints:
j.motorSpeed = f
def SetDensity(self, f):
for o in self.iter_polys:
o.density = f
def SetRestitution(self, f):
for o in self.iter_polys:
o.restitution = f
def EnableLimit(self):
self.SetLimit(True)
def DisableLimit(self):
self.SetLimit(False)
def SetLimit(self, b):
for j in self.iter_joints:
j.enableLimit = b
def EnableMotor(self):
self.SetMotor(True)
def DisableMotor(self):
self.SetMotor(False)
def SetMotor(self, b):
for j in self.iter_joints:
j.enableMotor = b
def DefaultVertices(self):
global k_scale
# feet
for poly in (self.LFootPoly, self.RFootPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.033,.143),
k_scale * box2d.b2Vec2(.023,.033),
k_scale * box2d.b2Vec2(.267,.035),
k_scale * box2d.b2Vec2(.265,.065),
k_scale * box2d.b2Vec2(.117,.143)])
# calves
for poly in (self.LCalfPoly, self.RCalfPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.089,.016),
k_scale * box2d.b2Vec2(.178,.016),
k_scale * box2d.b2Vec2(.205,.417),
k_scale * box2d.b2Vec2(.095,.417)])
# thighs
for poly in (self.LThighPoly, self.RThighPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.137,.032),
k_scale * box2d.b2Vec2(.243,.032),
k_scale * box2d.b2Vec2(.318,.343),
k_scale * box2d.b2Vec2(.142,.343)])
# pelvis
self.PelvisPoly.setVertices([
k_scale * box2d.b2Vec2(.105,.051),
k_scale * box2d.b2Vec2(.277,.053),
k_scale * box2d.b2Vec2(.320,.233),
k_scale * box2d.b2Vec2(.112,.233),
k_scale * box2d.b2Vec2(.067,.152)])
# stomach
self.StomachPoly.setVertices([
k_scale * box2d.b2Vec2(.088,.043),
k_scale * box2d.b2Vec2(.284,.043),
k_scale * box2d.b2Vec2(.295,.231),
k_scale * box2d.b2Vec2(.100,.231)])
# chest
self.ChestPoly.setVertices([
k_scale * box2d.b2Vec2(.091,.042),
k_scale * box2d.b2Vec2(.283,.042),
k_scale * box2d.b2Vec2(.177,.289),
k_scale * box2d.b2Vec2(.065,.289)])
# head
self.HeadCirc.radius = k_scale * .115
# neck
self.NeckPoly.setVertices([
k_scale * box2d.b2Vec2(.038,.054),
k_scale * box2d.b2Vec2(.149,.054),
k_scale * box2d.b2Vec2(.154,.102),
k_scale * box2d.b2Vec2(.054,.113)])
# upper arms
for poly in (self.LUpperArmPoly, self.RUpperArmPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.092,.059),
k_scale * box2d.b2Vec2(.159,.059),
k_scale * box2d.b2Vec2(.169,.335),
k_scale * box2d.b2Vec2(.078,.335),
k_scale * box2d.b2Vec2(.064,.248)])
# forearms
for poly in (self.LForearmPoly, self.RForearmPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.082,.054),
k_scale * box2d.b2Vec2(.138,.054),
k_scale * box2d.b2Vec2(.149,.296),
k_scale * box2d.b2Vec2(.088,.296)])
# hands
for poly in (self.LHandPoly, self.RHandPoly):
poly.setVertices([
k_scale * box2d.b2Vec2(.066,.031),
k_scale * box2d.b2Vec2(.123,.020),
k_scale * box2d.b2Vec2(.160,.127),
k_scale * box2d.b2Vec2(.127,.178),
k_scale * box2d.b2Vec2(.074,.178)])
def DefaultJoints(self):
global k_scale
#b.LAnkleDef.body1 = LFoot
#b.LAnkleDef.body2 = LCalf
#b.self.RAnkleDef.body1 = self.RFoot
#b.self.RAnkleDef.body2 = self.RCalf
# ankles
anchor = k_scale * box2d.b2Vec2(-.045,-.75)
self.LAnkleDef.localAnchor1 = self.RAnkleDef.localAnchor1 = anchor - self.LFootDef.position
self.LAnkleDef.localAnchor2 = self.RAnkleDef.localAnchor2 = anchor - self.LCalfDef.position
self.LAnkleDef.referenceAngle = self.RAnkleDef.referenceAngle = 0.0
self.LAnkleDef.lowerAngle = self.RAnkleDef.lowerAngle = -0.523598776
self.LAnkleDef.upperAngle = self.RAnkleDef.upperAngle = 0.523598776
#b.self.LKneeDef.body1 = self.LCalf
#b.self.LKneeDef.body2 = self.LThigh
#b.self.RKneeDef.body1 = self.RCalf
#b.self.RKneeDef.body2 = self.RThigh
# knees
anchor = k_scale * box2d.b2Vec2(-.030,-.355)
self.LKneeDef.localAnchor1 = self.RKneeDef.localAnchor1 = anchor - self.LCalfDef.position
self.LKneeDef.localAnchor2 = self.RKneeDef.localAnchor2 = anchor - self.LThighDef.position
self.LKneeDef.referenceAngle = self.RKneeDef.referenceAngle = 0.0
self.LKneeDef.lowerAngle = self.RKneeDef.lowerAngle = 0
self.LKneeDef.upperAngle = self.RKneeDef.upperAngle = 2.61799388
#b.self.LHipDef.body1 = self.LThigh
#b.self.LHipDef.body2 = Pelvis
#b.self.RHipDef.body1 = self.RThigh
#b.self.RHipDef.body2 = Pelvis
# hips
anchor = k_scale * box2d.b2Vec2(.005,-.045)
self.LHipDef.localAnchor1 = self.RHipDef.localAnchor1 = anchor - self.LThighDef.position
self.LHipDef.localAnchor2 = self.RHipDef.localAnchor2 = anchor - self.PelvisDef.position
self.LHipDef.referenceAngle = self.RHipDef.referenceAngle = 0.0
self.LHipDef.lowerAngle = self.RHipDef.lowerAngle = -2.26892803
self.LHipDef.upperAngle = self.RHipDef.upperAngle = 0
#b.self.LowerAbsDef.body1 = Pelvis
#b.self.LowerAbsDef.body2 = Stomach
# lower abs
anchor = k_scale * box2d.b2Vec2(.035,.135)
self.LowerAbsDef.localAnchor1 = anchor - self.PelvisDef.position
self.LowerAbsDef.localAnchor2 = anchor - self.StomachDef.position
self.LowerAbsDef.referenceAngle = 0.0
self.LowerAbsDef.lowerAngle = -0.523598776
self.LowerAbsDef.upperAngle = 0.523598776
#b.UpperAbsDef.body1 = Stomach
#b.UpperAbsDef.body2 = Chest
# upper abs
anchor = k_scale * box2d.b2Vec2(.045,.320)
self.UpperAbsDef.localAnchor1 = anchor - self.StomachDef.position
self.UpperAbsDef.localAnchor2 = anchor - self.ChestDef.position
self.UpperAbsDef.referenceAngle = 0.0
self.UpperAbsDef.lowerAngle = -0.523598776
self.UpperAbsDef.upperAngle = 0.174532925
#b.self.LowerNeckDef.body1 = Chest
#b.self.LowerNeckDef.body2 = Neck
# lower neck
anchor = k_scale * box2d.b2Vec2(-.015,.575)
self.LowerNeckDef.localAnchor1 = anchor - self.ChestDef.position
self.LowerNeckDef.localAnchor2 = anchor - self.NeckDef.position
self.LowerNeckDef.referenceAngle = 0.0
self.LowerNeckDef.lowerAngle = -0.174532925
self.LowerNeckDef.upperAngle = 0.174532925
#b.self.UpperNeckDef.body1 = Chest
#b.self.UpperNeckDef.body2 = Head
# upper neck
anchor = k_scale * box2d.b2Vec2(-.005,.630)
self.UpperNeckDef.localAnchor1 = anchor - self.ChestDef.position
self.UpperNeckDef.localAnchor2 = anchor - self.HeadDef.position
self.UpperNeckDef.referenceAngle = 0.0
self.UpperNeckDef.lowerAngle = -0.610865238
self.UpperNeckDef.upperAngle = 0.785398163
#b.self.LShoulderDef.body1 = Chest
#b.self.LShoulderDef.body2 = self.LUpperArm
#b.self.RShoulderDef.body1 = Chest
#b.self.RShoulderDef.body2 = self.RUpperArm
# shoulders
anchor = k_scale * box2d.b2Vec2(-.015,.545)
self.LShoulderDef.localAnchor1 = self.RShoulderDef.localAnchor1 = anchor - self.ChestDef.position
self.LShoulderDef.localAnchor2 = self.RShoulderDef.localAnchor2 = anchor - self.LUpperArmDef.position
self.LShoulderDef.referenceAngle = self.RShoulderDef.referenceAngle = 0.0
self.LShoulderDef.lowerAngle = self.RShoulderDef.lowerAngle = -1.04719755
self.LShoulderDef.upperAngle = self.RShoulderDef.upperAngle = 3.14159265
#b.self.LElbowDef.body1 = self.LForearm
#b.self.LElbowDef.body2 = self.LUpperArm
#b.self.RElbowDef.body1 = self.RForearm
#b.self.RElbowDef.body2 = self.RUpperArm
# elbows
anchor = k_scale * box2d.b2Vec2(-.005,.290)
self.LElbowDef.localAnchor1 = self.RElbowDef.localAnchor1 = anchor - self.LForearmDef.position
self.LElbowDef.localAnchor2 = self.RElbowDef.localAnchor2 = anchor - self.LUpperArmDef.position
self.LElbowDef.referenceAngle = self.RElbowDef.referenceAngle = 0.0
self.LElbowDef.lowerAngle = self.RElbowDef.lowerAngle = -2.7925268
self.LElbowDef.upperAngle = self.RElbowDef.upperAngle = 0
#b.self.LWristDef.body1 = self.LHand
#b.self.LWristDef.body2 = self.LForearm
#b.self.RWristDef.body1 = self.RHand
#b.self.RWristDef.body2 = self.RForearm
# wrists
anchor = k_scale * box2d.b2Vec2(-.010,.045)
self.LWristDef.localAnchor1 = self.RWristDef.localAnchor1 = anchor - self.LHandDef.position
self.LWristDef.localAnchor2 = self.RWristDef.localAnchor2 = anchor - self.LForearmDef.position
self.LWristDef.referenceAngle = self.RWristDef.referenceAngle = 0.0
self.LWristDef.lowerAngle = self.RWristDef.lowerAngle = -0.174532925
self.LWristDef.upperAngle = self.RWristDef.upperAngle = 0.174532925
def DefaultPositions(self):
global k_scale
for foot in (self.LFootDef, self.RFootDef):
foot.position = k_scale * box2d.b2Vec2(-.122,-.901)
for calf in (self.LCalfDef, self.RCalfDef):
calf.position = k_scale * box2d.b2Vec2(-.177,-.771)
for thigh in (self.LThighDef, self.RThighDef):
thigh.position = k_scale * box2d.b2Vec2(-.217,-.391)
for upperarm in (self.LUpperArmDef, self.RUpperArmDef):
upperarm.position = k_scale * box2d.b2Vec2(-.127,.228)
for forearm in (self.LForearmDef, self.RForearmDef):
forearm.position = k_scale * box2d.b2Vec2(-.117,-.011)
for hand in (self.LHandDef, self.RHandDef):
hand.position = k_scale * box2d.b2Vec2(-.112,-.136)
self.PelvisDef.position = k_scale * box2d.b2Vec2(-.177,-.101)
self.StomachDef.position= k_scale * box2d.b2Vec2(-.142,.088)
self.ChestDef.position = k_scale * box2d.b2Vec2(-.132,.282)
self.NeckDef.position = k_scale * box2d.b2Vec2(-.102,.518)
self.HeadDef.position = k_scale * box2d.b2Vec2(.022,.738)
if __name__=="__main__":
main(Test_Biped)
python-box2d-2.0.2+svn20100109.244/testbed/test_Gears.py 0000644 0000000 0000000 00000010542 11136402204 020574 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class Gears (Framework):
name="Gears"
joint1=None
joint2=None
joint3=None
joint4=None
joint5=None
_pickle_vars = ['joint1', 'joint2', 'joint3', 'joint4', 'joint5']
def __init__(self):
super(Gears, self).__init__()
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
ground.CreateShape(sd)
circle1=box2d.b2CircleDef()
circle1.radius = 1.0
circle1.density = 5.0
circle2=box2d.b2CircleDef()
circle2.radius = 2.0
circle2.density = 5.0
box=box2d.b2PolygonDef()
box.SetAsBox(0.5, 5.0)
box.density = 5.0
bd1=box2d.b2BodyDef()
bd1.position = (-3.0, 12.0)
body1 = self.world.CreateBody(bd1)
body1.CreateShape(circle1)
body1.SetMassFromShapes()
jd1=box2d.b2RevoluteJointDef()
jd1.body1 = ground
jd1.body2 = body1
jd1.localAnchor1 = ground.GetLocalPoint(bd1.position)
jd1.localAnchor2 = body1.GetLocalPoint(bd1.position)
jd1.referenceAngle = body1.GetAngle() - ground.GetAngle()
self.joint1 = self.world.CreateJoint(jd1).getAsType()
bd2=box2d.b2BodyDef()
bd2.position = (0.0, 12.0)
body2 = self.world.CreateBody(bd2)
body2.CreateShape(circle2)
body2.SetMassFromShapes()
jd2=box2d.b2RevoluteJointDef()
jd2.Initialize(ground, body2, bd2.position)
self.joint2 = self.world.CreateJoint(jd2).getAsType()
bd3=box2d.b2BodyDef()
bd3.position = (2.5, 12.0)
body3 = self.world.CreateBody(bd3)
body3.CreateShape(box)
body3.SetMassFromShapes()
jd3=box2d.b2PrismaticJointDef()
jd3.Initialize(ground, body3, bd3.position, (0.0, 1.0))
jd3.lowerTranslation = -5.0
jd3.upperTranslation = 5.0
jd3.enableLimit = True
self.joint3 = self.world.CreateJoint(jd3).getAsType()
jd4=box2d.b2GearJointDef()
jd4.body1 = body1
jd4.body2 = body2
jd4.joint1 = self.joint1
jd4.joint2 = self.joint2
jd4.ratio = circle2.radius / circle1.radius
self.joint4 = self.world.CreateJoint(jd4).getAsType()
jd5=box2d.b2GearJointDef()
jd5.body1 = body2
jd5.body2 = body3
jd5.joint1 = self.joint2
jd5.joint2 = self.joint3
jd5.ratio = -1.0 / circle2.radius
self.joint5 = self.world.CreateJoint(jd5).getAsType()
def Step(self, settings):
if self.joint1 and self.joint2 and self.joint3 and self.joint4 and self.joint5:
ratio = self.joint4.GetRatio()
value = self.joint1.GetJointAngle() + ratio * self.joint2.GetJointAngle()
self.DrawStringCR("theta1 + %.2f * theta2 = %.2f" % (ratio, value))
ratio = self.joint5.GetRatio()
value = self.joint2.GetJointAngle() + ratio * self.joint3.GetJointTranslation()
self.DrawStringCR("theta2 + %.2f * delta = %.2f" % (ratio, value))
super(Gears, self).Step(settings)
if __name__=="__main__":
main(Gears)
python-box2d-2.0.2+svn20100109.244/testbed/test_ContactCallbackTest.py 0000644 0000000 0000000 00000012372 11135461416 023417 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
from test_main import fwContactTypes
import math
import pprint
pp = pprint.PrettyPrinter(indent=4)
# Contributed by caspin (C++ version)
class ContactCallbackTest (Framework):
name="ContactCallbackTest"
ball=None
bullet=None
ball_shape=None
_pickle_vars = ['ball', 'bullet', 'ball_shape']
def __init__(self):
super(ContactCallbackTest, self).__init__()
groundBody = self.world.GetGroundBody()
sd=box2d.b2PolygonDef()
sd.friction = 0
sd.vertices = [(10.0, 10.0), (9.0, 7.0), (10.0, 0.0)]
sd.userData = 1
groundBody.CreateShape(sd)
sd.vertices = [(9.0, 7.0), (8.0, 0.0), (10.0, 0.0)]
sd.userData = 2
groundBody.CreateShape(sd)
sd.vertices = [(9.0, 7.0), (8.0, 5.0), (8.0, 0.0)]
sd.userData = 3
groundBody.CreateShape(sd)
sd.vertices = [(8.0, 5.0), (7.0, 4.0), (8.0, 0.0)]
sd.userData = 4
groundBody.CreateShape(sd)
sd.vertices = [(7.0, 4.0), (5.0, 0.0), (8.0, 0.0)]
sd.userData = 5
groundBody.CreateShape(sd)
sd.vertices = [(7.0, 4.0), (5.0, 3.0), (5.0, 0.0)]
sd.userData = 6
groundBody.CreateShape(sd)
sd.vertices = [(5.0, 3.0), (2.0, 2.0), (5.0, 0.0)]
sd.userData = 7
groundBody.CreateShape(sd)
sd.vertices = [(2.0, 2.0), (0.0, 0.0), (5.0, 0.0)]
sd.userData = 8
groundBody.CreateShape(sd)
sd.vertices = [(2.0, 2.0), (-2.0, 2.0), (0.0, 0.0)]
sd.userData = 9
groundBody.CreateShape(sd)
sd.vertices = [(-5.0, 0.0), (0.0, 0.0), (-2.0, 2.0)]
sd.userData = 10
groundBody.CreateShape(sd)
sd.vertices = [(-5.0, 0.0), (-2.0, 2.0), (-5.0, 3.0)]
sd.userData = 11
groundBody.CreateShape(sd)
sd.vertices = [(-5.0, 0.0), (-5.0, 3.0), (-7.0, 4.0)]
sd.userData = 12
groundBody.CreateShape(sd)
sd.vertices = [(-8.0, 0.0), (-5.0, 0.0), (-7.0, 4.0)]
sd.userData = 13
groundBody.CreateShape(sd)
sd.vertices = [(-8.0, 0.0), (-7.0, 4.0), (-8.0, 5.0)]
sd.userData = 14
groundBody.CreateShape(sd)
sd.vertices = [(-8.0, 0.0), (-8.0, 5.0), (-9.0, 7.0)]
sd.userData = 15
groundBody.CreateShape(sd)
sd.vertices = [(-10.0, 0.0), (-8.0, 0.0), (-9.0, 7.0)]
sd.userData = 16
groundBody.CreateShape(sd)
sd.vertices = [(-10.0, 0.0), (-9.0, 7.0), (-10.0, 10.0)]
sd.userData = 17
groundBody.CreateShape(sd)
sd.SetAsBox(.5,6,(10.5,6),0)
groundBody.CreateShape(sd)
sd.SetAsBox(.5,6,(-10.5,6),0)
groundBody.CreateShape(sd)
bd=box2d.b2BodyDef()
bd.position=(9.5,60)
self.ball = self.world.CreateBody( bd )
cd=box2d.b2PolygonDef()
cd.vertexCount = 8
w = 1.0
b = w / (2.0 + math.sqrt(2.0))
s = math.sqrt(2.0) * b
cd.vertices = [( 0.5 * s, 0.0),
( 0.5 * w, b),
( 0.5 * w, b + s),
( 0.5 * s, w),
(-0.5 * s, w),
(-0.5 * w, b + s),
(-0.5 * w, b),
(-0.5 * s, 0.0) ]
cd.density = 1.0
cd.userData = 'BALL'
self.ball_shape = self.ball.CreateShape(cd)
self.ball.SetMassFromShapes()
def Step(self, settings):
strings = []
name_dict = { fwContactTypes.contactAdded : "added",
fwContactTypes.contactRemoved : "removed",
fwContactTypes.contactPersisted : "persisted" }
strings = ["%s: %s, %s (%s)" % (name_dict[point.state], point.shape1.userData, point.shape2.userData, point.id.key)
for point in self.points]
if len(strings) > 15:
strings = strings[:14]
for string in strings:
self.DrawStringCR(string)
super(ContactCallbackTest, self).Step(settings)
if __name__=="__main__":
main(ContactCallbackTest)
python-box2d-2.0.2+svn20100109.244/testbed/console.py 0000644 0000000 0000000 00000022673 11156662747 020174 0 ustar root root #!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# Interactive Python-GTK Console
# Copyright ©, 1998 James Henstridge
# Copyright ©, 2005 Adam Hooper
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
# This module implements an interactive python session in a GTK window. To
# start the session, use the gtk_console command. Its specification is:
# gtk_console(namespace, title)
# where namespace is a dictionary representing the namespace of the session,
# title is the title on the window and
#
# As well as the starting attributes in namespace, the session will also
# have access to the list __history__, which is the command history.
import sys, string, traceback
import gobject
import gtk
import pango
import gtk.keysyms
stdout = sys.stdout
if not hasattr(sys, 'ps1'): sys.ps1 = '>>> '
if not hasattr(sys, 'ps2'): sys.ps2 = '... '
# some functions to help recognise breaks between commands
def remQuotStr(s):
'''Returns s with any quoted strings removed (leaving quote marks)'''
r = ''
inq = 0
qt = ''
prev = '_'
while len(s):
s0, s = s[0], s[1:]
if inq and (s0 != qt or prev == '\\'):
prev = s0
continue
prev = s0
if s0 in '\'"':
if inq:
inq = 0
else:
inq = 1
qt = s0
r = r + s0
return r
def bracketsBalanced(s):
'''Returns true iff the brackets in s are balanced'''
b = filter(lambda x: x in '([{', s)
e = filter(lambda x: x in ')]}', s)
return len(e) >= len(b)
class gtkoutfile:
'''A fake output file object. It sends output to a TK test widget,
and if asked for a file number, returns one set on instance creation'''
def __init__(self, w, fn, tag):
self.__fn = fn
self.__w = w
self.__tag = tag
def close(self): pass
flush = close
def fileno(self): return self.__fn
def isatty(self): return 0
def read(self, a): return ''
def readline(self): return ''
def readlines(self): return []
def write(self, s):
#stdout.write(str(self.__w.get_point()) + '\n')
self.__w.text_insert(self.__tag, s)
def writelines(self, l):
self.__w.text_insert(self.__tag, l)
def seek(self, a): raise IOError, (29, 'Illegal seek')
def tell(self): raise IOError, (29, 'Illegal seek')
truncate = tell
class Console(gtk.VBox):
def __init__(self, namespace={}, quit_cb=None):
gtk.VBox.__init__(self, spacing=12)
self.set_border_width(12)
self.quit_cb = quit_cb
self.inp = gtk.HBox()
self.pack_start(self.inp)
self.inp.show()
self.sw = gtk.ScrolledWindow()
self.sw.set_policy(gtk.POLICY_NEVER, gtk.POLICY_AUTOMATIC);
self.sw.set_shadow_type(gtk.SHADOW_IN)
self.inp.pack_start(self.sw, padding=1)
self.sw.show()
self.text = gtk.TextView()
self.text.modify_font(pango.FontDescription('Monospace'))
self.text.set_editable(False)
self.text.set_wrap_mode (gtk.WRAP_WORD)
self.sw.add(self.text)
self.text.show()
buffer = self.text.get_buffer()
self.normal = buffer.create_tag("normal")
self.error = buffer.create_tag("error")
self.error.set_property("foreground", "red")
self.command = buffer.create_tag('command')
self.command.set_property("foreground", "blue")
self.inputbox = gtk.HBox(spacing=2)
self.pack_end(self.inputbox, expand=False)
self.inputbox.show()
self.prompt = gtk.Label(sys.ps1)
self.prompt.set_padding(2, 0)
self.prompt.modify_font(pango.FontDescription('Monospace 10'))
self.inputbox.pack_start(self.prompt, expand=False)
self.prompt.show()
self.line = gtk.Entry()
self.line.modify_font(pango.FontDescription('Monospace'))
self.line.connect("key_press_event", self.key_function)
self.inputbox.pack_start(self.line, padding=2)
self.line.show()
self.namespace = namespace
self.cmd = ''
self.cmd2 = ''
# set up hooks for standard output.
self.stdout = gtkoutfile(self, sys.stdout.fileno(),
self.normal)
try :
# this will mostly fail on win32 ...
self.stderr = gtkoutfile(self, sys.stderr.fileno(),
self.error)
except :
# ... but gtkoutfile is not using the fileno anyway
self.stderr = gtkoutfile(self, -1, self.error)
# set up command history
self.history = ['']
self.histpos = 0
self.namespace['__history__'] = self.history
def scroll_to_end (self):
iter = self.text.get_buffer().get_end_iter()
self.text.scroll_to_iter(iter, 0.0)
return False # don't requeue this handler
def text_insert(self, tag, s):
buffer = self.text.get_buffer()
iter = buffer.get_end_iter()
buffer.insert_with_tags (iter, s, tag)
gobject.idle_add(self.scroll_to_end)
def init(self):
self.text.realize()
self.text.fg = self.text.style.fg[gtk.STATE_NORMAL]
self.text.bg = self.text.style.white
self.line.grab_focus()
def quit(self, *args):
#self.destroy()
if self.quit_cb: self.quit_cb()
def key_function(self, entry, event):
if event.keyval == gtk.keysyms.Return:
self.line.emit_stop_by_name("key_press_event")
self.eval()
elif event.keyval == gtk.keysyms.Tab:
self.line.emit_stop_by_name("key_press_event")
self.line.insert_text('\t')
gobject.idle_add(self.focus_text)
elif event.keyval in (gtk.keysyms.KP_Up, gtk.keysyms.Up) \
or (event.keyval in (gtk.keysyms.P, gtk.keysyms.p) and
event.state & gtk.gdk.CONTROL_MASK):
self.line.emit_stop_by_name("key_press_event")
self.historyUp()
gobject.idle_add(self.focus_text)
elif event.keyval in (gtk.keysyms.KP_Down, gtk.keysyms.Down) \
or (event.keyval in (gtk.keysyms.N, gtk.keysyms.n) and
event.state & gtk.gdk.CONTROL_MASK):
self.line.emit_stop_by_name("key_press_event")
self.historyDown()
gobject.idle_add(self.focus_text)
elif event.keyval in (gtk.keysyms.L, gtk.keysyms.l) and \
event.state & gtk.gdk.CONTROL_MASK:
self.text.get_buffer().set_text('')
elif event.keyval in (gtk.keysyms.D, gtk.keysyms.d) and \
event.state & gtk.gdk.CONTROL_MASK:
self.line.emit_stop_by_name("key_press_event")
self.ctrld()
def focus_text(self):
self.line.grab_focus()
return False # don't requeue this handler
def ctrld(self):
self.quit()
pass
def historyUp(self):
if self.histpos > 0:
l = self.line.get_text()
if len(l) > 0 and l[0] == '\n': l = l[1:]
if len(l) > 0 and l[-1] == '\n': l = l[:-1]
self.history[self.histpos] = l
self.histpos = self.histpos - 1
self.line.set_text(self.history[self.histpos])
def historyDown(self):
if self.histpos < len(self.history) - 1:
l = self.line.get_text()
if len(l) > 0 and l[0] == '\n': l = l[1:]
if len(l) > 0 and l[-1] == '\n': l = l[:-1]
self.history[self.histpos] = l
self.histpos = self.histpos + 1
self.line.set_text(self.history[self.histpos])
def eval(self):
l = self.line.get_text() + '\n'
if len(l) > 1 and l[0] == '\n': l = l[1:]
self.histpos = len(self.history) - 1
if len(l) > 0 and l[-1] == '\n':
self.history[self.histpos] = l[:-1]
else:
self.history[self.histpos] = l
self.line.set_text('')
self.text_insert(self.command, self.prompt.get() + l)
if l == '\n':
self.run(self.cmd)
self.cmd = ''
self.cmd2 = ''
return
self.histpos = self.histpos + 1
self.history.append('')
self.cmd = self.cmd + l
self.cmd2 = self.cmd2 + remQuotStr(l)
l = string.rstrip(l)
if not bracketsBalanced(self.cmd2) or l[-1] == ':' or \
l[-1] == '\\' or l[0] in ' \11':
self.prompt.set_text(sys.ps2)
self.prompt.queue_draw()
return
self.run(self.cmd)
self.cmd = ''
self.cmd2 = ''
def run(self, cmd):
sys.stdout, self.stdout = self.stdout, sys.stdout
sys.stderr, self.stderr = self.stderr, sys.stderr
try:
try:
r = eval(cmd, self.namespace, self.namespace)
if r is not None:
print `r`
except SyntaxError:
exec cmd in self.namespace
except:
if hasattr(sys, 'last_type') and \
sys.last_type == SystemExit:
self.quit()
else:
traceback.print_exc()
self.prompt.set_text(sys.ps1)
self.prompt.queue_draw()
#adj = self.text.get_vadjustment()
#adj.set_value(adj.upper - adj.page_size)
sys.stdout, self.stdout = self.stdout, sys.stdout
sys.stderr, self.stderr = self.stderr, sys.stderr
def gtk_console(parent, ns, title='Python'):
existing = parent.get_data('PythonConsole')
if existing:
existing.present()
return existing
win = gtk.Window()
parent._python_console = win
win.set_transient_for(parent)
win.set_destroy_with_parent(True)
win.set_default_size(475, 300)
win.set_title(title)
def key_cb(win, event):
if event.keyval in (gtk.keysyms.W, gtk.keysyms.w) and \
event.state & gtk.gdk.CONTROL_MASK:
win.hide()
if event.keyval == gtk.keysyms.Escape:
win.hide()
win.connect('key_press_event', key_cb)
def delete(win, event): win.hide(); return True
win.connect('delete-event', delete)
def quit(): win.hide()
cons = Console(namespace=ns, quit_cb=quit)
win.add(cons)
cons.show()
win.show()
cons.init()
return win
def console_cb(action, window):
gtk_console(window, {
'__builtins__':__builtins__,
'window':window,
})
python-box2d-2.0.2+svn20100109.244/testbed/test_SensorTest.py 0000644 0000000 0000000 00000007267 11135461416 021667 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class SensorTest (Framework):
name="SensorTest"
sensor=None
_pickle_vars=['sensor']
def __init__(self):
super(SensorTest, self).__init__()
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
ground.CreateShape(sd)
if True:
sd=box2d.b2PolygonDef()
sd.SetAsBox(10.0, 2.0, (0.0, 20.0), 0.0)
sd.isSensor = True
self.sensor = ground.CreateShape(sd)
else:
# Alternative test:
cd=box2d.b2CircleDef()
cd.isSensor = True
cd.radius = 5.0
cd.localPosition = (0.0, 20.0)
self.sensor = ground.CreateShape(cd)
sd=box2d.b2CircleDef()
sd.radius = 1.0
sd.density = 1.0
for i in range(10):
bd=box2d.b2BodyDef()
bd.position = (0.0 + 3.0 * i, 20.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
def Step(self, settings):
# Traverse the contact results. Apply a force on shapes
# that overlap the sensor.
for point in self.points:
if point.state == fwContactTypes.contactPersisted:
continue
shape1, shape2=point.shape1, point.shape2
other=None
if shape1 == self.sensor:
other = shape2.GetBody()
elif shape2 == self.sensor:
other = shape1.GetBody()
else:
continue
ground = self.sensor.GetBody()
typedshape = self.sensor.getAsType()
if self.sensor.GetType() == box2d.e_circleShape:
center = ground.GetWorldPoint(typedshape.GetLocalPosition())
elif self.sensor.GetType() == box2d.e_polygonShape:
center = ground.GetWorldPoint(typedshape.GetCentroid())
else:
print "don't know how to get the center of this shape, using (0,0)"
center = ground.GetWorldPoint(box2d.b2Vec2(0.0, 0.0))
d = center - point.position
if d.LengthSquared() < box2d.B2_FLT_EPSILON * box2d.B2_FLT_EPSILON:
continue
d.Normalize()
F = 100.0 * d
other.ApplyForce(F, point.position)
super(SensorTest, self).Step(settings)
if __name__=="__main__":
main(SensorTest)
python-box2d-2.0.2+svn20100109.244/testbed/test_Web.py 0000644 0000000 0000000 00000014466 11136402204 020261 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
# This tests distance joints, body destruction, and joint destruction.
class Web (Framework):
name="Web"
bodies=[]
joints=[]
_pickle_vars=['bodies', 'joints']
def __init__(self):
super(Web, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.5, 0.5)
sd.density = 5.0
sd.friction = 0.2
bd=box2d.b2BodyDef()
bd.position = (-5.0, 5.0)
self.bodies.append(self.world.CreateBody(bd))
self.bodies[0].CreateShape(sd)
self.bodies[0].SetMassFromShapes()
bd.position = (5.0, 5.0)
self.bodies.append(self.world.CreateBody(bd))
self.bodies[1].CreateShape(sd)
self.bodies[1].SetMassFromShapes()
bd.position = (5.0, 15.0)
self.bodies.append(self.world.CreateBody(bd))
self.bodies[2].CreateShape(sd)
self.bodies[2].SetMassFromShapes()
bd.position = (-5.0, 15.0)
self.bodies.append(self.world.CreateBody(bd))
self.bodies[3].CreateShape(sd)
self.bodies[3].SetMassFromShapes()
jd=box2d.b2DistanceJointDef()
jd.frequencyHz = 4.0
jd.dampingRatio = 0.5
jd.body1 = ground
jd.body2 = self.bodies[0]
jd.localAnchor1 = (-10.0, 10.0)
jd.localAnchor2 = (-0.5, -0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = ground
jd.body2 = self.bodies[1]
jd.localAnchor1 = (10.0, 10.0)
jd.localAnchor2 = (0.5, -0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = ground
jd.body2 = self.bodies[2]
jd.localAnchor1 = (10.0, 30.0)
jd.localAnchor2 = (0.5, 0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = ground
jd.body2 = self.bodies[3]
jd.localAnchor1 = (-10.0, 30.0)
jd.localAnchor2 = (-0.5, 0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = self.bodies[0]
jd.body2 = self.bodies[1]
jd.localAnchor1 = (0.5, 0.0)
jd.localAnchor2 = (-0.5, 0.0)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = self.bodies[1]
jd.body2 = self.bodies[2]
jd.localAnchor1 = (0.0, 0.5)
jd.localAnchor2 = (0.0, -0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = self.bodies[2]
jd.body2 = self.bodies[3]
jd.localAnchor1 = (-0.5, 0.0)
jd.localAnchor2 = (0.5, 0.0)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
jd.body1 = self.bodies[3]
jd.body2 = self.bodies[0]
jd.localAnchor1 = (0.0, -0.5)
jd.localAnchor2 = (0.0, 0.5)
p1 = jd.body1.GetWorldPoint(jd.localAnchor1)
p2 = jd.body2.GetWorldPoint(jd.localAnchor2)
d = p2 - p1
jd.length = d.Length()
self.joints.append(self.world.CreateJoint(jd).getAsType())
def Keyboard(self, key):
# Note: these functions are still causing some problems
if key==K_b:
for body in self.bodies:
self.bodies.remove(body)
self.world.DestroyBody(body)
break
elif key==K_j:
for joint in self.joints:
self.joints.remove(joint)
self.world.DestroyJoint(joint)
break
def Step(self, settings):
self.DrawStringCR("This demonstrates a soft distance joint.")
self.DrawStringCR("Press: (b) to delete a body, (j) to delete a joint")
super(Web, self).Step(settings)
def JointDestroyed(self, joint):
if joint in self.joints:
print "Joint destroyed and removed from the list"
self.joints.remove(joint)
if __name__=="__main__":
main(Web)
python-box2d-2.0.2+svn20100109.244/testbed/test_CollisionFiltering.py 0000644 0000000 0000000 00000012065 11135461416 023345 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class CollisionFiltering (Framework):
name="CollisionFiltering"
# This is a test of collision filtering.
# There is a triangle, a box, and a circle.
# There are 6 shapes. 3 large and 3 small.
# The 3 small ones always collide.
# The 3 large ones never collide.
# The boxes don't collide with triangles (except if both are small).
k_smallGroup = 1
k_largeGroup = -1
k_defaultCategory = 0x0001
k_triangleCategory = 0x0002
k_boxCategory = 0x0004
k_circleCategory = 0x0008
k_triangleMask = 0xFFFF
k_boxMask = 0xFFFF ^ k_triangleCategory
k_circleMask = 0xFFFF
def __init__(self):
super(CollisionFiltering, self).__init__()
# Ground body
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
sd.friction = 0.3
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
# Small triangle
triangleShapeDef=box2d.b2PolygonDef()
triangleShapeDef.vertexCount = 3
triangleShapeDef.setVertex(0,-1.0, 0.0)
triangleShapeDef.setVertex(1,1.0, 0.0)
triangleShapeDef.setVertex(2,0.0, 2.0)
triangleShapeDef.density = 1.0
triangleShapeDef.filter.groupIndex = self.k_smallGroup
triangleShapeDef.filter.categoryBits = self.k_triangleCategory
triangleShapeDef.filter.maskBits = self.k_triangleMask
triangleBodyDef=box2d.b2BodyDef()
triangleBodyDef.position = (-5.0, 2.0)
body1 = self.world.CreateBody(triangleBodyDef)
body1.CreateShape(triangleShapeDef)
body1.SetMassFromShapes()
# Large triangle (recycle definitions)
triangleShapeDef.setVertex(0, 2.0*triangleShapeDef.getVertex(0))
triangleShapeDef.setVertex(1, 2.0*triangleShapeDef.getVertex(1))
triangleShapeDef.setVertex(2, 2.0*triangleShapeDef.getVertex(2))
triangleShapeDef.filter.groupIndex = self.k_largeGroup
triangleBodyDef.position = (-5.0, 6.0)
triangleBodyDef.fixedRotation = True
body2 = self.world.CreateBody(triangleBodyDef)
body2.CreateShape(triangleShapeDef)
body2.SetMassFromShapes()
# Small box
boxShapeDef=box2d.b2PolygonDef()
boxShapeDef.SetAsBox(1.0, 0.5)
boxShapeDef.density = 1.0
boxShapeDef.filter.groupIndex = self.k_smallGroup
boxShapeDef.filter.categoryBits = self.k_boxCategory
boxShapeDef.filter.maskBits = self.k_boxMask
boxBodyDef=box2d.b2BodyDef()
boxBodyDef.position = (0.0, 2.0)
body3 = self.world.CreateBody(boxBodyDef)
body3.CreateShape(boxShapeDef)
body3.SetMassFromShapes()
# Large box (recycle definitions)
boxShapeDef.SetAsBox(2.0, 1.0)
boxShapeDef.filter.groupIndex = self.k_largeGroup
boxBodyDef.position = (0.0, 6.0)
body4 = self.world.CreateBody(boxBodyDef)
body4.CreateShape(boxShapeDef)
body4.SetMassFromShapes()
# Small circle
circleShapeDef=box2d.b2CircleDef()
circleShapeDef.radius = 1.0
circleShapeDef.density = 1.0
circleShapeDef.filter.groupIndex = self.k_smallGroup
circleShapeDef.filter.categoryBits = self.k_circleCategory
circleShapeDef.filter.maskBits = self.k_circleMask
circleBodyDef=box2d.b2BodyDef()
circleBodyDef.position = (5.0, 2.0)
body5 = self.world.CreateBody(circleBodyDef)
body5.CreateShape(circleShapeDef)
body5.SetMassFromShapes()
# Large circle
circleShapeDef.radius *= 2.0
circleShapeDef.filter.groupIndex = self.k_largeGroup
circleBodyDef.position = (5.0, 6.0)
body6 = self.world.CreateBody(circleBodyDef)
body6.CreateShape(circleShapeDef)
body6.SetMassFromShapes()
if __name__=="__main__":
main(CollisionFiltering)
python-box2d-2.0.2+svn20100109.244/testbed/pygame_keycodes.py 0000644 0000000 0000000 00000006425 11156662747 021677 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
# While the testbed tests were created with Pygame in mind, other backends
# can also be used. The keycodes are usualy the same in other frameworks
# but the testbed tests can use these constants to recognise the keyboard
# events.
K_0 = 48
K_1 = 49
K_2 = 50
K_3 = 51
K_4 = 52
K_5 = 53
K_6 = 54
K_7 = 55
K_8 = 56
K_9 = 57
K_AMPERSAND = 38
K_ASTERISK = 42
K_AT = 64
K_BACKQUOTE = 96
K_BACKSLASH = 92
K_BACKSPACE = 8
K_BREAK = 318
K_CAPSLOCK = 301
K_CARET = 94
K_CLEAR = 12
K_COLON = 58
K_COMMA = 44
K_DELETE = 127
K_DOLLAR = 36
K_DOWN = 274
K_END = 279
K_EQUALS = 61
K_ESCAPE = 27
K_EURO = 321
K_EXCLAIM = 33
K_F1 = 282
K_F10 = 291
K_F11 = 292
K_F12 = 293
K_F13 = 294
K_F14 = 295
K_F15 = 296
K_F2 = 283
K_F3 = 284
K_F4 = 285
K_F5 = 286
K_F6 = 287
K_F7 = 288
K_F8 = 289
K_F9 = 290
K_FIRST = 0
K_GREATER = 62
K_HASH = 35
K_HELP = 315
K_HOME = 278
K_INSERT = 277
K_KP0 = 256
K_KP1 = 257
K_KP2 = 258
K_KP3 = 259
K_KP4 = 260
K_KP5 = 261
K_KP6 = 262
K_KP7 = 263
K_KP8 = 264
K_KP9 = 265
K_KP_DIVIDE = 267
K_KP_ENTER = 271
K_KP_EQUALS = 272
K_KP_MINUS = 269
K_KP_MULTIPLY = 268
K_KP_PERIOD = 266
K_KP_PLUS = 270
K_LALT = 308
K_LAST = 323
K_LCTRL = 306
K_LEFT = 276
K_LEFTBRACKET = 91
K_LEFTPAREN = 40
K_LESS = 60
K_LMETA = 310
K_LSHIFT = 304
K_LSUPER = 311
K_MENU = 319
K_MINUS = 45
K_MODE = 313
K_NUMLOCK = 300
K_PAGEDOWN = 281
K_PAGEUP = 280
K_PAUSE = 19
K_PERIOD = 46
K_PLUS = 43
K_POWER = 320
K_PRINT = 316
K_QUESTION = 63
K_QUOTE = 39
K_QUOTEDBL = 34
K_RALT = 307
K_RCTRL = 305
K_RETURN = 13
K_RIGHT = 275
K_RIGHTBRACKET = 93
K_RIGHTPAREN = 41
K_RMETA = 309
K_RSHIFT = 303
K_RSUPER = 312
K_SCROLLOCK = 302
K_SEMICOLON = 59
K_SLASH = 47
K_SPACE = 32
K_SYSREQ = 317
K_TAB = 9
K_UNDERSCORE = 95
K_UNKNOWN = 0
K_UP = 273
K_a = 97
K_b = 98
K_c = 99
K_d = 100
K_e = 101
K_f = 102
K_g = 103
K_h = 104
K_i = 105
K_j = 106
K_k = 107
K_l = 108
K_m = 109
K_n = 110
K_o = 111
K_p = 112
K_q = 113
K_r = 114
K_s = 115
K_t = 116
K_u = 117
K_v = 118
K_w = 119
K_x = 120
K_y = 121
K_z = 122
if __name__ == '__main__':
# This file is generated using the code below
from pygame import locals
for nm_val in [(key, locals.__dict__[key])
for key in dir(locals)
if key.startswith('K_')]:
print "%s = %s" % nm_val
python-box2d-2.0.2+svn20100109.244/testbed/demos.py 0000644 0000000 0000000 00000020071 11135471136 017612 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
import os
import pygame
import Box2D as box2d
from pygame.locals import *
from settings import fwSettings
from pgu import gui
from test_main import fwDebugDraw
from distutils import sysconfig
global width, height
width, height = 640, 480
def main():
# Initialize pygame
screen = pygame.display.set_mode((width,height))
caption= "Python Box2D Testbed Demos"
pygame.display.set_caption(caption)
# Initialize the GUI
theme = gui.Theme("default")
app = gui.Desktop(theme=theme)
app.connect(gui.QUIT,app.quit,None)
main = gui.Container(width=width, height=height)
# Label at the top left
main.add(gui.Label("Box2D Testbed Demos", cls="h1"), 20, 20)
# The dimensions of the list of the demos
list_size= (width / 2, height / 2)
list_pos = (width/2 - list_size[0]/2, height/2 - list_size[1]/2)
# Create the actual widget
demolist = gui.List(width=list_size[0], height=list_size[1])
main.add(demolist, list_pos[0], list_pos[1])
# Add all the demos found in the directory to the list
add_demos(demolist)
buttonw = (list_size[0]/2-20) # width of the buttons
bottom = list_pos[1]+list_size[1]+20 # the y-location of the bottom of the list
# Create a Run button, calling run_demo on click
b = gui.Button("Run", width=buttonw)
main.add(b, list_pos[0], bottom)
b.connect(gui.CLICK, run_demo, demolist)
# Create a Quit button
b = gui.Button("Quit", width=buttonw)
main.add(b, list_pos[0]+buttonw+30, bottom)
b.connect(gui.CLICK, lambda x:pygame.event.post(pygame.event.Event(pygame.QUIT)), None)
# box2d initialization
z=10 #scale (10 pixels/physics unit)
# Since we're taking the debug draw implementation from the testbed, it requires a bit
# of ugliness to set it up properly.
renderer = fwDebugDraw()
renderer.surface = screen
renderer.viewZoom=z
renderer.viewCenter=box2d.b2Vec2(0,0)
renderer.width, renderer.height = width, height
renderer.viewOffset = renderer.viewCenter - box2d.b2Vec2(width, height)/2
renderer.SetFlags(box2d.b2DebugDraw.e_shapeBit) # we only want shapes to be drawn
renderer.DrawSolidPolygon = lambda a,b,c: 0 # make it not draw the polygons!
renderer.DrawPolygon = lambda a,b,c: 0 #
# Create the world
worldAABB=box2d.b2AABB()
worldAABB.lowerBound = (-100.0, -100.0)
worldAABB.upperBound = ( 100.0, 100.0)
gravity = (0.0, -10.0)
world = box2d.b2World(worldAABB, gravity, True)
world.SetDebugDraw(renderer)
# Create the ground
bd = box2d.b2BodyDef()
bd.position = (0.0, 0.0)
ground = world.CreateBody(bd)
# The borders of the screen
sd = box2d.b2PolygonDef()
sd.SetAsBox(1, height/z, (-width/(2*z)-1, 0), 0)
ground.CreateShape(sd)
sd.SetAsBox(1, height/z, (width/(2*z)+1, 0), 0)
ground.CreateShape(sd)
sd.SetAsBox(width/z, 1, (0,-height/(2*z)-1), 0)
ground.CreateShape(sd)
sd.SetAsBox(width/z, 1, (0,height/(2*z)+1), 0)
ground.CreateShape(sd)
# The shape for the file list
sd.SetAsBox(list_size[0]/(2*z), list_size[1]/(2*z))
ground.CreateShape(sd)
# Create a few balls to bounce around the screen
for i in range(10):
bd = box2d.b2BodyDef()
bd.allowSleep = True
bd.position = (box2d.b2Random(-width/(2*z), width/(2*z)), box2d.b2Random(-height/(2*z), height/(2*z)))
bd.isBullet = True
bomb = world.CreateBody(bd)
bomb.SetLinearVelocity(-5.0 * bd.position)
sd = box2d.b2CircleDef()
sd.radius = 1
sd.density = 1.0
sd.restitution = 0.7
bomb.CreateShape(sd)
bomb.SetMassFromShapes()
app.init(main)
main_loop(world, screen, demolist, app)
def get_shapes(world):
for body in world.bodyList:
shape = body.GetShapeList()
while shape:
yield (body, shape.getAsType())
shape=shape.GetNext()
def update_shapes(world):
# Check to see if any objects are sleeping or coming to a stop.
# Then give them a little push.
for body in world.bodyList:
v = body.GetLinearVelocity()
if body.IsSleeping() or v.LengthSquared() < 0.2:
i = body.GetWorldVector((box2d.b2Random(-200,200), box2d.b2Random(-200,200)))
p = body.GetWorldPoint((0.0, 0.0))
body.ApplyImpulse(i, p)
def main_loop(world, screen, demolist, app):
# Create a surface to draw the GUI onto
app_surface = pygame.Surface((width,height), SWSURFACE)
hz = 60.0
clock = pygame.time.Clock()
while True:
for event in pygame.event.get():
if event.type == QUIT or (event.type == KEYDOWN and event.key == K_ESCAPE):
return
elif event.type == KEYDOWN:
if event.key == K_RETURN:
run_demo(demolist)
elif event.type == MOUSEBUTTONDOWN:
if event.button ==3:
run_demo(demolist)
elif event.button ==4:
demolist.set_vertical_scroll(demolist.vscrollbar.value-100)
elif event.button ==5:
demolist.set_vertical_scroll(demolist.vscrollbar.value+100)
app.event(event)
# Tell the GUI to update itself, then blit it to the screen
app.update(app_surface) # pygame 1.8.1/pgu problem? 1.8.0 works fine
screen.blit(app_surface, (0,0))
# Wake up non/slow-moving shapes
update_shapes(world)
# Step the world
# (calls the debugdraw functions, so this is where the balls are drawn)
world.Step(1/hz, 10, 8)
clock.tick(hz)
#fps = clock.get_fps()
pygame.display.flip()
def add_demos(demolist):
# I don't feel like maintaining a list of demos.
# So just glob to see what test_*.py files are in the current
# directory and add them to the demo list.
import glob
ignore_list=("main")
for f in glob.glob("test_*.py"):
name = f[5:-3]
if name.lower() in ignore_list:
continue
demolist.add(name,value=f)
def run_demo(demolist):
# Run the currently selected demo (the widget itself is passed as an argument)
if demolist.value == None: return
print "Running: ", demolist.value
from sys import executable as python_interpreter
from platform import system as sys_platform
if sys_platform() == "Windows":
# Just in case we're in some directory with a space in it, use quotes
# around the path.
cmd = '"%s" -OO %s' % (python_interpreter, demolist.value)
else:
cmd = "%s -OO %s" % (python_interpreter, demolist.value)
print "-> %s" % cmd
ret = os.system(cmd)
if ret == 10 or ret/256 == 10: # user hit reload (somehow the retval on linux is *256)
run_demo(demolist)
if __name__=="__main__":
main()
python-box2d-2.0.2+svn20100109.244/testbed/test_PolyShapes.py 0000644 0000000 0000000 00000010242 11135461416 021630 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
import math
class PolyShapes (Framework):
name="PolyShapes"
bodyIndex=0
bodies=[]
sds=[]
circleDef=None
_pickle_vars=['bodies']
def __init__(self):
super(PolyShapes, self).__init__()
# Ground body
sds = self.sds
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
sd.friction = 0.3
for i in range(4):
sds.append(box2d.b2PolygonDef())
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sds[0].vertexCount = 3
sds[0].setVertex(0,-0.5, 0.0)
sds[0].setVertex(1,0.5, 0.0)
sds[0].setVertex(2,0.0, 1.5)
sds[0].density = 1.0
sds[0].friction = 0.3
sds[1].vertexCount = 3
sds[1].setVertex(0,-0.1, 0.0)
sds[1].setVertex(1,0.1, 0.0)
sds[1].setVertex(2,0.0, 1.5)
sds[1].density = 1.0
sds[1].friction = 0.3
sds[2].vertexCount = 8
w = 1.0
b = w / (2.0 + math.sqrt(2.0))
s = math.sqrt(2.0) * b
sds[2].setVertex(0,0.5 * s, 0.0)
sds[2].setVertex(1,0.5 * w, b)
sds[2].setVertex(2,0.5 * w, b + s)
sds[2].setVertex(3,0.5 * s, w)
sds[2].setVertex(4,-0.5 * s, w)
sds[2].setVertex(5,-0.5 * w, b + s)
sds[2].setVertex(6,-0.5 * w, b)
sds[2].setVertex(7,-0.5 * s, 0.0)
sds[2].density = 1.0
sds[2].friction = 0.3
sds[3].SetAsBox(0.5, 0.5)
#sds[3].vertexCount = 4
#sds[3].setVertex(0,-0.5, 0.0)
#sds[3].setVertex(1,0.5, 0.0)
#sds[3].setVertex(2,0.5, 1.0)
#sds[3].setVertex(3,-0.5, 1.0)
sds[3].density = 1.0
sds[3].friction = 0.3
self.circleDef=box2d.b2CircleDef()
self.circleDef.radius = 0.5
self.circleDef.density = 1.0
self.bodyIndex = 0
def Create(self, index):
bd=box2d.b2BodyDef()
x = box2d.b2Random(-2.0, 2.0)
bd.position = (x, 10.0)
bd.angle = box2d.b2Random(-box2d.b2_pi, box2d.b2_pi)
if index == 4:
bd.angularDamping = 0.02
self.bodies.append(self.world.CreateBody(bd) )
if index < 4:
self.bodies[-1].CreateShape(self.sds[index])
else:
self.bodies[-1].CreateShape(self.circleDef)
self.bodies[-1].SetMassFromShapes()
def DestroyBody(self):
for body in self.bodies:
self.bodies.remove(body)
self.world.DestroyBody(body)
return
def Keyboard(self, key):
if key==K_1 or key==K_2 or key==K_3 or key==K_4 or key==K_5:
self.Create(key - K_1)
elif key==K_d:
self.DestroyBody()
def Step(self, settings):
super(PolyShapes, self).Step(settings)
self.DrawStringCR("Press 1-5 to drop stuff")
if __name__=="__main__":
main(PolyShapes)
python-box2d-2.0.2+svn20100109.244/testbed/test_BreakableBody.py 0000644 0000000 0000000 00000036042 11135471136 022235 0 ustar root root #!/usr/bin/python
#
# Testbed example showing deformable and breakable bodies using the soft
# b2DistanceJoint and a small,liteweight triangle mesher.
# 2008-05-09 / nimodo
#
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
#
from test_main import *
import TriangleMesh as tm
def H(x):
return x/2.0
MIN_SQUAREDLENGTH =0.25 #0.5*0.5
# want the value on restart,
# break joint if reaction exceeds
g_maxAllowableForce = 200.0
data = {
'ring_nodes' : (
(6.00, 3.00),
(5.12, 5.12),
(3.00, 6.00),
(0.88, 5.12),
(0.00, 3.00),
(0.88, 0.88),
(3.00, 0.00),
(5.12, 0.88),
(4.50, 3.00),
(4.06, 4.06),
(3.00, 4.50),
(1.94, 4.06),
(1.50, 3.00),
(1.94, 1.94),
(3.00, 1.50),
(4.06, 1.94)),
'ring_segments' : (
(9, 10),
(10, 11),
(11, 12),
(12, 13),
(13, 14),
(14, 15),
(15, 16),
(16, 9)),
'ring_holes' : (
(3.00, 3.00), ),
# 'B'
'B_nodes' : (
(0.00, 0.00),
(4.00, 0.00),
(5.00, 2.00),
(5.00, 4.00),
(4.00, 5.00),
(5.00, 6.00),
(5.00, 8.00),
(4.00, 9.00),
(0.00, 9.00),
(0.00, 5.00),
(1.50, 1.50),
(3.50, 1.50),
(3.50, 4.00),
(1.50, 4.00),
(1.50, 6.00),
(3.50, 6.00),
(3.50, 8.50),
(1.50, 8.50)),
'B_segments' : (
(1, 2),
(2, 3),
(3, 4),
(4, 5),
(5, 6),
(6, 7),
(7, 8),
(8, 9),
(9, 10),
(10, 1),
(11, 12),
(12, 13),
(13, 14),
(14, 11),
(15, 16),
(16, 17),
(17, 18),
(18, 15)),
'B_holes' : (
(5.00, 5.00),
(2.50, 2.50),
(2.50, 7.00)),
# 'D'
'D_nodes' : (
(0.00, 0.00),
(4.00, 0.00),
(5.00, 2.50),
(5.00, 7.00),
(4.00, 9.00),
(0.00, 9.00),
(0.00, 5.00),
(1.50, 2.50),
(3.50, 2.50),
(3.50, 7.00),
(1.50, 7.00)),
'D_segments' : (
(1, 2),
(2, 3),
(3, 4),
(4, 5),
(5, 6),
(6, 7),
(7, 1),
(8, 9),
(9, 10),
(10, 11),
(11, 8)),
'D_holes' : (
(2.50, 5.00), ),
# 'x'
'x_nodes' : (
(0.00, 0.00),
(1.00, 0.00),
(5.00, 0.00),
(6.00, 0.00),
(6.00, 1.00),
(6.00, 5.00),
(6.00, 6.00),
(1.00, 6.00),
(5.00, 6.00),
(0.00, 6.00),
(0.00, 5.00),
(0.00, 1.00),
(3.00, 2.00),
(4.00, 3.00),
(3.00, 4.00),
(2.00, 3.00)),
'x_segments' : (
(2, 13),
(3, 13),
(5, 14),
(6, 14),
(8, 15),
(9, 15),
(11, 16),
(12, 16)),
'x_holes' : (
(3.00, 1.00),
(5.00, 3.00),
(3.00, 5.00),
(1.00, 3.00)),
# '2'
'two_nodes' : (
(0.00, 0.00),
(6.00, 0.00),
(6.00, 1.00),
(2.00, 1.00),
(2.00, 2.00),
(6.00, 6.00),
(6.00, 8.00),
(5.00, 9.00),
(2.00, 9.00),
(1.00, 7.50),
(0.00, 2.50),
(5.00, 6.50),
(5.00, 8.00),
(2.50, 8.00),
(2.00, 7.50)),
'two_segments' : (
(1, 2),
(2, 3),
(3, 4),
(4, 5),
(5, 6),
(6, 7),
(7, 8),
(8, 9),
(9, 10),
(10, 15),
(11, 12),
(12, 13),
(13, 14),
(14, 15)),
'two_holes' : (
(3.00, 5.00),
(4.00, 3.00)),
# '-' beam
'beanodes' : (
(0.00, 0.00),
(32.00, 0.00),
(32.00, 3.00),
(0.00, 3.00)),
'beasegments' : None,
'beaholes' : None,
# 'b' a box
'b_nodes' : (
(0.00, 0.00),
(10.00, 0.00),
(10.00, 10.00),
(0.00, 10.00),
(2.00, 2.00),
(8.00, 2.00),
(8.00, 8.00),
(2.00, 8.00)),
'b_segments' : (
(5, 6),
(6, 7),
(7, 8),
(8, 5)),
'b_holes' : (
(5.0, 5.0), )
}
# convert the data to the specific types
for key in data.keys():
if data[key] == None: continue
if key[-6:] == "_nodes" or key[-6:] == "_holes":
data[key] = [tm.tmVertex( (x, y) ) for x, y in data[key]]
elif key[-9:] == "_segments":
data[key] = [tm.tmSegmentId((v0,v1)) for v0,v1 in data[key]]
class BreakableBody(Framework):
name="BreakableBody"
maxAllowableForce = 0.0
drawMode = False
drawCount = 0
drawVertices = []
staticBodies=False
_pickle_vars=['maxAllowableForce', 'drawMode', 'drawCount', 'drawVertices',
'staticBodies']
def __init__(self):
super(BreakableBody, self).__init__()
if not self.settings.onlyInit:
self.viewZoom = 6.0
# geometries
gx, gy = 100.0, 1.0
dx, br = 34.0, 0.3
sx, sy = -dx-H(dx), 30
# ground
sd=box2d.b2PolygonDef()
bd=box2d.b2BodyDef()
bd.position = (0.0, 0.0)
ground = self.world.CreateBody(bd)
# bottom
sd.SetAsBox( H(gx), H(gy) )
ground.CreateShape(sd)
sd.SetAsBox( H(dx), H(gy), (-dx,sy-1.0), 0.0 )
ground.CreateShape(sd)
# dyn bodies
pd=box2d.b2PolygonDef()
dj=box2d.b2DistanceJointDef()
dj.dampingRatio = 1.0
dj.collideConnected = True
nodes, segments, holes = self.ExampleData('B')
dj.frequencyHz = 20
pd.density = 1.0/70.0
pd.friction = 0.4
pd.restitution = 0.01
self.CreateSoftBody( (sx,sy), 0, 0, pd, dj, nodes, segments, holes)
nodes, segments, holes = self.ExampleData('ring')
dj.frequencyHz = 20
pd.density = 1.0/36.0
pd.friction = 0.1
pd.restitution = 0.5
self.CreateSoftBody( (sx+6,sy), 0, 0, pd, dj,nodes, segments, holes)
nodes, segments, holes = self.ExampleData('x')
dj.frequencyHz = 0.0
pd.density = 0.2
pd.friction = 1.0
pd.restitution = 0.1
self.CreateSoftBody( (sx+13,sy), 0, 0, pd, dj,nodes, segments, holes)
nodes, segments, holes = self.ExampleData('two')
dj.frequencyHz = 20.0
pd.density = 0.01
pd.friction = 0.3
pd.restitution = 0.3
self.CreateSoftBody( (sx+20,sy), 0, 0, pd, dj, nodes, segments, holes)
nodes, segments, holes = self.ExampleData('D')
self.CreateSoftBody( (sx+28,sy), 0, 0, pd, dj, nodes, segments, holes)
nodes, segments, holes = self.ExampleData('b')
dj.frequencyHz = 20
dj.dampingRatio = 2.0
pd.restitution = 0.01
pd.density = 0.01
pd.friction = 0.9
self.CreateSoftBody( (-5,5*gy), 0, 0, pd, dj ,nodes, segments, holes)
cd=box2d.b2CircleDef()
bd=box2d.b2BodyDef()
cd.radius = br
cd.density= 0.001
bd.position = (0.0,10.0*gy)
for i in range(60):
b = self.world.CreateBody(bd)
b.CreateShape(cd)
b.SetMassFromShapes()
# Create compound (soft) body using a triangle mesh
# If meshDensity is 0, a minimal grid is generated.
# Actually pd and dj define the behaviour for all triangles
def CreateSoftBody(self, pos, meshDensity, options, pd, dj,nodes=[], segments=[], holes=[]):
n_nodes =len(nodes)
n_segments=len(segments)
n_holes =len(holes)
# TriangleMesh defs
md = tm.TriangleMesh()
# box2d defs
bd=box2d.b2BodyDef()
# in case of meshDensity>3 ...
md.SetMaxVertexCount(meshDensity)
if options: md.SetOptions(options)
# triangulator main
i = md.Mesh(nodes, segments, holes)
md.PrintData()
print "TriangleMesh.py:%s" % md.GetErrorMessage(i)
# check if enough proxies set in box2d, 10 proxies as reserve
if self.world.GetProxyCount()+md.GetInsideTriangleCount() > (box2d.b2_maxProxies-10):
print
print "Current proxy count:", self.world.GetProxyCount()
print "World proxy count if added:", self.world.GetProxyCount()+md.GetInsideTriangleCount()
print "Max proxies (Box2D setting):", (box2d.b2_maxProxies-10)
print "Error: Not enough proxies to insert the mesh!"
md.Reset()
return
# bodies (triangles)
triangles = md.GetTriangles()
if triangles==None: return
pd.vertexCount = 3
for i in range(md.GetTriangleCount()):
if triangles[i].inside:
pd.setVertices([triangles[i].v[0],
triangles[i].v[1],
triangles[i].v[2]])
try:
pd.checkValues()
except ValueError:
print "** Created an invalid shape"
exit(0)
bd.position=pos
b = self.world.CreateBody(bd)
b.CreateShape(pd)
b.SetMassFromShapes()
# we need the body pointer in the triangles for the joints later
triangles[i].userData = b
# joints
if pd.density>0.0:
# for each triangle-pair in edges, connect with a distance joint
edges = md.GetEdges()
for i in range(md.GetEdgeCount()):
t0 = edges[i].t[0]
t1 = edges[i].t[1]
if t0.inside==False or t1.inside==False: continue
# Get bodies
b1 = t0.userData
b2 = t1.userData
if b1==None or b2==None: continue
dj.Initialize( b1,b2, b1.GetWorldCenter(), b2.GetWorldCenter())
self.world.CreateJoint(dj).getAsType()
# clean TriangleMesh
md.Reset()
# maybe here to check for maximal reaction forces to break a body
def Step(self, settings):
global g_maxAllowableForce
F=0.0
jStressed = 0
for j in self.world.jointList:
tmp = j.GetReactionForce(settings.hz).Length() # for newer builds
#tmp = j.GetReactionForce().Length() # works for older builds
if tmp>F:
F = tmp
jStressed = j
if jStressed and (F>g_maxAllowableForce):
self.world.DestroyJoint(jStressed)
self.DrawStringCR("max.reactionforce=%f.0 allowable=%f.0 change:-+" % (F,g_maxAllowableForce));
onoff = { False: 'off', True: 'on' }
self.DrawStringCR("(d)rawmode-%s (m)esh (s)taticbody-%s" % (onoff[self.drawMode], onoff[self.staticBodies]))
p1, p2 = box2d.b2Vec2(), box2d.b2Vec2()
for i in xrange(self.drawCount-1):
p1 = (self.drawVertices[i].x ,self.drawVertices[i].y)
if i 0.0:
g_maxAllowableForce -= 5.0
elif key==K_PLUS or key==K_EQUALS:
g_maxAllowableForce += 5.0
elif key==K_d:
self.drawMode = not self.drawMode
elif key==K_s:
self.staticBodies = not self.staticBodies
elif key==K_m:
if self.drawCount>0:
pd = box2d.b2PolygonDef()
dj = box2d.b2DistanceJointDef()
dj.collideConnected = True
dj.frequencyHz = 20.0
dj.dampingRatio = 10.0
pd.friction = 0.9
pd.restitution = 0.1
if self.staticBodies:
pd.density = 0.0
else:
pd.density = 1.0/32.0
self.CreateSoftBody( box2d.b2Vec2(0.0,0.0), 0, tm.tmO_SEGMENTBOUNDARY|tm.tmO_GRADING|tm.tmO_CHECKINTERSECT,
pd, dj, self.drawVertices)
self.drawVertices = []
self.drawCount = 0
self.drawMode = False
def AddVertex(self, p):
if self.drawCount>0:
dx = self.drawVertices[self.drawCount-1].x - p.x
dy = self.drawVertices[self.drawCount-1].y - p.y
if dx*dx+dy*dy > MIN_SQUAREDLENGTH:
self.drawVertices.append( box2d.b2Vec2(p.x, p.y) )
self.drawCount+=1
else:
self.drawVertices.append( box2d.b2Vec2(p.x, p.y) )
self.drawCount+=1
def MouseDown(self, p):
if self.drawMode:
self.AddVertex(p)
else:
super(BreakableBody, self).MouseDown(p)
def MouseUp(self, p):
if not self.drawMode:
super(BreakableBody, self).MouseUp(p)
# examples
def ExampleData(self, which):
print "\nLoading data:", which
nodes = data["%s_nodes" % which]
segments = data["%s_segments" % which]
holes = data["%s_holes" % which]
return (nodes, segments, holes)
if __name__=="__main__":
main(BreakableBody)
python-box2d-2.0.2+svn20100109.244/testbed/test_Prismatic.py 0000644 0000000 0000000 00000006016 11136402204 021467 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class Prismatic (Framework):
name="Prismatic"
_pickle_vars=['joint']
def __init__(self):
super(Prismatic, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(2.0, 0.5)
sd.density = 5.0
sd.friction = 0.05
bd=box2d.b2BodyDef()
bd.position = (-10.0, 10.0)
bd.angle = 0.5 * box2d.b2_pi
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
pjd=box2d.b2PrismaticJointDef()
# Bouncy limit
pjd.Initialize(ground, body, (0.0, 0.0), (1.0, 0.0))
# Non-bouncy limit
#pjd.Initialize(ground, body, (-10.0, 10.0), (1.0, 0.0))
pjd.motorSpeed = 10.0
pjd.maxMotorForce = 1000.0
pjd.enableMotor = True
pjd.lowerTranslation = 0.0
pjd.upperTranslation = 20.0
pjd.enableLimit = True
self.joint = self.world.CreateJoint(pjd).getAsType()
def Keyboard(self, key):
if not self.joint:
return
if key==K_l:
self.joint.EnableLimit(not self.joint.IsLimitEnabled())
elif key==K_m:
self.joint.EnableMotor(not self.joint.IsMotorEnabled())
elif key==K_p:
self.joint.SetMotorSpeed(-self.joint.GetMotorSpeed())
def Step(self, settings):
self.DrawStringCR("Keys: (l) limits, (m) motors, (p) speed")
if self.joint:
force = self.joint.GetMotorForce()
self.DrawStringCR("Motor Force = %f.0" % force)
super(Prismatic, self).Step(settings)
if __name__=="__main__":
main(Prismatic)
python-box2d-2.0.2+svn20100109.244/testbed/test_SliderCrank.py 0000644 0000000 0000000 00000007733 11136402204 021744 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
# A motor driven slider crank with joint friction.
class SliderCrank (Framework):
name="SliderCrank"
joint1=None
joint2=None
_pickle_vars=['joint1', 'joint2']
def __init__(self):
super(SliderCrank, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
# Define crank.
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.5, 2.0)
sd.density = 1.0
rjd=box2d.b2RevoluteJointDef()
prevBody=ground
bd=box2d.b2BodyDef()
bd.position = (0.0, 7.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
rjd.Initialize(prevBody, body, (0.0, 5.0))
rjd.motorSpeed = 1.0 * box2d.b2_pi
rjd.maxMotorTorque = 10000.0
rjd.enableMotor = True
self.joint1 = self.world.CreateJoint(rjd).getAsType()
prevBody = body
# Define follower.
sd.SetAsBox(0.5, 4.0)
bd.position = (0.0, 13.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
rjd.Initialize(prevBody, body, (0.0, 9.0))
rjd.enableMotor = False
self.world.CreateJoint(rjd).getAsType()
prevBody = body
# Define piston
sd.SetAsBox(1.5, 1.5)
bd.position = (0.0, 17.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
rjd.Initialize(prevBody, body, (0.0, 17.0))
self.world.CreateJoint(rjd).getAsType()
pjd=box2d.b2PrismaticJointDef()
pjd.Initialize(ground, body, (0.0, 17.0), (0.0, 1.0))
pjd.maxMotorForce = 1000.0
pjd.enableMotor = True
self.joint2 = self.world.CreateJoint(pjd).getAsType()
# Create a payload
sd.density = 2.0
bd.position = (0.0, 23.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
def Keyboard(self, key):
if not self.joint1 or not self.joint2:
return
if key==K_f:
self.joint2.enableMotor = not self.joint2.enableMotor
self.joint2.GetBody2().WakeUp()
elif key==K_m:
self.joint1.enableMotor = not self.joint1.enableMotor
self.joint1.GetBody2().WakeUp()
def Step(self, settings):
self.DrawStringCR("Keys: (f) toggle friction, (m) toggle motor")
if self.joint1:
torque = self.joint1.GetMotorTorque()
self.DrawStringCR("Motor Torque = %.0f" % (torque))
super(SliderCrank, self).Step(settings)
if __name__=="__main__":
main(SliderCrank)
python-box2d-2.0.2+svn20100109.244/testbed/test_TheoJansen.py 0000644 0000000 0000000 00000016560 11136402204 021577 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
from pygame.locals import *
# Inspired by a contribution by roman_m (C++ version)
# Dimensions scooped from APE (http://www.cove.org/ape/index.htm)
class TheoJansen (Framework):
name="TheoJansen"
offset=None
chassis=None
wheel=None
motorJoint=None
motorOn = False
motorSpeed = 0
_pickle_vars=['offset', 'chassis', 'wheel',
'motorJoint', 'motorOn', 'motorSpeed']
def CreateLeg(self, s, wheelAnchor):
p1=box2d.b2Vec2(5.4 * s, -6.1)
p2=box2d.b2Vec2(7.2 * s, -1.2)
p3=box2d.b2Vec2(4.3 * s, -1.9)
p4=box2d.b2Vec2(3.1 * s, 0.8)
p5=box2d.b2Vec2(6.0 * s, 1.5)
p6=box2d.b2Vec2(2.5 * s, 3.7)
sd1=box2d.b2PolygonDef()
sd2=box2d.b2PolygonDef()
sd1.vertexCount = 3
sd2.vertexCount = 3
sd1.filter.groupIndex = -1
sd2.filter.groupIndex = -1
sd1.density = 1.0
sd2.density = 1.0
if s > 0.0:
sd1.setVertex(0, p1)
sd1.setVertex(1, p2)
sd1.setVertex(2, p3)
sd2.setVertex(0, (0,0))
sd2.setVertex(1, p5 - p4)
sd2.setVertex(2, p6 - p4)
else:
sd1.setVertex(0, p1)
sd1.setVertex(1, p3)
sd1.setVertex(2, p2)
sd2.setVertex(0, (0,0))
sd2.setVertex(1, p6 - p4)
sd2.setVertex(2, p5 - p4)
bd1=box2d.b2BodyDef()
bd2=box2d.b2BodyDef()
bd1.position = self.offset
bd2.position = p4 + self.offset
bd1.angularDamping = 10.0
bd2.angularDamping = 10.0
body1 = self.world.CreateBody(bd1)
body2 = self.world.CreateBody(bd2)
body1.CreateShape(sd1)
body2.CreateShape(sd2)
body1.SetMassFromShapes()
body2.SetMassFromShapes()
djd=box2d.b2DistanceJointDef()
# Using a soft distance constraint can reduce some jitter.
# It also makes the structure seem a bit more fluid by
# acting like a suspension system.
#djd.dampingRatio = 0.5
#djd.frequencyHz = 10.0
# usable, but doesn't act like it seems it should?
djd.Initialize(body1, body2, p2 + self.offset, p5 + self.offset)
self.world.CreateJoint(djd).getAsType()
djd.Initialize(body1, body2, p3 + self.offset, p4 + self.offset)
self.world.CreateJoint(djd).getAsType()
djd.Initialize(body1, self.wheel, p3 + self.offset, wheelAnchor + self.offset)
self.world.CreateJoint(djd).getAsType()
djd.Initialize(body2, self.wheel, p6 + self.offset, wheelAnchor + self.offset)
self.world.CreateJoint(djd).getAsType()
rjd=box2d.b2RevoluteJointDef()
rjd.Initialize(body2, self.chassis, p4 + self.offset)
self.world.CreateJoint(rjd).getAsType()
def __init__(self):
super(TheoJansen, self).__init__()
self.offset = (0.0, 8.0)
self.motorSpeed = 2.0
self.motorOn = True
pivot=box2d.b2Vec2(0.0, 0.8)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd.SetAsBox(0.5, 5.0, (-50.0, 15.0), 0.0)
ground.CreateShape(sd)
sd.SetAsBox(0.5, 5.0, (50.0, 15.0), 0.0)
ground.CreateShape(sd)
for i in range(40):
sd = box2d.b2CircleDef()
sd.density = 1.0
sd.radius = 0.25
bd=box2d.b2BodyDef()
bd.position = (-40.0 + 2.0 * i, 0.5)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
body.SetMassFromShapes()
sd=box2d.b2PolygonDef()
sd.density = 1.0
sd.SetAsBox(2.5, 1.0)
sd.filter.groupIndex = -1
bd=box2d.b2BodyDef()
bd.position = pivot + self.offset
self.chassis = self.world.CreateBody(bd)
self.chassis.CreateShape(sd)
self.chassis.SetMassFromShapes()
sd = box2d.b2CircleDef()
sd.density = 1.0
sd.radius = 1.6
sd.filter.groupIndex = -1
bd=box2d.b2BodyDef()
bd.position = pivot + self.offset
self.wheel = self.world.CreateBody(bd)
self.wheel.CreateShape(sd)
self.wheel.SetMassFromShapes()
jd=box2d.b2RevoluteJointDef()
jd.Initialize(self.wheel, self.chassis, pivot + self.offset)
jd.collideConnected = False
jd.motorSpeed = self.motorSpeed
jd.maxMotorTorque = 400.0
jd.enableMotor = self.motorOn
self.motorJoint = self.world.CreateJoint(jd).getAsType()
wheelAnchor = pivot + box2d.b2Vec2(0.0, -0.8)
self.CreateLeg(-1.0, wheelAnchor)
self.CreateLeg(1.0, wheelAnchor)
self.wheel.SetXForm(self.wheel.GetPosition(), 120.0 * box2d.b2_pi / 180.0)
self.CreateLeg(-1.0, wheelAnchor)
self.CreateLeg(1.0, wheelAnchor)
self.wheel.SetXForm(self.wheel.GetPosition(), -120.0 * box2d.b2_pi / 180.0)
self.CreateLeg(-1.0, wheelAnchor)
self.CreateLeg(1.0, wheelAnchor)
def Step(self, settings):
self.DrawStringCR("Keys: left = a, brake = s, right = d, toggle motor = m")
super(TheoJansen, self).Step(settings)
def Keyboard(self, key):
if not self.chassis:
return
if key==K_a:
self.chassis.WakeUp()
self.motorJoint.SetMotorSpeed(-self.motorSpeed)
elif key==K_s:
self.chassis.WakeUp()
self.motorJoint.SetMotorSpeed(0.0)
elif key==K_d:
self.chassis.WakeUp()
self.motorJoint.SetMotorSpeed(self.motorSpeed)
elif key==K_m:
self.chassis.WakeUp()
self.motorJoint.EnableMotor(not self.motorJoint.IsMotorEnabled())
if __name__=="__main__":
main(TheoJansen)
python-box2d-2.0.2+svn20100109.244/testbed/test_CollisionProcessing.py 0000644 0000000 0000000 00000012203 11151077147 023532 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class CollisionProcessing (Framework):
name="CollisionProcessing"
def __init__(self):
super(CollisionProcessing, self).__init__()
# Ground body
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
sd.friction = 0.3
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
xLo = -5.0
xHi = 5.0
yLo = 2.0
yHi = 35.0
# Small triangle
triangleShapeDef=box2d.b2PolygonDef()
triangleShapeDef.vertexCount = 3
triangleShapeDef.setVertex(0,-1.0, 0.0)
triangleShapeDef.setVertex(1,1.0, 0.0)
triangleShapeDef.setVertex(2,0.0, 2.0)
triangleShapeDef.density = 1.0
triangleBodyDef=box2d.b2BodyDef()
triangleBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body1 = self.world.CreateBody(triangleBodyDef)
body1.CreateShape(triangleShapeDef)
body1.SetMassFromShapes()
# Large triangle (recycle definitions)
triangleShapeDef.setVertex(0, 2.0*triangleShapeDef.getVertex(0))
triangleShapeDef.setVertex(1, 2.0*triangleShapeDef.getVertex(1))
triangleShapeDef.setVertex(2, 2.0*triangleShapeDef.getVertex(2))
triangleBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body2 = self.world.CreateBody(triangleBodyDef)
body2.CreateShape(triangleShapeDef)
body2.SetMassFromShapes()
# Small box
boxShapeDef=box2d.b2PolygonDef()
boxShapeDef.SetAsBox(1.0, 0.5)
boxShapeDef.density = 1.0
boxBodyDef=box2d.b2BodyDef()
boxBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body3 = self.world.CreateBody(boxBodyDef)
body3.CreateShape(boxShapeDef)
body3.SetMassFromShapes()
# Large box (recycle definitions)
boxShapeDef.SetAsBox(2.0, 1.0)
boxBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body4 = self.world.CreateBody(boxBodyDef)
body4.CreateShape(boxShapeDef)
body4.SetMassFromShapes()
# Small circle
circleShapeDef=box2d.b2CircleDef()
circleShapeDef.radius = 1.0
circleShapeDef.density = 1.0
circleBodyDef=box2d.b2BodyDef()
circleBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body5 = self.world.CreateBody(circleBodyDef)
body5.CreateShape(circleShapeDef)
body5.SetMassFromShapes()
# Large circle
circleShapeDef.radius *= 2.0
circleBodyDef.position = (box2d.b2Random(xLo, xHi), box2d.b2Random(yLo, yHi))
body6 = self.world.CreateBody(circleBodyDef)
body6.CreateShape(circleShapeDef)
body6.SetMassFromShapes()
def Step(self, settings):
# We are going to destroy some bodies according to contact
# points. We must buffer the bodies that should be destroyed
# because they may belong to multiple contact points.
nuke = []
# Traverse the contact results. Destroy bodies that
# are touching heavier bodies.
body_pairs = [(p.shape1.GetBody(), p.shape2.GetBody()) for p in self.points]
for body1, body2 in body_pairs:
mass1, mass2 = body1.GetMass(), body2.GetMass()
if mass1 > 0.0 and mass2 > 0.0:
if mass2 > mass1:
nuke_body = body1
else:
nuke_body = body2
if nuke_body not in nuke:
nuke.append(nuke_body)
# Destroy the bodies, skipping duplicates.
for b in nuke:
print "Nuking:", b
self.world.DestroyBody(b)
nuke = None
super(CollisionProcessing, self).Step(settings)
if __name__=="__main__":
main(CollisionProcessing)
python-box2d-2.0.2+svn20100109.244/testbed/test_ApplyForce.py 0000644 0000000 0000000 00000006651 11136402204 021605 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class ApplyForce (Framework):
name="ApplyForce"
body=None
_pickle_vars=['body']
def __init__(self):
super(ApplyForce, self).__init__()
self.world.SetGravity((0.0, 0.0))
k_restitution = 0.4
bd=box2d.b2BodyDef()
bd.position = (0.0, 20.0)
ground = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.density = 0.0
sd.restitution = k_restitution
sd.SetAsBox(0.2, 20.0, (-20.0, 0.0), 0.0)
ground.CreateShape(sd)
sd.SetAsBox(0.2, 20.0, (20.0, 0.0), 0.0)
ground.CreateShape(sd)
sd.SetAsBox(0.2, 20.0, (0.0, -20.0), 0.5 * box2d.b2_pi)
ground.CreateShape(sd)
sd.SetAsBox(0.2, 20.0, (0.0, 20.0), -0.5 * box2d.b2_pi)
ground.CreateShape(sd)
xf1 = box2d.b2XForm ()
xf1.R.Set(0.3524 * box2d.b2_pi)
xf1.position = box2d.b2Mul(xf1.R, (1.0, 0.0))
sd1=box2d.b2PolygonDef()
sd1.vertexCount = 3
sd1.setVertex(0, box2d.b2Mul(xf1, (-1.0, 0.0)))
sd1.setVertex(1, box2d.b2Mul(xf1, (1.0, 0.0)))
sd1.setVertex(2, box2d.b2Mul(xf1, (0.0, 0.5)))
sd1.density = 2.0
xf2 = box2d.b2XForm ()
xf2.R.Set(-0.3524 * box2d.b2_pi)
xf2.position = box2d.b2Mul(xf2.R, (-1.0, 0.0))
sd2=box2d.b2PolygonDef()
sd2.vertexCount = 3
sd2.setVertex(0, box2d.b2Mul(xf2, (-1.0, 0.0)))
sd2.setVertex(1, box2d.b2Mul(xf2, (1.0, 0.0)))
sd2.setVertex(2, box2d.b2Mul(xf2, (0.0, 0.5)))
sd2.density = 2.0
bd=box2d.b2BodyDef()
bd.angularDamping = 2.0
bd.linearDamping = 0.1
bd.position = (0.0, 1.05)
bd.angle = box2d.b2_pi
self.body = self.world.CreateBody(bd)
self.body.CreateShape(sd1)
self.body.CreateShape(sd2)
self.body.SetMassFromShapes()
def Keyboard(self, key):
if not self.body:
return
if key==K_w:
f = self.body.GetWorldVector((0.0, -200.0))
p = self.body.GetWorldPoint((0.0, 2.0))
self.body.ApplyForce(f, p)
elif key==K_a:
self.body.ApplyTorque(20.0)
elif key==K_d:
self.body.ApplyTorque(-20.0)
if __name__=="__main__":
main(ApplyForce)
python-box2d-2.0.2+svn20100109.244/testbed/test_BoxCutter.py 0000644 0000000 0000000 00000023513 11144324535 021465 0 ustar root root #!/usr/bin/python
#
# Original C++ version by Daid
# http://www.box2d.org/forum/viewtopic.php?f=3&t=1473
#
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class BoxCutter (Framework):
name="BoxCutter"
laserBody=None
_pickle_vars=['laserBody']
def __init__(self):
super(BoxCutter, self).__init__()
self.world.GetGroundBody().SetUserData("ground")
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
bd.userData = "ground1"
ground = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
ground.CreateShape(sd)
bd=box2d.b2BodyDef()
bd.position = (0.0, 50.0)
bd.userData = "ground2"
ground = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
ground.CreateShape(sd)
bd=box2d.b2BodyDef()
bd.position = (0.0, 1.0)
bd.userData = "laser"
self.laserBody = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(5.0, 1.0)
sd.density = 4.0
self.laserBody.CreateShape(sd)
self.laserBody.SetMassFromShapes()
sd=box2d.b2PolygonDef()
sd.SetAsBox(3.0, 3.0)
sd.density = 5.0
bd=box2d.b2BodyDef()
bd.userData = 1
bd.position = (0.0, 8.0)
body1 = self.world.CreateBody(bd)
body1.CreateShape(sd)
body1.SetMassFromShapes()
sd=box2d.b2PolygonDef()
sd.SetAsBox(3.0, 3.0)
sd.density = 5.0
bd=box2d.b2BodyDef()
bd.userData = 1
bd.position = (0.0, 8.0)
body1 = self.world.CreateBody(bd)
body1.CreateShape(sd)
body1.SetMassFromShapes()
# Split a shape through a segment
# Returns:
# False - Error on split
# True - Normal result is two new shape definitions.
def SplitShape(self, shape, segment, splitSize, newPolygon):
b = shape.GetBody()
xf = b.GetXForm()
hit,lambda_,normal=shape.TestSegment(xf, segment, 1.0)
if hit != box2d.e_hitCollide:
return False
entryPoint = (1-lambda_)*segment.p1+lambda_*segment.p2
reverseSegment=box2d.b2Segment()
reverseSegment.p1=segment.p2
reverseSegment.p2=segment.p1
hit,lambda_,normal=shape.TestSegment(xf, reverseSegment, 1.0)
if hit != box2d.e_hitCollide:
return False
exitPoint = (1-lambda_)*reverseSegment.p1+lambda_*reverseSegment.p2
localEntryPoint = b.GetLocalPoint(entryPoint)
localExitPoint = b.GetLocalPoint(exitPoint)
vertices = shape.getVertices_b2Vec2()
cutAdded = [-1,-1]
last = -1
for i in range(shape.GetVertexCount()):
#Find out if this vertex is on the old or new shape.
if box2d.b2Dot(box2d.b2Cross(localExitPoint-localEntryPoint, 1), vertices[i]-localEntryPoint) > 0:
n = 0
else:
n = 1
if last != n:
#If we switch from one shape to the other add the cut vertices.
if last == 0:
assert(cutAdded[0]==-1)
cutAdded[0] = newPolygon[last].vertexCount
newPolygon[last].setVertex(newPolygon[last].vertexCount, localExitPoint)
newPolygon[last].vertexCount+=1
newPolygon[last].setVertex(newPolygon[last].vertexCount, localEntryPoint)
newPolygon[last].vertexCount+=1
elif last == 1:
assert(cutAdded[last]==-1)
cutAdded[last] = newPolygon[last].vertexCount
newPolygon[last].setVertex(newPolygon[last].vertexCount, localEntryPoint)
newPolygon[last].vertexCount+=1
newPolygon[last].setVertex(newPolygon[last].vertexCount, localExitPoint)
newPolygon[last].vertexCount+=1
newPolygon[n].setVertex(newPolygon[n].vertexCount, vertices[i])
newPolygon[n].vertexCount+=1
last = n
#Add the cut in case it has not been added yet.
if cutAdded[0]==-1:
cutAdded[0] = newPolygon[0].vertexCount
newPolygon[0].setVertex(newPolygon[0].vertexCount, localExitPoint)
newPolygon[0].vertexCount+=1
newPolygon[0].setVertex(newPolygon[0].vertexCount, localEntryPoint)
newPolygon[0].vertexCount+=1
if cutAdded[1]==-1:
cutAdded[1] = newPolygon[1].vertexCount
newPolygon[1].setVertex(newPolygon[1].vertexCount, localEntryPoint)
newPolygon[1].vertexCount+=1
newPolygon[1].setVertex(newPolygon[1].vertexCount, localExitPoint)
newPolygon[1].vertexCount+=1
# Cut based on the split size
for n in range(2):
if cutAdded[n] > 0:
offset = newPolygon[n].getVertex(cutAdded[n]-1) - newPolygon[n].getVertex(cutAdded[n])
else:
offset = newPolygon[n].getVertex(newPolygon[n].vertexCount-1) - newPolygon[n].getVertex(0)
offset.Normalize()
newPolygon[n].setVertex(cutAdded[n], newPolygon[n].getVertex(cutAdded[n]) + splitSize * offset)
if cutAdded[n] < newPolygon[n].vertexCount-2:
offset = newPolygon[n].getVertex(cutAdded[n]+2) - newPolygon[n].getVertex(cutAdded[n]+1)
else:
offset = newPolygon[n].getVertex(0) - newPolygon[n].getVertex(newPolygon[n].vertexCount-1)
offset.Normalize()
newPolygon[n].setVertex(cutAdded[n]+1, newPolygon[n].getVertex(cutAdded[n]+1) + splitSize * offset)
#Check if the new shapes are not too tiny.
for n in range(2):
for i in range(newPolygon[n].vertexCount):
for j in range(newPolygon[n].vertexCount):
if i != j and (newPolygon[n].getVertex(i) - newPolygon[n].getVertex(j)).Length() < 0.1:
return False
# Make sure the shapes are valid before creation
try:
for n in range(2):
box2d.b2CheckPolygonDef(newPolygon[n])
except ValueError, s:
print "Created bad shape:", s
return False
return True
def Cut(self):
segmentLength = 30.0
segment=box2d.b2Segment()
laserStart=(5.0-0.1,0.0)
laserDir =(segmentLength,0.0)
segment.p1 = self.laserBody.GetWorldPoint(laserStart)
segment.p2 = segment.p1 + self.laserBody.GetWorldVector(laserDir)
max_shapes = 64
count, shapes = self.world.Raycast(segment, max_shapes, False, None)
for i in range(count):
#Make sure it's a polygon, we cannot cut circles.
if shapes[i].GetType() != box2d.e_polygonShape:
continue
polyShape = shapes[i].getAsType()
b = polyShape.GetBody()
#Custom check to make sure we don't cut stuff we don't want to cut.
if b.GetUserData() != 1:
continue #return if we cannot pass trough uncutable shapes.
pd=[box2d.b2PolygonDef(),box2d.b2PolygonDef()]
pd[0].density = 5.0
pd[1].density = 5.0
if self.SplitShape(polyShape, segment, 0.1, pd):
b.DestroyShape(shapes[i])
b.CreateShape(pd[0])
b.SetMassFromShapes()
b.WakeUp()
bd=box2d.b2BodyDef()
bd.userData = 1
bd.position = b.GetPosition()
bd.angle = b.GetAngle()
newBody = self.world.CreateBody(bd)
newBody.CreateShape(pd[1])
newBody.SetMassFromShapes()
newBody.SetAngularVelocity(b.GetAngularVelocity())
newBody.SetLinearVelocity(b.GetLinearVelocity())
def Keyboard(self, key):
if key==K_c:
self.Cut()
def Step(self, settings):
super(BoxCutter, self).Step(settings)
if not self.laserBody:
return
self.DrawStringCR("Keys: Cut = c")
segmentLength = 30.0
segment=box2d.b2Segment()
laserStart=(5.0-0.1,0.0)
laserDir =(segmentLength,0.0)
segment.p1 = self.laserBody.GetWorldPoint(laserStart)
segment.p2 = segment.p1+self.laserBody.GetWorldVector(laserDir)
laserColor=box2d.b2Color(1,0,0)
self.debugDraw.DrawSegment(segment.p1,segment.p2,laserColor)
if __name__=="__main__":
main(BoxCutter)
python-box2d-2.0.2+svn20100109.244/testbed/test_EdgesBuoyancy.py 0000644 0000000 0000000 00000022552 11135471136 022311 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class EdgesBuoyancy (Framework):
name="EdgesBuoyancy"
def __init__(self):
super(EdgesBuoyancy, self).__init__()
bcd = box2d.b2BuoyancyControllerDef()
bcd.offset = 15
bcd.normal = (0,1)
bcd.density = 2
bcd.linearDrag = 2
bcd.angularDrag = 1
print bcd
self.bc = self.world.CreateController(bcd)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
body = self.world.CreateBody(bd)
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
body.CreateShape(sd)
sd1=box2d.b2CircleDef()
sd1.radius = 0.5
sd1.localPosition = (-0.5, 0.5)
sd1.density = 2.0
sd2=box2d.b2CircleDef()
sd2.radius = 0.5
sd2.localPosition = (0.5, 0.5)
sd2.density = 0.0 # massless
for i in range(10):
x = box2d.b2Random(-0.1, 0.1)
bd=box2d.b2BodyDef()
bd.position = (x + 5.0, 1.05 + 2.5 * i)
bd.angle = box2d.b2Random(-box2d.b2_pi, box2d.b2_pi)
body = self.world.CreateBody(bd)
body.CreateShape(sd1)
body.CreateShape(sd2)
body.SetMassFromShapes()
self.bc.AddBody(body)
sd1=box2d.b2PolygonDef()
sd1.SetAsBox(0.25, 0.5)
sd1.density = 2.0
sd2=box2d.b2PolygonDef()
sd2.SetAsBox(0.25, 0.5, (0.0, -0.5), 0.5 * box2d.b2_pi)
sd2.density = 2.0
for i in range(10):
x = box2d.b2Random(-0.1, 0.1)
bd=box2d.b2BodyDef()
bd.position = (x - 5.0, 1.05 + 2.5 * i)
bd.angle = box2d.b2Random(-box2d.b2_pi, box2d.b2_pi)
body = self.world.CreateBody(bd)
body.CreateShape(sd1)
body.CreateShape(sd2)
body.SetMassFromShapes()
self.bc.AddBody(body)
xf1=box2d.b2XForm()
xf1.R.Set(0.3524 * box2d.b2_pi)
xf1.position = box2d.b2Mul(xf1.R, (1.0, 0.0))
sd1=box2d.b2PolygonDef()
sd1.vertexCount = 3
sd1.setVertex(0, box2d.b2Mul(xf1, (-1.0, 0.0)))
sd1.setVertex(1, box2d.b2Mul(xf1, (1.0, 0.0)))
sd1.setVertex(2, box2d.b2Mul(xf1, (0.0, 0.5)))
sd1.density = 2.0
xf2=box2d.b2XForm()
xf2.R.Set(-0.3524 * box2d.b2_pi)
xf2.position = box2d.b2Mul(xf2.R, (-1.0, 0.0))
sd2=box2d.b2PolygonDef()
sd2.vertexCount = 3
sd2.setVertex(0, box2d.b2Mul(xf2, (-1.0, 0.0)))
sd2.setVertex(1, box2d.b2Mul(xf2, (1.0, 0.0)))
sd2.setVertex(2, box2d.b2Mul(xf2, (0.0, 0.5)))
sd2.density = 2.0
for i in range(10):
x = box2d.b2Random(-0.1, 0.1)
bd=box2d.b2BodyDef()
bd.position = (x, 2.05 + 2.5 * i)
bd.angle = 0.0
body = self.world.CreateBody(bd)
body.CreateShape(sd1)
body.CreateShape(sd2)
body.SetMassFromShapes()
self.bc.AddBody(body)
sd_bottom=box2d.b2PolygonDef()
sd_bottom.SetAsBox( 1.5, 0.15 )
sd_bottom.density = 4.0
sd_left=box2d.b2PolygonDef()
sd_left.SetAsBox(0.15, 2.7, (-1.45, 2.35), 0.2)
sd_left.density = 4.0
sd_right=box2d.b2PolygonDef()
sd_right.SetAsBox(0.15, 2.7, (1.45, 2.35), -0.2)
sd_right.density = 4.0
bd=box2d.b2BodyDef()
bd.position = ( 0.0, 2.0 )
body = self.world.CreateBody(bd)
body.CreateShape(sd_bottom)
body.CreateShape(sd_left)
body.CreateShape(sd_right)
body.SetMassFromShapes()
self.bc.AddBody(body)
loop1=[
(0.063134534,8.3695248),
(0.94701801,9.3165428),
(0.0,9.0640047),
(-0.12626907,10.326695),
(1.4520943,11.77879),
(2.2728432,10.137292),
(2.3991123,11.147444),
(3.5986685,10.958041),
(3.9143411,7.3593722),
(4.1668793,9.4428119),
(5.4295699,9.3165428),
(6.2503189,8.3063903),
(6.6922606,10.137292),
(4.9876282,9.8216191),
(4.7350901,10.958041),
(7.2604714,11.652521),
(10.732871,11.147444),
(10.480333,10.642368),
(10.732871,9.8216191),
(11.55362,9.4428119),
(12.374369,9.3796773),
(13.005714,9.8216191),
(13.195118,10.38983),
(13.005714,10.768637),
(12.626907,10.894906),
(12.753176,11.526252),
(13.573925,11.715655),
(14.836616,11.399982),
(16.351844,10.768637),
(17.867073,11.399982),
(17.803939,10.263561),
(17.361997,8.3063903),
(17.803939,8.1801212),
(18.056477,9.5059464),
(18.182746,11.336848),
(18.561553,11.210579),
(18.561553,9.6322155),
(18.561553,7.7381795),
(18.687822,5.5284708),
(19.382302,5.6547398),
(19.066629,8.1801212),
(19.003495,10.263561),
(19.066629,11.463117),
(19.887378,11.841924),
(20.708127,11.273713),
(21.0238,10.011023),
(20.708127,7.2962377),
(21.086934,6.2860852),
(21.150069,3.7607038),
(20.392455,2.5611476),
(18.624688,2.5611476),
(20.771262,2.1192059),
(20.771262,0.22516988),
(18.624688,-0.2799064),
(13.826463,0.16203534),
(14.015867,1.7403987),
(13.195118,2.1823404),
(12.626907,1.5509951),
(12.879445,0.85651522),
(12.626907,0.35143895),
(10.543467,1.298457),
(11.490485,3.9501074),
(13.889598,3.6344347),
(13.889598,2.9399549),
(14.584077,3.8869729),
(11.932427,5.2127981),
(9.7227183,4.0132419),
(10.796005,3.5081657),
(9.7858528,3.2556275),
(10.796005,2.4980131),
(7.9549513,1.7403987),
(9.6595837,1.424726),
(9.217642,0.66711162),
(8.270624,-0.090502792),
(7.0079333,0.85651522),
(6.1240498,-0.15363733),
(6.1240498,3.192493),
(5.6821081,2.4348786),
(4.9876282,2.1192059),
(4.1037447,1.8666678),
(3.0304576,1.8666678),
(2.0834396,2.245475),
(1.6414979,2.6242822),
(1.3258252,3.5081657),
(1.2626907,0.47770802),
(0.63134534,0.035766276),
(0.063134534,0.9827842),
]
loop2 = [
(8.270624,6.1598161),
(8.270624,5.3390672),
(8.7757003,5.086529),
(9.4701801,5.5284708),
(9.217642,6.033547),
(8.7757003,6.412354),
]
b2Loop1 = [(loop[0] + 10.0, loop[1]+1.0) for loop in loop1]
b2Loop2 = [(loop[0] - 10.0, loop[1]) for loop in loop2]
b2Loop1.reverse()
bd=box2d.b2BodyDef()
bd.position = ( 0.0, 0.0 )
body = self.world.CreateBody(bd)
weight=box2d.b2CircleDef()
weight.filter.maskBits = 0
weight.density = 4.0
weight.radius = 0.5
weight.localPosition = (8.9, 5.75)
body.CreateShape(weight)
edgeDef=box2d.b2EdgeChainDef()
edgeDef.setVertices(b2Loop2)
body.CreateShape(edgeDef)
body.SetMassFromShapes()
#self.bc.AddBody(body)
# edges and buoyancy aren't quite working yet
# you can uncomment this and see what happens
body = self.world.CreateBody(bd)
weight.radius = 5.0
weight.localPosition = (20.5, 7.0)
body.CreateShape(weight)
edgeDef.setVertices(b2Loop1)
body.CreateShape(edgeDef)
body.SetMassFromShapes()
#self.bc.AddBody(body)
if __name__=="__main__":
main(EdgesBuoyancy)
python-box2d-2.0.2+svn20100109.244/testbed/cairo_main.glade 0000644 0000000 0000000 00000060715 11157660415 021245 0 ustar root root
640
480
800
600
True
True
True
True
True
True
True
True
True
True
GDK_POINTER_MOTION_MASK | GDK_BUTTON_MOTION_MASK | GDK_BUTTON1_MOTION_MASK | GDK_BUTTON2_MOTION_MASK | GDK_BUTTON3_MOTION_MASK | GDK_BUTTON_PRESS_MASK | GDK_BUTTON_RELEASE_MASK | GDK_KEY_PRESS_MASK | GDK_KEY_RELEASE_MASK | GDK_STRUCTURE_MASK | GDK_SCROLL_MASK
True
True
True
Hertz:
GTK_JUSTIFY_RIGHT
True
True
5 5 200 1 10 0
False
False
1
False
False
True
False
4
1
True
True
Position Iterations:
True
True
1 1 500 1 10 0
False
False
1
False
False
2
True
True
Velocity Iterations:
True
True
0 0 100 1 10 0
False
False
1
False
False
3
True
False
4
4
True
0
GTK_SHADOW_NONE
True
12
True
True
True
Shapes
0
True
True
True
Joints
0
True
1
True
True
Controllers
0
True
2
True
True
Core Shapes
0
True
3
True
True
AABBs
0
True
4
True
True
OBBs
0
True
5
True
True
Pairs
0
True
6
True
True
Center of Masses
0
True
7
True
<b>Draw</b>
True
label_item
False
False
5
True
False
4
6
True
True
Draw with Antialiasing
0
True
False
False
7
True
False
4
8
True
True
True
True
0
True
True
gtk-media-play
True
Play
1
True
True
True
0
True
True
gtk-media-pause
True
Pause
1
1
True
True
True
0
True
True
gtk-media-next
True
Step
1
2
False
False
9
True
False
4
10
True
True
True
True
You can access the "framework" and "world" variables
Open Python Console
0
False
False
11
False
False
4
1
True
2
False
1
python-box2d-2.0.2+svn20100109.244/testbed/test_SphereStack.py 0000644 0000000 0000000 00000004353 11135461416 021763 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class SphereStack (Framework):
name="SphereStack"
bodies = [ ]
e_count = 10
_pickle_vars=['bodies']
def __init__(self):
super(SphereStack, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
sd=box2d.b2CircleDef()
sd.radius = 1.0
sd.density = 1.0
for i in xrange(self.e_count):
bd=box2d.b2BodyDef()
bd.position = (0.0, 2.0 + 3.0 * i)
self.bodies.append( self.world.CreateBody(bd) )
self.bodies[-1].CreateShape(sd)
self.bodies[-1].SetMassFromShapes()
def Step(self, settings):
#for body in self.bodies:
# print "%g " % body.GetWorldCenter().y,
#for body in self.bodies:
# print "%g " % body.GetLinearVelocity().y,
#print ""
super(SphereStack, self).Step(settings)
if __name__=="__main__":
main(SphereStack)
python-box2d-2.0.2+svn20100109.244/testbed/test_ElasticBody.py 0000644 0000000 0000000 00000037733 11135461416 021761 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
import math
class ElasticBody (Framework):
name="ElasticBody"
bodies=[]
ground=None
elev=None
joint_elev=None
_pickle_vars=['bodies', 'ground', 'elev', 'joint_elev']
def __init__(self):
super(ElasticBody, self).__init__()
# Bottom static body
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 2.0)
sd.friction = 0.1
sd.restitution = 0.1
bd=box2d.b2BodyDef()
bd.position = (-1.0, -7.5)
self.ground = self.world.CreateBody(bd)
self.ground.CreateShape(sd)
# Upper static body
sd=box2d.b2PolygonDef()
sd.SetAsBox(20.0, 0.50,(0,0),0.047*box2d.b2_pi)
sd.friction = 0.01
sd.restitution = 0.001
bd=box2d.b2BodyDef()
bd.position = (-20, 93.0)
g = self.world.CreateBody(bd)
g.CreateShape(sd)
sd.SetAsBox(15, 0.50,(-15.0,12.5),0.0)
g.CreateShape(sd)
sd.SetAsBox(20,0.5,(0.0,-25.0),-0.5)
g.CreateShape(sd)
# Left channel left wall
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.7, 55.0)
sd.friction = 0.1
sd.restitution = 0.1
bd=box2d.b2BodyDef()
bd.position = (-49.3, 50.0)
g = self.world.CreateBody(bd)
g.CreateShape(sd)
# Right wall
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.7, 55.0)
sd.friction = 0.1
sd.restitution = 0.1
bd=box2d.b2BodyDef()
bd.position = (45, 50.0)
g = self.world.CreateBody(bd)
g.CreateShape(sd)
# Left channel right upper wall
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.5, 20.0)
sd.friction = 0.05
sd.restitution = 0.01
bd=box2d.b2BodyDef()
bd.position = (-42.0, 70.0)
bd.angle = -0.03*box2d.b2_pi
g = self.world.CreateBody(bd)
g.CreateShape(sd)
# Left channel right lower wall
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.50, 23.0)
sd.friction = 0.05
sd.restitution = 0.01
bd=box2d.b2BodyDef()
bd.position = (-44.0, 27.0)
g = self.world.CreateBody(bd)
g.CreateShape(sd)
# Bottom motors
cd=box2d.b2CircleDef()
cd.radius = 3.0
cd.density = 15.0
cd.friction = 1
cd.restitution = 0.2
# 1.
bd.position = (-40.0,2.5)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr=box2d.b2RevoluteJointDef()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
jr.maxMotorTorque = 30000
jr.enableMotor = True
jr.motorSpeed = 20
self.world.CreateJoint(jr).getAsType()
# 1. left down
bd.position = (-46.0,-2.5)
cd.radius = 1.5
jr.motorSpeed = -20
body = self.world.CreateBody(bd)
body.CreateShape(cd)
sd.SetAsBox(2.0, 0.50)
body.CreateShape(sd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter())
self.world.CreateJoint(jr).getAsType()
# 2.
cd.radius = 3.0
jr.motorSpeed = 20
bd.position = (-32.0,2.5)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 3.
jr.motorSpeed = 20
bd.position = (-24.0,1.5)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 4.
bd.position = (-16.0,0.8)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 5.
bd.position = (-8.0,0.5)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 6.
bd.position = (0.0,0.1)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 7.
bd.position = (8.0,-0.5)
body = self.world.CreateBody(bd)
body.CreateShape(cd)
sd.SetAsBox(3.7, 0.5)
body.CreateShape(sd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter()+(0,1))
self.world.CreateJoint(jr).getAsType()
# 8. right rotator
sd.SetAsBox(5, 0.5)
sd.density = 2.0
bd.position = (18.0,1)
rightmotor = self.world.CreateBody(bd) #
rightmotor.CreateShape(sd)
sd.SetAsBox(4.5, 0.5, (0,0),box2d.b2_pi/3)
rightmotor.CreateShape(sd)
sd.SetAsBox(4.5, 0.5, (0,0),box2d.b2_pi*2/3)
rightmotor.CreateShape(sd)
cd.radius = 4.2
rightmotor.CreateShape(cd)
rightmotor.SetMassFromShapes()
jr.Initialize (g,rightmotor,rightmotor.GetWorldCenter())
jr.maxMotorTorque = 70000
jr.motorSpeed = -4
self.world.CreateJoint(jr).getAsType()
# 9. left rotator
sd.SetAsBox(8.5, 0.5)
sd.density = 2.0
bd.position = (-34.0,17)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
sd.SetAsBox(8.5, 0.5, (0,0),box2d.b2_pi*.5)
body.CreateShape(sd)
cd.radius = 7
cd.friction = 0.9
body.CreateShape(cd)
body.SetMassFromShapes()
jr.Initialize (g,body,body.GetWorldCenter())
jr.maxMotorTorque = 100000
jr.motorSpeed = -5
self.world.CreateJoint(jr).getAsType()
# big compressor
sd.SetAsBox(3.0,4)
sd.density = 10.0
bd.position = (-16.0,17)
hammerleft = self.world.CreateBody(bd)
hammerleft.CreateShape(sd)
hammerleft.SetMassFromShapes()
jd=box2d.b2DistanceJointDef()
jd.Initialize(body, hammerleft, body.GetWorldCenter()+(0,6), hammerleft.GetWorldCenter() )
self.world.CreateJoint(jd).getAsType()
bd.position = (4.0,17)
hammerright = self.world.CreateBody(bd)
hammerright.CreateShape(sd)
hammerright.SetMassFromShapes()
jd.Initialize(body, hammerright, body.GetWorldCenter()-(0,6), hammerright.GetWorldCenter() )
self.world.CreateJoint(jd).getAsType()
# pusher
sd.SetAsBox(6,0.75)
bd.position = (-21.0,9)
pusher = self.world.CreateBody(bd) #
pusher.CreateShape(sd)
sd.SetAsBox(2,1.5,(-5,0),0)
pusher.SetMassFromShapes()
pusher.CreateShape(sd)
jd.Initialize(rightmotor,pusher,rightmotor.GetWorldCenter()+(-8.0,0),
pusher.GetWorldCenter()+(5.0,0) )
self.world.CreateJoint(jd).getAsType()
# Static bodies above motors
sd=box2d.b2PolygonDef()
cd=box2d.b2CircleDef()
sd.SetAsBox(9.0, 0.5)
sd.friction = 0.05
sd.restitution = 0.01
bd=box2d.b2BodyDef()
bd.position = (-15.5, 12)
bd.angle = 0.0
g = self.world.CreateBody(bd)
g.CreateShape(sd)
sd.SetAsBox(8, 0.5, (23,0),0)
g.CreateShape(sd)
# compressor statics
sd.SetAsBox(7.0, 0.5, (-2,9),0)
g.CreateShape(sd)
sd.SetAsBox(9.0, 0.5, (22,9),0)
g.CreateShape(sd)
sd.SetAsBox(19.0, 0.5, (-9,15),-0.05)
g.CreateShape(sd)
sd.SetAsBox(4.7, 0.5, (15,11.5),-0.5)
g.CreateShape(sd)
# below compressor
sd.SetAsBox(26.0, 0.3, (17,-4.4),-0.02)
g.CreateShape(sd)
cd.radius = 1.0
cd.friction = 1.0
cd.localPosition = (29,-6)
g.CreateShape(cd)
cd.radius = 0.7
cd.localPosition = (-2,-4.5)
g.CreateShape(cd)
# Elevator
bd=box2d.b2BodyDef()
cd=box2d.b2CircleDef()
sd=box2d.b2PolygonDef()
bd.position = (40.0,4.0)
self.elev = self.world.CreateBody(bd)
sd.SetAsBox(0.5, 2.5,(3.0,-3.0), 0)
sd.density = 1
sd.friction = 0.01
self.elev.CreateShape(sd)
sd.SetAsBox(7.0, 0.5, (-3.5,-5.5), 0)
self.elev.CreateShape(sd)
sd.SetAsBox(0.5, 2.5, (-11,-3.5), 0)
self.elev.CreateShape(sd)
self.elev.SetMassFromShapes()
jp=box2d.b2PrismaticJointDef()
jp.Initialize(self.ground,self.elev, bd.position, (0.0, 1.0))
jp.lowerTranslation = 0.0
jp.upperTranslation = 100.0
jp.enableLimit = True
jp.enableMotor = True
jp.maxMotorForce = 10000
jp.motorSpeed = 0
self.joint_elev = self.world.CreateJoint(jp).getAsType()
# Korb
sd.SetAsBox(2.3, 0.5,(1,0.0), 0.0)
sd.density = 0.5
bd.position = (29.0,6.5)
body = self.world.CreateBody(bd) #
body.CreateShape(sd)
sd.SetAsBox(2.5, 0.5,(3.0,-2), box2d.b2_pi/2)
body.CreateShape(sd)
sd.SetAsBox(4.6, 0.5,(7.8,-4.0), 0)
body.CreateShape(sd)
sd.SetAsBox(0.5, 4.5,(12,0.0), 0)
body.CreateShape(sd)
sd.SetAsBox(0.5, 0.5,(13,4.0), 0)
body.CreateShape(sd)
cd.radius = 0.7
cd.density = 1
cd.friction = 0.01
cd.localPosition = (0,0)
body.CreateShape(cd)
body.SetMassFromShapes()
jr=box2d.b2RevoluteJointDef()
jr.Initialize(self.elev,body, bd.position)
jr.enableLimit = True
jr.lowerAngle = -0.2
jr.upperAngle = box2d.b2_pi*1.1
jr.collideConnected = True
self.world.CreateJoint(jr).getAsType()
# upper body exit
sd.SetAsBox(14.0, 0.5,(-3.5,-10.0), 0.0)
bd.position = (17.5,96.0)
body = self.world.CreateBody(bd)
body.CreateShape(sd)
# "Elastic body" 64 bodies - something like a lin. elastic compound
# connected via dynamic forces (springs)
bodies = self.bodies
for i in range(64):
bodies.append(None)
sd=box2d.b2PolygonDef()
sd.SetAsBox(0.55, 0.55)
sd.density = 1.5
sd.friction = 0.01
sd.filter.groupIndex = -1
startpoint=(30,20)
bd=box2d.b2BodyDef()
bd.isBullet = False
bd.allowSleep = False
for i in range(8):
for j in range(8):
bd.position = (j*1.02, 2.51 + 1.02 * i)
bd.position += startpoint
body = self.world.CreateBody(bd)
bodies[8*i+j] = body
body.CreateShape(sd)
body.SetMassFromShapes()
# Apply dynamic forces (springs) and check elevator state
def Step(self, settings):
bodies = self.bodies
for i in range(8):
for j in range(8):
zero =(0.0,0.0)
down =(0.0, -0.5)
up =(0.0, 0.5)
right=(0.5, 0.0)
left =(-0.5, 0.0)
ind = i*8+j
indr = ind+1
indd = ind+8
spring = 500.0
damp = 5.0
if j<7:
self.AddSpringForce((bodies[ind]),zero,(bodies[indr]),zero,spring, damp, 1.0)
self.AddSpringForce((bodies[ind]),right,(bodies[indr]),left,0.5*spring, damp, 0.0)
if i<7:
self.AddSpringForce((bodies[ind]),zero,(bodies[indd]),zero,spring, damp, 1.0)
self.AddSpringForce((bodies[ind]),up,(bodies[indd]),down,0.5*spring,damp,0.0)
inddr = indd + 1
inddl = indd - 1
drdist = math.sqrt(2.0)
if i < 7 and j < 7:
self.AddSpringForce((bodies[ind]),zero,(bodies[inddr]),zero,spring, damp, drdist)
if i < 7 and j > 0:
self.AddSpringForce((bodies[ind]),zero,(bodies[inddl]),zero,spring, damp, drdist)
indr = ind+2
indd = ind+8*2
if j<6:
self.AddSpringForce((bodies[ind]),zero,(bodies[indr]),zero,spring, damp, 2.0)
if i<6:
self.AddSpringForce((bodies[ind]),zero,(bodies[indd]),zero,spring,damp,2.0)
inddr = indd + 2
inddl = indd - 2
drdist = math.sqrt(2.0)*2.0
if i < 6 and j < 6:
self.AddSpringForce((bodies[ind]),zero,(bodies[inddr]),zero,spring, damp, drdist)
if i < 6 and j > 1:
self.AddSpringForce((bodies[ind]),zero,(bodies[inddl]),zero,spring, damp, drdist)
# Check if bodies are near elevator
# Look if the body to lift is near the elevator
p1 = bodies[0].GetWorldCenter()
p2 = bodies[63].GetWorldCenter()
# self.elev: elevator prism. joint
e = self.elev.GetWorldCenter() + (0,7)
# maybe not the best way to do it...
# Bodies reached the elevator side
if p1.x>e.x or p2.x>e.x: # go up
if (p1.y= self.joint_elev.GetUpperLimit()-2:
self.joint_elev.SetMotorSpeed(-15)
#printf("lift goes down: %G\n",self.joint_elev.GetJointTranslation())
super(ElasticBody, self).Step(settings)
# Add a spring force
def AddSpringForce(self, bA, localA, bB, localB, k, friction, desiredDist):
pA = bA.GetWorldPoint(localA)
pB = bB.GetWorldPoint(localB)
diff=pB - pA
#Find velocities of attach points
vA = bA.GetLinearVelocity() - box2d.b2Cross(bA.GetWorldVector(localA), bA.GetAngularVelocity())
vB = bB.GetLinearVelocity() - box2d.b2Cross(bB.GetWorldVector(localB), bB.GetAngularVelocity())
vdiff=vB-vA
dx = diff.Normalize() #normalizes diff and puts length into dx
vrel = vdiff.x*diff.x + vdiff.y*diff.y
forceMag = -k*(dx-desiredDist) - friction*vrel
diff *= forceMag
bB.ApplyForce(diff, bA.GetWorldPoint(localA))
diff *= -1.0
bA.ApplyForce(diff, bB.GetWorldPoint(localB))
if __name__=="__main__":
main(ElasticBody)
python-box2d-2.0.2+svn20100109.244/testbed/test_ShapeEditing.py 0000644 0000000 0000000 00000005370 11136402204 022102 0 ustar root root #!/usr/bin/python
#
# C++ version Copyright (c) 2006-2007 Erin Catto http://www.gphysics.com
# Python version Copyright (c) 2008 kne / sirkne at gmail dot com
#
# Implemented using the pybox2d SWIG interface for Box2D (pybox2d.googlecode.com)
#
# This software is provided 'as-is', without any express or implied
# warranty. In no event will the authors be held liable for any damages
# arising from the use of this software.
# Permission is granted to anyone to use this software for any purpose,
# including commercial applications, and to alter it and redistribute it
# freely, subject to the following restrictions:
# 1. The origin of this software must not be misrepresented; you must not
# claim that you wrote the original software. If you use this software
# in a product, an acknowledgment in the product documentation would be
# appreciated but is not required.
# 2. Altered source versions must be plainly marked as such, and must not be
# misrepresented as being the original software.
# 3. This notice may not be removed or altered from any source distribution.
from test_main import *
class ShapeEditing (Framework):
name="ShapeEditing"
body=None
shape1=None
shape2=None
_pickle_vars=['body', 'shape1', 'shape2']
def __init__(self):
super(ShapeEditing, self).__init__()
sd=box2d.b2PolygonDef()
sd.SetAsBox(50.0, 10.0)
bd=box2d.b2BodyDef()
bd.position = (0.0, -10.0)
ground = self.world.CreateBody(bd)
ground.CreateShape(sd)
bodydef=box2d.b2BodyDef()
bodydef.position = (0.0, 10.0)
self.body = self.world.CreateBody(bodydef)
sd=box2d.b2PolygonDef()
sd.SetAsBox(4.0, 4.0, (0.0, 0.0), 0.0)
sd.density = 10.0
self.shape1 = self.body.CreateShape(sd)
self.body.SetMassFromShapes()
self.shape2 = None
def Keyboard(self, key):
if not self.body:
return
if key==K_c:
if not self.shape2:
sd=box2d.b2CircleDef()
sd.radius = 3.0
sd.density = 10.0
sd.localPosition = (0.5, -4.0)
self.shape2 = self.body.CreateShape(sd)
self.body.SetMassFromShapes()
self.body.WakeUp()
elif key==K_d:
if self.shape2:
self.body.DestroyShape(self.shape2)
self.shape2 = None
self.body.SetMassFromShapes()
self.body.WakeUp()
def Step(self, settings):
self.DrawStringCR("Press: (c) create a shape, (d) destroy the shape")
super(ShapeEditing, self).Step(settings)
if __name__=="__main__":
main(ShapeEditing)
python-box2d-2.0.2+svn20100109.244/testbed/data/ 0000755 0000000 0000000 00000000000 11414467236 017050 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/data/themes/ 0000755 0000000 0000000 00000000000 11414467236 020335 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/data/themes/gray/ 0000755 0000000 0000000 00000000000 11414467236 021277 5 ustar root root python-box2d-2.0.2+svn20100109.244/testbed/data/themes/gray/select.options.png 0000644 0000000 0000000 00000000265 11130023047 024740 0 ustar root root ‰PNG
IHDR oª¯ pHYs šœ tIMEÕ(%¹ tEXtComment Created with The GIMPïd%n +IDAT8Ëc` `d``øÿÿ?¥¦022QËE£4jШA£
ƒ¨ ;…,;)k“ IEND®B`‚ python-box2d-2.0.2+svn20100109.244/testbed/data/themes/gray/menu.option.normal.png 0000644 0000000 0000000 00000000203 11130023047 025521 0 ustar root root ‰PNG
IHDR oª¯ pHYs šœ tIMEÕ $¢3UQ "IDAT8Ëc¼rá5 •À¨A£4jШA£‘ :kœÆËºÜ IEND®B`‚ python-box2d-2.0.2+svn20100109.244/testbed/data/themes/gray/box.normal.png 0000644 0000000 0000000 00000000346 11130023047 024046 0 ustar root root ‰PNG
IHDR óÿa bKGD ÿ ÿ ÿ ½§“ pHYs šœ tIMEÕ
0à©ö tEXtComment Created with The GIMPïd%n JIDAT8Ëcd``øÏ@`b```øÿÿ?ÉØÁÁfÒÕ‹'‰¶u͆¨. Ø£Œ@©,Ø’'É8::’íFJ³3 Å1ó] IEND®B`‚ python-box2d-2.0.2+svn20100109.244/testbed/data/themes/gray/Vera.ttf 0000644 0000000 0000000 00000200614 11130023047 022675 0 ustar root root OS/2´_ôc ëp VPCLTÑŠ^— ëÈ 6cmap¤Ãè ±l Xcvt ÿÓ9 ü üfpgmç´ñÄ &` ‹gasp H glyftAÏ &ì