gemwarrior 0.10.8 → 0.11.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.
Files changed (93) hide show
  1. checksums.yaml +4 -4
  2. data/bin/gemwarrior +0 -0
  3. data/data/default_world.yaml +282 -436
  4. data/gemwarrior.gemspec +1 -1
  5. data/lib/gemwarrior/arena.rb +17 -17
  6. data/lib/gemwarrior/battle.rb +146 -77
  7. data/lib/gemwarrior/entities/armor.rb +34 -0
  8. data/lib/gemwarrior/entities/armor/iron_helmet.rb +17 -0
  9. data/lib/gemwarrior/entities/creature.rb +81 -4
  10. data/lib/gemwarrior/entities/creatures/cow.rb +24 -0
  11. data/lib/gemwarrior/entities/{items → creatures}/goat.rb +9 -11
  12. data/lib/gemwarrior/entities/creatures/pig.rb +24 -0
  13. data/lib/gemwarrior/entities/entity.rb +59 -5
  14. data/lib/gemwarrior/entities/item.rb +10 -22
  15. data/lib/gemwarrior/entities/items/apple.rb +2 -5
  16. data/lib/gemwarrior/entities/items/arena_door.rb +2 -6
  17. data/lib/gemwarrior/entities/items/bed.rb +7 -11
  18. data/lib/gemwarrior/entities/items/bookcase.rb +57 -0
  19. data/lib/gemwarrior/entities/items/bullet.rb +25 -0
  20. data/lib/gemwarrior/entities/items/couch.rb +6 -10
  21. data/lib/gemwarrior/entities/items/cup.rb +2 -5
  22. data/lib/gemwarrior/entities/items/dehumidifier.rb +3 -6
  23. data/lib/gemwarrior/entities/items/feather.rb +2 -5
  24. data/lib/gemwarrior/entities/items/floor_tile.rb +6 -10
  25. data/lib/gemwarrior/entities/items/flower.rb +1 -4
  26. data/lib/gemwarrior/entities/items/herb.rb +12 -13
  27. data/lib/gemwarrior/entities/items/keystone.rb +2 -5
  28. data/lib/gemwarrior/entities/items/ladder.rb +7 -11
  29. data/lib/gemwarrior/entities/items/letter.rb +20 -23
  30. data/lib/gemwarrior/entities/items/map.rb +3 -6
  31. data/lib/gemwarrior/entities/items/massive_door.rb +3 -7
  32. data/lib/gemwarrior/entities/items/pedestal.rb +6 -10
  33. data/lib/gemwarrior/entities/items/pond.rb +4 -8
  34. data/lib/gemwarrior/entities/items/rope.rb +4 -8
  35. data/lib/gemwarrior/entities/items/small_hole.rb +15 -77
  36. data/lib/gemwarrior/entities/items/snowman.rb +5 -9
  37. data/lib/gemwarrior/entities/items/sparkly_thing.rb +3 -7
  38. data/lib/gemwarrior/entities/items/stonemite.rb +2 -6
  39. data/lib/gemwarrior/entities/items/tent.rb +3 -6
  40. data/lib/gemwarrior/entities/items/throne.rb +7 -6
  41. data/lib/gemwarrior/entities/items/tree.rb +2 -6
  42. data/lib/gemwarrior/entities/items/waterfall.rb +9 -8
  43. data/lib/gemwarrior/entities/location.rb +49 -43
  44. data/lib/gemwarrior/entities/monster.rb +34 -28
  45. data/lib/gemwarrior/entities/monsters/alexandrat.rb +3 -3
  46. data/lib/gemwarrior/entities/monsters/amberoo.rb +3 -3
  47. data/lib/gemwarrior/entities/monsters/amethystle.rb +3 -3
  48. data/lib/gemwarrior/entities/monsters/apatiger.rb +3 -3
  49. data/lib/gemwarrior/entities/monsters/aquamarine.rb +3 -3
  50. data/lib/gemwarrior/entities/monsters/bloodstorm.rb +3 -3
  51. data/lib/gemwarrior/entities/monsters/bosses/emerald.rb +12 -27
  52. data/lib/gemwarrior/entities/monsters/bosses/garynetty.rb +17 -5
  53. data/lib/gemwarrior/entities/monsters/bosses/jaspern.rb +66 -0
  54. data/lib/gemwarrior/entities/monsters/citrinaga.rb +3 -3
  55. data/lib/gemwarrior/entities/monsters/coraliz.rb +3 -3
  56. data/lib/gemwarrior/entities/monsters/cubicat.rb +3 -3
  57. data/lib/gemwarrior/entities/monsters/diaman.rb +3 -3
  58. data/lib/gemwarrior/entities/{items → people}/arena_master.rb +8 -13
  59. data/lib/gemwarrior/entities/{items → people}/drunk_man.rb +14 -35
  60. data/lib/gemwarrior/entities/people/queen_ruby.rb +71 -0
  61. data/lib/gemwarrior/entities/people/rockney.rb +132 -0
  62. data/lib/gemwarrior/entities/{items → people}/shifty_woman.rb +7 -12
  63. data/lib/gemwarrior/entities/{items → people}/thin_man.rb +9 -14
  64. data/lib/gemwarrior/entities/people/ware_hawker.rb +153 -0
  65. data/lib/gemwarrior/entities/person.rb +20 -0
  66. data/lib/gemwarrior/entities/player.rb +102 -60
  67. data/lib/gemwarrior/entities/weapon.rb +38 -0
  68. data/lib/gemwarrior/entities/{items → weapons}/dagger.rb +5 -7
  69. data/lib/gemwarrior/entities/{items → weapons}/gun.rb +8 -10
  70. data/lib/gemwarrior/entities/{items → weapons}/mace.rb +6 -9
  71. data/lib/gemwarrior/entities/{items → weapons}/opalaser.rb +5 -7
  72. data/lib/gemwarrior/entities/weapons/spear.rb +23 -0
  73. data/lib/gemwarrior/entities/{items → weapons}/stalactite.rb +5 -7
  74. data/lib/gemwarrior/entities/weapons/stone.rb +23 -0
  75. data/lib/gemwarrior/evaluator.rb +111 -107
  76. data/lib/gemwarrior/game.rb +61 -29
  77. data/lib/gemwarrior/game_assets.rb +76 -0
  78. data/lib/gemwarrior/inventory.rb +77 -43
  79. data/lib/gemwarrior/misc/animation.rb +17 -13
  80. data/lib/gemwarrior/misc/{music.rb → audio.rb} +15 -7
  81. data/lib/gemwarrior/misc/audio_cues.rb +133 -0
  82. data/lib/gemwarrior/misc/formatting.rb +9 -9
  83. data/lib/gemwarrior/misc/player_levels.rb +21 -0
  84. data/lib/gemwarrior/repl.rb +32 -31
  85. data/lib/gemwarrior/version.rb +1 -1
  86. data/lib/gemwarrior/world.rb +155 -134
  87. metadata +34 -22
  88. data/lib/gemwarrior/entities/items/cow.rb +0 -26
  89. data/lib/gemwarrior/entities/items/pig.rb +0 -26
  90. data/lib/gemwarrior/entities/items/queen_ruby.rb +0 -62
  91. data/lib/gemwarrior/entities/items/spear.rb +0 -26
  92. data/lib/gemwarrior/entities/items/stone.rb +0 -25
  93. data/lib/gemwarrior/entities/items/ware_hawker.rb +0 -93
