Class: SFML::Vector2

Inherits:
Object
  • Object
show all
Defined in:
lib/sfml/system/vector2.rb

Overview

2D vector with float components. Operator-friendly and pattern-matchable.

v = SFML::Vector2[3, 4]
v.length          #=> 5.0
v + Vector2[1, 1] #=> Vector2(4, 5)
v * 2             #=> Vector2(6, 8)
x, y = v          # destructures via to_a

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(x = 0, y = 0) ⇒ Vector2

Returns a new instance of Vector2.



20
21
22
23
24
# File 'lib/sfml/system/vector2.rb', line 20

def initialize(x = 0, y = 0)
  @x = x
  @y = y
  freeze
end

Instance Attribute Details

#x ⇒ Object (readonly)

The X coordinate, Y coordinate components.



11
12
13
# File 'lib/sfml/system/vector2.rb', line 11

def x
  @x
end

#y ⇒ Object (readonly)

The X coordinate, Y coordinate components.



11
12
13
# File 'lib/sfml/system/vector2.rb', line 11

def y
  @y
end

Class Method Details

.[](x, y) ⇒ Object

Compact constructor: Vector2[3, 4] reads naturally as a literal.



14
# File 'lib/sfml/system/vector2.rb', line 14

def self.[](x, y) = new(x, y)

.from_native(struct) ⇒ Object

Returns the self.



166
167
168
# File 'lib/sfml/system/vector2.rb', line 166

def self.from_native(struct) # :nodoc:
  new(struct[:x], struct[:y])
end

.zero ⇒ Object

