Build Windows #3
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| # Build Windows (x86_64, MSYS2/MinGW) | |
| # Output: Portable zip + installer published to Dropbox. | |
| name: Build Windows | |
| on: | |
| workflow_dispatch: | |
| workflow_call: | |
| outputs: | |
| zip_url: | |
| description: Dropbox direct URL for rolling zip (pylux-latest or pylux-beta-latest on release/beta) | |
| value: ${{ jobs.build-windows_x64-msys2.outputs.zip_url }} | |
| installer_url: | |
| description: Dropbox direct URL for rolling installer (installer-latest or installer-beta-latest on release/beta) | |
| value: ${{ jobs.build-windows_x64-msys2.outputs.installer_url }} | |
| chiaki_version: | |
| description: Pylux version from CMakeLists.txt | |
| value: ${{ jobs.build-windows_x64-msys2.outputs.chiaki_version }} | |
| concurrency: | |
| group: build-windows-${{ github.ref }} | |
| cancel-in-progress: true | |
| env: | |
| CHIAKI_ENABLE_STEAMWORKS: "OFF" | |
| jobs: | |
| build-windows_x64-msys2: | |
| name: Build Pylux Windows x86_64 | |
| runs-on: windows-latest | |
| outputs: | |
| zip_url: ${{ steps.zip.outputs.url }} | |
| installer_url: ${{ steps.installer.outputs.url }} | |
| chiaki_version: ${{ steps.extract_version.outputs.version }} | |
| defaults: | |
| run: | |
| shell: msys2 {0} | |
| steps: | |
| - name: Disable autocrlf | |
| shell: pwsh | |
| run: | | |
| git config --global core.autocrlf false | |
| git config --global core.eol lf | |
| - uses: actions/checkout@v4 | |
| with: | |
| submodules: recursive | |
| - uses: msys2/setup-msys2@v2 | |
| with: | |
| msystem: mingw64 | |
| update: true | |
| install: git | |
| pacboy: >- | |
| ca-certificates:p | |
| cc:p | |
| cmake:p | |
| curl:p | |
| diffutils:p | |
| fast_float:p | |
| fftw:p | |
| hidapi:p | |
| json-c:p | |
| lcms2:p | |
| libdovi:p | |
| meson:p | |
| miniupnpc:p | |
| gcc:p | |
| nasm:p | |
| ninja:p | |
| openssl:p | |
| opus:p | |
| pkgconf:p | |
| protobuf:p | |
| python:p | |
| python-psutil:p | |
| python-glad:p | |
| python-jinja:p | |
| python-pip:p | |
| qt6-base:p | |
| qt6-declarative:p | |
| qt6-svg:p | |
| SDL2:p | |
| shaderc:p | |
| speexdsp:p | |
| spirv-cross:p | |
| vulkan:p | |
| vulkan-headers:p | |
| - name: Install python protobuf and zip | |
| run: | | |
| pip install protobuf | |
| pacman -S git make unzip zip jq --noconfirm | |
| - name: Build libbplacebo | |
| run: | | |
| scripts/build-libplacebo-windows.sh | |
| - name: Setup ffmpeg | |
| run: | | |
| curl -LO https://github.com/streetpea/FFmpeg-Builds/releases/download/latest/ffmpeg-n7.1-latest-win64-gpl-shared-7.1.zip | |
| unzip ffmpeg-n7.1-latest-win64-gpl-shared-7.1.zip | |
| cp -a "ffmpeg-n7.1-latest-win64-gpl-shared-7.1/bin/." /mingw64/bin | |
| cp -a "ffmpeg-n7.1-latest-win64-gpl-shared-7.1/include/." /mingw64/include | |
| cp -a "ffmpeg-n7.1-latest-win64-gpl-shared-7.1/lib/." /mingw64/lib | |
| - name: Add QmlWebEngine Import | |
| run: | | |
| cp scripts/qtwebengine_import.qml gui/src/qml/ | |
| - name: Configure Pylux | |
| run: | | |
| cmake -S . -B build -G "Ninja" -DCMAKE_BUILD_TYPE=Release -DCHIAKI_ENABLE_CLI=OFF -DCHIAKI_ENABLE_STEAMWORKS=${{ env.CHIAKI_ENABLE_STEAMWORKS }} -DCHIAKI_ENABLE_STEAM_SHORTCUT=ON | |
| - name: Build Pylux | |
| run: | | |
| cmake --build build --config Release --clean-first --target chiaki | |
| - name: Package Pylux | |
| run: | | |
| mkdir pylux | |
| cp build/gui/chiaki.exe pylux/pylux.exe | |
| if [ "${{ env.CHIAKI_ENABLE_STEAMWORKS }}" = "ON" ]; then | |
| cp third-party/steamworks/steamworks_sdk/redistributable_bin/win64/steam_api64.dll pylux/ | |
| cp steam_appid.txt pylux/ 2>/dev/null || echo "Warning: steam_appid.txt not found" | |
| fi | |
| export PATH="${{ github.workspace }}/build/third-party/cpp-steam-tools:/mingw64/share/qt6/bin/:/mingw64/bin/:${PATH}" | |
| export QT_PLUGIN_PATH="/mingw64/share/qt6/plugins" | |
| export QML2_IMPORT_PATH="/mingw64/share/qt6/qml" | |
| copy_dll_dep() { | |
| for dep; do | |
| case "$dep" in | |
| ""|*"/Windows/"*|*"/WINDOWS/"*|*"/System32/"*|*"/SYSTEM32/"*|*"/SysWOW64/"*|*"/SYSWOW64/"*) | |
| continue | |
| ;; | |
| esac | |
| if [ -f "$dep" ] && [ ! -e "pylux/${dep##*/}" ]; then | |
| echo "Copied $dep" | |
| cp "$dep" pylux/ | |
| echo "$dep" >> tmp0.txt | |
| fi | |
| done | |
| } | |
| # Recursively find and copy DLL dependencies of pylux.exe | |
| echo pylux/pylux.exe > tmp0.txt | |
| while [ -e tmp0.txt ] | |
| do | |
| cp tmp0.txt tmp.txt | |
| rm tmp0.txt | |
| sort -u tmp.txt -o tmp.txt | |
| ldd $(<tmp.txt) | awk '($2 == "=>") { print $3 }' | xargs -r copy_dll_dep | |
| done | |
| # Copy Qt plugins and QML modules | |
| windeployqt6.exe --no-translations --qmldir=gui/src/qml pylux/pylux.exe | |
| # Copy dependencies of Qt plugins (windeployqt6 doesn't copy plugin dependencies like libjpeg-8.dll) | |
| echo "Finding Qt plugin DLLs..." | |
| find pylux -type d \( -name plugins -o -name imageformats -o -name platforms -o -name sqldrivers \) -exec find {} -name "*.dll" \; | while read plugin; do | |
| echo "Found plugin: $plugin" | |
| echo "$plugin" >> tmp0.txt | |
| done | |
| echo "Copying plugin dependencies..." | |
| while [ -e tmp0.txt ] && [ -s tmp0.txt ] | |
| do | |
| cp tmp0.txt tmp.txt | |
| rm tmp0.txt | |
| sort -u tmp.txt -o tmp.txt | |
| ldd $(<tmp.txt) 2>/dev/null | awk '($2 == "=>") { print $3 }' | while read -r dep; do | |
| case "$dep" in | |
| ""|*"/Windows/"*|*"/WINDOWS/"*|*"/System32/"*|*"/SYSTEM32/"*|*"/SysWOW64/"*|*"/SYSWOW64/"*) | |
| continue | |
| ;; | |
| esac | |
| if [ -f "$dep" ] && [ ! -e "pylux/${dep##*/}" ]; then | |
| echo " Copying plugin dependency: ${dep##*/}" | |
| cp "$dep" pylux/ | |
| echo "$dep" >> tmp0.txt | |
| fi | |
| done | |
| done | |
| rm -f tmp0.txt tmp.txt | |
| - name: Create zip archive | |
| run: | | |
| zip -r pylux.zip pylux | |
| echo "RELEASE_PACKAGE_PATH=pylux.zip" >> $GITHUB_ENV | |
| - name: Extract version | |
| id: extract_version | |
| uses: ./.github/actions/extract-version | |
| - name: Compile .ISS to .EXE Installer | |
| uses: Minionguyjpro/Inno-Setup-Action@v1.2.2 | |
| with: | |
| path: "scripts/chiaki-ng.iss" | |
| options: /O+ | |
| - name: Rename installer with version | |
| run: | | |
| INSTALLER_NAME="pylux-windows-installer-${{ env.CHIAKI_VERSION }}.exe" | |
| cp pylux-windows-installer.exe "${INSTALLER_NAME}" | |
| echo "INSTALLER_NAME=${INSTALLER_NAME}" >> $GITHUB_ENV | |
| echo "Renamed installer to: ${INSTALLER_NAME}" | |
| - name: Publish portable zip | |
| id: zip | |
| uses: ./.github/actions/dropbox-publish | |
| with: | |
| file: ${{ env.RELEASE_PACKAGE_PATH }} | |
| latest-path: /pylux/windows/pylux${{ github.ref_name == 'release/beta' && '-beta' || '' }}-latest.zip | |
| versioned-path: /pylux/windows/pylux-${{ env.CHIAKI_VERSION }}.zip | |
| refresh-token: ${{ secrets.DROPBOX_REFRESH_TOKEN }} | |
| app-key: ${{ secrets.DROPBOX_APP_KEY }} | |
| app-secret: ${{ secrets.DROPBOX_APP_SECRET }} | |
| - name: Publish installer | |
| id: installer | |
| uses: ./.github/actions/dropbox-publish | |
| with: | |
| file: ${{ env.INSTALLER_NAME }} | |
| latest-path: /pylux/windows/pylux-windows-installer${{ github.ref_name == 'release/beta' && '-beta' || '' }}-latest.exe | |
| versioned-path: /pylux/windows/pylux-windows-installer-${{ env.CHIAKI_VERSION }}.exe | |
| refresh-token: ${{ secrets.DROPBOX_REFRESH_TOKEN }} | |
| app-key: ${{ secrets.DROPBOX_APP_KEY }} | |
| app-secret: ${{ secrets.DROPBOX_APP_SECRET }} | |
| - name: Build summary | |
| if: always() | |
| run: | | |
| ZIP_SIZE=$(ls -lh "${{ env.RELEASE_PACKAGE_PATH }}" 2>/dev/null | awk '{print $5}') | |
| INST_SIZE=$(ls -lh "${{ env.INSTALLER_NAME }}" 2>/dev/null | awk '{print $5}') | |
| if [ "${{ github.ref_name }}" = "release/beta" ]; then | |
| ROLLING_LABEL="rolling (beta: pylux-beta-latest.* / installer-beta-latest)" | |
| ZIP_NAME="pylux-beta-latest.zip" | |
| INST_NAME="pylux-windows-installer-beta-latest.exe" | |
| else | |
| ROLLING_LABEL="rolling (stable: pylux-latest.* / installer-latest)" | |
| ZIP_NAME="pylux-latest.zip" | |
| INST_NAME="pylux-windows-installer-latest.exe" | |
| fi | |
| { | |
| echo "## Pylux Windows — v${CHIAKI_VERSION}" | |
| echo "" | |
| echo "| Artifact | Size | Download (${ROLLING_LABEL}) | Versioned archive |" | |
| echo "| --- | --- | --- | --- |" | |
| echo "| Portable zip | ${ZIP_SIZE:-?} | [${ZIP_NAME}](${{ steps.zip.outputs.url }}) | \`/pylux/windows/pylux-${CHIAKI_VERSION}.zip\` |" | |
| echo "| Installer (.exe) | ${INST_SIZE:-?} | [${INST_NAME}](${{ steps.installer.outputs.url }}) | \`/pylux/windows/pylux-windows-installer-${CHIAKI_VERSION}.exe\` |" | |
| echo "" | |
| echo "### How to use" | |
| echo "- **Portable zip** — unzip anywhere and run \`pylux.exe\`. No install required." | |
| echo "- **Installer (.exe)** — run and follow the prompts; adds Start Menu shortcuts." | |
| } >> "$GITHUB_STEP_SUMMARY" | |