January 28, 2014♦
☀
E
F
F
L
U
E
N
C
E
☀
package Animation::Imitation;
use feature "say";
use Math::Trig;
use Animation::Animation;
use Data::Dumper;
use parent "Animation::Animation";
sub new
{
my $class = shift;
$class->SUPER::new(@_);
}
sub setFrames
{
my $self = shift;
my $duration = $self->getOption("duration", "frame");
my $count = $self->getOption("count", "frame");
my $height = $self->getOption("height");
my $width = $self->getOption("width");
my @outer_gradient = $self->readGradient($self->getOption("outer_form_gradient", "imitation"));
my @inner_gradient = $self->readGradient($self->getOption("inner_form_gradient", "imitation"));
my $frames = Image::Magick->new(size=>"${width}x$height");
my $rotation = 0;
my $step = deg2rad(360 / $count);
for (0..$count - 1)
{
$frames->Read("xc:none");
$frames->[$_]->Set(delay=>$duration);
$self->drawOuterForm($frames->[$_], \@outer_gradient, $rotation, $_);
$self->drawInnerForm($frames->[$_], \@inner_gradient, $rotation, $_);
$rotation -= $step;
}
$frames->Set(dispose=>"Background");
$self->SUPER::setFrames($frames);
}
sub drawOuterForm
{
my ($self, $frame, $gradient, $rotation, $index) = @_;
my $count = $self->getOption("outer_form_particle_count", "imitation");
my $step = deg2rad(360 / $count);
my $ratio = $self->getOption("outer_form_size", "imitation");
my $particle_ratio = $self->getOption("outer_form_particle_size", "imitation");
my $frame_width = $frame->Get("width");
my $radius = $ratio * $frame_width / 2;
my $particle_radius = $particle_ratio * $frame_width;
my @center = ($frame_width / 2, $frame_width / 2);
my $angle = $rotation;
my $shape = $self->getOption("outer_form_particle_shape", "imitation");
my $primitive = $self->getPrimitive($shape);
my $resolution = $self->getOption("outer_form_gradient_resolution", "imitation");
my (@origin, @points, $color);
for (0..$self->getOption("interval_count", "imitation") - 1)
{
my $interval = $_;
for (0..$count - 1)
{
$color = $gradient->[$self->getColor($gradient, $interval + $_ + $index, $resolution)];
@origin = $self->getPointOnCircle($radius, $angle, @center);
@points = $self->buildPoints($shape, $particle_radius, @origin);
$frame->Draw(fill=>$color, antialias=>"False", primitive=>$primitive,
points=>$self->buildPointsString(\@points));
$angle += $step;
}
$radius -= $radius * $self->getOption("outer_form_size_decrease", "imitation");
$particle_radius -= $particle_radius * $self->getOption("outer_form_particle_size_decrease",
"imitation");
}
}
sub drawInnerForm
{
my ($self, $frame, $gradient, $rotation, $index) = @_;
my $frame_width = $frame->Get("width");
my $inner_size = $self->getOption("inner_form_size", "imitation");
my $width = $frame_width * $inner_size;
my @origin = ($frame_width / 2, $frame_width / 2);
my $interval_count = $self->getOption("interval_count", "imitation");
my $interval_step = deg2rad(360 / ($interval_count *
$self->getOption("outer_form_particle_count",
"imitation")));
my $interval_size_decrease = $self->getOption("interval_size_decrease",
"imitation");
my $radius = $width / 2;
my $shape = $self->getOption("inner_form", "imitation");
my $primitive = $self->getPrimitive($shape);
my $resolution = $self->getOption("inner_form_gradient_resolution", "imitation");
my $cross_angle = deg2rad($self->getOption("inner_form_cross_angle", "imitation"));
my $cross_minor_radius_size = $self->getOption("inner_form_cross_minor_radius_size",
"imitation");
for (0..$interval_count - 1)
{
$color = $gradient->[$self->getColor($gradient, $_ + $index, $resolution)];
@points = $self->buildPoints($shape, $radius, @origin, $rotation, $cross_angle,
$cross_minor_radius_size);
$frame->Draw(fill=>$color, primitive=>$primitive, antialias=>"False",
points=>$self->buildPointsString(\@points));
$radius -= $radius * $interval_size_decrease;
$rotation += $interval_step;
}
}
1;
from time import time
from pygame import image, Surface, transform, mouse
from pygame.locals import *
from xenographic_wall.pgfw.GameChild import GameChild
from xenographic_wall.pgfw.Animation import Animation
class Introduction(GameChild):
def __init__(self, parent):
GameChild.__init__(self, parent)
self.config = self.get_configuration()
self.subscribe_to_events()
self.deactivate()
self.load_images()
self.reset()
self.set_zoom_parameters()
def subscribe_to_events(self):
self.subscribe_to(self.get_custom_event_id(), self.respond_to_event)
def respond_to_event(self, evt):
if self.is_command(evt, "reset-game"):
self.reset()
self.activate()
elif self.is_command(evt, "mouse-down-left"):
if self.title_active and self.active:
self.deactivate()
self.post_command("cancel-introduction")
else:
self.activate_title()
def activate_title(self):
self.title_active = True
def init_surface(self):
self.surf = Surface(self.config.get("display", "dimensions"))
def activate(self):
self.active = True
self.get_audio().stop_current_channel()
mouse.set_visible(True)
def deactivate(self):
self.active = False
def load_images(self):
load = image.load
get = self.get_resource
section = "intro"
self.mask = load(get(section, "mask")).convert()
self.cord = load(get(section, "cord")).convert_alpha()
self.starfield = load(get(section, "starfield")).convert()
self.sunburst = load(get(section, "sunburst")).convert_alpha()
self.title = load(get(section, "title")).convert_alpha()
self.prompt = load(get(section, "prompt")).convert_alpha()
def reset(self):
config = self.config.get_section("intro")
self.cord_speed = config["cord-speed"]
self.cord_range = config["cord-y-range"]
self.cord_y = self.cord_range[0]
self.deactivate_sunburst()
self.zoom_active = False
self.zoom_countdown_start = None
self.zoom_finished = False
self.zoom_step_count = 0
self.starfield_active = False
self.starfield_alpha = 0
self.fade_in_starfield_finished = False
self.title_active = False
self.prompt_visible = True
self.prompt_visibility_count = 0
self.reset_countdown_start = None
self.init_surface()
def set_zoom_parameters(self):
self.zoom_scale_step = 16, 12
self.zoom_shift_step = 7, 7
self.zoom_step_limit = 64
def activate_sunburst(self):
self.sunburst_active = True
def deactivate_sunburst(self):
self.sunburst_countdown_start = None
self.sunburst_active = False
def update(self):
if self.active:
self.check_reset_countdown()
self.move_cord()
self.update_sunburst()
self.zoom()
self.fade_in_starfield()
self.set_prompt_visibility()
surf = self.surf
if not self.zoom_active and not self.zoom_finished:
surf.blit(self.mask, (0, 0))
self.draw_sunburst()
surf.blit(self.cord, (0, int(self.cord_y)))
self.get_screen().blit(surf, (0, 0))
self.draw_starfield()
self.draw_title()
self.draw_prompt()
def check_reset_countdown(self):
start = self.reset_countdown_start
if start and time() - start > self.config.get("intro", "reset-delay"):
self.reset()
self.activate_title()
def move_cord(self):
cord_y = self.cord_y
limit = self.cord_range[1]
if cord_y < limit:
cord_y += self.cord_speed
if cord_y >= limit:
self.start_sunburst_countdown()
self.cord_y = cord_y
def start_sunburst_countdown(self):
self.sunburst_countdown_start = time()
def update_sunburst(self):
if not self.sunburst_active:
start = self.sunburst_countdown_start
if start and time() - start > self.config.get("intro",
"sunburst-delay"):
self.activate_sunburst()
self.start_zoom_countdown()
def start_zoom_countdown(self):
self.zoom_countdown_start = time()
def zoom(self):
start = self.zoom_countdown_start
config = self.config.get_section("intro")
if not self.zoom_finished and not self.zoom_active and start:
if time() - start > config["zoom-delay"]:
self.zoom_active = True
if self.zoom_active:
surf = self.surf
cur_width, cur_height = surf.get_size()
x_scale_step, y_scale_step = self.zoom_scale_step
surf = transform.smoothscale(surf, (int(cur_width + x_scale_step),
int(cur_height + y_scale_step)))
count = self.zoom_step_count + 1
if count > self.zoom_step_limit:
self.zoom_active = False
self.zoom_finished = True
self.starfield_active = True
if not self.get_audio().is_bgm_playing():
self.start_music()
else:
self.zoom_step_count = count
shift_step = self.zoom_shift_step
rect = self.get_screen().get_rect()
rect.left += shift_step[0]
rect.top += shift_step[1]
self.surf = surf.subsurface(rect).copy()
def start_music(self):
self.get_audio().play_bgm(self.get_resource("intro", "audio"))
def fade_in_starfield(self):
if self.starfield_active:
starfield = self.starfield
config = self.config.get_section("intro")
alpha = self.starfield_alpha + config["starfield-fade-step"]
if alpha < config["starfield-max-alpha"]:
self.starfield_alpha = alpha
elif not self.fade_in_starfield_finished:
self.activate_title()
self.start_reset_countdown()
self.fade_in_starfield_finished = True
self.apply_starfield_alpha()
def start_reset_countdown(self):
self.reset_countdown_start = time()
def apply_starfield_alpha(self):
self.starfield.set_alpha(self.starfield_alpha)
def set_prompt_visibility(self):
if self.title_active:
count = self.prompt_visibility_count + 1
if count > self.config.get("intro", "prompt-visible-frames"):
self.prompt_visible = not self.prompt_visible
count = 0
self.prompt_visibility_count = count
def draw_sunburst(self):
if self.sunburst_active:
self.surf.blit(self.sunburst, (0, 0))
def draw_starfield(self):
if self.starfield_active:
self.get_screen().blit(self.starfield, (0, 0))
def draw_title(self):
if self.title_active:
self.get_screen().blit(self.title, (0, 0))
def draw_prompt(self):
if self.title_active and self.prompt_visible:
self.get_screen().blit(self.prompt, (0, 0))