The (0, 0) vector. Reused as a singleton-style fallback (e.g. #normalize returns this for the zero vector).



18
# File 'lib/sfml/system/vector2.rb', line 18

def self.zero = new(0, 0)

Instance Method Details

#*(scalar) ⇒ Object

Multiply both components by scalar.



31
32
# File 'lib/sfml/system/vector2.rb', line 31

def *(scalar) = Vector2.new(@x * scalar, @y * scalar)
# Divide both components by `scalar`. Always promotes to Float.

#+(other) ⇒ Object

Component-wise addition.



27
28
# File 'lib/sfml/system/vector2.rb', line 27

def +(other) = Vector2.new(@x + other.x, @y + other.y)
# Component-wise subtraction.

#-(other) ⇒ Object

Component-wise subtraction.



29
30
# File 'lib/sfml/system/vector2.rb', line 29

def -(other) = Vector2.new(@x - other.x, @y - other.y)
# Multiply both components by `scalar`.

#-@ ⇒ Object

Negate both components.



35
# File 'lib/sfml/system/vector2.rb', line 35

def -@ = Vector2.new(-@x, -@y)

#/(scalar) ⇒ Object

Divide both components by scalar. Always promotes to Float.



33
34
# File 'lib/sfml/system/vector2.rb', line 33

def /(scalar) = Vector2.new(@x / scalar.to_f, @y / scalar.to_f)
# Negate both components.

#==(other) ⇒ Object Also known as: eql?

Value equality — two Vector2s are equal when both components match.



45
# File 'lib/sfml/system/vector2.rb', line 45

def ==(other) = other.is_a?(Vector2) && @x == other.x && @y == other.y

#abs ⇒ Object

Per-component absolute value.



143
# File 'lib/sfml/system/vector2.rb', line 143

def abs    = Vector2.new(@x.abs, @y.abs)

#angle ⇒ Object

Angle of this vector relative to +X axis, in radians (-π..π].



81
# File 'lib/sfml/system/vector2.rb', line 81

def angle = Math.atan2(@y, @x)

#angle_to(other) ⇒ Object

Angle from this vector to other as positions, in radians.



84
85
86
87
# File 'lib/sfml/system/vector2.rb', line 84

def angle_to(other)
  o = _coerce(other)
  Math.atan2(o.y - @y, o.x - @x)
end

#clamp_length(min_len = nil, max_len) ⇒ Object

Clamp the magnitude into [min_len, max_len]. Either bound may be nil to leave that side unclamped.



127
128
129
130
131
132
133
134
135
136
137
# File 'lib/sfml/system/vector2.rb', line 127

def clamp_length(min_len = nil, max_len)
  len = length
  return self if len.zero?
  target =
    if    max_len && len > max_len then max_len
    elsif min_len && len < min_len then min_len
    else len
    end
  return self if target == len
  self * (target / len)
end

#coerce(other) ⇒ Object

Lets Ruby evaluate 2 * vec as vec * 2. Without this, Numeric#* would raise TypeError because it doesn't know about Vector2.

Raises:

  • (TypeError)


39
40
41
42
# File 'lib/sfml/system/vector2.rb', line 39

def coerce(other)
  raise TypeError, "Vector2 cannot coerce #{other.class}" unless other.is_a?(Numeric)
  [self, other]
end

#cross(other) ⇒ Object

Scalar 2D cross product (a.k.a. perpendicular dot). Positive when other is counter-clockwise from self, negative when clockwise.



71
# File 'lib/sfml/system/vector2.rb', line 71

def cross(other) = (@x * other.y) - (@y * other.x)

#deconstruct ⇒ Object

Pattern-match support for in [x, y].



156
# File 'lib/sfml/system/vector2.rb', line 156

def deconstruct = [@x, @y]

#deconstruct_keys(_keys) ⇒ Object

Pattern-match support for in {x:, y:}.



159
# File 'lib/sfml/system/vector2.rb', line 159

def deconstruct_keys(_keys) = { x: @x, y: @y }

#distance(other) ⇒ Object

Euclidean distance to other — accepts a Vector2 or [x, y].



74
# File 'lib/sfml/system/vector2.rb', line 74

def distance(other)    = (self - _coerce(other)).length

#distance_sq(other) ⇒ Object

Squared distance to other — skip the sqrt if you only need to compare two distances.



78
# File 'lib/sfml/system/vector2.rb', line 78

def distance_sq(other) = (self - _coerce(other)).length_sq

#dot(other) ⇒ Object

Scalar dot product. Positive when both vectors point roughly the same way, negative when opposite, zero when perpendicular.



67
# File 'lib/sfml/system/vector2.rb', line 67

def dot(other)   = (@x * other.x) + (@y * other.y)

#hash ⇒ Object

Hash key support — Vector2s can be Hash keys / Set members.



48
# File 'lib/sfml/system/vector2.rb', line 48

def hash = [@x, @y].hash

#length ⇒ Object

Euclidean length √(x² + y²). For comparisons prefer length_sq — avoids the square root.



52
53
54
# File 'lib/sfml/system/vector2.rb', line 52

def length    = Math.sqrt(length_sq)
# Squared length (x² + y²) — comparisons can use this without the
# `sqrt` call.

#length_sq ⇒ Object

Squared length (x² + y²) — comparisons can use this without the sqrt call.



55
# File 'lib/sfml/system/vector2.rb', line 55

def length_sq = (@x * @x) + (@y * @y)

#lerp(other, t) ⇒ Object

Linear interpolation toward other. t in [0, 1] gives the standard mix; outside the range extrapolates.



105
106
107
108
# File 'lib/sfml/system/vector2.rb', line 105

def lerp(other, t)
  o = _coerce(other)
  Vector2.new(@x + (o.x - @x) * t, @y + (o.y - @y) * t)
end

#normalize ⇒ Object

Unit vector pointing the same way as self. Returns the zero vector unchanged (no division by zero).



59
60
61
62
63
# File 'lib/sfml/system/vector2.rb', line 59

def normalize
  len = length
  return Vector2.zero if len.zero?
  self / len
end

#perpendicular ⇒ Object

90° counter-clockwise rotation — equivalent to rotated_rad(π/2) but skips the trig. Handy for "the normal of an edge in 2D".



101
# File 'lib/sfml/system/vector2.rb', line 101

def perpendicular = Vector2.new(-@y, @x)

#project_on(other) ⇒ Object

Vector projection of self onto other.



111
112
113
114
115
116
# File 'lib/sfml/system/vector2.rb', line 111

def project_on(other)
  o = _coerce(other)
  d = o.length_sq
  return Vector2.zero if d.zero?
  o * (dot(o) / d)
end

#reflect(normal) ⇒ Object

Reflect this vector across the plane with normal. normal should be unit-length for the standard "bounce" behaviour.



120
121
122
123
# File 'lib/sfml/system/vector2.rb', line 120

def reflect(normal)
  n = _coerce(normal)
  self - (n * (2 * dot(n)))
end

#rotated(degrees) ⇒ Object

Vector rotated by degrees counter-clockwise. Use rotated_rad if you already have radians.



91
# File 'lib/sfml/system/vector2.rb', line 91

def rotated(degrees) = rotated_rad(degrees * Math::PI / 180.0)

#rotated_rad(radians) ⇒ Object

Vector rotated by radians counter-clockwise.



94
95
96
97
# File 'lib/sfml/system/vector2.rb', line 94

def rotated_rad(radians)
  c, s = Math.cos(radians), Math.sin(radians)
  Vector2.new(@x * c - @y * s, @x * s + @y * c)
end

#to_a ⇒ Object

As a 2-element [x, y] Array — supports splat destructuring: x, y = vec.



150
# File 'lib/sfml/system/vector2.rb', line 150

def to_a = [@x, @y]

#to_h ⇒ Object

As a {x:, y:} Hash.



153
# File 'lib/sfml/system/vector2.rb', line 153

def to_h = { x: @x, y: @y }

#to_native_f ⇒ Object

Returns the to native f.



171
172
173
# File 'lib/sfml/system/vector2.rb', line 171

def to_native_f # :nodoc:
  C::System::Vector2f.new.tap { |v| v[:x] = @x; v[:y] = @y }
end

#to_s ⇒ Object Also known as: inspect

String representation for debugging.



162
# File 'lib/sfml/system/vector2.rb', line 162

def to_s = "Vector2(#{@x}, #{@y})"

#to_v3(z = 0.0) ⇒ Object

Promote to a Vector3 with optional z (default 0).



146
# File 'lib/sfml/system/vector2.rb', line 146

def to_v3(z = 0.0) = Vector3.new(@x, @y, z)

#zero? ⇒ Boolean

true iff both components are zero.

Returns:

  • (Boolean)


140
# File 'lib/sfml/system/vector2.rb', line 140

def zero?  = @x.zero? && @y.zero?