BeamNG.Earth
BeamNG.drive용 1:1 비율 실시간 지구, 실제 고도·위성 이미지·부동 원점·보조 서버에서 LOD 스트리밍
README 전체를 불러오는 중입니다. 아래는 저장된 발췌입니다.
A toolkit and app suite for modding Viper Racing (1998): parse and rebuild its
file formats, browse and 3D-preview your cars and tracks, edit their textures,
swap tracks into the game's slots, set up the AI field, add modern resolutions,
and check your install for the fixes it needs to run well on a modern PC.
Everything is built on vrmod, a self-contained Python toolkit (pure standard
library apart from capstone, and even that only for one optional patch). The same
vrmod powers two front ends:README 전문 보기 ↗A toolkit and app suite for modding Viper Racing (1998): parse and rebuild its file formats, browse and 3D-preview your cars and tracks, edit their textures, swap tracks into the game's slots, set up the AI field, add modern resolutions, and check your install for the fixes it needs to run well on a modern PC.
Everything is built on vrmod, a self-contained Python toolkit (pure standard
library apart from capstone, and even that only for one optional patch). The same
vrmod powers two front ends:
| Front end | What it is | Where |
|---|---|---|
vrmod CLI + toolkit | Parsers/builders for every format, plus a local web UI | vrmod/ |
| Viper Racing Mod Manager | A native desktop app (pywebview) around the web UI | desktop/ |
Looking for community mods rather than the tools? They live at viper-racing-gallery — 2,023 cars and tracks, browsable at herbfargus.github.io/viper-racing-gallery.
Plus documentation in docs/, in three parts — readable on GitHub, or rendered with a contents page at
herbfargus.github.io/viper-racing-modding.
The HTML is built by CI and never committed, so it cannot drift from the Markdown the way the old hand-maintained copies did.
docs/reference/ — what the game is. The reverse
engineering, on three axes. Headings carry their evidence: ✅ CONFIRMED for
something read out of the binary or the file, ✅ MEASURED for something
observed in game.
| Doc | Axis |
|---|---|
| File formats | The bytes — the layout of every resource type the game ships |
| Asset tree | The structure — what's inside a .car/.trk, and where each texture it references resolves |
| Runtime | The behaviour — LOD per camera view, AI reactions, the engine's command-line parameters |
docs/history/ — what people did with it.
| Doc | What it covers |
|---|---|
| Modding history | The people, the tools they built between roughly 1999 and 2010, and how the formats came to be understood |
| Workflow comparison | The old one-off utilities against vrmod, job by job — including what still needs the old tools |
docs/archive/ — rescued primary sources. Not our writing:
community material from sites that no longer exist, preserved as it was.
Currently Wrxds's car tutorial, a
seventeen-step walkthrough with its original screenshots.
Repo naming: the GitHub repo is
viper-racing-modding; the Python package isvrmod; the desktop app's product name is "Viper Racing Mod Manager". The community gallery lives in its own repo and is deliberately not here; this repo is tools only.
vrmod/ the toolkit: parsers/builders, CLI, and the web UI (switcher_ui.py)
assets/ three.min.js (bundled for offline 3D) + stock slot icons
desktop/ the standalone app: app.py, the PyInstaller spec, icon
docs/reference/ the reverse engineering: bytes, structure, runtime behaviour
docs/history/ who built the old tools, and old workflow vs new
docs/archive/ rescued community material, preserved as it was
scripts/ check suites and corpus tooling
Game data is never committed — the toolkit reads your own install, and
.gitignore blocks *.car/.trk/.tra/.res, race.bin, etc.
vrmod is pure standard library apart from capstone (used only by the optional
race.bin vertex-buffer patch — imported lazily, so everything else, including the
whole viewing path, runs with no third-party dependency; that's what lets the
community gallery run it under Pyodide in the browser).
python -m vrmod.cli switcher "C:\path\to\Viper Racing\Data"
python -m venv .venv
.venv\Scripts\pip install -r requirements.txt
.venv\Scripts\python desktop\app.py
It opens on a landing screen; choose your Viper Racing Data folder (the one with
race.bin and your .car files) and it remembers it next time.
A car's page (edit mode → Configs) has a Preset picker: choose one and Apply
stages its tune into the car's .cf fields, Save writes it (backing up the original
the first time) and Restore original undoes it. A preset sets every physics field
of the car it was tested as — wheelbase, track, tyre sizes and ride height included — so
any car drives exactly like that car (Best on the Alleycat's body raced within 0.2 s of
the Viper it was tuned on, over the eight stock tracks). The catch is the look: the
car's wheels take the preset's size and position, so on a differently shaped car they
may not fit the body. The same from the command line:
python -m vrmod.cli presets
python -m vrmod.cli cfpatch viper.car viper-best.car --preset best
The shipped presets (vrmod/assets/presets/) — Best, Dragster and
Dragster 500 — were generated by an AI search from MGI's stock Viper, scored by AI
drivers' lap times on the eight stock tracks with scripted handling limits.
scripts/check_presets.py checks them.
The Game page's Career panel lists your career saves (Config/career/career<slot>.dat)
with each one's funds, and sets a career's money to any amount. A new career starts with
none. It's a save edit, so it works on the original game and the port; do it with the game
closed (the game saves the career over the file), and the first edit keeps a copy in
Backups. The same from the command line:
python -m vrmod.cli career <Data>
python -m vrmod.cli career <Data> --slot 0 --funds 10000000
scripts/check_careersave.py checks it.
With the venv set up, plus PyInstaller (pip install pyinstaller):
.venv\Scripts\python -m PyInstaller --noconfirm desktop\viper-mod-manager.spec
Produces a single file, dist\ViperModManager.exe (~16 MB) — that one
file is the whole app. The spec bundles vrmod/assets/ (three.js + slot icons),
capstone's native lib, pywebview's backend, and the app icon (desktop/icon.ico,
generated by desktop/make_icon.py). Paths in the spec are anchored to its own
location, so it builds from anywhere.
vrmod gallery walks a folder — any layout, stock and modded side by side — and
writes a static site: one interactive 3D page per car and per track, plus an
index linking them. No server, no hosting, no dependencies; open index.html
from disk.
python -m vrmod.cli gallery "C:\path\to\Data" out\gallery --serve
The community gallery is the same idea pointed at 2,023 mods instead of one install.
An optional engine upgrade from the companion viper-racing-port project (open source, GPL-3.0): a DLL placed beside the game (dinput.dll,
with SDL2.dll and viperport.ini) that runs Viper Racing on OpenGL and SDL instead of DirectDraw,
Direct3D and DirectSound. The 3D draws at the screen's native resolution with widescreen, the sound
has no DirectSound crackle, Alt-Tab comes back clean, and the engine's hard limits (physics objects,
textures, the texture table) are lifted. race.exe / race.bin aren't changed, and it works on
v1.0, v1.1 and the community 1.2.4–1.2.6 builds.
On v1.0 it also puts viperport.exe beside race.exe: the standalone, which runs the game on
the port's code alone. Your own race.exe is read as data, and none of its original code runs. It
runs v1.0 only, so it is never put beside a race.bin. It accepts a vrmod-patched race.exe and
refuses one with patches it doesn't know.
Install or remove it from the desktop app's Modern engine panel, or:
python -m vrmod.cli modern-engine "C:\path\to\Viper Racing\Data" # install (everything on)
python -m vrmod.cli modern-engine "C:\path\to\Viper Racing\Data" --remove
The panel's one setting is Graphics. Original looks as the 1998 game did. Enhanced gives sharper
distant textures (16x anisotropic filtering) at almost no cost, so it runs fine on older PCs. High
adds 4x anti-aliasing for smoother edges, for stronger graphics cards. It is written to
viperport.ini as [graphics] anisotropic= and msaa= (a missing key means 0, the original), and
anti-aliasing changes take effect the next time the game starts. Other values set by hand show as
Custom. Anisotropic filtering only applies where the game filters its textures, so Enhanced and High
also switch on filtering and mipmap in the game's own options.cfg (once the game has written
one; Original leaves them as they are, and the game's Graphics options can still change them). Install and Update keep the rest of viperport.ini as you left it, and only switch the
[platform] settings back on. From the command line, --graphics original|enhanced|high sets it and
--status shows it.
The app's Play button (top right, and in the Modern engine panel) starts the game the way this install starts. Its tooltip says which route it will take:
| install | Play starts |
|---|---|
| v1.0 with the modern engine | viperport.exe if viperport.exe --probe says it will run this race.exe; otherwise race.exe through the DLL, and Play says why |
| v1.0 without it | race.exe |
v1.1 and the community race.bin builds | the Viper Racing.exe launcher, which starts race.bin (through the DLL when installed) |
The game starts detached, with its own folder as the working directory. A viperport.exe from
before --probe existed can't be asked first. Play launches it and watches: if it exits with an
error within a few seconds, Play starts race.exe instead. The doctor reports the same answer
("Play runs the standalone engine", or why not).
python -m vrmod.cli play "C:\path\to\Viper Racing\Data" --dry-run # which route, start nothing
python -m vrmod.cli play "C:\path\to\Viper Racing\Data"
The files are bundled in vrmod/assets/modern_engine/: dinput.dll, viperport.exe and
SDL2.dll. scripts/update_modern_engine.py refreshes them from a viper-racing-port build
(hook\build and loader\build) and records the commit and each file's sha256 in SOURCE.txt.
The engine is also released on its own, for players who only want to play, on the viper-racing-port releases page:
| download | for | what's in it |
|---|---|---|
viperport-windows-<version>.zip | Windows | viperport.exe, dinput.dll, SDL2.dll, viperport.ini and a readme: copy them beside race.exe, then run viperport.exe (v1.0), or start a 1.1 / 1.2.x game as usual |
viperport-linux-<version>.tar.gz | Linux (x86, glibc 2.35 or newer: Ubuntu 22.04, Mint 21, Debian 12, Fedora 36 and later) | a native build of the engine, no Wine: viperport, viperport.sh, SDL2 in lib/ and README-linux.txt |
On Linux the engine runs v1.0's race.exe natively: the game is a 32-bit program, so it needs
your distro's 32-bit runtime and Mesa (one install line per distro family, in README-linux.txt).
Copy the CD's Data folder somewhere writable, unpack the tarball into it and run
./viperport.sh (--menu adds it to your application menu). Menus, sound, controllers and
TCP/IP races with Windows players all work. The mod manager itself is Windows-only for now.
v1.0's race.exe still contains MGI's in-house model editor. Its title bar says "Texture Tool", and
Ctrl+E on the main menu opens it. It loads modtool.res, which no disc ever shipped. Without
that file the game stops with "Can't load resource set" as soon as Ctrl+E is pressed. The only
copy people had was a community stand-in in which 18 of the 21 tool buttons are the same
placeholder, so the editor couldn't really be used.
vrmod writes its own modtool.res. Nothing in it is MGI's:
ui.res (catalog.stp). If that isn't there, vrmod uses a generated dark grid instead.point.mod, null.tex) and the textures the editor puts on the model:
wire_f.tex, the wireframe in triangle, vertex and geometry modes, and wedge.tex, the smoothed
and hard edges in edge mode. The stand-in has no wedge.tex.Installing the modern engine on v1.0 writes it too, and so does the doctor's fix, or:
python -m vrmod.cli modtool "C:\path\to\Viper Racing\Data" # write it
python -m vrmod.cli modtool "C:\path\to\Viper Racing\Data" --status
python -m vrmod.cli modtool "C:\path\to\Viper Racing\Data" --remove # put back what was there
vrmod only replaces a missing modtool.res, the community stand-in (recognised by its sha256) or
an earlier one of its own. It keeps the stand-in as modtool.res.vrmod-backup, and --remove (or
removing the modern engine) puts it back. Any other modtool.res is someone's own work, so vrmod
leaves it alone unless you pass --force.
.exe build.vrmod gallery) — working.