cyberarm_engine 0.12.1 → 0.13.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +8 -8
- data/.travis.yml +5 -5
- data/Gemfile +6 -6
- data/LICENSE.txt +21 -21
- data/README.md +43 -43
- data/Rakefile +10 -10
- data/bin/console +14 -14
- data/bin/setup +8 -8
- data/cyberarm_engine.gemspec +36 -36
- data/lib/cyberarm_engine.rb +47 -46
- data/lib/cyberarm_engine/animator.rb +54 -0
- data/lib/cyberarm_engine/background.rb +175 -175
- data/lib/cyberarm_engine/bounding_box.rb +149 -149
- data/lib/cyberarm_engine/common.rb +96 -96
- data/lib/cyberarm_engine/engine.rb +101 -101
- data/lib/cyberarm_engine/game_object.rb +256 -256
- data/lib/cyberarm_engine/game_state.rb +88 -88
- data/lib/cyberarm_engine/gosu_ext/circle.rb +8 -8
- data/lib/cyberarm_engine/ray.rb +55 -55
- data/lib/cyberarm_engine/shader.rb +262 -205
- data/lib/cyberarm_engine/text.rb +146 -146
- data/lib/cyberarm_engine/timer.rb +22 -22
- data/lib/cyberarm_engine/transform.rb +272 -83
- data/lib/cyberarm_engine/ui/border_canvas.rb +100 -100
- data/lib/cyberarm_engine/ui/dsl.rb +98 -101
- data/lib/cyberarm_engine/ui/element.rb +275 -259
- data/lib/cyberarm_engine/ui/elements/button.rb +66 -66
- data/lib/cyberarm_engine/ui/elements/check_box.rb +58 -58
- data/lib/cyberarm_engine/ui/elements/container.rb +176 -162
- data/lib/cyberarm_engine/ui/elements/edit_line.rb +171 -102
- data/lib/cyberarm_engine/ui/elements/flow.rb +16 -16
- data/lib/cyberarm_engine/ui/elements/image.rb +51 -51
- data/lib/cyberarm_engine/ui/elements/label.rb +49 -49
- data/lib/cyberarm_engine/ui/elements/progress.rb +49 -49
- data/lib/cyberarm_engine/ui/elements/stack.rb +12 -12
- data/lib/cyberarm_engine/ui/elements/toggle_button.rb +55 -55
- data/lib/cyberarm_engine/ui/event.rb +46 -45
- data/lib/cyberarm_engine/ui/gui_state.rb +134 -134
- data/lib/cyberarm_engine/ui/style.rb +36 -36
- data/lib/cyberarm_engine/ui/theme.rb +120 -119
- data/lib/cyberarm_engine/vector.rb +202 -198
- data/lib/cyberarm_engine/version.rb +4 -4
- metadata +6 -5
| @@ -1,175 +1,175 @@ | |
| 1 | 
            -
            module CyberarmEngine
         | 
| 2 | 
            -
              class Background
         | 
| 3 | 
            -
                attr_accessor :x, :y, :z, :width, :height, :angle, :debug
         | 
| 4 | 
            -
                attr_reader   :background
         | 
| 5 | 
            -
                def initialize(x: 0, y: 0, z: 0, width: 0, height: 0, background: Gosu::Color::BLACK, angle: 0, debug: false)
         | 
| 6 | 
            -
                  @x,@y,@z = x,y,z
         | 
| 7 | 
            -
                  @width,@height = width,height
         | 
| 8 | 
            -
                  @debug = debug
         | 
| 9 | 
            -
             | 
| 10 | 
            -
                  @paint  = Paint.new(background)
         | 
| 11 | 
            -
                  @angle  = angle
         | 
| 12 | 
            -
             | 
| 13 | 
            -
                  @top_left     = Vector.new(@x, @y)
         | 
| 14 | 
            -
                  @top_right    = Vector.new(@x + @width, @y)
         | 
| 15 | 
            -
                  @bottom_left  = Vector.new(@x, @y + @height)
         | 
| 16 | 
            -
                  @bottom_right = Vector.new(@x + @width, @y + @height)
         | 
| 17 | 
            -
                end
         | 
| 18 | 
            -
             | 
| 19 | 
            -
                def draw
         | 
| 20 | 
            -
                  Gosu.clip_to(@x, @y, @width, @height) do
         | 
| 21 | 
            -
                    Gosu.draw_quad(
         | 
| 22 | 
            -
                      @top_left.x,     @top_left.y,     @paint.top_left,
         | 
| 23 | 
            -
                      @top_right.x,    @top_right.y,    @paint.top_right,
         | 
| 24 | 
            -
                      @bottom_right.x, @bottom_right.y, @paint.bottom_right,
         | 
| 25 | 
            -
                      @bottom_left.x,  @bottom_left.y,  @paint.bottom_left,
         | 
| 26 | 
            -
                      @z
         | 
| 27 | 
            -
                    )
         | 
| 28 | 
            -
                  end
         | 
| 29 | 
            -
             | 
| 30 | 
            -
                  debug_outline if @debug
         | 
| 31 | 
            -
                end
         | 
| 32 | 
            -
             | 
| 33 | 
            -
                def update
         | 
| 34 | 
            -
                  origin_x = (@x + (@width/2))
         | 
| 35 | 
            -
                  origin_y = (@y + (@height/2))
         | 
| 36 | 
            -
             | 
| 37 | 
            -
                  points = [
         | 
| 38 | 
            -
                    @top_left     = Vector.new(@x, @y),
         | 
| 39 | 
            -
                    @top_right    = Vector.new(@x + @width, @y),
         | 
| 40 | 
            -
                    @bottom_left  = Vector.new(@x, @y + @height),
         | 
| 41 | 
            -
                    @bottom_right = Vector.new(@x + @width, @y + @height)
         | 
| 42 | 
            -
                  ]
         | 
