h3m 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,17 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --color
2
+ --format progress
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in h3m.gemspec
4
+ gemspec
@@ -0,0 +1,44 @@
1
+ # H3m
2
+
3
+ Simple parser for Heroes of Might and Magic III map format. Currently can extract info about map name, description, difficulty, size, subterranean presence and minimal required game version (to be continued, see TODO).
4
+
5
+ ## Usage
6
+
7
+ Usage example:
8
+
9
+ >> require "h3m"
10
+ >> m = H3m::Map.new("path/to/map/file.h3m")
11
+
12
+ >> m.name
13
+ => "Map name"
14
+
15
+ >> m.description
16
+ => "Map description"
17
+
18
+ >> # Version can be :SoD, :AB or :RoE
19
+ >> m.version
20
+ => :SoD
21
+
22
+ >> # Size can be :S, :M, :L and :XL
23
+ >> m.size
24
+ => :M
25
+
26
+ >> m.has_subterranean?
27
+ => false
28
+
29
+ >> # Difficulty can be :easy, :normal, :hard, :expert and :impossible
30
+ >> m.difficulty
31
+ => :normal
32
+
33
+
34
+ ## TODO
35
+
36
+ 1. players and alliances
37
+ 2. victory and lose conditions
38
+ 3. minimap image generation
39
+
40
+ ## License
41
+
42
+ Copyright (C) 2013 Maxim Andryunin
43
+
44
+ Released under the [MIT License](http://www.opensource.org/licenses/MIT).
@@ -0,0 +1,5 @@
1
+ require 'rspec/core/rake_task'
2
+
3
+ RSpec::Core::RakeTask.new('spec')
4
+
5
+ task :default => :spec
@@ -0,0 +1,26 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'h3m/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = "h3m"
8
+ spec.version = H3m::VERSION
9
+ spec.authors = ["Maxim Andryunin"]
10
+ spec.email = ["maxim.andryunin@gmail.com"]
11
+ spec.description = %q{This gem will can extract info about players, teams, map size and version, win conditions of Heroes 3 map}
12
+ spec.summary = %q{Extract some info from Heroes of Might and Magic 3 map (.h3m)}
13
+ spec.homepage = "https://github.com/andryunin/h3m"
14
+ spec.license = "MIT"
15
+
16
+ spec.files = `git ls-files`.split($/)
17
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
+ spec.require_paths = ["lib"]
20
+
21
+ spec.add_dependency "bindata"
22
+
23
+ spec.add_development_dependency "bundler", "~> 1.3"
24
+ spec.add_development_dependency "rspec", ">= 2.0.0"
25
+ spec.add_development_dependency "rake"
26
+ end
@@ -0,0 +1,7 @@
1
+ require "h3m/version"
2
+ require "zlib"
3
+
4
+ module H3m
5
+ autoload :Map, "h3m/map.rb"
6
+ autoload :MapRecord, "h3m/records.rb"
7
+ end
@@ -0,0 +1,77 @@
1
+ module H3m
2
+
3
+ class MapError < StandardError
4
+ end
5
+
6
+ class Map
7
+ # Map representation
8
+ #
9
+ # Example:
10
+ # >> map = H3m::Map.new("some-map-file.h3m")
11
+ # >> map.version
12
+ # => :SoD
13
+
14
+ attr_reader :path
15
+
16
+ def initialize(path)
17
+ @path = path
18
+ @gzip_file = File.new(path)
19
+ end
20
+
21
+ def file
22
+ @file ||= Zlib::GzipReader.new(@gzip_file)
23
+ end
24
+
25
+ # Get extension
26
+ # @return [Symbol] :SoD, :AB or :RoE
27
+ def version
28
+ @version ||= case record.heroes_version
29
+ when 0x0E then :RoE
30
+ when 0x15 then :AB
31
+ when 0x1C then :SoD
32
+ else
33
+ raise MapError, "unknown map version"
34
+ end
35
+ end
36
+
37
+ def size
38
+ @size ||= case record.map_size
39
+ when 36 then :S
40
+ when 72 then :M
41
+ when 108 then :L
42
+ when 144 then :XL
43
+ else
44
+ raise MapError, "unknown map size"
45
+ end
46
+ end
47
+
48
+ def name
49
+ record.map_name
50
+ end
51
+
52
+ def description
53
+ record.map_desc
54
+ end
55
+
56
+ def difficulty
57
+ @difficulty ||= case record.map_difficulty
58
+ when 0 then :easy
59
+ when 1 then :normal
60
+ when 2 then :hard
61
+ when 3 then :expert
62
+ when 4 then :impossible
63
+ else
64
+ raise MapError, "unknown map difficulty"
65
+ end
66
+ end
67
+
68
+ def has_subterranean?
69
+ record.map_has_subterranean != 0
70
+ end
71
+
72
+ def record
73
+ @record ||= H3m::MapRecord.read(file)
74
+ end
75
+ end
76
+
77
+ end
@@ -0,0 +1,49 @@
1
+ require 'bindata'
2
+
3
+ module H3m
4
+
5
+ class PlayerRecord < BinData::Record
6
+ endian :little
7
+
8
+ uint8 :max_level
9
+
10
+ uint8 :can_be_human
11
+ uint8 :can_be_computer
12
+ uint8 :computer_behaviour
13
+
14
+ uint8 :has_town_on_start
15
+ uint16 :can_have_town_types
16
+ uint8 :has_random_town
17
+ uint8 :has_main_town
18
+
19
+ uint8 :main_town_has_hero, onlyif: :has_main_town?
20
+ uint8 :main_town_type, onlyif: :has_main_town?
21
+ uint8 :main_town_coord_x, onlyif: :has_main_town?
22
+ uint8 :main_town_coord_y, onlyif: :has_main_town?
23
+ uint8 :main_town_coord_z, onlyif: :has_main_town?
24
+
25
+ def has_main_town?
26
+ has_main_town.nonzero?
27
+ end
28
+ end
29
+
30
+ class MapRecord < BinData::Record
31
+ endian :little
32
+
33
+ uint32 :heroes_version
34
+ uint8 :map_has_hero
35
+ uint32 :map_size
36
+ uint8 :map_has_subterranean
37
+
38
+ uint32 :map_name_size
39
+ string :map_name, read_length: :map_name_size
40
+
41
+ uint32 :map_desc_size
42
+ string :map_desc, read_length: :map_desc_size
43
+
44
+ uint8 :map_difficulty
45
+
46
+ array :players, type: :player_record, initial_length: 8
47
+ end
48
+
49
+ end
@@ -0,0 +1,3 @@
1
+ module H3m
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,54 @@
1
+ require "spec_helper"
2
+
3
+ describe H3m::Map do
4
+
5
+ before :all do
6
+ @files = Dir.glob("spec/resources/SoD_*.h3m")
7
+ @params = @files.map do |path|
8
+ filename = File.basename(path, ".h3m")
9
+ version, size = filename.split("_").map(&:to_sym)
10
+ {version: version, size: size}
11
+ end
12
+
13
+ end
14
+
15
+ it "should return correct version" do
16
+ @files.each_with_index do |path, index|
17
+ params = @params[index]
18
+ map = H3m::Map.new(path)
19
+ map.version.should == params[:version]
20
+ end
21
+ end
22
+
23
+ it "should return correct size" do
24
+ @files.each_with_index do |path, index|
25
+ params = @params[index]
26
+ map = H3m::Map.new(path)
27
+ map.size.should == params[:size]
28
+ end
29
+ end
30
+
31
+ it "should return correct name and description" do
32
+ map = H3m::Map.new("spec/resources/test_1.h3m")
33
+
34
+ map.name.should == "test map name"
35
+ map.description.should == "test map desc"
36
+ end
37
+
38
+ it "should correctly determine subterranean presence" do
39
+ map = H3m::Map.new("spec/resources/test_1.h3m")
40
+ map.has_subterranean?.should == true
41
+
42
+ map = H3m::Map.new("spec/resources/test_2.h3m")
43
+ map.has_subterranean?.should == false
44
+ end
45
+
46
+ it "should correctly determine map difficulty" do
47
+ map = H3m::Map.new("spec/resources/test_1.h3m")
48
+ map.difficulty.should == :normal
49
+
50
+ map = H3m::Map.new("spec/resources/test_2.h3m")
51
+ map.difficulty.should == :impossible
52
+ end
53
+
54
+ end
Binary file
Binary file
Binary file
Binary file
Binary file
Binary file
@@ -0,0 +1,15 @@
1
+ # See http://rubydoc.info/gems/rspec-core/RSpec/Core/Configuration
2
+
3
+ require "h3m"
4
+
5
+ RSpec.configure do |config|
6
+ config.treat_symbols_as_metadata_keys_with_true_values = true
7
+ config.run_all_when_everything_filtered = true
8
+ config.filter_run :focus
9
+
10
+ # Run specs in random order to surface order dependencies. If you find an
11
+ # order dependency and want to debug it, you can fix the order by providing
12
+ # the seed, which is printed after each run.
13
+ # --seed 1234
14
+ config.order = 'random'
15
+ end
metadata ADDED
@@ -0,0 +1,137 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: h3m
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Maxim Andryunin
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2013-06-21 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: bindata
16
+ requirement: !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: bundler
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ~>
36
+ - !ruby/object:Gem::Version
37
+ version: '1.3'
38
+ type: :development
39
+ prerelease: false
40
+ version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
42
+ requirements:
43
+ - - ~>
44
+ - !ruby/object:Gem::Version
45
+ version: '1.3'
46
+ - !ruby/object:Gem::Dependency
47
+ name: rspec
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: 2.0.0
54
+ type: :development
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: 2.0.0
62
+ - !ruby/object:Gem::Dependency
63
+ name: rake
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ! '>='
68
+ - !ruby/object:Gem::Version
69
+ version: '0'
70
+ type: :development
71
+ prerelease: false
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: '0'
78
+ description: This gem will can extract info about players, teams, map size and version,
79
+ win conditions of Heroes 3 map
80
+ email:
81
+ - maxim.andryunin@gmail.com
82
+ executables: []
83
+ extensions: []
84
+ extra_rdoc_files: []
85
+ files:
86
+ - .gitignore
87
+ - .rspec
88
+ - Gemfile
89
+ - README.md
90
+ - Rakefile
91
+ - h3m.gemspec
92
+ - lib/h3m.rb
93
+ - lib/h3m/map.rb
94
+ - lib/h3m/records.rb
95
+ - lib/h3m/version.rb
96
+ - spec/map_spec.rb
97
+ - spec/resources/SoD_L.h3m
98
+ - spec/resources/SoD_M.h3m
99
+ - spec/resources/SoD_S.h3m
100
+ - spec/resources/SoD_XL.h3m
101
+ - spec/resources/test_1.h3m
102
+ - spec/resources/test_2.h3m
103
+ - spec/spec_helper.rb
104
+ homepage: https://github.com/andryunin/h3m
105
+ licenses:
106
+ - MIT
107
+ post_install_message:
108
+ rdoc_options: []
109
+ require_paths:
110
+ - lib
111
+ required_ruby_version: !ruby/object:Gem::Requirement
112
+ none: false
113
+ requirements:
114
+ - - ! '>='
115
+ - !ruby/object:Gem::Version
116
+ version: '0'
117
+ required_rubygems_version: !ruby/object:Gem::Requirement
118
+ none: false
119
+ requirements:
120
+ - - ! '>='
121
+ - !ruby/object:Gem::Version
122
+ version: '0'
123
+ requirements: []
124
+ rubyforge_project:
125
+ rubygems_version: 1.8.24
126
+ signing_key:
127
+ specification_version: 3
128
+ summary: Extract some info from Heroes of Might and Magic 3 map (.h3m)
129
+ test_files:
130
+ - spec/map_spec.rb
131
+ - spec/resources/SoD_L.h3m
132
+ - spec/resources/SoD_M.h3m
133
+ - spec/resources/SoD_S.h3m
134
+ - spec/resources/SoD_XL.h3m
135
+ - spec/resources/test_1.h3m
136
+ - spec/resources/test_2.h3m
137
+ - spec/spec_helper.rb