nwn-lib 0.3.6 → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
data/BINARIES CHANGED
@@ -1,45 +1,40 @@
1
- == nwn-gff-print
2
-
3
- Usage: nwn-gff-print [options] file/- [file, file, ..]
4
- -y, --yaml Dump as yaml
5
- -k, --kivinen Dump as kivinens dump format (like the perl tools)
6
- --kivinen-full-path Print the full path (implies -k)
7
- -b, --print-basename Prefix the file basename to the output
8
- -f, --print-filename Prefix the full filename to the output
9
- -t, --print-types Print types as well
10
- -m, --marshal Native ruby marshalling. Warning: raw bytes
11
- --postfix P Write output to file postfixed with P instead of stdout
12
- --float_rounding F Round floating point numbers to the specified number of righthand digits
13
- --type filetype Override the file type (implies --struct 0xffffffff)
14
- --struct id Override struct id (as hex, please)
15
- -p, --path path Only print the given path
16
- -v, --verbose Be verbose
17
-
18
- This prints out the given file(s) (or stdin, if -) as the specified format (-y, -k, -m)
19
- [-k] is the same as gffprint.pl
20
- [-kt] is the same as gffprint.pl -t
21
- [-m] is the native ruby marshal format (see Marshal.dump(obj))
22
- [-y] is standard YAML
23
- [--postfix] will write out each processed file to the same directory as the infile, with the given postfix appended
24
- [--float_rounding] can be used to truncate FPs to the given precision.
25
- [-p] will print out a given path within the GFF data (for example <tt>/ItemList[2]</tt>)
26
-
27
- == nwn-gff-import
28
-
29
- Usage: nwn-gff-import [options] file/- [file, file, file]
30
- -y, --yaml Import as yaml
31
- -m, --marshal Import as native ruby marshal data
32
- -o, --outfile F Write to outfile instead of stdout
33
- --postfix P Strip the given postfix from file and write to that instead of stdout (overrides -o)
34
-
35
- This is the equivalent to gffencode.pl. This can be used to transform marshalled gff data back into gff binary data.
36
-
37
- Example (save to run on a shell, prints out hex data):
38
-
39
- nwn-gff-print -y my_item.uti | nwn-gff-import.rb -y - - | xxd
40
-
41
- == nwn-gff-irb
42
-
43
- Usage: nwn-gff-irb file
44
-
45
- nwn-gff-irb allows interactive editing of gff files. There are some examples on the CHEATSHEET.
1
+ == nwn-gff
2
+
3
+ A generic converter that can be used for converting gff files to and fro from various
4
+ file formats and presentations, and transform them with custom script filters.
5
+
6
+ Type
7
+ nwn-gff -h
8
+ for help, it should be self-explanatory.
9
+
10
+ There are some usage examples on the CHEATSHEET.
11
+
12
+ == nwn-irb
13
+
14
+ nwn-irb is a interactive shell preloading all relevant libs, and optionally
15
+ loading a gff file.
16
+
17
+ There are some usage examples on the CHEATSHEET.
18
+
19
+ == nwn-dsl
20
+
21
+ A standalone script interpreter. See the example scripts in the gem distribution
22
+ under scripts/.
23
+
24
+ == Things under tools/
25
+
26
+ These are not added to PATH, you'll have to specify their path explicitly; you can
27
+ find them in your gem repository (/usr/lib/ruby/1.8/gems/ or similar).
28
+
29
+ === migrate_03x_to_04x.sh
30
+
31
+ This can be used to migrate old YAML dumps made with version 0.3.x to the new,
32
+ compacter format of 0.4.x.
33
+
34
+ Usage is simple: just pass all old .yml files to the script, it will convert them
35
+ in-place (read: make a backup!).
36
+
37
+ This uses nwn-gff-convert and nwn-gff, so all environment variables are taken into
38
+ consideration. You will want to point NWN_LIB_INFER_DATA_FILE to something useful.
39
+
40
+ Backup and testing is ADVISED!
data/CHANGELOG CHANGED
@@ -105,3 +105,7 @@ Bernhard Stoeckner <elven@swordcoast.net> (5):
105
105
 
