Metin2 game client (P0–P11) + mobile asset pipeline

Networked client on the existing Godot 4.7 + libgr2 renderer:
- net: m2dev wire protocol (libsodium KX + XChaCha20), auth/select/game
  phases, EntityStore world model, ~all GC/CG headers. char create/delete,
  private shop / mall / cube, SHOP_GC_START_EX, guild, party (+ CG_PARTY_SET_STATE),
  quests, dragon soul, refine, safebox, exchange.
- UI: in-game windows migrated 1:1 from the reference uiscript/root .py —
  char status (/stat), inventory+equipment, select-item ([SELECT_ITEM] quest
  token), system-option + game-option + ESC system menu, private-shop 39-grid,
  party info board, shop tabs, atlas, minimap, quickbar, chat, …
- EterGrnLib polish: GR2 material blend/two-sided, LOD crossfade, motion-event
  dispatch, contact shadow, ray-AABB picking, weapon grip pre-transform.

Portable asset IO (A1) — all extension/libgr2/formats/mtproto reads routed
through godot::FileAccess (res:// PCK works on iOS/Android); standalone-lib
*_path() kept for the non-Godot CTests. AssetResolver + PropertyRegistry
switched to a baked index (bake_asset_index.gd) instead of std::filesystem.

Mobile builds: build-{android,ios}.sh, export-android.sh, pack-assets.sh,
gen-debug-keystore.sh. Assets ship as a zip mounted at runtime by
project/asset_pack.gd (adb push now; HTTP download is a drop-in later).

ctest 10/10, 34 GDScript suites, macOS/iOS/Android all build.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_013EJxkHiNKS4kybHS3XKyAJ
This commit is contained in:
shen
2026-08-31 20:02:12 +09:00
co-authored by Claude Sonnet 5
parent f4917a2b3b
commit 47baf6c0c6
414 changed files with 69568 additions and 385 deletions
+70
View File
@@ -0,0 +1,70 @@
# Third-party native dependencies
The GDExtension links three native libraries that are **not** part of Godot or
godot-cpp. Phase 1 (macOS) pulled them from Homebrew; that stops working the
moment we cross-compile for the Android NDK or the iOS SDK (BACKLOG F1/F2), so as
of 2026-08-30 all three are built from source as part of our own CMake build.
Everything lives under `extension/third_party/` and is wired by
`extension/third_party/CMakeLists.txt`, which exposes three aliases:
| Alias | Backing target | Consumed by |
|-----------------|------------------|------------------------|
| `mt3p::sodium` | `sodium` | `mtnet`, `mtpack`, `mtproto` |
| `mt3p::zstd` | `libzstd_static` | `mtpack` |
| `mt3p::minilzo` | `minilzo` | `mtproto` |
No source file changed: `#include <sodium.h>`, `#include <zstd.h>` and
`#include <lzo/lzo1x.h>` all still resolve (the last via a 1-line shim header,
see below).
## libsodium — via `robinlinden/libsodium-cmake`
* **Submodule:** `extension/third_party/libsodium-cmake` @ `9b2848d`
* itself carries `jedisct1/libsodium` @ `93a7d0d` (libsodium 1.0.20 line) as a
**nested** submodule — clones need `--recursive`.
* **Why the wrapper:** upstream libsodium is autotools-only. This MIT-licensed
wrapper is a pure CMakeLists over an untouched libsodium checkout; it generates
`version.h`, sets `CONFIGURED`, and builds clean for macOS / iOS / Android /
Windows. Used by many mobile projects.
* **Build options we force:** `SODIUM_DISABLE_TESTS=ON`, `SODIUM_MINIMAL=OFF`
(we need `crypto_kx`, `crypto_auth`, `crypto_aead_xchacha20poly1305`,
`crypto_stream_xchacha20`, `crypto_generichash`/BLAKE2b — all outside the
"minimal" set).
* **License:** ISC (libsodium) + MIT (wrapper). Ship-safe.
## libzstd — `facebook/zstd`
* **Submodule:** `extension/third_party/zstd` @ tag **v1.5.6** (`794ea1b0`).
* Built through upstream `build/cmake` with:
`ZSTD_BUILD_PROGRAMS/SHARED/TESTS/CONTRIB=OFF`, `ZSTD_BUILD_STATIC=ON`,
`ZSTD_LEGACY_SUPPORT=OFF`, `ZSTD_MULTITHREAD_SUPPORT=OFF` (the eterpack path
only does single-shot `ZSTD_compress`/`ZSTD_decompress`).
* Target consumed: `libzstd_static` (carries its own public include dir).
* **License:** BSD-3-Clause / GPLv2 dual. Ship-safe under BSD.
## miniLZO — vendored source (not a submodule)
* **Files:** `extension/third_party/minilzo/{minilzo.c,minilzo.h,lzoconf.h,lzodefs.h}`
copied verbatim from **lzo-2.10** (`minilzo.c` sha1 `019debb3…`), plus
`README.LZO`, `COPYING`, `AUTHORS` as required by the LZO license.
* Upstream LZO has no git repo (oberhumer.com tarball only), and miniLZO is a
4-file amalgamation, so it is copied in rather than submoduled.
* **Shim:** `minilzo/lzo/lzo1x.h` is a 1-line `#include "../minilzo.h"` so
`extension/src/proto/proto.cpp` keeps `#include <lzo/lzo1x.h>` unchanged.
miniLZO's API (`lzo_init`, `lzo1x_decompress_safe`, `LZO_E_OK`, `lzo_uint`) is a
strict subset of full LZO and covers everything the CLZO path uses.
* **License:** **GPLv2**. Acceptable for this internal, non-published,
non-commercial project on the same footing as `libgr2/src/oodle1.c` — but LZO
must be removed, replaced, or commercially licensed before any public release
or commercial use. (item_proto/mob_proto are the only LZO consumers; a
clean-room LZO1X decompressor is the eventual fix.)
## Rebuilding / fetching
`./build.sh` auto-runs `git submodule update --init --recursive` if any of the
three (godot-cpp, zstd, libsodium-cmake+libsodium) is missing. miniLZO needs no
fetch.
Homebrew `libsodium` / `zstd` / `lzo` are no longer referenced by the build and
can be uninstalled.