| 43 | 
            -
             | 
| 44 | 
            -
                  [@top_left, @top_right, @bottom_left, @bottom_right].each do |vector|
         | 
| 45 | 
            -
                    temp_x = vector.x - origin_x
         | 
| 46 | 
            -
                    temp_y = vector.y - origin_y
         | 
| 47 | 
            -
             | 
| 48 | 
            -
                    # 90 is up here, while gosu uses 0 for up.
         | 
| 49 | 
            -
                    radians = (@angle + 90).gosu_to_radians
         | 
| 50 | 
            -
                    vector.x = (@x + (@width/2))  + ((temp_x * Math.cos(radians)) - (temp_y * Math.sin(radians)))
         | 
| 51 | 
            -
                    vector.y = (@y + (@height/2)) + ((temp_x * Math.sin(radians)) + (temp_y * Math.cos(radians)))
         | 
| 52 | 
            -
                  end
         | 
| 53 | 
            -
             | 
| 54 | 
            -
                  # [
         | 
| 55 | 
            -
                  #   [:top,    @top_left, @top_right],
         | 
| 56 | 
            -
                  #   [:right,  @top_right, @bottom_right],
         | 
| 57 | 
            -
                  #   [:bottom, @bottom_right, @bottom_left],
         | 
| 58 | 
            -
                  #   [:left,   @bottom_left, @top_left]
         | 
| 59 | 
            -
                  # ].each do |edge|
         | 
| 60 | 
            -
                  #   points.each do |point|
         | 
| 61 | 
            -
                  #     puts "#{edge.first} -> #{shortest_distance(point, edge[1], edge[2])}"
         | 
| 62 | 
            -
                  #   end
         | 
| 63 | 
            -
                  # end
         | 
| 64 | 
            -
                end
         | 
| 65 | 
            -
             | 
| 66 | 
            -
                def shortest_distance(point, la, lb)
         | 
| 67 | 
            -
                  a = la.x - lb.x
         | 
| 68 | 
            -
                  b = la.y - lb.y
         | 
| 69 | 
            -
                  c = Gosu.distance(la.x, la.y, lb.x, lb.y)
         | 
| 70 | 
            -
                  p a,b,c
         | 
| 71 | 
            -
                  d = (a * point.x + b * point.y + c).abs / (Math.sqrt(a * a + b * b))
         | 
| 72 | 
            -
                  puts "Distance: #{d}"
         | 
| 73 | 
            -
                  exit!
         | 
| 74 | 
            -
                  return d
         | 
| 75 | 
            -
                end
         | 
| 76 | 
            -
             | 
| 77 | 
            -
                def debug_outline
         | 
| 78 | 
            -
                  # Top
         | 
| 79 | 
            -
                  Gosu.draw_line(
         | 
| 80 | 
            -
                    @x,          @y,           Gosu::Color::RED,
         | 
| 81 | 
            -
                    @x + @width, @y,           Gosu::Color::RED,
         | 
| 82 | 
            -
                    @z
         | 
| 83 | 
            -
                  )
         | 
| 84 | 
            -
             | 
| 85 | 
            -
                  # Right
         | 
| 86 | 
            -
                  Gosu.draw_line(
         | 
| 87 | 
            -
                    @x + @width, @y,           Gosu::Color::RED,
         | 
| 88 | 
            -
                    @x + @width, @y + @height, Gosu::Color::RED,
         | 
| 89 | 
            -
                    @z
         | 
| 90 | 
            -
                  )
         | 
| 91 | 
            -
             | 
| 92 | 
            -
                  # Bottom
         | 
| 93 | 
            -
                  Gosu.draw_line(
         | 
| 94 | 
            -
                    @x + @width, @y + @height, Gosu::Color::RED,
         | 
| 95 | 
            -
                    @x, @y + @height,          Gosu::Color::RED,
         | 
| 96 | 
            -
                    @z
         | 
| 97 | 
            -
                  )
         | 
| 98 | 
            -
             | 
| 99 | 
            -
                  # Left
         | 
| 100 | 
            -
                  Gosu.draw_line(
         | 
| 101 | 
            -
                    @x, @y + @height,          Gosu::Color::RED,
         | 
| 102 | 
            -
                    @x, @y,                    Gosu::Color::RED,
         | 
| 103 | 
            -
                    @z
         | 
| 104 | 
            -
                  )
         | 
| 105 | 
            -
                end
         | 
| 106 | 
            -
             | 
| 107 | 
            -
                def background=(_background)
         | 
| 108 | 
            -
                  @paint.set(_background)
         | 
| 109 | 
            -
                  update
         | 
| 110 | 
            -
                end
         | 
| 111 | 
            -
             | 
| 112 | 
            -
                def angle=(n)
         | 
| 113 | 
            -
                  @angle = n
         | 
| 114 | 
            -
                  update
         | 
| 115 | 
            -
                end
         | 
| 116 | 
            -
              end
         | 
| 117 | 
            -
             | 
| 118 | 
            -
              class Paint
         | 
| 119 | 
            -
                attr_accessor :top_left, :top_right, :bottom_left, :bottom_right
         | 
| 120 | 
            -
                def initialize(background)
         | 
| 121 | 
            -
                  set(background)
         | 
| 122 | 
            -
                end
         | 
| 123 | 
            -
             | 
| 124 | 
            -
                def set(background)
         | 
| 125 | 
            -
                  @background = background
         | 
| 126 | 
            -
             | 
| 127 | 
            -
             | 
| 128 | 
            -
                  if background.is_a?(Numeric)
         | 
| 129 | 
            -
                    @top_left     = background
         | 