@@ -5,12 +5,14 @@ require 'colorize'
5
5
  require 'matrext'
6
6
 
7
7
  require_relative 'misc/animation'
8
- require_relative 'misc/music'
9
- require_relative 'world'
8
+ require_relative 'misc/audio'
9
+ require_relative 'misc/formatting'
10
10
  require_relative 'evaluator'
11
- require_relative 'repl'
12
- require_relative 'inventory'
11
+ require_relative 'game_assets'
13
12
  require_relative 'game_options'
13
+ require_relative 'inventory'
14
+ require_relative 'repl'
15
+ require_relative 'world'
14
16
 
15
17
  module Gemwarrior
16
18
  class Game
@@ -20,8 +22,11 @@ module Gemwarrior
20
22
  ROX_DEFAULT = 0
21
23
  ROX_DEBUG = 300
22
24
 
23
- attr_accessor :world, :evaluator, :repl,
24
- :monsters, :items
25
+ attr_accessor :world,
26
+ :evaluator,
27
+ :repl,
28
+ :monsters,
29
+ :weapons
25
30
 
26
31
  def initialize(options)
27
32
  # set game options
@@ -33,9 +38,14 @@ module Gemwarrior
33
38
  GameOptions.add 'sound_volume', options.fetch(:sound_volume)
