From b5f22e1874786bf0641bc0cfe1f6c2eedf0ff649 Mon Sep 17 00:00:00 2001 From: aszlig Date: Fri, 21 Jun 2019 04:37:37 +0200 Subject: pkgs/games: Add Warcraft II BNE This is supported by the Stratagus/Wargus engine and it's using the data files from the GOG version. I had this laying in the repository for a while but didn't commit and push it yet, so let's call it done by now :-) Signed-off-by: aszlig --- pkgs/games/gog/default.nix | 1 + pkgs/games/gog/warcraft2/default.nix | 148 +++++++++++++++++++++++++++++++++++ pkgs/games/gog/warcraft2/xdg.patch | 37 +++++++++ 3 files changed, 186 insertions(+) create mode 100644 pkgs/games/gog/warcraft2/default.nix create mode 100644 pkgs/games/gog/warcraft2/xdg.patch (limited to 'pkgs/games/gog') diff --git a/pkgs/games/gog/default.nix b/pkgs/games/gog/default.nix index 479dbc27..6588d6f2 100644 --- a/pkgs/games/gog/default.nix +++ b/pkgs/games/gog/default.nix @@ -24,6 +24,7 @@ let the-longest-journey = callPackage ./the-longest-journey {}; thimbleweed-park = callPackage ./thimbleweed-park.nix {}; war-for-the-overworld = callPackage ./war-for-the-overworld.nix {}; + warcraft2 = callPackage ./warcraft2 {}; wizard-of-legend = callPackage ./wizard-of-legend.nix {}; xeen = callPackage ./xeen.nix {}; }; diff --git a/pkgs/games/gog/warcraft2/default.nix b/pkgs/games/gog/warcraft2/default.nix new file mode 100644 index 00000000..c576439f --- /dev/null +++ b/pkgs/games/gog/warcraft2/default.nix @@ -0,0 +1,148 @@ +{ stdenv, lib, buildSandbox, writeTextFile, runCommand, fetchGog, fetchurl +, fetchFromGitHub, winePackages, xvfb_run, ffmpeg, rename + +# Dependencies for the Stratagus engine +, cmake, pkgconfig, toluapp, lua5_1, libpng, libmng, zlib, SDL, fluidsynth +, bzip2, libmikmod, libogg, libvorbis, libtheora, libGLU_combined, sqlite +}: + +let + timgm6mb = fetchurl { + name = "TimGM6mb.sf2"; + url = "https://sourceforge.net/p/mscore/code/3412/" + + "tree/trunk/mscore/share/sound/TimGM6mb.sf2?format=raw"; + sha256 = "0m68a5z43nirirq9rj2xzz6z5qpyhdwk40s83sqhr4lc09i8ndy5"; + }; + + stratagus = stdenv.mkDerivation { + name = "stratagus-${version}"; + version = "2.4.2git20190615"; + + src = fetchFromGitHub { + owner = "Wargus"; + repo = "stratagus"; + rev = "c7fc80ff7e89ab969d867121b6f679f81ea60ecb"; + sha256 = "1n39lxd8qg03kw884llcal3h95y34lys44hib2mdb3qhd5dg9a18"; + }; + + patches = [ ./xdg.patch ]; + + # Both check_version and detectPresence in addition to a bunch of functions + # in stratagus-tinyfiledialogs.h are trying to run various tools via + # /bin/sh, so let's NOP them out. + postPatch = '' + sed -i -e '/^int/!s/\(check_version\|detectPresence\)([^)]*)/1/g' \ + gameheaders/stratagus-game-launcher.h + sed -i -e '/^\(static \+\)\?int/!s/[a-zA-Z0-9]\+Present *([^)]*)/0/g' \ + gameheaders/stratagus-tinyfiledialogs.h + ''; + + NIX_CFLAGS_COMPILE = [ "-Wno-error=format-overflow" ]; + cmakeFlags = [ + "-DOpenGL_GL_PREFERENCE=GLVND" "-DENABLE_DEV=ON" + "-DGAMEDIR=${placeholder "out"}/bin" + ]; + nativeBuildInputs = [ cmake pkgconfig toluapp ]; + buildInputs = [ + toluapp lua5_1 libpng libmng zlib SDL fluidsynth bzip2 libmikmod libogg + libvorbis libtheora libGLU_combined sqlite + ]; + }; + + stormlib = stdenv.mkDerivation { + name = "stormlib-${version}"; + version = "9.22git20190615"; + + src = fetchFromGitHub { + owner = "ladislav-zezula"; + repo = "StormLib"; + rev = "2f0e0e69e6b3739d7c450ac3d38816aee45ac3c2"; + sha256 = "04f43c6bwfxiiw1kplxb3ds8g9r633y587z8ir97hrrzw5nmni3w"; + }; + + nativeBuildInputs = [ cmake ]; + buildInputs = [ zlib bzip2 ]; + }; + + wargus = stdenv.mkDerivation { + name = "wargus-${version}"; + version = "2.4.2git20190615"; + + src = fetchFromGitHub { + owner = "Wargus"; + repo = "wargus"; + rev = "932c4974dfea9805f6710f254de191e65dadb50d"; + sha256 = "13vpfd4yx43n5sqzj79km7gcv9al3mqskkij335f0c9p28rqf47v"; + }; + + # This fixes up the data path by letting it be set using an environment + # variable later in the wrapper and also hardcodes the MuseScore sound + # font. + # + # In addition, wartool.cpp contains a few lines like this: + # + # sprintf(extract, "%s.something", extract); + # + # The problem here is that sprintf() modifies the data pointed by extract + # *IN PLACE*, so this essentially truncates the contents to ".something". + # + # While it may be even better to use strncat() here, the application isn't + # critical for security, so for the sake of laziness, let's just use + # strcat() instead. + postPatch = '' + sed -i -e ' + s/^\( *# *define \+DATA_PATH\).*/\1 getenv("WARGUS_DATAPATH")/ + ' wargus.cpp + + sed -i -e 's!"[^"]*\/TimGM6mb.sf2"!"${timgm6mb}"!g' \ + wargus.cpp scripts/stratagus.lua + + sed -i -e ' + s/sprintf( *\([^,]\+\), "%s\([^"]\+\)", *\1 *)/strcat(\1, "\2")/ + ' wartool.cpp + + # XXX: Crashes the game, see https://github.com/Wargus/wargus/issues/260 + rm -r scripts/lists/campaigns/For\ the\ Motherland\ * + ''; + + cmakeFlags = [ "-DGAMEDIR=${placeholder "out"}/bin" ]; + nativeBuildInputs = [ cmake pkgconfig ]; + buildInputs = [ stratagus zlib libpng bzip2 stormlib ]; + }; + + version = "2.02.4"; + + # XXX: Unfortunately, innoextract (even Git master) doesn't support this + # archive, so let's resort to a headless wine for extraction. + gameData = runCommand "warcraft2-data-${version}" { + src = fetchGog { + name = "setup-warcraft-2-${version}.exe"; + productId = 1418669891; + downloadName = "en1installer0"; + sha256 = "1cf3c1ylgdrvkk7y25v47f66m6lp9m4wvl2aldpxzrrqdrlk34k3"; + }; + nativeBuildInputs = [ winePackages.minimal xvfb_run ffmpeg wargus rename ]; + } '' + export WINEPREFIX="$PWD" + wine wineboot.exe + xvfb-run -s '-screen 0 1024x768x24' wine "$src" /sp- /lang=english /silent + gameDir='drive_c/GOG Games/Warcraft II BNE' + find "$gameDir" -mindepth 1 -depth \ + -exec rename 's/(.*)\/([^\/]*)/$1\/\L$2/' {} \; + wartool -v -r "$gameDir" "$out" + cp -rnst "$out" ${lib.escapeShellArg wargus}/share/games/stratagus/wargus/* + ''; + +in buildSandbox (writeTextFile { + name = "warcraft2-${version}"; + destination = "/bin/warcraft2"; + executable = true; + text = '' + #!${stdenv.shell} + export WARGUS_DATAPATH=${lib.escapeShellArg gameData} + exec ${lib.escapeShellArg "${wargus}/bin/wargus"} "$@" + ''; +}) { + paths.required = [ "$XDG_DATA_HOME/wc2" ]; + paths.runtimeVars = [ "LD_LIBRARY_PATH" ]; +} diff --git a/pkgs/games/gog/warcraft2/xdg.patch b/pkgs/games/gog/warcraft2/xdg.patch new file mode 100644 index 00000000..979a86e3 --- /dev/null +++ b/pkgs/games/gog/warcraft2/xdg.patch @@ -0,0 +1,37 @@ +diff --git a/src/stratagus/parameters.cpp b/src/stratagus/parameters.cpp +index a705ba21d..8585856b0 100644 +--- a/src/stratagus/parameters.cpp ++++ b/src/stratagus/parameters.cpp +@@ -48,26 +48,13 @@ void Parameters::SetDefaultValues() + + void Parameters::SetDefaultUserDirectory() + { +-#ifdef USE_GAME_DIR +- userDirectory = StratagusLibPath; +-#elif USE_WIN32 +- userDirectory = getenv("APPDATA"); +-#else +- userDirectory = getenv("HOME"); +-#endif +- +- if (!userDirectory.empty()) { +- userDirectory += "/"; ++ const char *xdg_data_home = getenv("XDG_DATA_HOME"); ++ if (xdg_data_home == NULL) { ++ userDirectory = getenv("HOME"); ++ userDirectory += "/.local/share"; ++ } else { ++ userDirectory = xdg_data_home; + } +- +-#ifdef USE_GAME_DIR +-#elif USE_WIN32 +- userDirectory += "Stratagus"; +-#elif defined(USE_MAC) +- userDirectory += "Library/Stratagus"; +-#else +- userDirectory += ".stratagus"; +-#endif + } + + static std::string GetLocalPlayerNameFromEnv() -- cgit 1.4.1