| 130 | 
            -
                    @top_right    = background
         | 
| 131 | 
            -
                    @bottom_left  = background
         | 
| 132 | 
            -
                    @bottom_right = background
         | 
| 133 | 
            -
                  elsif background.is_a?(Gosu::Color)
         | 
| 134 | 
            -
                    @top_left     = background
         | 
| 135 | 
            -
                    @top_right    = background
         | 
| 136 | 
            -
                    @bottom_left  = background
         | 
| 137 | 
            -
                    @bottom_right = background
         | 
| 138 | 
            -
                  elsif background.is_a?(Array)
         | 
| 139 | 
            -
                    if background.size == 1
         | 
| 140 | 
            -
                      set(background.first)
         | 
| 141 | 
            -
                    elsif background.size == 2
         | 
| 142 | 
            -
                      @top_left     = background.first
         | 
| 143 | 
            -
                      @top_right    = background.last
         | 
| 144 | 
            -
                      @bottom_left  = background.first
         | 
| 145 | 
            -
                      @bottom_right = background.last
         | 
| 146 | 
            -
                    elsif background.size == 4
         | 
| 147 | 
            -
                      @top_left     = background[0]
         | 
| 148 | 
            -
                      @top_right    = background[1]
         | 
| 149 | 
            -
                      @bottom_left  = background[2]
         | 
| 150 | 
            -
                      @bottom_right = background[3]
         | 
| 151 | 
            -
                    else
         | 
| 152 | 
            -
                      raise ArgumentError, "background array was empty or had wrong number of elements (expected 2 or 4 elements)"
         | 
| 153 | 
            -
                    end
         | 
| 154 | 
            -
                  elsif background.is_a?(Hash)
         | 
| 155 | 
            -
                    @top_left     = background[:top_left]
         | 
| 156 | 
            -
                    @top_right    = background[:top_right]
         | 
| 157 | 
            -
                    @bottom_left  = background[:bottom_left]
         | 
| 158 | 
            -
                    @bottom_right = background[:bottom_right]
         | 
| 159 | 
            -
                  elsif background.is_a?(Range)
         | 
| 160 | 
            -
                    set([background.begin, background.begin, background.end, background.end])
         | 
| 161 | 
            -
                  else
         | 
| 162 | 
            -
                    raise ArgumentError, "background '#{background}' of type '#{background.class}' was not able to be processed"
         | 
| 163 | 
            -
                  end
         | 
| 164 | 
            -
                end
         | 
| 165 | 
            -
              end
         | 
| 166 | 
            -
            end
         | 
| 167 | 
            -
             | 
| 168 | 
            -
            # Add <=> method to support Range based gradients
         | 
| 169 | 
            -
            module Gosu
         | 
| 170 | 
            -
             class Color
         | 
| 171 | 
            -
               def <=>(other)
         | 
| 172 | 
            -
                 self
         | 
| 173 | 
            -
               end
         | 
| 174 | 
            -
             end
         | 
| 175 | 
            -
            end
         | 
| 1 | 
            +
            module CyberarmEngine
         | 
| 2 | 
            +
              class Background
         | 
| 3 | 
            +
                attr_accessor :x, :y, :z, :width, :height, :angle, :debug
         | 
| 4 | 
            +
                attr_reader   :background
         | 
| 5 | 
            +
                def initialize(x: 0, y: 0, z: 0, width: 0, height: 0, background: Gosu::Color::BLACK, angle: 0, debug: false)
         | 
| 6 | 
            +
                  @x,@y,@z = x,y,z
         | 
| 7 | 
            +
                  @width,@height = width,height
         | 
| 8 | 
            +
                  @debug = debug
         | 
| 9 | 
            +
             | 
| 10 | 
            +
                  @paint  = Paint.new(background)
         | 
| 11 | 
            +
                  @angle  = angle
         | 
| 12 | 
            +
             | 
| 13 | 
            +
                  @top_left     = Vector.new(@x, @y)
         | 
| 14 | 
            +
                  @top_right    = Vector.new(@x + @width, @y)
         | 
| 15 | 
            +
                  @bottom_left  = Vector.new(@x, @y + @height)
         | 
| 16 | 
            +
                  @bottom_right = Vector.new(@x + @width, @y + @height)
         | 
| 17 | 
            +
                end
         | 
| 18 | 
            +
             | 
| 19 | 
            +
                def draw
         | 
| 20 | 
            +
                  Gosu.clip_to(@x, @y, @width, @height) do
         | 
| 21 | 
            +
                    Gosu.draw_quad(
         | 
| 22 | 
            +
                      @top_left.x,     @top_left.y,     @paint.top_left,
         | 
| 23 | 
            +
                      @top_right.x,    @top_right.y,    @paint.top_right,
         | 
| 24 | 
            +
                      @bottom_right.x, @bottom_right.y, @paint.bottom_right,
         | 
| 25 | 
            +
                      @bottom_left.x,  @bottom_left.y,  @paint.bottom_left,
         | 
| 26 | 
            +
                      @z
         | 
| 27 | 
            +
                    )
         | 
| 28 | 
            +
                  end
         | 
| 29 | 
            +
             | 
| 30 | 
            +
                  debug_outline if @debug
         | 
| 31 | 
            +
                end
         | 
| 32 | 
            +
             | 
| 33 | 
            +
                def update
         | 
| 34 | 
            +
                  origin_x = (@x + (@width/2))
         | 
| 35 | 
            +
                  origin_y = (@y + (@height/2))
         | 
| 36 | 
            +
             | 