34
39
  GameOptions.add 'use_wordnik', options.fetch(:use_wordnik)
35
40
 
36
- # add classes for monsters and items to game
41
+ # add classes for creatures, monsters, people, items, weapons, and armor to game
42
+ # also add them to the global GameAssets
43
+ init_creatures
37
44
  init_monsters
45
+ init_people
38
46
  init_items
47
+ init_weapons
48
+ init_armor
39
49
 
40
50
  # create new world based on default template
41
51
  self.world = init_world
@@ -47,7 +57,7 @@ module Gemwarrior
47
57
  world.player.mood = world.player.generate_mood
48
58
  world.player.inventory = GameOptions.data['debug_mode'] ? INVENTORY_DEBUG : INVENTORY_DEFAULT
49
59
  world.player.rox = GameOptions.data['debug_mode'] ? ROX_DEBUG : ROX_DEFAULT
50
-
60
+
51
61
  world.duration = { mins: 0, secs: 0, ms: 0 }
52
62
  world.emerald_beaten = false
53
63
 
@@ -59,7 +69,7 @@ module Gemwarrior
59
69
  self.repl = Repl.new(self, world, evaluator)
60
70
 
61
71
  # enter Jool!
62
- repl.start('look', options.fetch(:extra_command), options.fetch(:new_skip), options.fetch(:resume_skip))
72
+ repl.start('look', options.fetch(:extra_command), options.fetch(:new_skip), options.fetch(:resume_skip))
63
73
  end
64
74
 
65
75
  def update_options_file
@@ -73,33 +83,55 @@ module Gemwarrior
73
83
 
74
84
  private
75
85
 
86
+ # convert an entity filename to a class so it can be added to game asset singleton registry
87
+ def file_to_class(filename)
88
+ filename_to_string = Formatting.upstyle(filename.split('/').last.split('.')[0], no_space: true)
89
+ Gemwarrior.const_get(filename_to_string).new
90
+ end
91
+
92
+ def init_creatures
93
+ Dir.glob(File.expand_path('../entities/creatures/*.rb', __FILE__)).each do |creature|
94
+ require_relative creature
95
+ GameCreatures.add(file_to_class(creature))
96
+ end
97
+ end
98
+
76
99
  def init_monsters
77
- Dir.glob(File.expand_path('../entities/monsters/*.rb', __FILE__)).each do |item|
78
- require_relative item
100
+ Dir.glob(File.expand_path('../entities/monsters/*.rb', __FILE__)).each do |monster|
101
+ require_relative monster
102
+ GameMonsters.add(file_to_class(monster))
79
103
  end
80
- Dir.glob(File.expand_path('../entities/monsters/bosses/*.rb', __FILE__)).each do |item|
81
- require_relative item
104
+ Dir.glob(File.expand_path('../entities/monsters/bosses/*.rb', __FILE__)).each do |boss|
105
+ require_relative boss
106
+ GameMonsters.add(file_to_class(boss))
82
107
  end
108
+ end
83
109
 
84
- self.monsters = [
85
- Alexandrat.new,
86
- Amberoo.new,
87
- Amethystle.new,
88
- Apatiger.new,
89
- Aquamarine.new,
90
- Bloodstorm.new,
91
- Citrinaga.new,
92
- Coraliz.new,
93
- Cubicat.new,
94
- Diaman.new,
95
- Emerald.new,
96
- Garynetty.new
97
- ]
110
+ def init_people
111
+ Dir.glob(File.expand_path('../entities/people/*.rb', __FILE__)).each do |person|
112
+ require_relative person
113
+ GamePeople.add(file_to_class(person))
114
+ end
98
115
  end
99
116
 
