Merge branch 'master' of makar:/var/www/git/pgfw

This commit is contained in:
Frank DeMarco 2016-03-11 23:40:18 -05:00
commit 05619331aa
6 changed files with 143 additions and 94 deletions

View File

@ -1,92 +1,50 @@
from os import listdir
from os.path import join
from pygame.mixer import Channel, Sound, music, find_channel
from pygame.mixer import Channel, Sound, music, find_channel, get_num_channels
from GameChild import *
from Input import *
class Audio(GameChild):
current_channel = None
paused = False
muted = False
UP, DOWN = .1, -.1
BASE_VOLUME = .8
def __init__(self, game):
GameChild.__init__(self, game)
self.delegate = self.get_delegate()
self.load_fx()
self.original_volumes = {}
self.volume = self.BASE_VOLUME
if self.check_command_line("-mute"):
self.volume = 0
self.subscribe(self.respond)
def load_fx(self):
fx = {}
if self.get_configuration().has_option("audio", "sfx-path"):
root = self.get_resource("audio", "sfx-path")
if root:
for name in listdir(root):
fx[name.split(".")[0]] = Sound(join(root, name))
self.fx = fx
def set_volume(self, volume=None, increment=None, mute=False):
if mute:
self.volume = 0
elif increment:
self.volume += increment
if self.volume > 1:
self.volume = 1.0
elif self.volume < 0:
self.volume = 0
else:
self.volume = volume
def respond(self, event):
if self.delegate.compare(event, "mute"):
self.mute()
compare = self.get_game().delegate.compare
if compare(event, "volume-mute"):
self.set_volume(mute=True)
elif compare(event, "volume-up"):
self.set_volume(increment=self.UP)
elif compare(event, "volume-down"):
self.set_volume(increment=self.DOWN)
def mute(self):
self.muted = True
self.set_volume()
def unmute(self):
self.muted = False
self.set_volume()
def set_volume(self):
volume = int(not self.muted)
music.set_volume(volume)
if self.current_channel:
self.current_channel.set_volume(volume)
def play_bgm(self, path, stream=False):
self.stop_current_channel()
if stream:
music.load(path)
music.play(-1)
else:
self.current_channel = Sound(path).play(-1)
self.set_volume()
def stop_current_channel(self):
music.stop()
if self.current_channel:
self.current_channel.stop()
self.current_channel = None
self.paused = False
def play_fx(self, name, panning=.5):
if not self.muted:
channel = find_channel(True)
if panning != .5:
offset = 1 - abs(panning - .5) * 2
if panning < .5:
channel.set_volume(1, offset)
else:
channel.set_volume(offset, 1)
channel.play(self.fx[name])
def pause(self):
channel = self.current_channel
paused = self.paused
if paused:
music.unpause()
if channel:
channel.unpause()
else:
music.pause()
if channel:
channel.pause()
self.paused = not paused
def is_bgm_playing(self):
current = self.current_channel
if current and current.get_sound():
return True
return music.get_busy()
def update(self):
for ii in xrange(get_num_channels()):
channel = Channel(ii)
sound = channel.get_sound()
if sound is not None:
if sound not in self.original_volumes.keys():
self.original_volumes[sound] = sound.get_volume()
sound.set_volume(self.original_volumes[sound] * self.volume)

View File

@ -115,7 +115,9 @@ class Configuration(RawConfigParser):
set_option(section, "toggle-fullscreen", "K_F11", False)
set_option(section, "reset-game", "K_F8", False)
set_option(section, "record-video", "K_F10", False)
set_option(section, "mute", "K_F12", False)
set_option(section, "volume-down", "K_F1", False)
set_option(section, "volume-up", "K_F2", False)
set_option(section, "volume-mute", "K_F3", False)
set_option(section, "toggle-interpolator", "K_F7", False)
section = "joy"
add_section(section)

View File

@ -54,6 +54,7 @@ class Game(GameChild):
self.update()
else:
self.interpolator.gui.update()
self.audio.update()
if self.video_recorder.requested:
self.video_recorder.update()

View File