| 37 | 
            +
                  points = [
         | 
| 38 | 
            +
                    @top_left     = Vector.new(@x, @y),
         | 
| 39 | 
            +
                    @top_right    = Vector.new(@x + @width, @y),
         | 
| 40 | 
            +
                    @bottom_left  = Vector.new(@x, @y + @height),
         | 
| 41 | 
            +
                    @bottom_right = Vector.new(@x + @width, @y + @height)
         | 
| 42 | 
            +
                  ]
         | 
| 43 | 
            +
             | 
| 44 | 
            +
                  [@top_left, @top_right, @bottom_left, @bottom_right].each do |vector|
         | 
| 45 | 
            +
                    temp_x = vector.x - origin_x
         | 
| 46 | 
            +
                    temp_y = vector.y - origin_y
         | 
| 47 | 
            +
             | 
| 48 | 
            +
                    # 90 is up here, while gosu uses 0 for up.
         | 
| 49 | 
            +
                    radians = (@angle + 90).gosu_to_radians
         | 
| 50 | 
            +
                    vector.x = (@x + (@width/2))  + ((temp_x * Math.cos(radians)) - (temp_y * Math.sin(radians)))
         | 
| 51 | 
            +
                    vector.y = (@y + (@height/2)) + ((temp_x * Math.sin(radians)) + (temp_y * Math.cos(radians)))
         | 
| 52 | 
            +
                  end
         | 
| 53 | 
            +
             | 
| 54 | 
            +
                  # [
         | 
| 55 | 
            +
                  #   [:top,    @top_left, @top_right],
         | 
| 56 | 
            +
                  #   [:right,  @top_right, @bottom_right],
         | 
| 57 | 
            +
                  #   [:bottom, @bottom_right, @bottom_left],
         | 
| 58 | 
            +
                  #   [:left,   @bottom_left, @top_left]
         | 
| 59 | 
            +
                  # ].each do |edge|
         | 
| 60 | 
            +
                  #   points.each do |point|
         | 
| 61 | 
            +
                  #     puts "#{edge.first} -> #{shortest_distance(point, edge[1], edge[2])}"
         | 
| 62 | 
            +
                  #   end
         | 
| 63 | 
            +
                  # end
         | 
| 64 | 
            +
                end
         | 
| 65 | 
            +
             | 
| 66 | 
            +
                def shortest_distance(point, la, lb)
         | 
| 67 | 
            +
                  a = la.x - lb.x
         | 
| 68 | 
            +
                  b = la.y - lb.y
         | 
| 69 | 
            +
                  c = Gosu.distance(la.x, la.y, lb.x, lb.y)
         | 
| 70 | 
            +
                  p a,b,c
         | 
| 71 | 
            +
                  d = (a * point.x + b * point.y + c).abs / (Math.sqrt(a * a + b * b))
         | 
| 72 | 
            +
                  puts "Distance: #{d}"
         | 
| 73 | 
            +
                  exit!
         | 
| 74 | 
            +
                  return d
         | 
| 75 | 
            +
                end
         | 
| 76 | 
            +
             | 
| 77 | 
            +
                def debug_outline
         | 
| 78 | 
            +
                  # Top
         | 
| 79 | 
            +
                  Gosu.draw_line(
         | 
| 80 | 
            +
                    @x,          @y,           Gosu::Color::RED,
         | 
| 81 | 
            +
                    @x + @width, @y,           Gosu::Color::RED,
         | 
| 82 | 
            +
                    @z
         | 
| 83 | 
            +
                  )
         | 
| 84 | 
            +
             | 
| 85 | 
            +
                  # Right
         | 
| 86 | 
            +
                  Gosu.draw_line(
         | 
| 87 | 
            +
                    @x + @width, @y,           Gosu::Color::RED,
         | 
| 88 | 
            +
                    @x + @width, @y + @height, Gosu::Color::RED,
         | 
| 89 | 
            +
                    @z
         | 
| 90 | 
            +
                  )
         | 
| 91 | 
            +
             | 
| 92 | 
            +
                  # Bottom
         | 
| 93 | 
            +
                  Gosu.draw_line(
         | 
| 94 | 
            +
                    @x + @width, @y + @height, Gosu::Color::RED,
         | 
| 95 | 
            +
                    @x, @y + @height,          Gosu::Color::RED,
         | 
| 96 | 
            +
                    @z
         | 
| 97 | 
            +
                  )
         | 
| 98 | 
            +
             | 
| 99 | 
            +
                  # Left
         | 
| 100 | 
            +
                  Gosu.draw_line(
         | 
| 101 | 
            +
                    @x, @y + @height,          Gosu::Color::RED,
         | 
| 102 | 
            +
                    @x, @y,                    Gosu::Color::RED,
         | 
| 103 | 
            +
                    @z
         | 
| 104 | 
            +
                  )
         | 
| 105 | 
            +
                end
         | 
| 106 | 
            +
             | 
| 107 | 
            +
                def background=(_background)
         | 
| 108 | 
            +
                  @paint.set(_background)
         | 
| 109 | 
            +
                  update
         | 
| 110 | 
            +
                end
         | 
| 111 | 
            +
             | 
| 112 | 
            +
                def angle=(n)
         | 
| 113 | 
            +
                  @angle = n
         | 
| 114 | 
            +
                  update
         | 
| 115 | 
            +
                end
         | 
| 116 | 
            +
              end
         | 
| 117 | 
            +
             | 
| 118 | 
            +
              class Paint
         | 
| 119 | 
            +
                attr_accessor :top_left, :top_right, :bottom_left, :bottom_right
         | 
| 120 | 
            +
                def initialize(background)
         | 
| 121 | 
            +
                  set(background)
         | 
| 122 | 
            +
                end
         | 
| 123 | 
            +
             | 
| 124 | 
            +
                def set(background)
         | 
| 125 | 
            +
                  @background = background
         | 
| 126 | 
            +
             | 
| 127 | 
            +
             | 