100
117
  def init_items
101
118
  Dir.glob(File.expand_path('../entities/items/*.rb', __FILE__)).each do |item|
102
119
  require_relative item
120
+ GameItems.add(file_to_class(item))
121
+ end
122
+ end
123
+
124
+ def init_weapons
125
+ Dir.glob(File.expand_path('../entities/weapons/*.rb', __FILE__)).each do |weapon|
126
+ require_relative weapon
127
+ GameWeapons.add(file_to_class(weapon))
128
+ end
129
+ end
130
+
131
+ def init_armor
132
+ Dir.glob(File.expand_path('../entities/armor/*.rb', __FILE__)).each do |armor|
133
+ require_relative armor
134
+ GameArmor.add(file_to_class(armor))
103
135
  end
104
136
  end
105
137
 
@@ -109,7 +141,7 @@ module Gemwarrior
109
141
  if mode.eql?('Y')
110
142
  if File.exist?(GameOptions.data['default_world_path_yaml'])
111
143
  File.open(GameOptions.data['default_world_path_yaml'], 'r') do |f|
112
- return YAML::load(f)
144
+ return YAML.load(f)
113
145
  end
114
146
  else
115
147
  puts "Error: cannot load #{GameOptions.data['default_world_path_yaml']}."
@@ -117,7 +149,7 @@ module Gemwarrior
117
149
  else
118
150
  if File.exist?(GameOptions.data['default_world_path_bin'])
119
151
  File.open(GameOptions.data['default_world_path_bin'], 'r') do |f|
120
- return Marshal::load(f)
152
+ return Marshal.load(f)
121
153
  end
122
154
  else
123
155
  puts "Error: cannot load #{GameOptions.data['default_world_path_bin']}."
@@ -0,0 +1,76 @@
1
+ # lib/gemwarrior/game_assets.rb
2
+ # Gem Warrior Global Assets
3
+ ## Game Armor
4
+ ## Game Creatures
5
+ ## Game Items
6
+ ## Game Monsters
7
+ ## Game People
8
+ ## Game Weapons
9
+
10
+ module Gemwarrior
11
+ module GameArmor
12
+ def self.add obj
13
+ @@data ||= []
14
+ @@data.push(obj)
15
+ end
16
+
17
+ def self.data
18
+ @@data ||= []
19
+ end
20
+ end
21
+
22
+ module GameCreatures
23
+ def self.add obj
24
+ @@data ||= []
25
+ @@data.push(obj)
26
+ end
27
+
28
+ def self.data
29
+ @@data ||= []
30
+ end
31
+ end
32
+
33
+ module GameItems
34
+ def self.add obj
35
+ @@data ||= []
36
+ @@data.push(obj)
37
+ end
38
+
39
+ def self.data
40
+ @@data ||= []
41
+ end
42
+ end
43
+
44
+ module GameMonsters
45
+ def self.add obj
46
+ @@data ||= []
47
+ @@data.push(obj)
48
+ end
49
+
50
+ def self.data
51
+ @@data ||= []
52
+ end
53
+ end
54
+
55
+ module GamePeople
56
+ def self.add obj
57
+ @@data ||= []
58
+ @@data.push(obj)
59
+ end
60
+
61
+ def self.data
62
+ @@data ||= []
63
+ end
64
+ end
65
+
66
+ module GameWeapons
67
+ def self.add obj
68
+ @@data ||= []
69
+ @@data.push(obj)
70
+ end
71
+
72
+ def self.data
73
+ @@data ||= []
74
+ end
75
+ end
76
+ end
@@ -6,59 +6,84 @@ require_relative 'game_options'
6
6
  module Gemwarrior
7
7
  class Inventory
8
8
  # CONSTANTS
