MicroStorageAPI 1.0.0

dotnet add package MicroStorageAPI --version 1.0.0
                    
NuGet\Install-Package MicroStorageAPI -Version 1.0.0
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="MicroStorageAPI" Version="1.0.0" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="MicroStorageAPI" Version="1.0.0" />
                    
Directory.Packages.props
<PackageReference Include="MicroStorageAPI" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add MicroStorageAPI --version 1.0.0
                    
#r "nuget: MicroStorageAPI, 1.0.0"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package MicroStorageAPI@1.0.0
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=MicroStorageAPI&version=1.0.0
                    
Install as a Cake Addin
#tool nuget:?package=MicroStorageAPI&version=1.0.0
                    
Install as a Cake Tool

Icon MicroStorage API

MicroStorage API is an open-source Spore modding library that lets any mod that uses it to store custom data inside saved adventures, which can be either serialized structures/classes, short to medium strings, or even small files. These adventures then can be published to Spore.com and played by both modded and vanilla Spore: Galactic Adventures players. MicroStorage is the way to add additional content for mod users.

MicroStorage API is based (and dependent) on Spore ModAPI, initially developed by emd4600.

How to Install

  1. In Visual Studio 2022, create a C++ project using the Spore ModAPI template (follow the official ModAPI tutorial, just ignore the "VS 2019" part of it).
  2. In the Solution Explorer, right-click your mod project (the one with the name you gave it, NOT "Spore ModAPI") and select "Manage NuGet Packages...".
  3. Type "MicroStorage API" in the searchbar and select "nuget.org" as the package source.
  4. Select the latest version and press "Install".
  5. Include MicroStorageAPI.h your .cpp file:
#include <MicroStorageAPI.h>

How to Use

MicroStorage API uses the mComments field in cScenarioString classes, which is unused in the final game, as it was meant for translators of Maxis adventures to provide additional context. Yet, this field is getting saved and loaded anyway.

To separate records (payloads) saved by different mods, MicroStorage uses the namespace:resource key system, in which namespace is the unique mod ID (private globally), and resource is the record ID (private internally).

Initializing MicroStorageClient

To operate with MicroStorage API, you must create a mod-specific instance of the MicroStorageClient class, which then should be stored in a global variable (the best practice is to call the class constructor inside your Initialize() function):

  • YourModGlobals.h (name it yourself):
#pragma once

class MicroStorageClient;

extern MicroStorageClient* g_msc;

// ... Other global variables, if you have any
  • dllmain.cpp:
// dllmain.cpp : Defines the entry point for the DLL application.
#include "stdafx.h"
#include "YourModGlobals.h" // The name you gave to the globals header
// ... Other includes
#include <MicroStorageAPI.h>

MicroStorageClient* g_msc = nullptr;

void Initialize()
{
	//                                       =================
	//                                       \/             ||
	g_msc = new MicroStorageClient("UniqueIDofYourMod"); // ||
	// This ID should be taken from the "unique"   ===========
	// attribute in your ModInfo.xml, as it's already meant
	// to be non-repeating between mods.

	// ... Other stuff to initialize
}

void Dispose()
{
	if (g_msc)
	{
		delete g_msc;
		g_msc = nullptr;
	}

	// ... Other stuff to dispose
}

// ...

After initializing your Client, you can use it in the code by including the globals header (in this example it's named YourModGlobals.h).

Reading & Writing MicroStorage Records

MicroStorage operates with EAIO streams (IO::IStream*) in both reading and writing operations.

The provided example code extracts the EAIO stream of the file by its Resource Key (cursors~!cursor-talkto.cur) and writes it inside a new MicroStorage Record:

//////////////////////////
// Add new (TestRecord) //
//////////////////////////

// 1. Gets cScenarioData and cScenarioResource from the currently opened Adventure Creator.
cScenarioDataPtr scenarioData = ScenarioMode.GetData();
cScenarioResourcePtr scenarioResource = scenarioData->mpResource;
// 2. Specifies the Resource Key to look up.
ResourceKey key = ResourceKey(id("cursor-talkto"), id("cur"), GroupIDs::Cursors);
// 3. Looks up the provided key, returns a pointer to the database where the resource is located.
Resource::Database* db = ResourceManager.FindRecord(key, nullptr);
if (db)
{
	// 4. Opens the file record.
	Resource::IRecord* record = nullptr;
	db->OpenRecord(key, &record);
	// 5. Extracts the EAIO stream of the opened record.
	IO::IStream* stream = record->GetStream();
	// 6. Starts a new history (undo) entry.
	scenarioData->StartHistoryEntry();
	// 7. Writes the contents of the stream inside the new MicroStorage Record.
	g_msc->Write(stream, id("TestRecord"), scenarioResource.get());
	// 8. Commits changes to the history entry.
	scenarioData->CommitHistoryEntry();
}

After the new MicroStorage Record was created, it can be read back. This example reads the contents of the previously created MicroStorage Record into MemoryStream:

///////////////////////
// Read (TestRecord) //
///////////////////////

// 1. Creates a new SharedPointer to initialize MemoryStream with.
IO::SharedPointer* sharedPtr = new IO::SharedPointer(0, nullptr);
// 2. Creates and initializes a new MemoryStream.
MemoryStreamPtr memoryStream = new IO::MemoryStream(sharedPtr, 0);
memoryStream->SetData(sharedPtr, 0);
// 3. Allows the MemoryStream to resize.
//    (Required if you don't know the size of the record.)
memoryStream->SetOption(IO::MemoryStream::kOptionResizeEnabled, 1);
// 4. Reads the contents of the MicroStorage Record
g_msc->Read(scenarioResource.get(), id("TestRecord"), memoryStream.get());

Publishing an Adventure

It's important to keep the size of any encoded data as small as possible, as Spore.com itself has a strict limit of 600 000 bytes (~585KB) per one published creation; for adventures this also includes 4 large images that usually take up to 4/5 of this size.

To keep adventures made with your mod publishable, you should avoid using MicroStorage Records to store large amounts of data.

Here's a short list of examples on what to NOT use MicroStorage for (if you don't want to break the publishing functionality):

  • AVI/VP6 videos (.avi, .vp6).
  • EALayer3/XAS audio samples, except for very short ones (.snr, .sns).
  • RenderWare/Spore-baked 3D models (.rw4 a.k.a. .rdx9, .gmdl).
  • Large uncompressed or lossless-compressed images (.png, .*bitImage, .raster in some cases).
  • Actual serialized game saves.
  • Enormous amounts of smaller files/data structures (a thousand of small 1KB files is still 1MB).

Although cScenarioResource is stored inside PNGs a compressed DBPF container, most of these won't get much smaller after saving.

Product Compatible and additional computed target framework versions.
native native is compatible. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

This package has no dependencies.

NuGet packages

This package is not used by any NuGet packages.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
1.0.0 211 6/8/2026