| 128 | 
            +
                  if background.is_a?(Numeric)
         | 
| 129 | 
            +
                    @top_left     = background
         | 
| 130 | 
            +
                    @top_right    = background
         | 
| 131 | 
            +
                    @bottom_left  = background
         | 
| 132 | 
            +
                    @bottom_right = background
         | 
| 133 | 
            +
                  elsif background.is_a?(Gosu::Color)
         | 
| 134 | 
            +
                    @top_left     = background
         | 
| 135 | 
            +
                    @top_right    = background
         | 
| 136 | 
            +
                    @bottom_left  = background
         | 
| 137 | 
            +
                    @bottom_right = background
         | 
| 138 | 
            +
                  elsif background.is_a?(Array)
         | 
| 139 | 
            +
                    if background.size == 1
         | 
| 140 | 
            +
                      set(background.first)
         | 
| 141 | 
            +
                    elsif background.size == 2
         | 
| 142 | 
            +
                      @top_left     = background.first
         | 
| 143 | 
            +
                      @top_right    = background.last
         | 
| 144 | 
            +
                      @bottom_left  = background.first
         | 
| 145 | 
            +
                      @bottom_right = background.last
         | 
| 146 | 
            +
                    elsif background.size == 4
         | 
| 147 | 
            +
                      @top_left     = background[0]
         | 
| 148 | 
            +
                      @top_right    = background[1]
         | 
| 149 | 
            +
                      @bottom_left  = background[2]
         | 
| 150 | 
            +
                      @bottom_right = background[3]
         | 
| 151 | 
            +
                    else
         | 
| 152 | 
            +
                      raise ArgumentError, "background array was empty or had wrong number of elements (expected 2 or 4 elements)"
         | 
| 153 | 
            +
                    end
         | 
| 154 | 
            +
                  elsif background.is_a?(Hash)
         | 
| 155 | 
            +
                    @top_left     = background[:top_left]
         | 
| 156 | 
            +
                    @top_right    = background[:top_right]
         | 
| 157 | 
            +
                    @bottom_left  = background[:bottom_left]
         | 
| 158 | 
            +
                    @bottom_right = background[:bottom_right]
         | 
| 159 | 
            +
                  elsif background.is_a?(Range)
         | 
| 160 | 
            +
                    set([background.begin, background.begin, background.end, background.end])
         | 
| 161 | 
            +
                  else
         | 
| 162 | 
            +
                    raise ArgumentError, "background '#{background}' of type '#{background.class}' was not able to be processed"
         | 
| 163 | 
            +
                  end
         | 
| 164 | 
            +
                end
         | 
| 165 | 
            +
              end
         | 
| 166 | 
            +
            end
         | 
| 167 | 
            +
             | 
| 168 | 
            +
            # Add <=> method to support Range based gradients
         | 
| 169 | 
            +
            module Gosu
         | 
| 170 | 
            +
             class Color
         | 
| 171 | 
            +
               def <=>(other)
         | 
| 172 | 
            +
                 self
         | 
| 173 | 
            +
               end
         | 
| 174 | 
            +
             end
         | 
| 175 | 
            +
            end
         | 
| @@ -1,150 +1,150 @@ | |
| 1 | 
            -
            module CyberarmEngine
         | 
| 2 | 
            -
              class BoundingBox
         | 
| 3 | 
            -
                attr_accessor :min, :max
         | 
| 4 | 
            -
             | 
| 5 | 
            -
                def initialize(*args)
         | 
| 6 | 
            -
                  case args.size
         | 
| 7 | 
            -
                  when 0
         | 
| 8 | 
            -
                    @min = Vector.new(0, 0, 0)
         | 
| 9 | 
            -
                    @max = Vector.new(0, 0, 0)
         | 
| 10 | 
            -
                  when 2
         | 
| 11 | 
            -
                    @min = args.first.clone
         | 
| 12 | 
            -
                    @max = args.last.clone
         | 
| 13 | 
            -
                  when 4
         | 
| 14 | 
            -
                    @min = Vector.new(args[0], args[1], 0)
         | 
| 15 | 
            -
                    @max = Vector.new(args[2], args[3], 0)
         | 
| 16 | 
            -
                  when 6
         | 
| 17 | 
            -
                    @min = Vector.new(args[0], args[1], args[2])
         | 
| 18 | 
            -
                    @max = Vector.new(args[3], args[4], args[5])
         | 
| 19 | 
            -
                  else
         | 
| 20 | 
            -
                    raise "Invalid number of arguments! Got: #{args.size}, expected: 0, 2, 4, or 6."
         | 
| 21 | 
            -
                  end
         | 
| 22 | 
            -
                end
         | 
| 23 | 
            -
             | 
| 24 | 
            -
                def ==(other)
         | 
| 25 | 
            -
                  @min == other.min &&
         | 
| 26 | 
            -
                  @max == other.max
         | 
| 27 | 
            -
                end
         | 
| 28 | 
            -
             | 
| 29 | 
            -
                # returns a new bounding box that includes both bounding boxes
         | 
| 30 | 
            -
                def union(other)
         | 
| 31 | 
            -
                  temp = BoundingBox.new
         | 
| 32 | 
            -
                  temp.min.x = [@min.x, other.min.x].min
         | 
| 33 | 
            -
                  temp.min.y = [@min.y, other.min.y].min
         | 
| 34 | 
            -
                  temp.min.z = [@min.z, other.min.z].min
         | 
| 35 | 
            -
             | 
| 36 | 
            -
                  temp.max.x = [@max.x, other.max.x].max
         | 
| 37 | 
            -
                  temp.max.y = [@max.y, other.max.y].max
         | 
| 38 | 
            -
                  temp.max.z = [@max.z, other.max.z].max
         | 