9
- ERROR_ITEM_REMOVE_INVALID = 'Your inventory does not contain that item, so you cannot drop it.'
10
- ERROR_ITEM_ADD_UNTAKEABLE = 'That would be great if you could take that thing, wouldn\'t it? Well, it\'s not so great for you right now.'
11
- ERROR_ITEM_ADD_INVALID = 'That item does not exist here.'
12
- ERROR_ITEM_EQUIP_INVALID = 'You do not possess anything called that to equip.'
13
- ERROR_ITEM_EQUIP_NONWEAPON = 'That cannot be equipped as a weapon.'
14
- ERROR_ITEM_UNEQUIP_INVALID = 'You do not possess anything called that to unequip.'
15
- ERROR_ITEM_UNEQUIP_NONWEAPON = 'That cannot be unequipped.'
16
-
17
- attr_accessor :items, :weapon
18
-
19
- def initialize(items = [], weapon = nil)
20
- self.items = items
9
+ ERROR_ITEM_REMOVE_INVALID = 'Your inventory does not contain that item, so you cannot drop it.'
10
+ ERROR_ITEM_ADD_UNTAKEABLE = 'That would be great if you could take that, wouldn\'t it? Huh!'
11
+ ERROR_ITEM_ADD_INVALID = 'That item cannot be added.'
12
+ ERROR_ITEM_DESCRIBE_INVALID = 'That does not seem to be in the inventory.'
13
+ ERROR_ITEM_EQUIP_INVALID = 'You do not possess anything called that to equip.'
14
+ ERROR_ITEM_EQUIP_NONARMAMENT = 'That item cannot be equipped.'
15
+ ERROR_ITEM_UNEQUIP_INVALID = 'You do not possess anything called that to unequip.'
16
+ ERROR_ITEM_UNEQUIP_NONARMAMENT = 'That item cannot be unequipped.'
17
+
18
+ attr_accessor :items,
19
+ :weapon,
20
+ :armor
21
+
22
+ def initialize(items = [], weapon = nil, armor = nil)
23
+ self.items = items
21
24
  self.weapon = weapon
25
+ self.armor = armor
26
+ end
27
+
28
+ def is_empty?
29
+ self.items.nil? || self.items.empty?
22
30
  end
23
31
 
24
32
  def list_contents
25
- if items.nil? || items.empty?
26
- return '[empty]'
27
- else
28
- return "#{items.map(&:name).join ', '}"
29
- end
33
+ is_empty? ? '[empty]' : "#{self.items.map(&:name).join(', ')}"
30
34
  end
31
35
 
32
36
  def contains_item?(item_name)
33
- items.map(&:name).include?(item_name)
37
+ self.items.map{ |i| i.name.downcase }.include?(item_name.downcase)
38
+ end
39
+
40
+ def contains_battle_item?
41
+ battle_item_found = false
42
+ self.items.each do |i|
43
+ battle_item_found = true if i.useable_battle
44
+ end
45
+ battle_item_found
46
+ end
47
+
48
+ def list_battle_items
49
+ battle_items = []
50
+ self.items.each do |i|
51
+ battle_items.push(i) if i.useable_battle
52
+ end
53
+ battle_items
34
54
  end
35
55
 
36
56
  def describe_item(item_name)
37
57
  if contains_item?(item_name)
38
- items.each do |i|
58
+ self.items.each do |i|
39
59
  if i.name.eql?(item_name)
40
60
  if GameOptions.data['debug_mode']
41
- return i.describe
61
+ return i.describe_detailed
42
62
  else
43
- return i.description
63
+ return i.describe
44
64
  end
45
65
  end
46
66
  end
47
67
  else
48
- return false
68
+ ERROR_ITEM_DESCRIBE_INVALID
49
69
  end
50
70
  end
51
71
 
52
72
  def equip_item(item_name)
53
73
  if contains_item?(item_name)
54
- items.each do |i|
74
+ self.items.each do |i|
55
75
  if i.name.eql?(item_name)
56
76
  if i.equippable
57
77
  i.equipped = true
58
- self.weapon = i
59
- return "The #{i.name} has taken charge, and been equipped."
78
+ if i.is_weapon
79
+ self.weapon = i
80
+ return "The #{i.name} has taken charge, and been equipped."
81
+ elsif i.is_armor
82
+ self.armor = i
83
+ return "The #{i.name} has fortified, and has been equipped."
84
+ end
60
85
  else
61
- return ERROR_ITEM_EQUIP_NONWEAPON
86
+ return ERROR_ITEM_EQUIP_NONARMAMENT
62
87
  end
63
88
  end
