Class: Doom::Game::Animations

Inherits:
Object
  • Object
show all
Defined in:
lib/doom/game/animations.rb

Overview

Animated texture/flat cycling, matching Chocolate Doom’s P_InitPicAnims and P_UpdateSpecials from p_spec.c.

All animations run at 8 tics per frame (8/35 sec ≈ 0.23s). Frames must be consecutive entries in the WAD; the engine uses start/end names to find the range.

Constant Summary collapse

TICS_PER_FRAME =
8
ANIMDEFS =
is_texture, start_name, end_name

From Chocolate Doom animdefs[] in p_spec.c

[
  # Animated flats
  [false, 'NUKAGE1',  'NUKAGE3'],
  [false, 'FWATER1',  'FWATER4'],
  [false, 'SWATER1',  'SWATER4'],
  [false, 'LAVA1',    'LAVA4'],
  [false, 'BLOOD1',   'BLOOD3'],
  [false, 'RROCK05',  'RROCK08'],
  [false, 'SLIME01',  'SLIME04'],
  [false, 'SLIME05',  'SLIME08'],
  [false, 'SLIME09',  'SLIME12'],
  # Animated wall textures
  [true, 'BLODGR1',  'BLODGR4'],
  [true, 'SLADRIP1', 'SLADRIP3'],
  [true, 'BLODRIP1', 'BLODRIP4'],
  [true, 'FIREWALA', 'FIREWALL'],
  [true, 'GSTFONT1', 'GSTFONT3'],
  [true, 'FIRELAV3', 'FIRELAVA'],
  [true, 'FIREMAG1', 'FIREMAG3'],
  [true, 'FIREBLU1', 'FIREBLU2'],
  [true, 'ROCKRED1', 'ROCKRED3'],
  [true, 'BFALL1',   'BFALL4'],
  [true, 'SFALL1',   'SFALL4'],
  [true, 'WFALL1',   'WFALL4'],
  [true, 'DBRAIN1',  'DBRAIN4'],
].freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(texture_names, flat_names) ⇒ Animations

Returns a new instance of Animations.



45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
# File 'lib/doom/game/animations.rb', line 45

def initialize(texture_names, flat_names)
  @flat_translation = {}      # flat_name -> current_frame_name
  @texture_translation = {}   # texture_name -> current_frame_name
  @anims = []

  ANIMDEFS.each do |is_texture, start_name, end_name|
    names = is_texture ? texture_names : flat_names

    start_idx = names.index(start_name)
    end_idx = names.index(end_name)
    next unless start_idx && end_idx
    next if end_idx <= start_idx

    frames = names[start_idx..end_idx]
    next if frames.size < 2

    @anims << {
      is_texture: is_texture,
      frames: frames,
      speed: TICS_PER_FRAME,
    }
  end
end

Instance Attribute Details

#flat_translationObject (readonly)

Returns the value of attribute flat_translation.



43
44
45
# File 'lib/doom/game/animations.rb', line 43

def flat_translation
  @flat_translation
end

#texture_translationObject (readonly)

Returns the value of attribute texture_translation.



43
44
45
# File 'lib/doom/game/animations.rb', line 43

def texture_translation
  @texture_translation
end

Instance Method Details

#translate_flat(name) ⇒ Object

Translate a flat name to its current animation frame



87
88
89
# File 'lib/doom/game/animations.rb', line 87

def translate_flat(name)
  @flat_translation[name] || name
end

#translate_texture(name) ⇒ Object

Translate a texture name to its current animation frame



92
93
94
# File 'lib/doom/game/animations.rb', line 92

def translate_texture(name)
  @texture_translation[name] || name
end

#update(leveltime) ⇒ Object

Call every game tic (or approximate with leveltime). Matches Chocolate Doom P_UpdateSpecials:

pic = basepic + ((leveltime / speed + i) % numpics)


72
73
74
75
76
77
78
79
80
81
82
83
84
# File 'lib/doom/game/animations.rb', line 72

def update(leveltime)
  @anims.each do |anim|
    frames = anim[:frames]
    numpics = frames.size
    phase = leveltime / anim[:speed]
    translation = anim[:is_texture] ? @texture_translation : @flat_translation

    numpics.times do |i|
      current_frame = frames[(phase + i) % numpics]
      translation[frames[i]] = current_frame
    end
  end
end