| 39 | 
            -
             | 
| 40 | 
            -
                  return temp
         | 
| 41 | 
            -
                end
         | 
| 42 | 
            -
             | 
| 43 | 
            -
                # returns the difference between both bounding boxes
         | 
| 44 | 
            -
                def difference(other)
         | 
| 45 | 
            -
                  temp = BoundingBox.new
         | 
| 46 | 
            -
                  temp.min = @min - other.min
         | 
| 47 | 
            -
                  temp.max = @max - other.max
         | 
| 48 | 
            -
             | 
| 49 | 
            -
                  return temp
         | 
| 50 | 
            -
                end
         | 
| 51 | 
            -
             | 
| 52 | 
            -
                # returns whether bounding box intersects other
         | 
| 53 | 
            -
                def intersect?(other)
         | 
| 54 | 
            -
                  if other.is_a?(Ray)
         | 
| 55 | 
            -
                    other.intersect?(self)
         | 
| 56 | 
            -
                  elsif other.is_a?(BoundingBox)
         | 
| 57 | 
            -
                    (@min.x <= other.max.x && @max.x >= other.min.x) &&
         | 
| 58 | 
            -
                    (@min.y <= other.max.y && @max.y >= other.min.y) &&
         | 
| 59 | 
            -
                    (@min.z <= other.max.z && @max.z >= other.min.z)
         | 
| 60 | 
            -
                  else
         | 
| 61 | 
            -
                    raise "Unknown collider: #{other.class}"
         | 
| 62 | 
            -
                  end
         | 
| 63 | 
            -
                end
         | 
| 64 | 
            -
             | 
| 65 | 
            -
                # does this bounding box envelop other bounding box? (inclusive of border)
         | 
| 66 | 
            -
                def contains?(other)
         | 
| 67 | 
            -
                  other.min.x >= min.x && other.min.y >= min.y && other.min.z >= min.z &&
         | 
| 68 | 
            -
                  other.max.x <= max.x && other.max.y <= max.y && other.max.z <= max.z
         | 
| 69 | 
            -
                end
         | 
| 70 | 
            -
             | 
| 71 | 
            -
                # returns whether the 3D vector is inside of the bounding box
         | 
| 72 | 
            -
                def inside?(vector)
         | 
| 73 | 
            -
                  (vector.x.between?(@min.x, @max.x) || vector.x.between?(@max.x, @min.x)) &&
         | 
| 74 | 
            -
                  (vector.y.between?(@min.y, @max.y) || vector.y.between?(@max.y, @min.y)) &&
         | 
| 75 | 
            -
                  (vector.z.between?(@min.z, @max.z) || vector.z.between?(@max.z, @min.z))
         | 
| 76 | 
            -
                end
         | 
| 77 | 
            -
             | 
| 78 | 
            -
                # returns whether the 2D vector is inside of the bounding box
         | 
| 79 | 
            -
                def point?(vector)
         | 
| 80 | 
            -
                  (vector.x.between?(@min.x, @max.x) || vector.x.between?(@max.x, @min.x)) &&
         | 
| 81 | 
            -
                  (vector.y.between?(@min.y, @max.y) || vector.y.between?(@max.y, @min.y))
         | 
| 82 | 
            -
                end
         | 
| 83 | 
            -
             | 
| 84 | 
            -
                def volume
         | 
| 85 | 
            -
                  width * height * depth
         | 
| 86 | 
            -
                end
         | 
| 87 | 
            -
             | 
| 88 | 
            -
                def width
         | 
| 89 | 
            -
                  @max.x - @min.x
         | 
| 90 | 
            -
                end
         | 
| 91 | 
            -
             | 
| 92 | 
            -
                def height
         | 
| 93 | 
            -
                  @max.y - @min.y
         | 
| 94 | 
            -
                end
         | 
| 95 | 
            -
             | 
| 96 | 
            -
                def depth
         | 
| 97 | 
            -
                  @max.z - @min.z
         | 
| 98 | 
            -
                end
         | 
| 99 | 
            -
             | 
| 100 | 
            -
                def normalize(entity)
         | 
| 101 | 
            -
                  temp = BoundingBox.new
         | 
| 102 | 
            -
                  temp.min.x = @min.x.to_f * entity.scale.x
         | 
| 103 | 
            -
                  temp.min.y = @min.y.to_f * entity.scale.y
         | 
| 104 | 
            -
                  temp.min.z = @min.z.to_f * entity.scale.z
         | 
| 105 | 
            -
             | 
| 106 | 
            -
                  temp.max.x = @max.x.to_f * entity.scale.x
         | 
| 107 | 
            -
                  temp.max.y = @max.y.to_f * entity.scale.y
         | 
| 108 | 
            -
                  temp.max.z = @max.z.to_f * entity.scale.z
         | 
| 109 | 
            -
             | 
| 110 | 
            -
                  return temp
         | 
| 111 | 
            -
                end
         | 
| 112 | 
            -
             | 
| 113 | 
            -
                def normalize_with_offset(entity)
         | 
| 114 | 
            -
                  temp = BoundingBox.new
         | 
| 115 | 
            -
                  temp.min.x = @min.x.to_f * entity.scale.x + entity.position.x
         | 
| 116 | 
            -
                  temp.min.y = @min.y.to_f * entity.scale.y + entity.position.y
         | 
| 117 | 
            -
                  temp.min.z = @min.z.to_f * entity.scale.z + entity.position.z
         | 
| 118 | 
            -
             | 
| 119 | 
            -
                  temp.max.x = @max.x.to_f * entity.scale.x + entity.position.x
         | 
| 120 | 
            -
                  temp.max.y = @max.y.to_f * entity.scale.y + entity.position.y
         | 
