e410d82680
The built hacked binary segfaults on Linux the moment a native GTK3 dialog (file/folder browse) opens while a GLFW/OpenGL context is live: sqweek/dialog's Linux backend never calls XInitThreads() before gtk_init(), and GLFW's own X11 backend installs a process-wide Xlib error handler that collides with GTK's. Vendor a pinned copy of github.com/sqweek/dialog (New BSD) into modding/sqweek-dialog/ so it can be patched like every other vendored source here: sqweek-dialog-patches/01-xinitthreads.patch adds the missing XInitThreads() call, and hacked-patches/01-use-patched-dialog.patch adds a go.mod replace directive pointing hacked's own sqweek/dialog dependency at that local copy. build-hacked.sh now stages both hacked/ and sqweek-dialog/ into a scratch modding/build/ directory and applies their patch series before compiling, rather than building hacked/ in place; .gitignore picks up that new scratch directory. Also expand modding/README.md: number its existing sections and add a worked "Example: Editing a message" walkthrough covering Static World Data, the Messages window's clipboard-only text editing, saving the Mod Location, and the absolute-path requirement for run.sh's mod-folder argument.
114 lines
5.2 KiB
Markdown
114 lines
5.2 KiB
Markdown
# Modding
|
|
|
|
Tools and reference material for modding System Shock (1994) itself - distinct
|
|
from the rest of this repository, which is the [QuestShock](../README.md) VR
|
|
port of the game engine. Everything modding-related lives under this folder.
|
|
|
|
Both pieces here come from the [InkyBlackness](https://inkyblackness.github.io)
|
|
project and are vendored unmodified, each under its own upstream license (see
|
|
below) - neither is relicensed by this repository's own MIT license.
|
|
|
|
## 1. Layout
|
|
|
|
- `hacked/` - [InkyBlackness HackEd](https://github.com/inkyblackness/hacked),
|
|
the graphical mod editor. A vendored source snapshot (New BSD License),
|
|
taken from the `main` branch on 2026-09-26. To update it, replace this
|
|
directory with a fresh checkout and update that date.
|
|
- `ss-specs/` - [InkyBlackness ss-specs](https://github.com/inkyblackness/ss-specs),
|
|
the unofficial file-format specifications the editor (and any other modding
|
|
tool) is written against. Reference documentation only, not built. A
|
|
vendored snapshot (CC BY-NC-SA 4.0 - **non-commercial**, unlike the rest of
|
|
this repository), taken from the `main` branch on 2026-09-26.
|
|
- `hacked-build-image/` - the Dockerfile (and supporting scripts) for the
|
|
`hacked` build environment: the Go toolchain plus every dependency
|
|
`hacked/go.mod` pins, fetched once at image-build time so the actual build
|
|
needs no network access. Mirrors the main project's own `build-image/`
|
|
(see the repository root's [README.md](../README.md) section 4) one level
|
|
down, for this subproject.
|
|
- `hacked-build-image.sh` / `hacked-build-run-image.sh` /
|
|
`hacked-build-upload-image.sh` - build the image, run it to compile
|
|
`hacked/`, and push it to a registry, respectively. Same pattern as the
|
|
root project's own `build-image.sh`/`run-image.sh`/`upload-image.sh`.
|
|
- `Makefile` - `hacked` (default) builds `hacked/` via the image; `build-image`
|
|
(re)builds the image itself; `clean` removes `dist/`.
|
|
- `dist/` - build output (git-ignored), created by `make hacked`.
|
|
|
|
Shockolate (the engine `../engine/` vendors) already has its own modding
|
|
support (level/resource files, `res/data/`); this folder is about the
|
|
external tools that create and inspect that content, not about changing the
|
|
engine itself.
|
|
|
|
## 2. Building `hacked`
|
|
|
|
Packages `dist/<version>.linux64.tgz` and `dist/<version>.win64.zip` (native
|
|
Linux build, Windows amd64 cross-compiled via mingw-w64 - both from the same
|
|
source, in one run).
|
|
|
|
**Prerequisites:** Docker - same as the root project, nothing modding-specific
|
|
to install locally.
|
|
|
|
```sh
|
|
cd modding
|
|
|
|
# 1. Build the hacked-build-image (once, or after hacked-build-image/ or
|
|
# hacked/go.mod|go.sum changes)
|
|
./hacked-build-image.sh
|
|
|
|
# 2. Compile hacked/ for Linux and Windows
|
|
make hacked
|
|
```
|
|
|
|
`<version>` is `hacked-<date>`, not an InkyBlackness release version:
|
|
`hacked/` is a vendored snapshot here, not its own git checkout, so there is
|
|
no tag to derive a real version from (see
|
|
`hacked-build-image/build-hacked.sh`'s own comment).
|
|
|
|
Run the result: `dist/linux/hacked/hacked` on Linux,
|
|
`dist\win\hacked\hacked.exe` on Windows. Needs OpenGL 3.2; usage is documented
|
|
on [hacked's own wiki](https://github.com/inkyblackness/hacked/wiki).
|
|
|
|
### 2.1. Publishing the build-image
|
|
|
|
Same registry as the root project's own build-image (see the repository
|
|
root's `registry.env.example`), under a separate image name so the two don't
|
|
collide:
|
|
|
|
```sh
|
|
./hacked-build-upload-image.sh
|
|
```
|
|
|
|
Reads `REGISTRY`/`REGISTRY_USER`/`REGISTRY_PASSWORD` and (optionally)
|
|
`HACKED_REGISTRY_IMAGE` from `../registry.env`, same as the root scripts.
|
|
Don't bump `hacked-build-image/VERSION` just because the Dockerfile changed -
|
|
only once a build with the current version has actually succeeded, same
|
|
policy as the root project's own `build-image/VERSION`.
|
|
|
|
## 3. Example: Editing a message
|
|
|
|
`hacked` has no inline text editor - every text field is edited by right-click
|
|
-> **Copy to Clipboard**, editing the text in an external editor, then
|
|
right-click -> **Copy from Clipboard** back into the field. Example: changing
|
|
Rebecca Lansing's first email.
|
|
|
|
1. Run `dist/linux/hacked/hacked` (or the Windows build).
|
|
2. **Window -> Project.** Under **Static World Data**, **Add...** and browse to
|
|
the game's whole `res/assets/ss_ee/data/` directory (see the root
|
|
[README.md](../README.md) section 3 for where that comes from), so every
|
|
`.res`/`.dat` file is available.
|
|
3. **Window -> Messages** (F5). **Message Type**: `Mails`. **Index**: `26`
|
|
(Rebecca's first mail). Edit **Sender**/**Subject**/**Title**/the message
|
|
text via the clipboard round-trip above.
|
|
4. Back in the **Project** window, under **Mod Location**, click **Save**
|
|
(first time: **Browse...** to an empty folder, for example
|
|
`./modding/mymod`).
|
|
5. Test it from the root project's desktop build:
|
|
```sh
|
|
./dist/run.sh "$(pwd)/modding/mymod"
|
|
```
|
|
The mod-folder argument **must be an absolute path**: `run.sh` `cd`s into
|
|
`dist/` before launching the engine, so a relative path resolves against
|
|
the wrong directory and the mod silently fails to load (the engine's
|
|
`ProcessModDirectory()` reports nothing on a bad path). When the path is
|
|
right, the terminal shows `ProcessModDirectory ...` / `Found resource
|
|
file: ...` / `Loading mod file ...` for confirmation.
|