You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
The Models layer (Models/) defines the domain types that the rest of the application works
with. The most important classes are JsonObject and JsonArray -- a custom, mutable JSON
tree that preserves field order, supports binary data, and integrates with the name mapper.
Wrapper classes (Ship, Multitool, Frigate, Companion, Inventory) provide typed
accessors over raw JSON objects. Enums define the game's classification systems.
Custom JSON Model
Why Not System.Text.Json?
The NMS save format has requirements that standard .NET JSON libraries do not satisfy:
Field order matters. The game may depend on property ordering; reordering fields
during round-trip could corrupt saves.
Binary data in strings. Some JSON string values contain raw bytes >= 0x80. These are
preserved as BinaryData objects using Latin-1 encoding.
Exact numeric round-trip. The game writes floats like 0.30000001192092898. .NET's
double.ToString might produce 0.30000001192092896 (same IEEE 754 bits, different
text). RawDouble preserves the original text.
Name mapping. Obfuscated 3-character keys must be translated transparently.
Path-based access with transforms.GetValue("PlayerStateData.Health") must resolve
through registered context transforms.
JsonObject
File
Models/JsonObject.cs
Purpose
Mutable JSON object with ordered key-value pairs, path access, transforms, and deep cloning
Stores entries as an ordered list of name-value pairs. Builds a Dictionary<string, int>
index lazily when the object has more than 8 properties, giving O(1) key lookup for large
objects while avoiding dictionary overhead for small ones.
Method
Description
Parse(string)
Static factory; parses a JSON string into a JsonObject
JSON parsing and serialization with NMS-specific features
A static class that provides the parsing engine. Key features:
Key interning pool -- deduplicates repeated key strings across all parsed objects,
reducing memory usage significantly for large saves with thousands of identical keys.
Lazy line/column tracking -- position is only computed on error (via
JsonReader.ComputeLine/Column), avoiding per-character overhead on the hot path.
Obfuscated key mapping -- when a global JsonNameMapper is set via
SetDefaultMapper, all parsed objects automatically translate keys.
BinaryData support -- strings containing high bytes become BinaryData instances.
RawDouble preservation -- floating-point numbers store both the parsed double and
the original text.
Method
Description
SetDefaultMapper(mapper)
Set the global name mapper for all future parsing
GetDefaultMapper()
Retrieve the current global mapper
Serialize(value, formatted, skipReverseMapping)
Serialize any JSON value to string
JsonReader
File
Models/JsonReader.cs
Purpose
High-performance character-level JSON reader
A sealed class that wraps a source string and provides character-by-character reading.
Optimized for speed: no per-character line/column tracking. Line and Column properties
are computed on demand from the current Position by scanning backward.
Method
Description
Read()
Read next character, advance position
Peek()
Look ahead without advancing
Advance(newPos)
Jump to a position
ReadSkipWhitespace()
Read next non-whitespace (also skips null bytes)
ReadDigit()
Read 0-9 or return -1
ReadIf(expected)
Conditional single-char read
ReadIfEither(a, b)
Conditional read for two alternatives
JsonException
File
Models/JsonException.cs
Purpose
JSON parsing/serialization error with optional position information
Extends Exception with Line and Column properties (0 if unknown). Three constructor
overloads support message-only, message with position, and message with inner exception and
position.
Value Types
BinaryData
File
Models/BinaryData.cs
Purpose
Wrapper for binary data found in JSON strings
NMS JSON sometimes contains strings with bytes >= 0x80. Since JSON is text, these bytes are
preserved by loading with Latin-1 encoding and wrapping in BinaryData. The class provides
ToByteArray(), IndexOf(byte), Substring(start, len) (Latin-1 decoded),
ToHexString(), and value-based equality.
RawDouble
File
Models/RawDouble.cs
Purpose
Double-precision float with original JSON text for lossless round-trip
A readonly struct with Value (the parsed double) and Text (the original JSON text).
ToString() returns Text, not a reformatted number. An implicit conversion to double
allows arithmetic. This prevents unnecessary diffs when saving -- the game might write
0.30000001192092898 but double.ToString would produce a slightly different decimal
representation of the same IEEE 754 bits.
IPropertyChangeListener
File
Models/IPropertyChangeListener.cs
Purpose
Observer interface for JSON property changes
Single method: PropertyChanged(path, oldValue, newValue). Can be attached to JsonObject
or JsonArray via the Listener property. Used to track modifications for undo/redo or
dirty-state detection.
Entity Wrapper Classes
These classes provide typed accessors over JsonObject instances from the save file. They
do not copy data -- they hold a reference to the underlying JSON node and read/write through
it.
Ship
File
Models/Ship.cs
Purpose
Wrapper for a player-owned starship
Property
Type
JSON Key
Index
int
(constructor arg)
Name
string
"Name"
Seed
string?
"Resource.Seed"
Type
ShipType
"ShipType" (enum-parsed)
Class
ShipClass
"ShipClass" (defaults to C)
Inventory
JsonObject?
"Inventory"
TechInventory
JsonObject?
"Inventory_TechOnly"
CargoInventory
JsonObject?
"Inventory_Cargo"
Data
JsonObject
(underlying node)
Multitool
File
Models/Multitool.cs
Purpose
Wrapper for a player-owned multitool weapon
Property
Type
JSON Key
Index
int
(constructor arg)
Name
string
"Name" (defaults to "Multitool {Index+1}")
Seed
string?
"Seed"
Type
MultitoolType
"MultitoolType" (enum-parsed)
Class
ShipClass
"MultitoolClass" (defaults to C)
Inventory
JsonObject?
"Inventory"
Data
JsonObject
(underlying node)
Frigate
File
Models/Frigate.cs
Purpose
Wrapper for a fleet frigate
Property
Type
JSON Key
Index
int
(constructor arg)
IsEnabled
bool
"Enabled"
NpcType
string?
"Type"
ShipType
string?
"ShipType"
Rank
string?
"Rank"
Data
JsonObject
(underlying node)
Companion
File
Models/Companion.cs
Purpose
Wrapper for a companion creature (pet)
Property
Type
JSON Key
Index
int
(constructor arg)
Type
string?
"Type"
Seed
string?
"Seed"
Data
JsonObject
(underlying node)
Inventory
File
Models/Inventory.cs
Purpose
Wrapper for an inventory grid
Property
Type
JSON Key
Type
InventoryType
(constructor arg)
Width
int
"Width"
Height
int
"Height"
Slots
JsonArray?
"Slots"
ValidSlotIndices
JsonArray?
"ValidSlotIndices"
Data
JsonObject
(underlying node)
Recipe / RecipeElement
File
Models/Recipe.cs
Purpose
Crafting/refining recipe with ingredients and result