| 121 | 
            -
                  temp.max.z = @max.z.to_f * entity.scale.z + entity.position.z
         | 
| 122 | 
            -
             | 
| 123 | 
            -
                  return temp
         | 
| 124 | 
            -
                end
         | 
| 125 | 
            -
             | 
| 126 | 
            -
                def +(other)
         | 
| 127 | 
            -
                  box = BoundingBox.new
         | 
| 128 | 
            -
                  box.min = self.min + other.min
         | 
| 129 | 
            -
                  box.min = self.max + other.max
         | 
| 130 | 
            -
             | 
| 131 | 
            -
                  return box
         | 
| 132 | 
            -
                end
         | 
| 133 | 
            -
             | 
| 134 | 
            -
                def -(other)
         | 
| 135 | 
            -
                  box = BoundingBox.new
         | 
| 136 | 
            -
                  box.min = self.min - other.min
         | 
| 137 | 
            -
                  box.min = self.max - other.max
         | 
| 138 | 
            -
             | 
| 139 | 
            -
                  return box
         | 
| 140 | 
            -
                end
         | 
| 141 | 
            -
             | 
| 142 | 
            -
                def sum
         | 
| 143 | 
            -
                  @min.sum + @max.sum
         | 
| 144 | 
            -
                end
         | 
| 145 | 
            -
             | 
| 146 | 
            -
                def clone
         | 
| 147 | 
            -
                  BoundingBox.new(@min.x, @min.y, @min.z, @max.x, @max.y, @max.z)
         | 
| 148 | 
            -
                end
         | 
| 149 | 
            -
              end
         | 
| 1 | 
            +
            module CyberarmEngine
         | 
| 2 | 
            +
              class BoundingBox
         | 
| 3 | 
            +
                attr_accessor :min, :max
         | 
| 4 | 
            +
             | 
| 5 | 
            +
                def initialize(*args)
         | 
| 6 | 
            +
                  case args.size
         | 
| 7 | 
            +
                  when 0
         | 
| 8 | 
            +
                    @min = Vector.new(0, 0, 0)
         | 
| 9 | 
            +
                    @max = Vector.new(0, 0, 0)
         | 
| 10 | 
            +
                  when 2
         | 
| 11 | 
            +
                    @min = args.first.clone
         | 
| 12 | 
            +
                    @max = args.last.clone
         | 
| 13 | 
            +
                  when 4
         | 
| 14 | 
            +
                    @min = Vector.new(args[0], args[1], 0)
         | 
| 15 | 
            +
                    @max = Vector.new(args[2], args[3], 0)
         | 
| 16 | 
            +
                  when 6
         | 
| 17 | 
            +
                    @min = Vector.new(args[0], args[1], args[2])
         | 
| 18 | 
            +
                    @max = Vector.new(args[3], args[4], args[5])
         | 
| 19 | 
            +
                  else
         | 
| 20 | 
            +
                    raise "Invalid number of arguments! Got: #{args.size}, expected: 0, 2, 4, or 6."
         | 
| 21 | 
            +
                  end
         | 
| 22 | 
            +
                end
         | 
| 23 | 
            +
             | 
| 24 | 
            +
                def ==(other)
         | 
| 25 | 
            +
                  @min == other.min &&
         | 
| 26 | 
            +
                  @max == other.max
         | 
| 27 | 
            +
                end
         | 
| 28 | 
            +
             | 
| 29 | 
            +
                # returns a new bounding box that includes both bounding boxes
         | 
| 30 | 
            +
                def union(other)
         | 
| 31 | 
            +
                  temp = BoundingBox.new
         | 
| 32 | 
            +
                  temp.min.x = [@min.x, other.min.x].min
         | 
| 33 | 
            +
                  temp.min.y = [@min.y, other.min.y].min
         | 
| 34 | 
            +
                  temp.min.z = [@min.z, other.min.z].min
         | 
| 35 | 
            +
             | 
| 36 | 
            +
                  temp.max.x = [@max.x, other.max.x].max
         | 
| 37 | 
            +
                  temp.max.y = [@max.y, other.max.y].max
         | 
| 38 | 
            +
                  temp.max.z = [@max.z, other.max.z].max
         | 
| 39 | 
            +
             | 
| 40 | 
            +
                  return temp
         | 
| 41 | 
            +
                end
         | 
| 42 | 
            +
             | 
| 43 | 
            +
                # returns the difference between both bounding boxes
         | 
| 44 | 
            +
                def difference(other)
         | 
| 45 | 
            +
                  temp = BoundingBox.new
         | 
| 46 | 
            +
                  temp.min = @min - other.min
         | 
| 47 | 
            +
                  temp.max = @max - other.max
         | 
| 48 | 
            +
             | 
| 49 | 
            +
                  return temp
         | 
| 50 | 
            +
                end
         | 
| 51 | 
            +
             | 
| 52 | 
            +
                # returns whether bounding box intersects other
         | 
| 53 | 
            +
                def intersect?(other)
         | 
| 54 | 
            +
                  if other.is_a?(Ray)
         | 
| 55 | 
            +
                    other.intersect?(self)
         | 
| 56 | 
            +
                  elsif other.is_a?(BoundingBox)
         | 
| 57 | 
            +
                    (@min.x <= other.max.x && @max.x >= other.min.x) &&
         | 
| 58 | 
            +
                    (@min.y <= other.max.y && @max.y >= other.min.y) &&
         | 
| 59 | 
            +
                    (@min.z <= other.max.z && @max.z >= other.min.z)
         | 
| 60 | 
            +
                  else
         | 
| 61 | 
            +
                    raise "Unknown collider: #{other.class}"
         | 
| 62 | 
            +
                  end
         | 
| 63 | 
            +
                end
         | 
| 64 | 
            +
             | 