64
89
  end
@@ -69,14 +94,19 @@ module Gemwarrior
69
94
 
70
95
  def unequip_item(item_name)
71
96
  if contains_item?(item_name)
72
- items.each do |i|
97
+ self.items.each do |i|
73
98
  if i.name.eql?(item_name)
74
99
  if i.equippable
75
100
  i.equipped = false
76
- self.weapon = nil
77
- return "The #{i.name} has been demoted to unequipped."
101
+ if i.is_weapon
102
+ self.weapon = nil
103
+ return "The #{i.name} has been demoted to unequipped."
104
+ elsif i.is_armor
105
+ self.armor = nil
106
+ return "The #{i.name} has been demoted to unequipped."
107
+ end
78
108
  else
79
- return ERROR_ITEM_UNEQUIP_NONWEAPON
109
+ return ERROR_ITEM_UNEQUIP_NONARMAMENT
80
110
  end
81
111
  end
82
112
  end
@@ -85,27 +115,31 @@ module Gemwarrior
85
115
  end
86
116
  end
87
117
 
88
- def add_item(cur_loc, item_name, player)
89
- cur_loc.items.each do |i|
90
- if i.name.eql?(item_name)
91
- if i.takeable
92
- items.push(i)
93
- cur_loc.remove_item(item_name)
118
+ def add_item(item_name, cur_loc = nil, player = nil)
119
+ if cur_loc.nil?
120
+ self.items.push(item_name)
121
+ else
122
+ cur_loc.items.each do |i|
123
+ if i.name.eql?(item_name)
124
+ if i.takeable
125
+ self.items.push(i)
126
+ cur_loc.remove_item(item_name)
94
127
 
95
- # stats
96
- player.items_taken += 1
128
+ # stats
129
+ player.items_taken += 1
97
130
 
98
- return "Added #{item_name} to your increasing collection of bits of tid."
99
- else
100
- return ERROR_ITEM_ADD_UNTAKEABLE
131
+ return "Added #{item_name} to your increasing collection of bits of tid.".colorize(:green)
132
+ else
133
+ return ERROR_ITEM_ADD_UNTAKEABLE.colorize(:red)
134
+ end
101
135
  end
102
136
  end
103
137
  end
104
- ERROR_ITEM_ADD_INVALID
138
+ ERROR_ITEM_ADD_INVALID.colorize(:red)
105
139
  end
106
140
 
107
141
  def remove_item(item_name)
108
- items.delete_at(items.map(&:name).index(item_name) || items.length)
142
+ self.items.delete_at(self.items.map(&:name).index(item_name) || self.items.length)
109
143
  unless self.weapon.nil?
110
144
  self.weapon = nil if self.weapon.name.eql?(item_name)
111
145
  end
@@ -1,25 +1,29 @@
1
1
  # lib/gemwarrior/misc/animation.rb
2
- # Animation routine
2
+ # Animation routine using matrext
3
3
 
4
4
  module Gemwarrior
5
5
  module Animation
6
6
  def self.run(opts)
7
7
  options = {
8
- oneline: false,
9
- speed: nil,
10
- alpha: true,
11
- numeric: true,
12
- random: true
8
+ oneline: false,
9
+ speed: nil,
10
+ alpha: true,
11
+ numeric: true,
12
+ random: true,
13
+ color: nil,
14
+ background: nil
13
15
  }.merge(opts)
14
16
 
15
17
  th = Thread.new do
16
- print Matrext::process({
17
- phrase: options.fetch(:phrase),
18
- oneline: options.fetch(:oneline),
19
- speed: options.fetch(:speed),
20
- alpha: options.fetch(:alpha),
21
- numeric: options.fetch(:numeric),
22
- random: options.fetch(:random)
18
+ print Matrext.process({
19
+ phrase: options.fetch(:phrase),
20
+ oneline: options.fetch(:oneline),
21
+ speed: options.fetch(:speed),
22
+ alpha: options.fetch(:alpha),
23
+ numeric: options.fetch(:numeric),
24
+ random: options.fetch(:random),
25
+ color: options.fetch(:color),
26
+ background: options.fetch(:background)
23
27
  })
24
28
  end
25
29