jemini 2009.10.27
Sign up to get free protection for your applications and to get access to all the features.
- data/README.txt +9 -0
- data/bin/jemini +26 -0
- data/lib/ibxm.jar +0 -0
- data/lib/jinput.jar +0 -0
- data/lib/jogg-0.0.7.jar +0 -0
- data/lib/jorbis-0.0.15.jar +0 -0
- data/lib/jruby-complete.jar +0 -0
- data/lib/lwjgl.jar +0 -0
- data/lib/lwjgl_util_applet.jar +0 -0
- data/lib/native_files/OpenAL32.dll +0 -0
- data/lib/native_files/jinput-dx8.dll +0 -0
- data/lib/native_files/jinput-dx8_64.dll +0 -0
- data/lib/native_files/jinput-raw.dll +0 -0
- data/lib/native_files/jinput-raw_64.dll +0 -0
- data/lib/native_files/jinput-wintab.dll +0 -0
- data/lib/native_files/libjinput-linux.so +0 -0
- data/lib/native_files/libjinput-linux64.so +0 -0
- data/lib/native_files/libjinput-osx.jnilib +0 -0
- data/lib/native_files/liblwjgl.jnilib +0 -0
- data/lib/native_files/liblwjgl.so +0 -0
- data/lib/native_files/liblwjgl64.so +0 -0
- data/lib/native_files/libopenal.so +0 -0
- data/lib/native_files/lwjgl.dll +0 -0
- data/lib/native_files/openal.dylib +0 -0
- data/lib/natives-linux.jar +0 -0
- data/lib/natives-mac.jar +0 -0
- data/lib/natives-win32.jar +0 -0
- data/lib/phys2d.jar +0 -0
- data/lib/slick.jar +0 -0
- data/package/jar/jemini.jar +0 -0
- data/src/behavior.rb +248 -0
- data/src/behavior_event.rb +23 -0
- data/src/behaviors/animated_image.rb +88 -0
- data/src/behaviors/audible.rb +16 -0
- data/src/behaviors/axis_stateful.rb +35 -0
- data/src/behaviors/bounding_box_collidable.rb +27 -0
- data/src/behaviors/cardinal_movable.rb +121 -0
- data/src/behaviors/clickable.rb +19 -0
- data/src/behaviors/countable.rb +32 -0
- data/src/behaviors/debug_physical.rb +43 -0
- data/src/behaviors/debug_tangible.rb +31 -0
- data/src/behaviors/drawable.rb +7 -0
- data/src/behaviors/drawable_image.rb +111 -0
- data/src/behaviors/drawable_line.rb +32 -0
- data/src/behaviors/drawable_shape.rb +48 -0
- data/src/behaviors/fading_image_trail_emittable.rb +32 -0
- data/src/behaviors/game_object_emittable.rb +13 -0
- data/src/behaviors/grid_bound.rb +108 -0
- data/src/behaviors/handles_events.rb +33 -0
- data/src/behaviors/inertial.rb +14 -0
- data/src/behaviors/magnetic.rb +34 -0
- data/src/behaviors/metered.rb +3 -0
- data/src/behaviors/movable.rb +81 -0
- data/src/behaviors/particle_emitter.rb +27 -0
- data/src/behaviors/physical.rb +384 -0
- data/src/behaviors/physical_cardinal_movable.rb +111 -0
- data/src/behaviors/physical_image.rb +45 -0
- data/src/behaviors/pointer.rb +30 -0
- data/src/behaviors/pressable.rb +17 -0
- data/src/behaviors/regional.rb +76 -0
- data/src/behaviors/rotates_to_point.rb +19 -0
- data/src/behaviors/spatial.rb +43 -0
- data/src/behaviors/stateful.rb +33 -0
- data/src/behaviors/taggable.rb +28 -0
- data/src/behaviors/tangible.rb +59 -0
- data/src/behaviors/timeable.rb +88 -0
- data/src/behaviors/top_down_vehicle.rb +42 -0
- data/src/behaviors/triangle_trail_emittable.rb +46 -0
- data/src/behaviors/unique.rb +0 -0
- data/src/behaviors/updates.rb +8 -0
- data/src/behaviors/updates_at_consistant_rate.rb +28 -0
- data/src/behaviors/vectored_movement.rb +48 -0
- data/src/behaviors/world_collidable.rb +9 -0
- data/src/color.rb +70 -0
- data/src/events/grid_changed_event.rb +8 -0
- data/src/events/physical_message.rb +9 -0
- data/src/events/tangible_collision_event.rb +8 -0
- data/src/file_system.rb +17 -0
- data/src/game.rb +110 -0
- data/src/game_object.rb +176 -0
- data/src/game_objects/background.rb +10 -0
- data/src/game_objects/fading_image.rb +23 -0
- data/src/game_objects/tangible_object.rb +4 -0
- data/src/game_objects/text.rb +71 -0
- data/src/game_objects/triangle_trail.rb +85 -0
- data/src/game_state.rb +164 -0
- data/src/inflector.rb +68 -0
- data/src/input_helpers/joystick_dead_zone_filter.rb +9 -0
- data/src/jemini.rb +31 -0
- data/src/jemini_version.rb +4 -0
- data/src/listenable_mixin.rb +15 -0
- data/src/logger_mixin.rb +11 -0
- data/src/managers/basic_game_object_manager.rb +95 -0
- data/src/managers/basic_physics_manager.rb +95 -0
- data/src/managers/basic_render_manager.rb +49 -0
- data/src/managers/basic_tile_manager.rb +3 -0
- data/src/managers/basic_update_manager.rb +30 -0
- data/src/managers/diagnostic/diagnostic_input_manager.rb +0 -0
- data/src/managers/input_manager.rb +161 -0
- data/src/managers/input_support/input_binding.rb +77 -0
- data/src/managers/input_support/input_builder.rb +44 -0
- data/src/managers/input_support/input_listener.rb +74 -0
- data/src/managers/input_support/input_message.rb +5 -0
- data/src/managers/input_support/joystick_listener.rb +53 -0
- data/src/managers/input_support/key_listener.rb +27 -0
- data/src/managers/input_support/mouse_listener.rb +38 -0
- data/src/managers/input_support/slick_input_listener.rb +20 -0
- data/src/managers/input_support/slick_input_message.rb +11 -0
- data/src/managers/input_support/slick_input_translator.rb +15 -0
- data/src/managers/message_queue.rb +60 -0
- data/src/managers/network_manager.rb +41 -0
- data/src/managers/render_support/hardware_cursor.rb +13 -0
- data/src/managers/resource_manager.rb +167 -0
- data/src/managers/sound_manager.rb +47 -0
- data/src/managers/tag_manager.rb +47 -0
- data/src/managers/tangible_manager.rb +36 -0
- data/src/math.rb +23 -0
- data/src/org/rubyforge/rawr/Main.java +67 -0
- data/src/platform.rb +28 -0
- data/src/proc_enhancement.rb +5 -0
- data/src/project_generator.rb +138 -0
- data/src/resource.rb +31 -0
- data/src/spline.rb +13 -0
- data/src/states/input_diagnostic_state.rb +53 -0
- data/src/vector.rb +143 -0
- data/test/test_state.rb +3 -0
- metadata +188 -0
@@ -0,0 +1,88 @@
|
|
1
|
+
#Makes an object receive an event when a given time period has elapsed.
|
2
|
+
class Timeable < Jemini::Behavior
|
3
|
+
depends_on :Updates
|
4
|
+
|
5
|
+
def load
|
6
|
+
@game_object.enable_listeners_for :timer_tick, :countdown_complete
|
7
|
+
@timers = {}
|
8
|
+
@game_object.on_update do |delta|
|
9
|
+
update_timers delta
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
#Add a countdown delay of the given number of seconds to the object.
|
14
|
+
#When the specified time has elapsed, a :countdown_complete event with the specified name will be passed to the object.
|
15
|
+
#If notify_frequency is specified, a :timer_tick event with the Timer object will be passed to the object each time the specified interval elapses.
|
16
|
+
def add_countdown(name, seconds, notify_frequency = nil)
|
17
|
+
@timers[name] = Timer.new(name, Timer::COUNTDOWN, seconds, notify_frequency) {|timer| @game_object.notify :timer_tick, timer }
|
18
|
+
end
|
19
|
+
|
20
|
+
#Add a countup delay to the object. See add_countdown.
|
21
|
+
def add_countup(name, seconds, notify_frequency = nil)
|
22
|
+
@timers[name] = Timer.new(name, Timer::COUNTUP, seconds, notify_frequency) {|timer| @game_object.notify :timer_tick, timer }
|
23
|
+
end
|
24
|
+
|
25
|
+
private
|
26
|
+
def update_timers(delta)
|
27
|
+
@timers.each do |name, timer|
|
28
|
+
timer.apply_delta delta
|
29
|
+
if timer.countdown_complete?
|
30
|
+
@game_object.notify :countdown_complete, name
|
31
|
+
end
|
32
|
+
end
|
33
|
+
# in order to keep from mutating the array while we iterate, handle separately.
|
34
|
+
@timers.delete_if {|name, timer| timer.countdown_complete? }
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
#Used to track how much time has elapsed.
|
39
|
+
class Timer
|
40
|
+
COUNTDOWN = :countdown
|
41
|
+
COUNTUP = :countup
|
42
|
+
def initialize(name, direction, seconds, notify_frequency, ¬ify_callback)
|
43
|
+
@name = name
|
44
|
+
@direction = direction
|
45
|
+
@milliseconds = seconds * 1000.0
|
46
|
+
@notify_frequency = notify_frequency * 1000.0 if notify_frequency
|
47
|
+
@notify_callback = notify_callback unless notify_frequency.nil?
|
48
|
+
@current_milliseconds = 0
|
49
|
+
@milliseconds_since_last_notify = 0
|
50
|
+
end
|
51
|
+
|
52
|
+
#Use the given elapsed time to determine if callbacks should be triggered.
|
53
|
+
def apply_delta(delta_in_milliseconds)
|
54
|
+
return if @countdown_complete
|
55
|
+
|
56
|
+
@current_milliseconds += delta_in_milliseconds
|
57
|
+
@milliseconds_since_last_notify += delta_in_milliseconds
|
58
|
+
|
59
|
+
if @notify_callback && @notify_frequency && (@milliseconds_since_last_notify >= @notify_frequency)
|
60
|
+
@notify_callback.call(self)
|
61
|
+
@milliseconds_since_last_notify = 0
|
62
|
+
end
|
63
|
+
@countdown_complete = true if (COUNTDOWN == @direction) && (@current_milliseconds >= @milliseconds)
|
64
|
+
end
|
65
|
+
|
66
|
+
def reset
|
67
|
+
@current_milliseconds = 0
|
68
|
+
@countdown_complete = false
|
69
|
+
end
|
70
|
+
|
71
|
+
#Number of timer ticks (notification periods) that have passed.
|
72
|
+
def ticks_elapsed
|
73
|
+
(@current_milliseconds / (@notify_frequency)).round
|
74
|
+
end
|
75
|
+
|
76
|
+
#Number of timer ticks (notification periods) left before the countdown/countup is complete.
|
77
|
+
def ticks_left
|
78
|
+
((@milliseconds - @current_milliseconds) / (@notify_frequency)).round
|
79
|
+
end
|
80
|
+
|
81
|
+
def percent_complete
|
82
|
+
@current_milliseconds / @milliseconds
|
83
|
+
end
|
84
|
+
|
85
|
+
def countdown_complete?
|
86
|
+
@countdown_complete
|
87
|
+
end
|
88
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
#Allows an object to accelerate and turn within a 2D plane.
|
2
|
+
class TopDownVehicle < Jemini::Behavior
|
3
|
+
attr_accessor :minimum_speed_to_turn
|
4
|
+
alias_method :set_minimum_speed_to_turn, :minimum_speed_to_turn=
|
5
|
+
|
6
|
+
depends_on :VectoredMovement
|
7
|
+
|
8
|
+
def load
|
9
|
+
@vm_behavior = @game_object.send(:instance_variable_get, :@__behaviors)[:VectoredMovement]
|
10
|
+
@game_object.set_damping 0.1
|
11
|
+
@game_object.set_angular_damping 0.1
|
12
|
+
@minimum_speed_to_turn = 2.5
|
13
|
+
@vectored_movement_turning = false
|
14
|
+
|
15
|
+
#TODO: Replace this with a spline method that determines how far to turn based on the spline
|
16
|
+
@game_object.on_update do
|
17
|
+
if @turning && !@vectored_movement_turning && (@game_object.velocity.x.abs + @game_object.velocity.y.abs) > @minimum_speed_to_turn
|
18
|
+
@at_beginning_of_turn.call
|
19
|
+
@vectored_movement_turning = true
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
def begin_acceleration(message)
|
25
|
+
@vm_behavior.begin_acceleration(message)
|
26
|
+
end
|
27
|
+
|
28
|
+
def end_acceleration(message)
|
29
|
+
@vm_behavior.end_acceleration(message)
|
30
|
+
end
|
31
|
+
|
32
|
+
def begin_turn(message)
|
33
|
+
@turning = true
|
34
|
+
@at_beginning_of_turn = Proc.new { @vm_behavior.begin_turn(message) }
|
35
|
+
end
|
36
|
+
|
37
|
+
def end_turn(message)
|
38
|
+
@turning = false
|
39
|
+
@vm_behavior.end_turn(message)
|
40
|
+
@vectored_movement_turning = false
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,46 @@
|
|
1
|
+
require 'behaviors/drawable'
|
2
|
+
|
3
|
+
#Makes an object draw a shrinking trail behind itself as it moves.
|
4
|
+
class TriangleTrailEmittable < Jemini::Behavior
|
5
|
+
#depends_on :Movable2d
|
6
|
+
depends_on :Updates
|
7
|
+
depends_on_kind_of :Spatial
|
8
|
+
|
9
|
+
def load
|
10
|
+
@emitter = game_state.create :TriangleTrail
|
11
|
+
@emitter_offset = [0,0]
|
12
|
+
|
13
|
+
|
14
|
+
@game_object.on_update do
|
15
|
+
@emitter.position = Vector.new(@emitter_offset[0] + @game_object.x, @emitter_offset[1] + @game_object.y)
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def unload
|
20
|
+
game_state.remove @emitter
|
21
|
+
end
|
22
|
+
|
23
|
+
#Transparency to use. 1.0 is opaque. Default is 0.5.
|
24
|
+
def alpha
|
25
|
+
@emitter.alpha
|
26
|
+
end
|
27
|
+
|
28
|
+
def alpha=(alpha)
|
29
|
+
@emitter.alpha = alpha
|
30
|
+
end
|
31
|
+
|
32
|
+
#Takes an Array with the relative x and y coordinates to begin the trail.
|
33
|
+
def emit_triangle_trail_from_offset(offset)
|
34
|
+
@emitter_offset = offset
|
35
|
+
end
|
36
|
+
|
37
|
+
#Specifies the half-width of the widest part of the trail.
|
38
|
+
def emit_triangle_trail_with_radius(radius)
|
39
|
+
@emitter.radius = radius
|
40
|
+
end
|
41
|
+
|
42
|
+
#Name of layer to draw trail on.
|
43
|
+
def layer=(layer_name)
|
44
|
+
game_state.manager(:game_object).move_game_object_to_layer(@emitter, layer_name)
|
45
|
+
end
|
46
|
+
end
|
File without changes
|
@@ -0,0 +1,28 @@
|
|
1
|
+
#Makes an object receive events when a time period has elapsed.
|
2
|
+
class UpdatesAtConsistantRate < Jemini::Behavior
|
3
|
+
attr_accessor :updates_per_second
|
4
|
+
|
5
|
+
def load
|
6
|
+
@update_delay = 0
|
7
|
+
@time_since_last_update = 0
|
8
|
+
@game_object.enable_listeners_for :update
|
9
|
+
self.updates_per_second = 30
|
10
|
+
end
|
11
|
+
|
12
|
+
def updates_per_second=(count)
|
13
|
+
if 0 == count
|
14
|
+
@update_delay = 0
|
15
|
+
else
|
16
|
+
@update_delay = 1000 / count
|
17
|
+
end
|
18
|
+
@updates_per_second = count
|
19
|
+
end
|
20
|
+
|
21
|
+
def update(delta_in_milliseconds)
|
22
|
+
@time_since_last_update += delta_in_milliseconds
|
23
|
+
if @time_since_last_update > @update_delay
|
24
|
+
@time_since_last_update -= @update_delay
|
25
|
+
notify :update
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
#Makes an object move within a 2D plane.
|
2
|
+
class VectoredMovement < Jemini::Behavior
|
3
|
+
attr_accessor :forward_speed, :reverse_speed, :rotation_speed
|
4
|
+
alias_method :set_forward_speed, :forward_speed=
|
5
|
+
alias_method :set_reverse_speed, :reverse_speed=
|
6
|
+
alias_method :set_rotation_speed, :rotation_speed=
|
7
|
+
|
8
|
+
depends_on :Physical
|
9
|
+
depends_on :HandlesEvents
|
10
|
+
|
11
|
+
def load
|
12
|
+
@game_object.set_damping 0.0
|
13
|
+
@game_object.set_angular_damping 0.0
|
14
|
+
|
15
|
+
@forward_speed = 0
|
16
|
+
@reverse_speed = 0
|
17
|
+
@rotation_speed = 0
|
18
|
+
|
19
|
+
@intended_velocity = 0
|
20
|
+
@angular_velocity = 0
|
21
|
+
@movement_vector = Vector.new(0,0)
|
22
|
+
|
23
|
+
@game_object.on_update do
|
24
|
+
@game_object.set_angular_velocity(@angular_velocity)
|
25
|
+
@game_object.add_velocity(Vector.from_polar_vector(@intended_velocity, @game_object.rotation))
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def begin_acceleration(message)
|
30
|
+
@intended_velocity = :forward == message.value ? @forward_speed : @reverse_speed
|
31
|
+
end
|
32
|
+
|
33
|
+
def end_acceleration(message)
|
34
|
+
@intended_velocity = 0
|
35
|
+
end
|
36
|
+
|
37
|
+
def begin_turn(message)
|
38
|
+
if :clockwise == message.value
|
39
|
+
@angular_velocity = @rotation_speed
|
40
|
+
else
|
41
|
+
@angular_velocity = -@rotation_speed
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def end_turn(message)
|
46
|
+
@angular_velocity = 0
|
47
|
+
end
|
48
|
+
end
|
@@ -0,0 +1,9 @@
|
|
1
|
+
#Makes an object generate an event if it collides with another.
|
2
|
+
class WorldCollidable < Jemini::Behavior
|
3
|
+
depends_on :BoundingBoxCollidable
|
4
|
+
depends_on_kind_of :CollisionPoolAlgorithm
|
5
|
+
|
6
|
+
def world_collision_check
|
7
|
+
get_collision_candidates.each {|candidate| collision_check candidate}
|
8
|
+
end
|
9
|
+
end
|
data/src/color.rb
ADDED
@@ -0,0 +1,70 @@
|
|
1
|
+
class Color
|
2
|
+
attr_reader :native_color
|
3
|
+
|
4
|
+
def initialize(red_or_other, blue = 0.0, green = 0.0, alpha = 1.0)
|
5
|
+
if red_or_other.kind_of? Numeric
|
6
|
+
@native_color = new_native_color(red_or_other, blue, green, alpha)
|
7
|
+
else
|
8
|
+
# create from predefined Slick colors
|
9
|
+
fixed_color = Java::org::newdawn::slick::Color.send(red_or_other.to_s.downcase)
|
10
|
+
# we don't want to change the original, so we copy it
|
11
|
+
@native_color = new_native_color(fixed_color.r, fixed_color.g, fixed_color.b, fixed_color.a)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
def red
|
16
|
+
@native_color.r
|
17
|
+
end
|
18
|
+
|
19
|
+
def blue
|
20
|
+
@native_color.b
|
21
|
+
end
|
22
|
+
|
23
|
+
def green
|
24
|
+
@native_color.g
|
25
|
+
end
|
26
|
+
|
27
|
+
def alpha
|
28
|
+
@native_color.a
|
29
|
+
end
|
30
|
+
|
31
|
+
def transparency
|
32
|
+
1.0 - alpha
|
33
|
+
end
|
34
|
+
|
35
|
+
def red=(new_red)
|
36
|
+
@native_color.r = new_red
|
37
|
+
end
|
38
|
+
|
39
|
+
def green=(new_green)
|
40
|
+
@native_color.g = new_green
|
41
|
+
end
|
42
|
+
|
43
|
+
def blue=(new_blue)
|
44
|
+
@native_color.b = new_blue
|
45
|
+
end
|
46
|
+
|
47
|
+
def alpha=(new_alpha)
|
48
|
+
@native_color.a = new_alpha
|
49
|
+
end
|
50
|
+
|
51
|
+
def transparency=(new_transparency)
|
52
|
+
self.alpha = 1.0 - new_transparency
|
53
|
+
end
|
54
|
+
|
55
|
+
def darken_by(amount)
|
56
|
+
@native_color.darken amount
|
57
|
+
end
|
58
|
+
|
59
|
+
def darken_by!(amount)
|
60
|
+
@native_color = @native_color.darken amount
|
61
|
+
end
|
62
|
+
|
63
|
+
def fade_by(amount)
|
64
|
+
self.alpha = alpha * (1.0 - amount)
|
65
|
+
end
|
66
|
+
private
|
67
|
+
def new_native_color(red, blue, green, alpha)
|
68
|
+
Java::org::newdawn::slick::Color.new(red, blue, green, alpha)
|
69
|
+
end
|
70
|
+
end
|
data/src/file_system.rb
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
class File
|
2
|
+
def self.in_jar?(path)
|
3
|
+
path =~ /(\.jar!)|(^-$)/
|
4
|
+
end
|
5
|
+
|
6
|
+
def self.jar_of(path, jar_name=nil)
|
7
|
+
base_dir_plus_jar = path.split('.jar!').first
|
8
|
+
if jar_name
|
9
|
+
dirs = base_dir_plus_jar.split('/')
|
10
|
+
base_dir_plus_jar = (dirs[0..dirs.size - 2] + ['data']).join('/')
|
11
|
+
end
|
12
|
+
# jar_name = base_dir_plus_jar.split('/').last
|
13
|
+
# jar_name + '.jar'
|
14
|
+
base_dir_plus_jar.sub('file:', '') + '.jar'
|
15
|
+
end
|
16
|
+
|
17
|
+
end
|
data/src/game.rb
ADDED
@@ -0,0 +1,110 @@
|
|
1
|
+
module Jemini
|
2
|
+
class Game < Java::org::newdawn::slick::BasicGame
|
3
|
+
include_class 'org.newdawn.slick.AppGameContainer'
|
4
|
+
attr_accessor :screen_size, :fullscreen, :initial_state
|
5
|
+
|
6
|
+
def initialize(options={})
|
7
|
+
super(options[:screen_title] || 'Jemini Game')
|
8
|
+
@initial_state = options[:initial_state] || :MainState
|
9
|
+
@screen_size = options[:screen_size] || Vector.new(800, 600)
|
10
|
+
@fullscreen = options[:fullscreen]
|
11
|
+
@always_render = !!options[:always_render] # coercing to boolean, always_render can't be nil/null
|
12
|
+
@fresh_state = true
|
13
|
+
end
|
14
|
+
|
15
|
+
def init(container)
|
16
|
+
@container = container
|
17
|
+
@container.always_render = @always_render
|
18
|
+
GameState.active_state = load_state(@initial_state)
|
19
|
+
GameState.active_state.load
|
20
|
+
end
|
21
|
+
|
22
|
+
# depcrecated
|
23
|
+
def screen_width
|
24
|
+
screen_size.x
|
25
|
+
end
|
26
|
+
|
27
|
+
# depcrecated
|
28
|
+
def screen_height
|
29
|
+
screen_size.y
|
30
|
+
end
|
31
|
+
|
32
|
+
def app
|
33
|
+
@app ||= create_app
|
34
|
+
end
|
35
|
+
|
36
|
+
def canvas
|
37
|
+
@canvas ||= create_canvas
|
38
|
+
end
|
39
|
+
|
40
|
+
def update(container, delta)
|
41
|
+
#don't tell the new state that it now has to update load time worth of a delta
|
42
|
+
if @fresh_state
|
43
|
+
delta = 0
|
44
|
+
@fresh_state = false
|
45
|
+
end
|
46
|
+
# Workaround for image loading with Slick.
|
47
|
+
# Must be done in game init or game loop (instead of immediately in the event).
|
48
|
+
if @queued_state
|
49
|
+
# @queued_state.load_resources
|
50
|
+
game_state = load_state(*@queued_state)
|
51
|
+
game_state.load(*@state_args)
|
52
|
+
GameState.active_state = game_state
|
53
|
+
@queued_state = nil
|
54
|
+
@fresh_state = true
|
55
|
+
return
|
56
|
+
end
|
57
|
+
GameState.active_state.manager(:input).poll(screen_size.x, screen_size.y, delta)
|
58
|
+
GameState.active_state.manager(:message_queue).process_messages(delta)
|
59
|
+
GameState.active_state.manager(:update).update(delta)
|
60
|
+
GameState.active_state.manager(:game_object).__process_pending_game_objects
|
61
|
+
end
|
62
|
+
|
63
|
+
def render(container, graphics)
|
64
|
+
GameState.active_state.manager(:render).render(graphics)
|
65
|
+
end
|
66
|
+
|
67
|
+
def load_state(state_name, args = [])
|
68
|
+
require "states/#{state_name.underscore}" unless Object.const_defined? state_name.camelize
|
69
|
+
@state_args = args
|
70
|
+
state_name.camelize.constantize.new @container, self
|
71
|
+
end
|
72
|
+
|
73
|
+
def switch_state(state_name)
|
74
|
+
queue_state load_state(state_name)
|
75
|
+
end
|
76
|
+
|
77
|
+
def queue_state(state, *args)
|
78
|
+
@queued_state = [state, *args]
|
79
|
+
end
|
80
|
+
|
81
|
+
def fresh_state?
|
82
|
+
@fresh_state
|
83
|
+
end
|
84
|
+
|
85
|
+
def active_state
|
86
|
+
GameState.active_state
|
87
|
+
end
|
88
|
+
|
89
|
+
private
|
90
|
+
def create_app
|
91
|
+
@app = AppGameContainer.new(self, screen_size.x, screen_size.y, fullscreen)
|
92
|
+
@app.vsync = false
|
93
|
+
@app.maximum_logic_update_interval = 60
|
94
|
+
@app.smooth_deltas = false #true
|
95
|
+
#main.container = container
|
96
|
+
@app.start
|
97
|
+
end
|
98
|
+
|
99
|
+
def create_canvas
|
100
|
+
@canvas = Java::org::newdawn::slick::CanvasGameContainer.new(self)
|
101
|
+
@canvas.set_size(screen_size.x, screen_size.y)
|
102
|
+
container = @canvas.container
|
103
|
+
container.vsync = false
|
104
|
+
container.maximum_logic_update_interval = 60
|
105
|
+
#container.start
|
106
|
+
@canvas
|
107
|
+
end
|
108
|
+
|
109
|
+
end
|
110
|
+
end
|