@ -9,12 +9,12 @@ from pygame.transform import flip
from pygame.locals import *
from Animation import Animation
from Vector import Vector
from extension import get_hue_shifted_surface
from Vector import Vector, EVector
from extension import get_hue_shifted_surface, get_step
class Sprite(Animation):
def __init__(self, parent, framerate=None):
def __init__(self, parent, framerate=None, neighbors=[], mass=None):
Animation.__init__(self, parent, self.shift_frame, framerate)
self.frames = []
self.mirrored = False
@ -22,10 +22,12 @@ class Sprite(Animation):
self.locations = []
self.framesets = [Frameset(self, framerate=framerate)]
self.frameset_index = 0
self.neighbors = neighbors
self.mass = mass
self.step = EVector()
self.set_frameset(0)
self.locations.append(Location(self))
self.motion_overflow = Vector()
self.stop()
self.display_surface = self.get_display_surface()
def __getattr__(self, name):
@ -208,21 +210,26 @@ class Sprite(Animation):
for frameset in self.framesets:
frameset.reverse()
def go(self, dx=0, dy=0):
self.go_vector = Vector(dx, dy)
def set_step(self, dx=0, dy=0, magnitude=None, angle=0):
self.step.set_step(dx, dy, magnitude, angle)
def stop(self):
self.go_vector = Vector()
def cancel_step(self):
self.step.set_step(0, 0)
def is_going(self):
return self.go_vector != [0, 0]
def is_stepping(self):
return bool(self.step)
def update(self, areas=None, substitute=None):
Animation.update(self)
if self.is_going():
self.move(*self.go_vector)
if self.is_stepping():
self.move(self.step.dx, self.step.dy)
for neighbor in self.neighbors:
self.move(*get_step(self.location.center, neighbor.location.center,
neighbor.mass))
if self.get_current_frameset().length():
self.draw(areas, substitute)
# for location in self.locations:
# location.update()
def draw(self, areas=None, substitute=None):
for location in self.locations:
@ -253,6 +260,10 @@ class Location(Rect):
overflow[1] -= int(overflow[1])
return excess
def move_to(self, x, y, base=None):
ox, oy = self.apply_motion_overflow(base)
self.move_ip(x - ox, y - oy)
def reset_motion_overflow(self):
self.motion_overflow.place_at_origin()
@ -273,6 +284,18 @@ class Location(Rect):
def is_hidden(self):
return self.hidden
def update(self):
pass
# for neighbor in self.sprite.neighbors:
# if neighbor.mass:
# closest = neighbor.location
# for location in neighbor.locations[1:]:
# if get_distance(self.center, location.center) < \
# get_distance(self.center, closest.center):
# closest = location
# self.move_ip(get_step(self.center, closest.center,
# neighbor.mass))
class Fader(Surface):

View File

@ -1,8 +1,18 @@
from math import pi, degrees
from extension import get_delta, get_distance, get_angle
class Vector(list):
def __init__(self, x=0, y=0):
list.__init__(self, (x, y))
def __repr__(self):
message = "<%f" % self[0]
for value in self[1:]:
message += ", %f" % value
return message + ">"
def __getattr__(self, name):
if name == "x":
return self[0]
@ -48,6 +58,24 @@ class Vector(list):
self.y *= other
return self
def __eq__(self, other):
for sv, ov in zip(self, other):
if value != other[ii]:
return False
return True
def __ne__(self, other):
for sv, ov in zip(self, other):
if value == other[ii]:
return False
return True
def __nonzero__(self):
for value in self:
if bool(value):
return True
return False
def apply_to_components(self, function):
self.x = function(self.x)
self.y = function(self.y)
@ -67,3 +95,37 @@ class Vector(list):
def place_at_origin(self):
self.x = 0
self.y = 0
class EVector(Vector):
def __init__(self, x=0, y=0, dx=0, dy=0, magnitude=None, angle=0):
Vector.__init__(self, x, y)
self.set_step(dx, dy, magnitude, angle)
def set_step(self, dx=0, dy=0, magnitude=None, angle=0):
"""specify angle in radians, counter-clockwise, 0 is up"""
if magnitude is not None:
self.magnitude = magnitude
self.angle = angle
self.dx, self.dy = get_delta(angle, magnitude, False)
else:
self.dx = dx
self.dy = dy
if dx == 0 and dy == 0:
self.magnitude = 0
self.angle = 0
else:
end = self.x + dx, self.y + dy
self.magnitude = get_distance(self, end)
self.angle = -get_angle(self, end) - pi
def __repr__(self):
return "<dx=%.2f, dy=%.2f, m=%.2f, ang=%.2f>" % \
(self.dx, self.dy, self.magnitude, self.angle)
def __nonzero__(self):
return bool(self.magnitude)
def move(self):
self += self.dx, self.dy

View File

@ -1,5 +1,5 @@
from random import randint
from math import sin, cos, atan2, radians, sqrt
from math import sin, cos, atan2, radians, sqrt, pi
from pygame import Surface, PixelArray, Color
from pygame.mixer import get_num_channels, Channel
@ -9,9 +9,12 @@ def get_step(start, end, speed):
angle = get_angle(start, end)
return speed * sin(angle), speed * cos(angle)
def get_angle(start, end):
def get_angle(start, end, transpose=False):
"""counterclockwise, 0 is down"""
return atan2(end[0] - start[0], end[1] - start[1])
angle = atan2(end[0] - start[0], end[1] - start[1])
if transpose:
return -angle - pi
return angle
def get_endpoint(start, angle, magnitude, translate_angle=True):
"""clockwise, 0 is up"""
@ -172,8 +175,8 @@ def get_shadowed_text(text, font, offset, color, antialias=True, shadow_color=(0
foreground = font.render(text, antialias, color)
background = font.render(text, antialias, shadow_color)
alpha = SRCALPHA if antialias else 0
surface = Surface((foreground.get_width() + offset[0],
foreground.get_height() + offset[1]), alpha)
surface = Surface((foreground.get_width() + abs(offset[0]),
foreground.get_height() + abs(offset[1])), alpha)
if not antialias:
surface.set_colorkey(colorkey)
surface.fill(colorkey)
@ -185,5 +188,5 @@ def get_shadowed_text(text, font, offset, color, antialias=True, shadow_color=(0
def get_hsla_color(hue, saturation=100, lightness=50, alpha=100):
color = Color(0, 0, 0, 0)
color.hsla = hue, saturation, lightness, alpha
color.hsla = hue % 360, saturation, lightness, alpha
return color