Mercurial > Kubik
changeset 137:62af0b5c0e8e
walk.py
| author | Radomir Dopieralski <sheep-devel@sheep.art.pl> |
|---|---|
| date | Tue, 15 Jul 2014 22:56:33 +0200 |
| parents | 14087ba87a99 |
| children | 49d2e68a50b3 |
| files | kubik.py walk.py |
| diffstat | 2 files changed, 119 insertions(+), 7 deletions(-) [+] |
line wrap: on
line diff
--- a/kubik.py Tue Jul 15 00:51:47 2014 +0200 +++ b/kubik.py Tue Jul 15 22:56:33 2014 +0200 @@ -57,9 +57,9 @@ """ # Lengths of leg segments, in mm - coxa = 36.0 # between the hip and the knee + coxa = 40.0 # between the hip and the knee femur = 30.0 # between the knee and the ankle - tibia = 36.0 # between the ankle and the foot + tibia = 36.5 # between the ankle and the foot base = 45.0, 45.0 # from the center of body home = 45.0, 45.0, -35.0 @@ -73,8 +73,16 @@ else: self.y_direction = -1 self.hip_offset = -45 * self.y_direction - self.position = ( + self.home = ( self.home[0], self.home[1] * self.y_direction, self.home[2]) + self.position = list(self.home) + + def __repr__(self): + return "<Leg (%r, %r, %r)>" % ( + self.position[0], + self.position[1], + self.position[2], + ) def __iter__(self): """Iterate over all joints.""" @@ -111,7 +119,7 @@ def rotate(self, degrees): """Rotate the leg around the center of the body horizontally.""" - radians = math.radians(degrees) + radians = math.radians(degrees * self.y_direction) x, y, z = self.position bx = self.base[0] + x by = self.base[1] + y * self.y_direction @@ -173,18 +181,18 @@ ] for leg, shift in zip(self.legs, shifts): x, y, z = leg.position - if (x, y) != (leg.home[0], leg.home[1] * leg.y_direction): + if (x, y) != (leg.home[0], leg.home[1]): self.shift = shift leg.move_to((None, None, 5)) for i in range(2): yield - leg.move_to((leg.home[0], leg.home[1] * leg.y_direction, None)) + leg.move_to((leg.home[0], leg.home[1], None)) for i in range(2): yield leg.move_to((None, None, leg.home[2] + 1)) for i in range(4): yield - leg.move_to((None, None, leg.home[2])) + leg.move_to(leg.home) self.shift = [0, 0, 0] def home(self):
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/walk.py Tue Jul 15 22:56:33 2014 +0200 @@ -0,0 +1,104 @@ +import pygame + +import kubik + + +FPS = 12 + + +class Walk(object): + def __init__(self, robot): + self.robot = robot + self.speed = [0, 0] + self.rotation = 1.0 + self.stride = 35 + self.shift_speed = 3 + self.shift_steps = 4 + self.down = -40 + self.up = -20 + self.legs = [ + (self.robot.legs[0], (1, -1), 1, (35, -35)), + (self.robot.legs[1], (1, 1), 1, (35, 35)), + (self.robot.legs[3], (-1, -1), -1, (35, -35)), + (self.robot.legs[2], (-1, 1), -1, (35, 35)), + ] + self.on_floor = set((leg, side) + for leg, shift, side, home in self.legs) + + def _retract_leg(self, step): + dx, dy = self.speed + leg, side = step + leg.move_by((-dx * side, -dy, 0)) + leg.rotate(self.rotation * side / 3) + + def _retract(self): + while True: + for step in self.on_floor: + self._retract_leg(step) + yield + + def _raise_leg(self, leg, side): + leg.move_to((None, None, self.up)) + self.on_floor.remove((leg, side)) + + def _advance_leg(self, leg, side, home): + dx, dy = self.speed + leg.move_to(( + home[0] + dx * self.stride * side - (abs(dx) + abs(dy)) * 15, + home[1] + dy * self.stride - ( + abs(dy) + abs(dx)) * 15 * leg.y_direction, + None, + )) + leg.rotate(-self.rotation * self.stride * side / 3) + + def _lower_leg(self, leg): + leg.move_to((None, None, self.down + 1)) + + def _ground_leg(self, leg, side): + leg.move_to((None, None, self.down)) + self.on_floor.add((leg, side)) + + def _stomp(self): + shifted = 0, 0 + while True: + for leg, shift, side, home in self.legs: + for frame in range(self.shift_steps): + if shift[0] != shifted[0]: + self.robot.shift[0] += shift[0] * self.shift_speed + if shift[1] != shifted[1]: + self.robot.shift[1] += shift[1] * self.shift_speed + yield + self._raise_leg(leg, side) + for frame in range(2): + yield + self._advance_leg(leg, side, home) + self._lower_leg(leg) + for frame in range(4): + yield + self._ground_leg(leg, side) + for frame in range(self.shift_steps): + if shift[0] != shifted[0]: + self.robot.shift[0] -= shift[0] * self.shift_speed + if shift[1] != shifted[1]: + self.robot.shift[1] -= shift[1] * self.shift_speed + yield + shifted = shift + + def run(self): + clock = pygame.time.Clock() + stomp = self._stomp() + retract = self._retract() + try: + while True: + stomp.next() + retract.next() + robot.update() + clock.tick(FPS) + finally: + self.robot.home() + + +if __name__ == '__main__': + robot = kubik.Robot() + walk = Walk(robot) + walk.run()
