Class: Ra::Ray

Inherits:
Object
  • Object
show all
Defined in:
lib/ra/ray.rb

Overview

A ray is positioned at an origin travelling by a direction. A ray is cast and used to identify collisions with objects. For example:

ray = Ra::Ray.new(
  origin: Vector[0, 0, 0, Ra::Tuple::POINT],
  direction: Vector[1, 2, 3, Ra::Tuple::VECTOR],
)
ray.position(t: 1) == Vector[1, 2, 3, Ra::Tuple::VECTOR]
ray.position(t: 2) == Vector[2, 4, 6, Ra::Tuple::VECTOR]
ray.position(t: 3) == Vector[3, 6, 9, Ra::Tuple::VECTOR]

A ray can be transformed. This is useful when considering the ray relative to an object that has a transform associated with it. For example:

ray = Ra::Ray.new(
  origin: Vector[0, 0, 0, Ra::Tuple::POINT],
  direction: Vector[1, 2, 3, Ra::Tuple::VECTOR],
)
ray.transform(transform: Ra::Transform.scale(1, 2, 3))

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(origin:, direction:) ⇒ Ray

Returns a new instance of Ray.

Parameters:

  • origin (Vector)

    e.g. Vector[1, 2, 3, Ra::Tuple::POINT]

  • direction (Vector)

    e.g. Vector[1, 2, 3, Ra::Tuple::VECTOR]



34
35
36
37
# File 'lib/ra/ray.rb', line 34

def initialize(origin:, direction:)
  @origin = origin
  @direction = direction
end

Instance Attribute Details

#directionVector

Returns:

  • (Vector)


30
31
32
# File 'lib/ra/ray.rb', line 30

def direction
  @direction
end

#originVector

Returns:

  • (Vector)


26
27
28
# File 'lib/ra/ray.rb', line 26

def origin
  @origin
end

Instance Method Details

#==(other) ⇒ Boolean

Returns:

  • (Boolean)


55
56
57
# File 'lib/ra/ray.rb', line 55

def ==(other)
  origin == other.origin && direction == other.direction
end

#direction_w0

Returns 0 = vector / 1 = point.

Returns:

  • (0)

    0 = vector / 1 = point



120
121
122
# File 'lib/ra/ray.rb', line 120

def direction_w
  @direction[3]
end

#direction_xNumeric

Returns:

  • (Numeric)


105
106
107
# File 'lib/ra/ray.rb', line 105

def direction_x
  @direction[0]
end

#direction_yNumeric

Returns:

  • (Numeric)


110
111
112
# File 'lib/ra/ray.rb', line 110

def direction_y
  @direction[1]
end

#direction_zNumeric

Returns:

  • (Numeric)


115
116
117
# File 'lib/ra/ray.rb', line 115

def direction_z
  @direction[2]
end

#origin_w1

Returns 0 = vector / 1 = point.

Returns:

  • (1)

    0 = vector / 1 = point



140
141
142
# File 'lib/ra/ray.rb', line 140

def origin_w
  @origin[3]
end

#origin_xNumeric

Returns:

  • (Numeric)


125
126
127
# File 'lib/ra/ray.rb', line 125

def origin_x
  @origin[0]
end

#origin_yNumeric

Returns:

  • (Numeric)


130
131
132
# File 'lib/ra/ray.rb', line 130

def origin_y
  @origin[1]
end

#origin_zNumeric

Returns:

  • (Numeric)


135
136
137
# File 'lib/ra/ray.rb', line 135

def origin_z
  @origin[2]
end

#position(t:) ⇒ Vector

Parameters:

  • t (Numeric)

Returns:

  • (Vector)


41
42
43
# File 'lib/ra/ray.rb', line 41

def position(t:)
  @origin + (@direction * t)
end

#t_x(x) ⇒ Numeric

The time t when the ray is at x

Parameters:

  • x (Numeric)

Returns:

  • (Numeric)


80
81
82
83
84
# File 'lib/ra/ray.rb', line 80

def t_x(x)
  return if direction_x.zero?

  (x - origin_x) / direction_x
end

#t_y(y) ⇒ Numeric?

The time t when the ray is at y

Parameters:

  • y (Numeric)

Returns:

  • (Numeric, nil)


89
90
91
92
93
# File 'lib/ra/ray.rb', line 89

def t_y(y)
  return if direction_y.zero?

  (y - origin_y) / direction_y
end

#t_z(z) ⇒ Numeric?

The time t when the ray is at z

Parameters:

  • z (Numeric)

Returns:

  • (Numeric, nil)


98
99
100
101
102
# File 'lib/ra/ray.rb', line 98

def t_z(z)
  return if direction_z.zero?

  (z - origin_z) / direction_z
end

#transform(transform) ⇒ Ra::Ray

Parameters:

Returns:



47
48
49
50
51
52
# File 'lib/ra/ray.rb', line 47

def transform(transform)
  self.class.new(
    origin: transform * @origin,
    direction: transform * @direction,
  )
end

#x(t:) ⇒ Numeric

Parameters:

  • t (Numeric)

Returns:

  • (Numeric)


61
62
63
# File 'lib/ra/ray.rb', line 61

def x(t:)
  origin_x + (direction_x * t)
end

#y(t:) ⇒ Numeric

Parameters:

  • t (Numeric)

Returns:

  • (Numeric)


67
68
69
# File 'lib/ra/ray.rb', line 67

def y(t:)
  origin_y + (direction_y * t)
end

#z(t:) ⇒ Numeric

Parameters:

  • t (Numeric)

Returns:

  • (Numeric)


73
74
75
# File 'lib/ra/ray.rb', line 73

def z(t:)
  origin_z + (direction_z * t)
end