[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]
[pygame] Circular number system?
- To: pygame-users <pygame-users@xxxxxxxx>
- Subject: [pygame] Circular number system?
- From: Daniel Jo <ostsol@xxxxxxxxx>
- Date: Sun, 22 Feb 2009 12:51:25 -0700
- Delivered-to: archiver@xxxxxxxx
- Delivered-to: pygame-users-outgoing@xxxxxxxx
- Delivered-to: pygame-users@xxxxxxxx
- Delivery-date: Sun, 22 Feb 2009 14:51:28 -0500
- Dkim-signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=domainkey-signature:mime-version:received:date:message-id:subject :from:to:content-type:content-transfer-encoding; bh=BYIDgirpWijjA4livU1WdSd3fyh+kT1P+oyBoAJPmAo=; b=iKGeFCt8os9rAO/GqiuD/MDKrvfEJb19v2Sunww9aV9yiAoSMtvoQcUP6KWldZed4M ZfYXiesQu6sbAC8qnNO4xsX9rJ1BLjaG1rCAfe0iWbDwnoJcA/sF9gPlD3kiaxHDtV4m uCTUnXFAOTTgvrNxGLCBYthcm9RkaNGzcPA9A=
- Domainkey-signature: a=rsa-sha1; c=nofws; d=gmail.com; s=gamma; h=mime-version:date:message-id:subject:from:to:content-type :content-transfer-encoding; b=WCYPE/Uiz9D5iuYgjK7Ck6/rbGzSZ7JtHY3DC+aO1GLV4jzrzGJONx7MqDqwJH7r2I 3DtGx7BSAZ1gziPXI3DXZ0PNKh1szf+KD/n6DXC4MB7ZhGMPHf/rbIvWFay1UGV9eycB 9H4ekgW4nv5vmnFXF4x80f2px2m/zOn6XP5Z0=
- Reply-to: pygame-users@xxxxxxxx
- Sender: owner-pygame-users@xxxxxxxx
What I mean by "circular" is sort of like a clock, where passing the
upper limit takes one back to the start again. Two hours passed 11 on
a 12-hour clock is 1 o'clock. Similarily three hours before 2 is 11
o'clock. Another example is a compass. Forty-five degrees left of
north, 0 degrees, is 315 degrees, rather than -45.
My need for it is for the latter example. In such an example,
comparisons such as "less-than" and "greater-than" aren't so important
as "left-of" and "right-of", respectively. Anything in the range
[180,360) is left of 0 and anything in the range (0, 180] is right of
0. Similarily, anything in the range [270,360) and [0,90) is left of
0.
My implementation is more of a utility class than a data-type:
import math
class RingBase (object):
def __init__ (self, lower, upper):
self.lower = lower
self.upper = upper
self.span = upper - lower
def __call__ (self, value):
if value > self.upper:
loops = int (value / self.span)
return value - self.span * loops
if value < self.lower:
loops = int (abs (value) / self.span) + 1
return value + self.span * loops
return value
def _lo (self, v1, v2):
v1 = self (v1)
v2 = self (v2)
half = self.span * 0.5
left = v2 - half
if left < self.lower:
if v1 >= self.upper - (v2 - self.lower):
return True
elif v1 < v2:
return True
elif v1 < v2 and v1 > left:
return True
return False
def _ro (self, v1, v2):
v1 = self (v1)
v2 = self (v2)
half = self.span * 0.5
right = v2 + half
if right >= self.upper:
if v1 <= self.lower + (self.upper - v2):
return True
elif v1 > v2:
return True
elif v1 > v2 and v1 < right:
return True
return False
class Ring (RingBase):
def __init__ (self, lower, upper):
super (Ring, self).__init__ (lower, upper)
lo = RingBase._lo
ro = RingBase._ro
class Radian (RingBase):
def __init__ (self):
super (Radian, self).__init__ (0.0, 2.0 * math.pi)
lo = RingBase._ro
ro = RingBase._lo
An instance of Ring is callable and is used to clamp a value within
the Ring's limits. For example. . .
ring = Ring (0, 12)
print ring (13)
. . . yields 1.
print ring (-1)
. . . yields 11.
ring.lo (11, 1)
. . . asks if 11 is left of 1 and returns True.
So is there anything else like this out there?
-Daniel