| 65 | 
            +
                # does this bounding box envelop other bounding box? (inclusive of border)
         | 
| 66 | 
            +
                def contains?(other)
         | 
| 67 | 
            +
                  other.min.x >= min.x && other.min.y >= min.y && other.min.z >= min.z &&
         | 
| 68 | 
            +
                  other.max.x <= max.x && other.max.y <= max.y && other.max.z <= max.z
         | 
| 69 | 
            +
                end
         | 
| 70 | 
            +
             | 
| 71 | 
            +
                # returns whether the 3D vector is inside of the bounding box
         | 
| 72 | 
            +
                def inside?(vector)
         | 
| 73 | 
            +
                  (vector.x.between?(@min.x, @max.x) || vector.x.between?(@max.x, @min.x)) &&
         | 
| 74 | 
            +
                  (vector.y.between?(@min.y, @max.y) || vector.y.between?(@max.y, @min.y)) &&
         | 
| 75 | 
            +
                  (vector.z.between?(@min.z, @max.z) || vector.z.between?(@max.z, @min.z))
         | 
| 76 | 
            +
                end
         | 
| 77 | 
            +
             | 
| 78 | 
            +
                # returns whether the 2D vector is inside of the bounding box
         | 
| 79 | 
            +
                def point?(vector)
         | 
| 80 | 
            +
                  (vector.x.between?(@min.x, @max.x) || vector.x.between?(@max.x, @min.x)) &&
         | 
| 81 | 
            +
                  (vector.y.between?(@min.y, @max.y) || vector.y.between?(@max.y, @min.y))
         | 
| 82 | 
            +
                end
         | 
| 83 | 
            +
             | 
| 84 | 
            +
                def volume
         | 
| 85 | 
            +
                  width * height * depth
         | 
| 86 | 
            +
                end
         | 
| 87 | 
            +
             | 
| 88 | 
            +
                def width
         | 
| 89 | 
            +
                  @max.x - @min.x
         | 
| 90 | 
            +
                end
         | 
| 91 | 
            +
             | 
| 92 | 
            +
                def height
         | 
| 93 | 
            +
                  @max.y - @min.y
         | 
| 94 | 
            +
                end
         | 
| 95 | 
            +
             | 
| 96 | 
            +
                def depth
         | 
| 97 | 
            +
                  @max.z - @min.z
         | 
| 98 | 
            +
                end
         | 
| 99 | 
            +
             | 
| 100 | 
            +
                def normalize(entity)
         | 
| 101 | 
            +
                  temp = BoundingBox.new
         | 
| 102 | 
            +
                  temp.min.x = @min.x.to_f * entity.scale.x
         | 
| 103 | 
            +
                  temp.min.y = @min.y.to_f * entity.scale.y
         | 
| 104 | 
            +
                  temp.min.z = @min.z.to_f * entity.scale.z
         | 
| 105 | 
            +
             | 
| 106 | 
            +
                  temp.max.x = @max.x.to_f * entity.scale.x
         | 
| 107 | 
            +
                  temp.max.y = @max.y.to_f * entity.scale.y
         | 
| 108 | 
            +
                  temp.max.z = @max.z.to_f * entity.scale.z
         | 
| 109 | 
            +
             | 
| 110 | 
            +
                  return temp
         | 
| 111 | 
            +
                end
         | 
| 112 | 
            +
             | 
| 113 | 
            +
                def normalize_with_offset(entity)
         | 
| 114 | 
            +
                  temp = BoundingBox.new
         | 
| 115 | 
            +
                  temp.min.x = @min.x.to_f * entity.scale.x + entity.position.x
         | 
| 116 | 
            +
                  temp.min.y = @min.y.to_f * entity.scale.y + entity.position.y
         | 
| 117 | 
            +
                  temp.min.z = @min.z.to_f * entity.scale.z + entity.position.z
         | 
| 118 | 
            +
             | 
| 119 | 
            +
                  temp.max.x = @max.x.to_f * entity.scale.x + entity.position.x
         | 
| 120 | 
            +
                  temp.max.y = @max.y.to_f * entity.scale.y + entity.position.y
         | 
| 121 | 
            +
                  temp.max.z = @max.z.to_f * entity.scale.z + entity.position.z
         | 
| 122 | 
            +
             | 
| 123 | 
            +
                  return temp
         | 
| 124 | 
            +
                end
         | 
| 125 | 
            +
             | 
| 126 | 
            +
                def +(other)
         | 
| 127 | 
            +
                  box = BoundingBox.new
         | 
| 128 | 
            +
                  box.min = self.min + other.min
         | 
| 129 | 
            +
                  box.min = self.max + other.max
         | 
| 130 | 
            +
             | 
| 131 | 
            +
                  return box
         | 
| 132 | 
            +
                end
         | 
| 133 | 
            +
             | 
| 134 | 
            +
                def -(other)
         | 
| 135 | 
            +
                  box = BoundingBox.new
         | 
| 136 | 
            +
                  box.min = self.min - other.min
         | 
| 137 | 
            +
                  box.min = self.max - other.max
         | 
| 138 | 
            +
             | 
| 139 | 
            +
                  return box
         | 
| 140 | 
            +
                end
         | 
| 141 | 
            +
             | 
| 142 | 
            +
                def sum
         | 
| 143 | 
            +
                  @min.sum + @max.sum
         | 
| 144 | 
            +
                end
         | 
| 145 | 
            +
             | 
| 146 | 
            +
                def clone
         | 
| 147 | 
            +
                  BoundingBox.new(@min.x, @min.y, @min.z, @max.x, @max.y, @max.z)
         | 
| 148 | 
            +
                end
         | 
| 149 | 
            +
              end
         | 
| 150 150 | 
             
            end
         |