106
106
  Stuart Coyle <stuart.coyle@gmail.com> (1):
107
107
  TwoDA: use four spaces for field separation instead of tabs, indent columns
108
+
109
+ ==== 0.4.0
110
+ Bernhard Stoeckner <elven@swordcoast.net>:
111
+ too many to sanely list, see README for migration information
data/CHEATSHEET CHANGED
@@ -1,75 +1,9 @@
1
- ==== Extract item from creature inventory
1
+ ==== Convert all item files in the current directory to yaml and back
2
2
 
3
- nwn-gff-print --type UTI -kt -p 'ItemList[12]' creature.bic | gffencode.pl -o item.uti
3
+ for x in *.uti; do
4
+ nwn-gff-convert -i"$x" -o"$x.yml" -lg -ky
5
+ done
4
6
 
5
- ==== Convert all item files in the current directory to yaml
6
-
7
- nwn-gff-print -v -y --postfix .yml *.uti
8
-
9
- ==== Convert all yaml item files back to their gff counterpart
10
-
11
- nwn-gff-import -y --postfix .yml *.uti.yml
12
-
13
- ==== Makefile rules for building resources from yml files
14
-
15
- postfix := uti
16
-
17
- objects := $(basename $(wildcard *.$(postfix).yml))
18
-
19
- all: $(objects)
20
-
21
- $(objects) : %.$(postfix) : %.$(postfix).yml
22
- nwn-gff-import -y -o $@ $<
23
-
24
- clean:
25
- -@rm $(objects)
26
-
27
- This ruleset will automatically rebuild changed ymls to their respective .uti counterparts.
28
- This only serves as an example on how to do it; it does not constitute a complete build environment.
29
-
30
- ==== Quick-edit a item
31
-
32
- your/prompt$ nwn-gff-irb my_item.uti
33
- Your GFF file is in `GFF' (type: "UTI ").
34
- Type `save' to save to the filename it came from (make a backup!), `exit' (or Ctrl+D) to exit (without saving).
35
- To save to a different location, type `save "path/to/new/location.ext"'.
36
-
37
- irb(main):001:0> GFF.root_struct.keys
38
- => ["ModelPart2", "Cursed", "ModelPart3", "Cost", "StackSize", "Charges", "Comment", "PaletteID", "BaseItem", "Tag", "DescIdentified", "Identified", "Plot", "TemplateResRef", "PropertiesList", "AddCost", "Stolen", "Description", "LocalizedName", "ModelPart1"]
39
-
40
- irb(main):002:0> GFF['LocalizedName/4']
41
- => "Mundane Feuerpfeile (aus Eibe)"
42
-
43
- irb(main):003:0> GFF['LocalizedName/4'] = 'New Name'
44
- => "New Name"
45
-
46
- irb(main):004:0> GFF['LocalizedName']
47
- => #<NWN::Gff::Element:0xb790641c @type=:cexolocstr, @value=[#<struct NWN::Gff::CExoLocString language=4, text="New Name">, #<struct NWN::Gff::CExoLocString language=0, text="Pfeil">], @_str_ref=1517, @label="LocalizedName">
48
-
49
- irb(main):005:0> save
50
- Saving to `/home/elven/code/nwn/nwn-lib.git/my_item.uti' ..
51
- saved.
52
- => nil
53
-
54
- irb(main):006:0> exit
55
-
56
- ==== Add a item property, the semi-human way
57
-
58
- irb(main):001:0> Helpers.item_property('Cast_Spell')
59
- ArgumentError: Property Cast_Spell needs subtype of type IPRP_SPELLS, but none given.
60
- from /var/lib/gems/1.8/gems/nwn-lib-0.2.3/lib/nwn/helpers.rb:108:in `item_property'
61
- from (irb):1
62
-
63
- irb(main):002:0> Helpers.item_property('Cast_Spell', 'Invisib')
64
- ArgumentError: Cannot resolve invisib. Partial matches: ["Improved_Invisibility", "Invisibility", "Invisibility_Purge", "Invisibility_Sphere", "See_Invisibility"].
65
- from /var/lib/gems/1.8/gems/nwn-lib-0.2.3/lib/nwn/helpers.rb:79:in `resolve_or_match_partial'
66
- from /var/lib/gems/1.8/gems/nwn-lib-0.2.3/lib/nwn/helpers.rb:116:in `item_property'
67
- from (irb):2
68
-
69
- irb(main):003:0> Helpers.item_property('Cast_Spell', 'Invisibility')
70
- ArgumentError: Property Cast_Spell requires a cost value of type IPRP_CHARGECOST, but none given
71
- from /var/lib/gems/1.8/gems/nwn-lib-0.2.3/lib/nwn/helpers.rb:122:in `item_property'
72
- from (irb):3
73
-
74
- irb(main):004:0> Helpers.item_property('Cast_Spell', 'Invisibility', 'Unlimi')
75
- => {"PropertyName"=>#<NWN::Gff::Element:0xb75f4e68 ..
7
+ for x in *.uti.yml; do
8
+ nwn-gff-convert -i"$x" -o"$(basename $x .yml)" -ly -kg
9
+ done
data/COPYING CHANGED
@@ -1,4 +1,4 @@
1
- Copyright (C) 2008 Bernhard Stoeckner <elven@swordcoast.net>
1
+ Copyright (C) 2008 Bernhard Stoeckner <elven@swordcoast.net> and contributors
2
2
 
3
3
  This program is free software; you can redistribute it and/or modify
4
4
  it under the terms of the GNU General Public License as published by
@@ -0,0 +1,50 @@
1
+ == Internal data representation
2
+
3
+ All data is representend internally as simple hashes or arrays. On load,
4
+ each structure will be extended by a representing module containing
5
+ the API and some application logic.
6
+
7
+ * Structs are normal hashes extended by NWN::Gff::Struct
8
+ * Lists are arrays extended by NWN::Gff::List
9
+ * Fields are normal hashes extended by NWN::Gff::Field
10
+ * CExoLocStrings are normal hashes extended by NWN::Gff::CExoLocString
11
+
12
+
13
+ === Struct
14
+
15
+ Example:
16
+ "/AddCost" => {"value" => 5, "label" => "AddCost", "type" => :dword}
17
+
18
+ Also, a NWN::Gff::Struct also has these accessors:
19
+
20
+ * data_type: A string describing the data type of this struct. (see Data Type)
21
+ * data_version: A string describing the version (usually "V3.2")
22
+ * struct_id: the struct Id of this struct.
23
+ * element: The NWN::Gff::Field which this struct contains. This is nil
24
+ for root structs.
25
+
26
+
27
+ === Field
28
+
29
+ Each field is a hash containing two keys:
30
+ "value": The data contained in this field, depending on
31
+ "type": The data type. For known data types, see NWN::Gff::Gff.
32
+
33
+ Additionally, "label" is a key set by the Readers saying its' label name.
34
+ This key, however, will not be written out to YAML (since it would be
35
+ redundant).
36
+
37
+ Also, each field has a .parent, which is a simple accessor set by
38
+ the various readers pointing to the struct it is member of.
39
+
40
+
41
+ === Data Type
42
+
43
+ Each Struct has a data_type, which describes the type of data the struct contains.
44
+ For top-level structs, this equals the data type written to the GFF file ("UTI",
45
+ for example); for sub structures, this is usually the top-level data type + the
46
+ field label ("UTI/PropertiesList", for example). This is used by various loaders/writers
47
+ to infer field types and default values.
48
+
49
+ This also means that inventory items in /ItemList/ structs have a type of "UTI" and
50
+ thus could be exported to item files, or re-attached somewhere else with minimum scripting.
data/README CHANGED
@@ -4,55 +4,45 @@ This package provides a library for reading, changing, and writing common file f
4
4
 
5
5
  They should work with NWN2 just as well, since the file format specifications did not change.
6
6
 
7
- There are various things included in this distribution:
8
- * some binaries under bin/ (see BINARIES)
9
- * the actual library under lib/nwn
7
+ === Upgrade from 0.3.6 to 0.4.x
10
8
 
11
- == Attention Unicode/UTF-users
9
+ With the release of 0.4.0, the API changed significantly. Previous yaml dumps made with 0.3.x are INCOMPATIBLE, and so are all scripts.
10
+ I can't help you with your API bindings, but for your YAML dumps, a converter script has been provided (see BINARIES).
12
11
 
13
- ruby 1.8 does not support character sets natively, and as such nwn-gff-irb will <b>FAIL</b> to encode non-standard characters properly on non-latin1 shells.
14
- This will be worked around in a future release until the release of ruby 1.9, which will provide native charset support.
15
-
16
- == Quickstart
12
+ === A word on version numbers
17
13
 
18
- It is easiest to just use the gem, which is available through rubyforge (<tt>sudo gem install nwn-lib</tt>).
14
+ Please consider all version releases below 1.0.0 to be unstable, even though the code is fully functional - further API changes may not be avoidable between major revisions - such as is the case with 0.3 -> 0.4.
19
15
 
20
- As an alternative, fetch the latest development files with git[http://git.swordcoast.net/?p=nwn/nwn-lib.git;a=summary].
21
-
22
- require 'rubygems'
23
- require 'nwn/gff'
16
+ === Features of nwn-lib
24
17
 
25
- # Read a GFF file
26
- o = NWN::Gff::Reader.read(IO.read('/tmp/test-creature.gff'))
18
+ * a feature-complete parser and generator of valid GFF V3.2 data
19
+ * shell scripts and tools to simplify your life (see BINARIES)
20
+ * kivinen-style ("gffprint.pl") presentation of data
21
+ * yaml presentation of data
22
+ * ruby-native marshalling of gff data
23
+ * extensive developer API
24
+ * a powerful get-out-of-my-way scripting system for data transformation (see SCRIPTING)
25
+ * guessing of field-types and -values for shorter plaintext data dumps (see TYPE_AND_VALUE_INFERRING)
27
26
 
28
- # Do some modifications to it
29
- o['/Tag'] = 'testtag'
27
+ Also in the box:
30
28
 
31
- # And write it somewhere else
32
- bytes = NWN::Gff::Writer.dump(o)
29
+ * a CHEATSHEET showing off some cool tricks
30
+ * some gadgetry for working with 2da files
33
31
 
34
- File.open('/tmp/test-creature-2.gff', 'w') {|f| f.write(bytes) }
32
+ === Attention Unicode/UTF-users
35
33
 
36
- Modification API is fairly limited, for now, but will improve soon.
37
-
38
- == GFF data structures: Quick Intro
34
+ ruby 1.8 does not support character sets natively, and as such nwn-gff-irb will <b>FAIL</b> to encode non-standard characters properly on non-latin1 shells.
35
+ This will be worked around in a future release until the release of ruby 1.9, which will provide native charset support.
39
36
 
40
- Ruby GFF data structures are nearly a 1:1 wrapper around the known format.
37
+ === Quickstart
41
38
 
42
- Each GFF object has a root structure with a +struct_id+ of 0.
39
+ To use it, simply install the gem (available on rubyforge):
43
40
 
44
- === Label
45
- A Label is a string of up to 16 bytes, and occurs as keys in Structs.
41
+ gem1.8 install nwn-lib
46
42
 
47
- === Struct
48
- A struct is a hash. It is a unordered collection of key => value pairs.
49
- Keys are Labels, values are either:
50
- * Structs
51
- * Lists
52
- * Elements
43
+ And do the following in a script of your own devising:
53
44
 
54
- === List
55
- A list is an *ordered* array of Structs.
45
+ require 'rubygems'
46
+ require 'nwn/all'
56
47
 
57
- === Element
58
- A Element is a distinct value of a given type. For all possible types, see the +Types+ hash in the NWN::Gff module.
48
+ For nwn-lib scripts, see SCRIPTING.
data/Rakefile CHANGED
@@ -9,16 +9,18 @@ include FileUtils
9
9
  # Configuration
10
10
  ##############################################################################
11
11
  NAME = "nwn-lib"
12
- VERS = "0.3.6"
12
+ VERS = "0.4.0"
13
13
  CLEAN.include ["**/.*.sw?", "pkg", ".config", "rdoc", "coverage"]
14
14
  RDOC_OPTS = ["--quiet", "--line-numbers", "--inline-source", '--title', \
15
15
  'nwn-lib: a ruby library for accessing NWN resource files', \
16
16
  '--main', 'README']
17
17
 
18
+ DOCS = ["README", "BINARIES", "DATA_STRUCTURES", "SCRIPTING", "SETTINGS", "TYPE_VALUE_INFERRING", "CHEATSHEET", "CHANGELOG", "COPYING"]
19
+
18
20
  Rake::RDocTask.new do |rdoc|
19
21
  rdoc.rdoc_dir = "rdoc"
20
22
  rdoc.options += RDOC_OPTS
21
- rdoc.rdoc_files.add ["README", "BINARIES", "CHEATSHEET", "CHANGELOG", "COPYING", "doc/*.rdoc", "lib/**/*.rb"]
23
+ rdoc.rdoc_files.add DOCS + ["doc/*.rdoc", "lib/**/*.rb"]
22
24
  end
23
25
 
24
26
  desc "Packages up nwn-lib"
@@ -30,16 +32,16 @@ spec = Gem::Specification.new do |s|
30
32
  s.version = VERS
31
33
  s.platform = Gem::Platform::RUBY
32
34
  s.has_rdoc = true
33
- s.extra_rdoc_files = ["README", "BINARIES", "CHEATSHEET", "CHANGELOG", "COPYING"] + Dir["doc/*.rdoc"]
35
+ s.extra_rdoc_files = DOCS + Dir["doc/*.rdoc"]
34
36
  s.rdoc_options += RDOC_OPTS + ["--exclude", "^(examples|extras)\/"]
35
37
  s.summary = "a ruby library for accessing Neverwinter Nights resource files"
36
38
  s.description = s.summary
37
39
  s.author = "Bernhard Stoeckner"
38
40
  s.email = "elven@swordcoast.net"
39
41
  s.homepage = "http://nwn-lib.elv.es"
40
- s.executables = ["nwn-gff-print", "nwn-gff-irb", "nwn-gff-import"]
42
+ s.executables = ["nwn-gff", "nwn-dsl", "nwn-irb"]
41
43
  s.required_ruby_version = ">= 1.8.4"
42
- s.files = %w(COPYING CHANGELOG README Rakefile) + Dir.glob("{bin,doc,spec,lib}/**/*")
44
+ s.files = %w(COPYING CHANGELOG README Rakefile) + Dir.glob("{bin,doc,spec,lib,tools,scripts,data}/**/*")
43
45
  s.require_path = "lib"
44
46
  s.bindir = "bin"
45
47
  end
@@ -0,0 +1,44 @@
1
+ To help you manage your NWN data more efficiently, nwn-lib supports
2
+ user-written, small (or large) scripts that follow the unix principle
3
+ of piping.
4
+
5
+ === Filter Scripts
6
+
7
+ Filter Scripts act as an argument to nwn-gff, and will be invoked
8
+ as a pass-through for data filtering and transformation.
9
+ Filters always depend on self being a Gff element.
10
+
11
+ An example of a filter script would be a snippet, that truncates
12
+ all floating points to a fixed size before outputting them to yaml.
13
+
14
+ Filter scripts are usually not executable by themself.
15
+
16
+ === Standalone Scripts
17
+
18
+ Standalone scripts are shell scripts invokable from command line,
19
+ and do not operate on specific files; instead, they get invoked
20
+ with their own (optional) parameters and act independently of
21
+ data sources.
22
+
23
+ An example for a standalone script would be a script, that asks
24
+ the user for a name and then generates a random item from that.
25
+
26
+ You can create standalone scripts by prefixing them with the proper
27
+ shebang:
28
+
29
+ #!/usr/bin/env nwn-dsl
30
+
31
+ If you are on systems which do not support executable scripts this
32
+ way, simply call them with nwn-dsl.
33
+
34
+ DSL stands for domain-specific-language by the way, and this is quite
35
+ a stretch, considering your scripts will be written in plain old ruby.
36
+
37
+ === API
38
+
39
+ There are various helpers available to scripts. See NWN::Gff::Scripting
40
+ for a list of helper methods; additionally you can use all other API
41
+ functions, of course.
42
+
43
+ There are some examples packaged together with nwn-lib, check the scripts/
44
+ directory with the distribution.
@@ -0,0 +1,80 @@
1
+ There are various environment variables you can configure to adjust various parts of nwn-lib.
2
+
3
+ <b>All of them are optional!</b>
4
+
5
+ Under linux, just add them to your shell environment (usually .bashrc), like so:
6
+
7
+ export NWN_LIB_INFER_DATA_FILE=/usr/lib/ruby/gems/1.8/gems/nwn-lib-0.4.0/data/gff-common-nwn1.yaml
8
+
9
+
10
+ == NWN_LIB_INFER_DATA_FILE
11
+
12
+ The path to the type/value inferring data file. See TYPE_VALUE_INFERRING for a definition.
13
+
14
+ Please be advised that inferring support for YAML is <b>EXPERIMENTAL</b> and may result in
15
+ <b>module and gff file corruption</b>.
16
+
17
+ == NWN_LIB_DONT_COMPACT_FIELDS
18
+
19
+ Set to non-nil ("1" will do) to prevent nwn-lib from compacting scalar fields into a more-readable
20
+ (but still fully parseable) format, if type inferring data is available.
21
+
22
+ === Without compacting
23
+ ItemList:
24
+ value:
25
+ - !nwn-lib.elv.es,2008-12/struct
26
+ __data_type: UTC/ItemList
27
+ __struct_id: 0
28
+ InventoryRes: {value: herb053}
29
+ PaletteID: {value: 6}
30
+ SkillList: [{value: 0}, {value: 0}, {value: 0}, {value: 0}, ...
31
+
32
+ === With compacting
33
+ ItemList:
34
+ - !nwn-lib.elv.es,2008-12/struct
35
+ __data_type: UTC/ItemList
36
+ InventoryRes: herb053
37
+ PaletteID: 6
38
+ SkillList: [0, 0, 0, 0, 0, 0, 2, 0, 0, 0 ...
39
+
40
+
41
+ == NWN_LIB_DONT_COMPACT_LIST_STRUCTS
42
+
43
+ Setting this to non-nil ("1" will do) will prevent nwn-lib from compacting lists that contain
44
+ structs, if type inferring data is available.
45
+
46
+ === Without compacting
47
+ SkillList:
48
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
49
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
50
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
51
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
52
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
53
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
54
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 2}
55
+ - !nwn-lib.elv.es,2008-12/struct {__data_type: UTC/SkillList, Rank: 0}
56
+ ...
57
+
58
+ === With compacting
59
+ SkillList: [0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, ...
60
+
61
+
62
+ == NWN_LIB_CLEAR_KNOWN_VALUES
63
+
64
+ Set to non-nil ("1" will do) to make nwn-lib omit fields that resolve to default values
65
+ as configured in $NWN_LIB_INFER_DATA_FILE.
66
+
67
+ The default is to not omit known-value data fields.
68
+
69
+ == NWN_LIB_FILTER_EMPTY_EXOLOCSTR
70
+
71
+ Set to non-nil ("1" will do) to make nwn-lib filter out empty exolocstr fields from
72
+ input files on reading.
73
+
74
+ The default is to keep them as-is.
75
+
76
+ == NWN_LIB_2DA_LOCATION
77
+
78
+ Set to a path containing all 2da files to initialize the 2da cache. This is needed for
79
+ most interactive helpers and a few type infer gizmos.
80
+