Compare commits

..

1 Commits

Author SHA1 Message Date
Luke Street 625f752fb9 Try Android CI 2026-05-10 00:26:00 -06:00
174 changed files with 1453 additions and 7687 deletions
+12 -12
View File
@@ -10,7 +10,7 @@ on:
env: env:
SCCACHE_GHA_ENABLED: "true" SCCACHE_GHA_ENABLED: "true"
RUSTC_WRAPPER: "sccache" RUSTC_WRAPPER: "sccache"
SENTRY_DSN: ${{ secrets.SENTRY_DSN }} # SENTRY_DSN: ${{ secrets.SENTRY_DSN }}
jobs: jobs:
build-linux: build-linux:
@@ -50,7 +50,7 @@ jobs:
libxss-dev libfuse2 libusb-1.0-0-dev libdecor-0-dev libpipewire-0.3-dev libunwind-dev libxss-dev libfuse2 libusb-1.0-0-dev libdecor-0-dev libpipewire-0.3-dev libunwind-dev
- name: Setup sccache - name: Setup sccache
uses: mozilla-actions/sccache-action@v0.0.10 uses: mozilla-actions/sccache-action@v0.0.9
- name: Print sccache stats - name: Print sccache stats
run: sccache --show-stats run: sccache --show-stats
@@ -67,9 +67,9 @@ jobs:
- name: Upload artifacts - name: Upload artifacts
uses: actions/upload-artifact@v7 uses: actions/upload-artifact@v7
with: with:
name: dusklight-${{env.DUSK_VERSION}}-linux-${{matrix.preset}}-${{matrix.artifact_arch}} name: dusk-${{env.DUSK_VERSION}}-linux-${{matrix.preset}}-${{matrix.artifact_arch}}
path: | path: |
build/install/Dusklight-*.AppImage build/install/Dusk-*.AppImage
build/install/debug.tar.* build/install/debug.tar.*
build-apple: build-apple:
@@ -124,7 +124,7 @@ jobs:
rustup target add x86_64-apple-darwin rustup target add x86_64-apple-darwin
- name: Setup sccache - name: Setup sccache
uses: mozilla-actions/sccache-action@v0.0.10 uses: mozilla-actions/sccache-action@v0.0.9
- name: Configure CMake - name: Configure CMake
run: cmake --preset ${{matrix.preset}} run: cmake --preset ${{matrix.preset}}
@@ -135,9 +135,9 @@ jobs:
- name: Upload artifacts - name: Upload artifacts
uses: actions/upload-artifact@v7 uses: actions/upload-artifact@v7
with: with:
name: dusklight-${{env.DUSK_VERSION}}-${{matrix.artifact_name}} name: dusk-${{env.DUSK_VERSION}}-${{matrix.artifact_name}}
path: | path: |
build/install/Dusklight.app build/install/Dusk.app
build/install/debug.tar.* build/install/debug.tar.*
build-android: build-android:
@@ -175,7 +175,7 @@ jobs:
java-version: 17 java-version: 17
- name: Setup Android SDK - name: Setup Android SDK
uses: android-actions/setup-android@v4 uses: android-actions/setup-android@v3
- name: Install Android SDK packages - name: Install Android SDK packages
run: sdkmanager "platforms;android-36" "build-tools;36.1.0" "ndk;${ANDROID_NDK_VERSION}" run: sdkmanager "platforms;android-36" "build-tools;36.1.0" "ndk;${ANDROID_NDK_VERSION}"
@@ -186,13 +186,13 @@ jobs:
rustup target add ${{matrix.rust_target}} rustup target add ${{matrix.rust_target}}
- name: Setup sccache - name: Setup sccache
uses: mozilla-actions/sccache-action@v0.0.10 uses: mozilla-actions/sccache-action@v0.0.9
- name: Configure CMake - name: Configure CMake
run: cmake --preset ${{matrix.preset}} run: cmake --preset ${{matrix.preset}}
- name: Build native library - name: Build native library
run: cmake --build --preset ${{matrix.preset}} --target dusklight run: cmake --build --preset ${{matrix.preset}} --target dusk
- name: Stage stripped JNI library - name: Stage stripped JNI library
run: ANDROID_STAGE_ABIS="${{matrix.abi}}" platforms/android/scripts/stage-jni-libs.sh run: ANDROID_STAGE_ABIS="${{matrix.abi}}" platforms/android/scripts/stage-jni-libs.sh
@@ -204,7 +204,7 @@ jobs:
- name: Upload artifacts - name: Upload artifacts
uses: actions/upload-artifact@v7 uses: actions/upload-artifact@v7
with: with:
name: dusklight-${{env.DUSK_VERSION}}-android-${{matrix.artifact_arch}} name: dusk-${{env.DUSK_VERSION}}-android-${{matrix.artifact_arch}}
path: platforms/android/app/build/outputs/apk/release/app-${{matrix.abi}}-release-unsigned.apk path: platforms/android/app/build/outputs/apk/release/app-${{matrix.abi}}-release-unsigned.apk
build-windows: build-windows:
@@ -266,7 +266,7 @@ jobs:
- name: Upload artifacts - name: Upload artifacts
uses: actions/upload-artifact@v7 uses: actions/upload-artifact@v7
with: with:
name: dusklight-${{env.DUSK_VERSION}}-win32-msvc-${{matrix.artifact_arch}} name: dusk-${{env.DUSK_VERSION}}-win32-msvc-${{matrix.artifact_arch}}
path: | path: |
build/install/*.exe build/install/*.exe
build/install/*.dll build/install/*.dll
-4
View File
@@ -41,10 +41,6 @@ compile_commands.json
# MacOS # MacOS
.DS_Store .DS_Store
# direnv / nix
.direnv/
.envrc
# ISOs # ISOs
*.iso *.iso
+1 -1
View File
@@ -2,7 +2,7 @@
"version": "0.2.0", "version": "0.2.0",
"configurations": [ "configurations": [
{ {
"name": "(gdb) Launch Dusklight MSVC", "name": "(gdb) Launch Dusk MSVC",
"type": "cppvsdbg", "type": "cppvsdbg",
"request": "launch", "request": "launch",
"program": "${command:cmake.launchTargetPath}", "program": "${command:cmake.launchTargetPath}",
+1 -1
View File
@@ -1,5 +1,5 @@
{ {
"cmake.buildDirectory": "${workspaceFolder}/build/dusklight/${buildType}/${variant:tp_version}", "cmake.buildDirectory": "${workspaceFolder}/build/dusk/${buildType}/${variant:tp_version}",
"cmake.generator": "Ninja", "cmake.generator": "Ninja",
"cmake.configureSettings": { "cmake.configureSettings": {
"CMAKE_EXPORT_COMPILE_COMMANDS": "ON" "CMAKE_EXPORT_COMPILE_COMMANDS": "ON"
+53 -82
View File
@@ -5,19 +5,8 @@ if (NOT CMAKE_BUILD_TYPE)
"Build type options: Debug Release RelWithDebInfo MinSizeRel" FORCE) "Build type options: Debug Release RelWithDebInfo MinSizeRel" FORCE)
endif () endif ()
set(DUSK_VERSION_OVERRIDE "" CACHE STRING "Override version string (skips git detection and format validation)") # obtain revision info from git
find_package(Git)
if (DUSK_VERSION_OVERRIDE)
set(DUSK_WC_DESCRIBE "${DUSK_VERSION_OVERRIDE}")
set(DUSK_VERSION_STRING "0.0.0.0")
set(DUSK_SHORT_VERSION_STRING "0.0.0")
set(DUSK_WC_REVISION "")
set(DUSK_WC_BRANCH "")
set(DUSK_WC_DATE "")
message(STATUS "Dusklight version overridden to ${DUSK_WC_DESCRIBE}")
else ()
# obtain revision info from git
find_package(Git)
if (GIT_FOUND) if (GIT_FOUND)
# make sure version information gets re-run when the current Git HEAD changes # make sure version information gets re-run when the current Git HEAD changes
execute_process(WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND ${GIT_EXECUTABLE} rev-parse --git-path HEAD execute_process(WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} COMMAND ${GIT_EXECUTABLE} rev-parse --git-path HEAD
@@ -74,15 +63,13 @@ else ()
set(DUSK_SHORT_VERSION_STRING "0.0.0") set(DUSK_SHORT_VERSION_STRING "0.0.0")
endif () endif ()
endif ()
# Add version information to CI environment variables # Add version information to CI environment variables
if(DEFINED ENV{GITHUB_ENV}) if(DEFINED ENV{GITHUB_ENV})
file(APPEND "$ENV{GITHUB_ENV}" "DUSK_VERSION=${DUSK_WC_DESCRIBE}\n") file(APPEND "$ENV{GITHUB_ENV}" "DUSK_VERSION=${DUSK_WC_DESCRIBE}\n")
endif() endif()
message(STATUS "Dusklight version set to ${DUSK_WC_DESCRIBE}") message(STATUS "Dusk version set to ${DUSK_WC_DESCRIBE}")
message(STATUS "Build type: ${CMAKE_BUILD_TYPE}") message(STATUS "Build type: ${CMAKE_BUILD_TYPE}")
project(dusklight LANGUAGES C CXX VERSION ${DUSK_VERSION_STRING}) project(dusk LANGUAGES C CXX VERSION ${DUSK_VERSION_STRING})
if (APPLE) if (APPLE)
enable_language(OBJC OBJCXX) enable_language(OBJC OBJCXX)
endif () endif ()
@@ -125,6 +112,11 @@ option(DUSK_BUILD_WARNINGS "Enable compiler warnings (off by default)")
option(DUSK_SELECTED_OPT "If on, selected parts of the project will be compiled with optimizations on Debug, intending to make the game run at 30 FPS. Note for MSVC: you will need to remove '/RTC1' from your debug flags in CMake.") option(DUSK_SELECTED_OPT "If on, selected parts of the project will be compiled with optimizations on Debug, intending to make the game run at 30 FPS. Note for MSVC: you will need to remove '/RTC1' from your debug flags in CMake.")
option(DUSK_MOVIE_SUPPORT "If on, compile against libjpeg-turbo to enable THP file decoding" ON) option(DUSK_MOVIE_SUPPORT "If on, compile against libjpeg-turbo to enable THP file decoding" ON)
option(DUSK_ENABLE_UPDATE_CHECKER "Enable update checking support" ON) option(DUSK_ENABLE_UPDATE_CHECKER "Enable update checking support" ON)
if(ANDROID)
set(DUSK_MOVIE_SUPPORT OFF)
endif ()
option(DUSK_ENABLE_SENTRY_NATIVE "Enable sentry-native crash reporting support" OFF) option(DUSK_ENABLE_SENTRY_NATIVE "Enable sentry-native crash reporting support" OFF)
set(DUSK_SENTRY_DSN "" CACHE STRING "Sentry DSN") set(DUSK_SENTRY_DSN "" CACHE STRING "Sentry DSN")
set(DUSK_SENTRY_ENVIRONMENT "development" CACHE STRING "Sentry environment") set(DUSK_SENTRY_ENVIRONMENT "development" CACHE STRING "Sentry environment")
@@ -142,9 +134,9 @@ endif ()
if (DUSK_MOVIE_SUPPORT) if (DUSK_MOVIE_SUPPORT)
find_package(libjpeg-turbo 3.0 CONFIG QUIET) find_package(libjpeg-turbo 3.0 CONFIG QUIET)
if (libjpeg-turbo_FOUND) if (libjpeg-turbo_FOUND)
message(STATUS "dusklight: Using system libjpeg-turbo") message(STATUS "dusk: Using system libjpeg-turbo")
else () else ()
message(STATUS "dusklight: Fetching libjpeg-turbo") message(STATUS "dusk: Fetching libjpeg-turbo")
include(ExternalProject) include(ExternalProject)
set(_jpeg_install_dir ${CMAKE_BINARY_DIR}/libjpeg-turbo-install) set(_jpeg_install_dir ${CMAKE_BINARY_DIR}/libjpeg-turbo-install)
if (WIN32) if (WIN32)
@@ -163,8 +155,6 @@ if (DUSK_MOVIE_SUPPORT)
list(APPEND _jpeg_cmake_args -DCMAKE_TOOLCHAIN_FILE=${_jpeg_toolchain_file}) list(APPEND _jpeg_cmake_args -DCMAKE_TOOLCHAIN_FILE=${_jpeg_toolchain_file})
endif () endif ()
set(_jpeg_passthrough_vars set(_jpeg_passthrough_vars
ANDROID_ABI
ANDROID_PLATFORM
CMAKE_BUILD_TYPE CMAKE_BUILD_TYPE
CMAKE_C_COMPILER CMAKE_C_COMPILER
CMAKE_C_COMPILER_LAUNCHER CMAKE_C_COMPILER_LAUNCHER
@@ -236,13 +226,13 @@ endif ()
include(FetchContent) include(FetchContent)
# Declare all dependencies first so CMake can download them in parallel # Declare all dependencies first so CMake can download them in parallel
message(STATUS "dusklight: Fetching cxxopts") message(STATUS "dusk: Fetching cxxopts")
FetchContent_Declare(cxxopts FetchContent_Declare(cxxopts
URL https://github.com/jarro2783/cxxopts/archive/refs/tags/v3.3.1.tar.gz URL https://github.com/jarro2783/cxxopts/archive/refs/tags/v3.3.1.tar.gz
URL_HASH SHA256=3bfc70542c521d4b55a46429d808178916a579b28d048bd8c727ee76c39e2072 URL_HASH SHA256=3bfc70542c521d4b55a46429d808178916a579b28d048bd8c727ee76c39e2072
DOWNLOAD_EXTRACT_TIMESTAMP TRUE DOWNLOAD_EXTRACT_TIMESTAMP TRUE
) )
message(STATUS "dusklight: Fetching nlohmann/json") message(STATUS "dusk: Fetching nlohmann/json")
FetchContent_Declare(json FetchContent_Declare(json
URL https://github.com/nlohmann/json/releases/download/v3.12.0/json.tar.xz URL https://github.com/nlohmann/json/releases/download/v3.12.0/json.tar.xz
URL_HASH SHA256=42f6e95cad6ec532fd372391373363b62a14af6d771056dbfc86160e6dfff7aa URL_HASH SHA256=42f6e95cad6ec532fd372391373363b62a14af6d771056dbfc86160e6dfff7aa
@@ -251,7 +241,7 @@ FetchContent_Declare(json
FetchContent_MakeAvailable(cxxopts json) FetchContent_MakeAvailable(cxxopts json)
if (DUSK_ENABLE_SENTRY_NATIVE) if (DUSK_ENABLE_SENTRY_NATIVE)
message(STATUS "dusklight: Fetching sentry-native") message(STATUS "dusk: Fetching sentry-native")
set(SENTRY_BUILD_SHARED_LIBS OFF CACHE BOOL "" FORCE) set(SENTRY_BUILD_SHARED_LIBS OFF CACHE BOOL "" FORCE)
set(SENTRY_BACKEND crashpad CACHE STRING "" FORCE) set(SENTRY_BACKEND crashpad CACHE STRING "" FORCE)
if (WIN32) if (WIN32)
@@ -276,12 +266,6 @@ if (DUSK_ENABLE_SENTRY_NATIVE)
endif () endif ()
endif () endif ()
# Use signed char on ARM to match the original game (and x86)
string(TOLOWER "${CMAKE_SYSTEM_PROCESSOR}" _arch)
if(_arch MATCHES "^(arm|aarch64)" AND CMAKE_CXX_COMPILER_FRONTEND_VARIANT STREQUAL "GNU")
add_compile_options(-fsigned-char)
endif()
if (CMAKE_SYSTEM_NAME STREQUAL Windows) if (CMAKE_SYSTEM_NAME STREQUAL Windows)
set(PLATFORM_NAME win32) set(PLATFORM_NAME win32)
elseif (CMAKE_SYSTEM_NAME STREQUAL Darwin) elseif (CMAKE_SYSTEM_NAME STREQUAL Darwin)
@@ -302,15 +286,15 @@ include(files.cmake)
# TODO: version handling for res includes # TODO: version handling for res includes
set(DUSK_BUNDLE_NAME Dusklight) set(DUSK_BUNDLE_NAME Dusk)
set(DUSK_BUNDLE_IDENTIFIER dev.twilitrealm.dusk) set(DUSK_BUNDLE_IDENTIFIER dev.twilitrealm.dusk)
set(DUSK_COMPANY_NAME "Twilit Realm") set(DUSK_COMPANY_NAME "Twilit Realm")
set(DUSK_FILE_DESCRIPTION "Dusklight") set(DUSK_FILE_DESCRIPTION "Dusk")
set(DUSK_PRODUCT_NAME "Dusklight") set(DUSK_PRODUCT_NAME "Dusk")
set(DUSK_COPYRIGHT "Copyright (C) Twilit Realm contributors") set(DUSK_COPYRIGHT "Copyright (C) Twilit Realm contributors")
source_group("dolzel" FILES ${DOLZEL_FILES} ${Z2AUDIOLIB_FILES} ${REL_FILES}) source_group("dolzel" FILES ${DOLZEL_FILES} ${Z2AUDIOLIB_FILES} ${REL_FILES})
source_group("dusklight" FILES ${DUSK_FILES} ${DUSK_HTTP_BACKEND_FILES}) source_group("dusk" FILES ${DUSK_FILES} ${DUSK_HTTP_BACKEND_FILES})
set(GAME_COMPILE_DEFS TARGET_PC WIDESCREEN_SUPPORT=1 AVOID_UB=1 VERSION=0 MTX_USE_PS=1) set(GAME_COMPILE_DEFS TARGET_PC WIDESCREEN_SUPPORT=1 AVOID_UB=1 VERSION=0 MTX_USE_PS=1)
@@ -347,30 +331,30 @@ if (DUSK_ENABLE_UPDATE_CHECKER)
set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/winhttp.cpp) set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/winhttp.cpp)
list(APPEND GAME_LIBS winhttp) list(APPEND GAME_LIBS winhttp)
list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_WINHTTP=1) list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_WINHTTP=1)
message(STATUS "dusklight: Enabled update checker (WinHTTP)") message(STATUS "dusk: Enabled update checker (WinHTTP)")
elseif (ANDROID) elseif (ANDROID)
set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/android.cpp) set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/android.cpp)
list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_ANDROID=1) list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_ANDROID=1)
message(STATUS "dusklight: Enabled update checker (Android)") message(STATUS "dusk: Enabled update checker (Android)")
elseif (APPLE) elseif (APPLE)
find_library(FOUNDATION_FRAMEWORK Foundation REQUIRED) find_library(FOUNDATION_FRAMEWORK Foundation REQUIRED)
set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/url_session.mm) set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/url_session.mm)
set_source_files_properties(src/dusk/http/url_session.mm PROPERTIES COMPILE_FLAGS -fobjc-arc) set_source_files_properties(src/dusk/http/url_session.mm PROPERTIES COMPILE_FLAGS -fobjc-arc)
list(APPEND GAME_LIBS ${FOUNDATION_FRAMEWORK}) list(APPEND GAME_LIBS ${FOUNDATION_FRAMEWORK})
list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_URLSESSION=1) list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_URLSESSION=1)
message(STATUS "dusklight: Enabled update checker (NSURLSession)") message(STATUS "dusk: Enabled update checker (NSURLSession)")
elseif (CMAKE_SYSTEM_NAME STREQUAL Linux) elseif (CMAKE_SYSTEM_NAME STREQUAL Linux)
find_package(CURL QUIET OPTIONAL_COMPONENTS HTTPS SSL) find_package(CURL QUIET OPTIONAL_COMPONENTS HTTPS SSL)
if (CURL_FOUND AND CURL_HTTPS_FOUND AND CURL_SSL_FOUND) if (CURL_FOUND AND CURL_HTTPS_FOUND AND CURL_SSL_FOUND)
set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/curl.cpp) set(DUSK_HTTP_BACKEND_SOURCE src/dusk/http/curl.cpp)
list(APPEND GAME_LIBS CURL::libcurl) list(APPEND GAME_LIBS CURL::libcurl)
list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_LIBCURL=1) list(APPEND GAME_COMPILE_DEFS DUSK_HTTP_BACKEND_LIBCURL=1)
message(STATUS "dusklight: Enabled update checker (libcurl)") message(STATUS "dusk: Enabled update checker (libcurl)")
else () else ()
message(STATUS "dusklight: Disabled update checker (libcurl + HTTPS/SSL not found)") message(STATUS "dusk: Disabled update checker (libcurl + HTTPS/SSL not found)")
endif () endif ()
else () else ()
message(STATUS "dusklight: Disabled update checker (unsupported platform)") message(STATUS "dusk: Disabled update checker (unsupported platform)")
endif () endif ()
endif () endif ()
list(APPEND DUSK_FILES ${DUSK_HTTP_BACKEND_SOURCE}) list(APPEND DUSK_FILES ${DUSK_HTTP_BACKEND_SOURCE})
@@ -448,37 +432,31 @@ endif ()
set(DUSK_FILES src/dusk/main.cpp ${GAME_BASE_FILES} ${GAME_DEBUG_FILES}) set(DUSK_FILES src/dusk/main.cpp ${GAME_BASE_FILES} ${GAME_DEBUG_FILES})
if(ANDROID) if(ANDROID)
add_library(dusklight SHARED ${DUSK_FILES}) add_library(dusk SHARED ${DUSK_FILES})
set_target_properties(dusklight PROPERTIES OUTPUT_NAME main) set_target_properties(dusk PROPERTIES OUTPUT_NAME main)
else () else ()
add_executable(dusklight ${DUSK_FILES}) add_executable(dusk ${DUSK_FILES})
endif () endif ()
target_compile_definitions(dusklight PRIVATE ${GAME_COMPILE_DEFS}) target_compile_definitions(dusk PRIVATE ${GAME_COMPILE_DEFS})
target_include_directories(dusklight PRIVATE ${GAME_INCLUDE_DIRS}) target_include_directories(dusk PRIVATE ${GAME_INCLUDE_DIRS})
target_link_libraries(dusklight PRIVATE aurora::main ${GAME_LIBS} ${JSYSTEM_LINK_LIBRARIES}) target_link_libraries(dusk PRIVATE aurora::main ${GAME_LIBS} ${JSYSTEM_LINK_LIBRARIES})
target_precompile_headers(dusklight PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:${CMAKE_SOURCE_DIR}/include/dusk_pch.hpp>") target_precompile_headers(dusk PRIVATE "$<$<COMPILE_LANGUAGE:CXX>:${CMAKE_SOURCE_DIR}/include/dusk_pch.hpp>")
if (TARGET crashpad_handler) if (TARGET crashpad_handler)
add_dependencies(dusklight crashpad_handler) add_dependencies(dusk crashpad_handler)
add_custom_command(TARGET dusklight POST_BUILD
COMMAND ${CMAKE_COMMAND} -E copy_if_different
"$<TARGET_FILE:crashpad_handler>"
"$<TARGET_FILE_DIR:dusklight>"
COMMENT "Copying crashpad handler"
)
endif () endif ()
if (ANDROID) if (ANDROID)
# SDLActivity loads SDL_main via dlsym on Android. Since aurora::main is a static # SDLActivity loads SDL_main via dlsym on Android. Since aurora::main is a static
# archive, force an undefined reference so the linker keeps the SDL_main object. # archive, force an undefined reference so the linker keeps the SDL_main object.
target_link_options(dusklight PRIVATE "-Wl,-u,SDL_main") target_link_options(dusk PRIVATE "-Wl,-u,SDL_main")
endif () endif ()
if (NOT APPLE) if (NOT APPLE)
add_custom_command(TARGET dusklight POST_BUILD add_custom_command(TARGET dusk POST_BUILD
COMMAND ${CMAKE_COMMAND} -E copy_directory COMMAND ${CMAKE_COMMAND} -E copy_directory
"${CMAKE_SOURCE_DIR}/res" "${CMAKE_SOURCE_DIR}/res"
"$<TARGET_FILE_DIR:dusklight>/res" "$<TARGET_FILE_DIR:dusk>/res"
COMMENT "Copying resources" COMMENT "Copying resources"
) )
endif () endif ()
@@ -486,9 +464,9 @@ endif ()
if (WIN32) if (WIN32)
set(DUSK_WINDOWS_RESOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/platforms/windows) set(DUSK_WINDOWS_RESOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/platforms/windows)
set(DUSK_WINDOWS_ICON_PNG ${CMAKE_CURRENT_SOURCE_DIR}/res/icon.png) set(DUSK_WINDOWS_ICON_PNG ${CMAKE_CURRENT_SOURCE_DIR}/res/icon.png)
set(DUSK_WINDOWS_ICON_ICO ${CMAKE_CURRENT_BINARY_DIR}/dusklight.ico) set(DUSK_WINDOWS_ICON_ICO ${CMAKE_CURRENT_BINARY_DIR}/dusk.ico)
set(DUSK_WINDOWS_RC ${CMAKE_CURRENT_BINARY_DIR}/dusklight.rc) set(DUSK_WINDOWS_RC ${CMAKE_CURRENT_BINARY_DIR}/dusk.rc)
set(DUSK_WINDOWS_MANIFEST ${CMAKE_CURRENT_BINARY_DIR}/dusklight.manifest) set(DUSK_WINDOWS_MANIFEST ${CMAKE_CURRENT_BINARY_DIR}/dusk.manifest)
add_custom_command( add_custom_command(
OUTPUT ${DUSK_WINDOWS_ICON_ICO} OUTPUT ${DUSK_WINDOWS_ICON_ICO}
@@ -501,14 +479,14 @@ if (WIN32)
COMMENT "Generating Windows icon" COMMENT "Generating Windows icon"
) )
configure_file(${DUSK_WINDOWS_RESOURCE_DIR}/dusklight.manifest.in ${DUSK_WINDOWS_MANIFEST} @ONLY) configure_file(${DUSK_WINDOWS_RESOURCE_DIR}/dusk.manifest.in ${DUSK_WINDOWS_MANIFEST} @ONLY)
configure_file(${DUSK_WINDOWS_RESOURCE_DIR}/dusklight.rc.in ${DUSK_WINDOWS_RC} @ONLY) configure_file(${DUSK_WINDOWS_RESOURCE_DIR}/dusk.rc.in ${DUSK_WINDOWS_RC} @ONLY)
target_sources(dusklight PRIVATE ${DUSK_WINDOWS_ICON_ICO} ${DUSK_WINDOWS_RC}) target_sources(dusk PRIVATE ${DUSK_WINDOWS_ICON_ICO} ${DUSK_WINDOWS_RC})
set_target_properties(dusklight PROPERTIES WIN32_EXECUTABLE TRUE) set_target_properties(dusk PROPERTIES WIN32_EXECUTABLE TRUE)
if (MSVC) if (MSVC)
target_link_options(dusklight PRIVATE /MANIFEST:NO) target_link_options(dusk PRIVATE /MANIFEST:NO)
endif () endif ()
endif () endif ()
@@ -524,10 +502,10 @@ if (APPLE)
file(GLOB_RECURSE DUSK_RESOURCE_FILES file(GLOB_RECURSE DUSK_RESOURCE_FILES
"${DUSK_RESOURCE_DIR}/Assets.car" "${DUSK_RESOURCE_DIR}/Assets.car"
"${DUSK_RESOURCE_DIR}/Base.lproj/*" "${DUSK_RESOURCE_DIR}/Base.lproj/*"
"${DUSK_RESOURCE_DIR}/Dusklight.icns") "${DUSK_RESOURCE_DIR}/Dusk.icns")
file(GLOB_RECURSE DUSK_APP_RESOURCE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/res/*") file(GLOB_RECURSE DUSK_APP_RESOURCE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/res/*")
target_sources(dusklight PRIVATE ${DUSK_RESOURCE_FILES}) target_sources(dusk PRIVATE ${DUSK_RESOURCE_FILES})
target_sources(dusklight PRIVATE ${DUSK_APP_RESOURCE_FILES}) target_sources(dusk PRIVATE ${DUSK_APP_RESOURCE_FILES})
foreach (FILE ${DUSK_RESOURCE_FILES}) foreach (FILE ${DUSK_RESOURCE_FILES})
file(RELATIVE_PATH NEW_FILE "${DUSK_RESOURCE_DIR}" ${FILE}) file(RELATIVE_PATH NEW_FILE "${DUSK_RESOURCE_DIR}" ${FILE})
get_filename_component(NEW_FILE_PATH ${NEW_FILE} DIRECTORY) get_filename_component(NEW_FILE_PATH ${NEW_FILE} DIRECTORY)
@@ -539,36 +517,29 @@ if (APPLE)
set_property(SOURCE ${FILE} PROPERTY MACOSX_PACKAGE_LOCATION "Resources/${NEW_FILE_PATH}") set_property(SOURCE ${FILE} PROPERTY MACOSX_PACKAGE_LOCATION "Resources/${NEW_FILE_PATH}")
endforeach () endforeach ()
set_target_properties( set_target_properties(
dusklight PROPERTIES dusk PROPERTIES
MACOSX_BUNDLE TRUE MACOSX_BUNDLE TRUE
MACOSX_BUNDLE_BUNDLE_NAME ${DUSK_BUNDLE_NAME} MACOSX_BUNDLE_BUNDLE_NAME ${DUSK_BUNDLE_NAME}
MACOSX_BUNDLE_GUI_IDENTIFIER ${DUSK_BUNDLE_IDENTIFIER} MACOSX_BUNDLE_GUI_IDENTIFIER ${DUSK_BUNDLE_IDENTIFIER}
MACOSX_BUNDLE_BUNDLE_VERSION ${DUSK_VERSION_STRING} MACOSX_BUNDLE_BUNDLE_VERSION ${DUSK_VERSION_STRING}
MACOSX_BUNDLE_SHORT_VERSION_STRING ${DUSK_SHORT_VERSION_STRING} MACOSX_BUNDLE_SHORT_VERSION_STRING ${DUSK_SHORT_VERSION_STRING}
MACOSX_BUNDLE_INFO_PLIST ${DUSK_INFO_PLIST} MACOSX_BUNDLE_INFO_PLIST ${DUSK_INFO_PLIST}
OUTPUT_NAME Dusklight OUTPUT_NAME Dusk
XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "YES" XCODE_ATTRIBUTE_CODE_SIGNING_ALLOWED "YES"
XCODE_ATTRIBUTE_CODE_SIGNING_REQUIRED "YES" XCODE_ATTRIBUTE_CODE_SIGNING_REQUIRED "YES"
) )
endif () endif ()
if (APPLE AND NOT IOS AND NOT TVOS)
find_library(APPKIT_FRAMEWORK AppKit REQUIRED)
target_sources(dusklight PRIVATE src/dusk/file_select_macos.mm)
set_source_files_properties(src/dusk/file_select_macos.mm PROPERTIES COMPILE_FLAGS -fobjc-arc)
target_link_libraries(dusklight PRIVATE ${APPKIT_FRAMEWORK})
endif ()
if (IOS) if (IOS)
find_library(UIKIT_FRAMEWORK UIKit REQUIRED) find_library(UIKIT_FRAMEWORK UIKit REQUIRED)
find_library(UNIFORM_TYPE_IDENTIFIERS_FRAMEWORK UniformTypeIdentifiers REQUIRED) find_library(UNIFORM_TYPE_IDENTIFIERS_FRAMEWORK UniformTypeIdentifiers REQUIRED)
target_sources(dusklight PRIVATE src/dusk/ios/FileSelectDialog.m) target_sources(dusk PRIVATE src/dusk/ios/FileSelectDialog.m)
set_source_files_properties(src/dusk/ios/FileSelectDialog.m PROPERTIES COMPILE_FLAGS -fobjc-arc) set_source_files_properties(src/dusk/ios/FileSelectDialog.m PROPERTIES COMPILE_FLAGS -fobjc-arc)
target_link_libraries(dusklight PRIVATE ${UIKIT_FRAMEWORK} ${UNIFORM_TYPE_IDENTIFIERS_FRAMEWORK}) target_link_libraries(dusk PRIVATE ${UIKIT_FRAMEWORK} ${UNIFORM_TYPE_IDENTIFIERS_FRAMEWORK})
endif () endif ()
include(extern/aurora/cmake/AuroraCopyRuntimeDLLs.cmake) include(extern/aurora/cmake/AuroraCopyRuntimeDLLs.cmake)
aurora_copy_runtime_dlls(dusklight) aurora_copy_runtime_dlls(dusk)
if (DUSK_SELECTED_OPT) if (DUSK_SELECTED_OPT)
if (CMAKE_CXX_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC") if (CMAKE_CXX_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
@@ -606,13 +577,13 @@ function(get_target_prefix target result_var)
endif () endif ()
endif () endif ()
endfunction() endfunction()
list(APPEND BINARY_TARGETS dusklight) list(APPEND BINARY_TARGETS dusk)
set(EXTRA_TARGETS "") set(EXTRA_TARGETS "")
if (TARGET crashpad_handler) if (TARGET crashpad_handler)
list(APPEND EXTRA_TARGETS crashpad_handler) list(APPEND EXTRA_TARGETS crashpad_handler)
endif () endif ()
install(TARGETS ${BINARY_TARGETS} ${EXTRA_TARGETS} DESTINATION ${CMAKE_INSTALL_PREFIX}) install(TARGETS ${BINARY_TARGETS} ${EXTRA_TARGETS} DESTINATION ${CMAKE_INSTALL_PREFIX})
aurora_install_runtime_dlls(dusklight ${CMAKE_INSTALL_PREFIX}) aurora_install_runtime_dlls(dusk ${CMAKE_INSTALL_PREFIX})
if (NOT APPLE) if (NOT APPLE)
install(DIRECTORY ${CMAKE_SOURCE_DIR}/res DESTINATION ${CMAKE_INSTALL_PREFIX}) install(DIRECTORY ${CMAKE_SOURCE_DIR}/res DESTINATION ${CMAKE_INSTALL_PREFIX})
endif () endif ()
+32 -23
View File
@@ -30,7 +30,7 @@
"CMAKE_CXX_COMPILER_LAUNCHER": "sccache", "CMAKE_CXX_COMPILER_LAUNCHER": "sccache",
"DUSK_ENABLE_SENTRY_NATIVE": { "DUSK_ENABLE_SENTRY_NATIVE": {
"type": "BOOL", "type": "BOOL",
"value": true "value": false
}, },
"DUSK_SENTRY_DSN": "$env{SENTRY_DSN}", "DUSK_SENTRY_DSN": "$env{SENTRY_DSN}",
"DUSK_SENTRY_ENVIRONMENT": "production" "DUSK_SENTRY_ENVIRONMENT": "production"
@@ -249,11 +249,22 @@
"type": "BOOL", "type": "BOOL",
"value": false "value": false
}, },
"CMAKE_DISABLE_FIND_PACKAGE_PkgConfig": { "CMAKE_DISABLE_FIND_PACKAGE_BZip2": {
"type": "BOOL", "type": "BOOL",
"value": true "value": true
}, },
"CMAKE_IGNORE_PREFIX_PATH": "/opt/homebrew" "CMAKE_DISABLE_FIND_PACKAGE_LibLZMA": {
"type": "BOOL",
"value": true
},
"CMAKE_DISABLE_FIND_PACKAGE_zstd": {
"type": "BOOL",
"value": true
},
"CMAKE_DISABLE_FIND_PACKAGE_Freetype": {
"type": "BOOL",
"value": true
}
}, },
"vendor": { "vendor": {
"microsoft.com/VisualStudioSettings/CMake/1.0": { "microsoft.com/VisualStudioSettings/CMake/1.0": {
@@ -318,11 +329,7 @@
"cacheVariables": { "cacheVariables": {
"CMAKE_INSTALL_PREFIX": "${sourceDir}/build/install", "CMAKE_INSTALL_PREFIX": "${sourceDir}/build/install",
"CMAKE_TOOLCHAIN_FILE": "$env{ANDROID_HOME}/ndk/$env{ANDROID_NDK_VERSION}/build/cmake/android.toolchain.cmake", "CMAKE_TOOLCHAIN_FILE": "$env{ANDROID_HOME}/ndk/$env{ANDROID_NDK_VERSION}/build/cmake/android.toolchain.cmake",
"ANDROID_PLATFORM": "android-28", "ANDROID_PLATFORM": "android-28"
"BUILD_SHARED_LIBS": {
"type": "BOOL",
"value": false
}
} }
}, },
{ {
@@ -351,13 +358,7 @@
"inherits": [ "inherits": [
"android-base", "android-base",
"ci" "ci"
], ]
"cacheVariables": {
"DUSK_ENABLE_SENTRY_NATIVE": {
"type": "BOOL",
"value": false
}
}
}, },
{ {
"name": "x-android-ci-arm64", "name": "x-android-ci-arm64",
@@ -409,7 +410,7 @@
}, },
"CMAKE_OSX_DEPLOYMENT_TARGET": "11.0", "CMAKE_OSX_DEPLOYMENT_TARGET": "11.0",
"CMAKE_IGNORE_PREFIX_PATH": "/opt/homebrew", "CMAKE_IGNORE_PREFIX_PATH": "/opt/homebrew",
"BUILD_SHARED_LIBS": { "DUSK_MOVIE_SUPPORT": {
"type": "BOOL", "type": "BOOL",
"value": false "value": false
} }
@@ -442,7 +443,11 @@
], ],
"cacheVariables": { "cacheVariables": {
"CMAKE_C_COMPILER_LAUNCHER": "sccache", "CMAKE_C_COMPILER_LAUNCHER": "sccache",
"CMAKE_CXX_COMPILER_LAUNCHER": "sccache" "CMAKE_CXX_COMPILER_LAUNCHER": "sccache",
"DUSK_MOVIE_SUPPORT": {
"type": "BOOL",
"value": false
}
} }
}, },
{ {
@@ -452,7 +457,11 @@
], ],
"cacheVariables": { "cacheVariables": {
"CMAKE_C_COMPILER_LAUNCHER": "sccache", "CMAKE_C_COMPILER_LAUNCHER": "sccache",
"CMAKE_CXX_COMPILER_LAUNCHER": "sccache" "CMAKE_CXX_COMPILER_LAUNCHER": "sccache",
"DUSK_MOVIE_SUPPORT": {
"type": "BOOL",
"value": false
}
} }
}, },
{ {
@@ -536,7 +545,7 @@
"description": "iOS release build with debug info", "description": "iOS release build with debug info",
"displayName": "iOS RelWithDebInfo", "displayName": "iOS RelWithDebInfo",
"targets": [ "targets": [
"dusklight" "dusk"
] ]
}, },
{ {
@@ -545,7 +554,7 @@
"description": "tvOS release build with debug info", "description": "tvOS release build with debug info",
"displayName": "tvOS RelWithDebInfo", "displayName": "tvOS RelWithDebInfo",
"targets": [ "targets": [
"dusklight" "dusk"
] ]
}, },
{ {
@@ -554,7 +563,7 @@
"description": "Android arm64-v8a release build with debug info", "description": "Android arm64-v8a release build with debug info",
"displayName": "Android arm64-v8a RelWithDebInfo", "displayName": "Android arm64-v8a RelWithDebInfo",
"targets": [ "targets": [
"dusklight" "dusk"
] ]
}, },
{ {
@@ -563,7 +572,7 @@
"description": "Android x86_64 release build with debug info", "description": "Android x86_64 release build with debug info",
"displayName": "Android x86_64 RelWithDebInfo", "displayName": "Android x86_64 RelWithDebInfo",
"targets": [ "targets": [
"dusklight" "dusk"
] ]
}, },
{ {
@@ -572,7 +581,7 @@
"description": "(Internal) Android CI arm64-v8a", "description": "(Internal) Android CI arm64-v8a",
"displayName": "(Internal) Android CI arm64-v8a", "displayName": "(Internal) Android CI arm64-v8a",
"targets": [ "targets": [
"dusklight" "dusk"
] ]
}, },
{ {
+12 -15
View File
@@ -1,30 +1,27 @@
<div align="center"> <div align="center">
<img src="res/logo.png" alt="Logo" width="640"> <img src="res/logo-mascot.png" alt="Logo" width="640">
<p align="center"> <p align="center">
<a href="https://twilitrealm.dev">Official Website</a> <a href="https://twilitrealm.dev">Official Website</a>
<a href="https://discord.gg/6NpMhefCK9">Discord</a> <a href="https://discord.gg/dusktp">Discord</a>
</p> </p>
</div> </div>
# Overview # Overview
Dusklight is a reverse-engineered reimplementation of Twilight Princess. Dusk is a reverse-engineered reimplementation of Twilight Princess.
It aims to be as accurate as possible to the original while also providing new options, enhancements, and tools to customize your experience. It aims to be as accurate as possible to the original while also providing new options, enhancements, and tools to customize your experience.
# Setup # Setup
> [!IMPORTANT] > [!IMPORTANT]
> Dusklight does *not* provide any copyrighted assets. You must provide your own copy of the original game. > Dusk does *not* provide any copyrighted assets. You must provide your own copy of the original game.
> [!IMPORTANT]
> At a minimum, Dusklight requires a GPU with support for either D3D12, Vulkan, or Metal. Your experience with specific hardware, operating systems, and drivers may vary. In particular, older Intel iGPUs have a high likelihood of incompatibility. We are also aware of a number of issues on devices with Adreno GPUs and are working to resolve them.
### 1. Verify your dump ### 1. Verify your dump
First, make sure your dump of the game is clean and supported by Dusklight. You can do this by checking the SHA-1 hash of your dump against this list of supported versions: First, make sure your dump of the game is clean and supported by Dusk. You can do this by checking the SHA-1 hash of your dump against this list of supported versions:
| Version | SHA-1 hash | | Version | SHA-1 hash |
|--------------| ------------------------------------------ | |--------------| ------------------------------------------ |
@@ -33,12 +30,12 @@ First, make sure your dump of the game is clean and supported by Dusklight. You
*Support for other versions of the game is planned in the future. *Support for other versions of the game is planned in the future.
### 2. Download [Dusklight](https://github.com/TwilitRealm/dusklight/releases) ### 2. Download [Dusk](https://github.com/TwilitRealm/dusk/releases)
### 3. Setup the game ### 3. Setup the game
**Windows / macOS / Linux** **Windows / macOS / Linux**
- Extract the .zip file - Extract the .zip file
- Launch Dusklight - Launch Dusk
- Press **Select Disc Image** and provide the path to your supported game dump - Press **Select Disc Image** and provide the path to your supported game dump
- Press **Play**! - Press **Play**!
@@ -46,20 +43,20 @@ First, make sure your dump of the game is clean and supported by Dusklight. You
- Follow the [iOS setup guide](docs/ios-install-altstore.md) - Follow the [iOS setup guide](docs/ios-install-altstore.md)
**Android** **Android**
- Install the Dusklight APK - Install the Dusk apk
- Launch Dusklight - Launch Dusk
- Press **Select Disc Image** and provide the path to your supported game dump - Press **Select Disc Image** and provide the path to your supported game dump
- Press **Play**! - Press **Play**!
# Building # Building
If you'd like to build Dusklight from source, please read the [build instructions](docs/building.md). If you'd like to build Dusk from source, please read the [build instructions](docs/building.md).
Pull requests are welcomed! Note that we do not accept contributions that are primarily AI-generated and will close your PR if we suspect as much. Please also see the [code conventions](docs/code-conventions.md). Pull requests are welcomed! Note that we do not accept contributions that are primarily AI-generated and will close your PR if we suspect as much.
# Credits # Credits
Special thanks to the [TP decompilation](https://github.com/zeldaret/tp) team, the GC/Wii decompilation community, the [Aurora](https://github.com/encounter/aurora) developers, the [TP speedrunning community](https://zsrtp.link), and all [contributors](https://github.com/TwilitRealm/dusklight/graphs/contributors). Special thanks to the [TP decompilation](https://github.com/zeldaret/tp) team, the GC/Wii decompilation community, the [Aurora](https://github.com/encounter/aurora) developers, the [TP speedrunning community](https://zsrtp.link), and all [contributors](https://github.com/TwilitRealm/dusk/graphs/contributors).
<br/> <br/>
<div align="center"> <div align="center">
+9 -17
View File
@@ -1,26 +1,18 @@
#!/bin/bash -ex #!/bin/bash -ex
shopt -s extglob
if [[ -n "${GITHUB_WORKSPACE:-}" ]]; then
cd "$GITHUB_WORKSPACE"
fi
build_dir="$PWD/build"
linuxdeploy="$build_dir/linuxdeploy-$(uname -m).AppImage"
# Get linuxdeploy # Get linuxdeploy
mkdir -p "$build_dir" cd "$RUNNER_WORKSPACE"
curl -fL "https://github.com/linuxdeploy/linuxdeploy/releases/download/continuous/linuxdeploy-$(uname -m).AppImage" -o "$linuxdeploy" curl -fOL https://github.com/linuxdeploy/linuxdeploy/releases/download/continuous/linuxdeploy-$(uname -m).AppImage
chmod +x "$linuxdeploy" chmod +x linuxdeploy-$(uname -m).AppImage
# Build AppImage # Build AppImage
cd "$GITHUB_WORKSPACE"
mkdir -p build/appdir/usr/{bin,share/{applications,icons/hicolor}} mkdir -p build/appdir/usr/{bin,share/{applications,icons/hicolor}}
for install_path in build/install/*; do cp -r build/install/!(*.*) build/appdir/usr/bin
[[ "$(basename "$install_path")" == *.* ]] && continue
cp -r "$install_path" build/appdir/usr/bin
done
cp -r platforms/freedesktop/{16x16,32x32,48x48,64x64,128x128,256x256,512x512,1024x1024} build/appdir/usr/share/icons/hicolor cp -r platforms/freedesktop/{16x16,32x32,48x48,64x64,128x128,256x256,512x512,1024x1024} build/appdir/usr/share/icons/hicolor
cp platforms/freedesktop/dusklight.desktop build/appdir/usr/share/applications cp platforms/freedesktop/dusk.desktop build/appdir/usr/share/applications
cd build/install cd build/install
VERSION="$DUSK_VERSION" NO_STRIP=1 "$linuxdeploy" \ VERSION="$DUSK_VERSION" NO_STRIP=1 "$RUNNER_WORKSPACE"/linuxdeploy-$(uname -m).AppImage \
-l /usr/lib/x86_64-linux-gnu/libusb-1.0.so --appdir "$build_dir/appdir" --output appimage -l /usr/lib/x86_64-linux-gnu/libusb-1.0.so --appdir "$GITHUB_WORKSPACE"/build/appdir --output appimage
+52 -182
View File
@@ -1,165 +1,51 @@
# Building Dusklight ### Building
#### Prerequisites
## Dependencies
The following dependencies are required:
* [CMake 3.25+](https://cmake.org) * [CMake 3.25+](https://cmake.org)
* Windows: Install `CMake Tools` in Visual Studio
* macOS: `brew install cmake`
* [Python 3+](https://python.org) * [Python 3+](https://python.org)
* Windows: [Microsoft Store](https://go.microsoft.com/fwlink?linkID=2082640)
### Windows * Verify it's added to `%PATH%` by typing `python` in `cmd`.
* macOS: `brew install python@3`
* Install [CMake 3.25+](https://cmake.org) by searching `CMake Tools` in Visual Studio * **[Windows]** [Visual Studio 2026 Community](https://www.visualstudio.com/en-us/products/visual-studio-community-vs.aspx)
* Install Python 3 from the [Microsoft Store](https://go.microsoft.com/fwlink?linkID=2082640) and verify it's added to `%PATH%` by typing `python` in `cmd`. * Select `C++ Development` and verify the following packages are included:
* `Windows 11 SDK`
Recommended IDEs: * `CMake Tools`
* `C++ Clang Compiler`
* [Visual Studio 2026 Community](https://www.visualstudio.com/en-us/products/visual-studio-community-vs.aspx). During installation: * `C++ Clang-cl`
* Select `C++ Development` and verify the following packages are included: * **[macOS]** [Xcode 16.4+](https://developer.apple.com/xcode/download/)
* `Windows 11 SDK` * **[Linux]** Actively tested on Ubuntu 24.04, Arch Linux & derivatives.
* `CMake Tools` * Ubuntu 24.04+ packages
* `C++ Clang Compiler` ```
* `C++ Clang-cl` build-essential curl git ninja-build clang lld zlib1g-dev libcurl4-openssl-dev \
libglu1-mesa-dev libdbus-1-dev libvulkan-dev libxi-dev libxrandr-dev libasound2-dev libpulse-dev \
### macOS libudev-dev libpng-dev libncurses5-dev cmake libx11-xcb-dev python3 python-is-python3 \
libclang-dev libfreetype-dev libxinerama-dev libxcursor-dev python3-markupsafe libgtk-3-dev \
* Make sure [Homebrew](https://brew.sh) is installed libxss-dev libxtst-dev
* Install [CMake 3.25+](https://cmake.org) ```
* Arch Linux packages
```
base-devel cmake ninja llvm vulkan-headers python python-markupsafe clang lld alsa-lib libpulse libxrandr freetype2
```
* Fedora packages
```
cmake vulkan-headers ninja-build clang-devel llvm-devel libpng-devel
```
* It's also important that you install the developer tools and libraries
```
sudo dnf groupinstall "Development Tools" "Development Libraries"
```
#### Setup
Clone and initialize the Dusk repository
```sh ```sh
brew install cmake git clone --recursive https://github.com/TwilitRealm/dusk.git
``` cd dusk
* Install Python 3
```sh
brew install python@3
```
Recommended IDEs:
* [Xcode 16.4 or later](https://developer.apple.com/xcode/)
* [Visual Studio Code](https://code.visualstudio.com/download/)
* [CLion](https://www.jetbrains.com/clion/)
### Linux
Actively tested on Ubuntu 24.04, Arch Linux & derivatives.
**Ubuntu 24.04+ packages**
<details>
<summary>Click to expand</summary>
* Run the following command to install the required dependencies:
```sh
sudo apt update && sudo apt install -y \
build-essential \
clang \
cmake \
curl \
git \
libasound2-dev \
libclang-dev \
libcurl4-openssl-dev \
libdbus-1-dev \
libfreetype-dev \
libglu1-mesa-dev \
libgtk-3-dev \
libncurses5-dev \
libpng-dev \
libpulse-dev \
libudev-dev \
libvulkan-dev \
libx11-xcb-dev \
libxcursor-dev \
libxi-dev \
libxinerama-dev \
libxrandr-dev \
libxss-dev \
libxtst-dev \
lld \
ninja-build \
python-is-python3 \
python3 \
python3-markupsafe \
zlib1g-dev
```
</details>
<br>
**Arch Linux packages**
<details>
<summary>Click to expand</summary>
* Run the following command to install the required dependencies:
```sh
sudo pacman -S --needed \
alsa-lib \
base-devel \
clang \
cmake \
freetype2 \
libpulse \
libxrandr \
lld \
llvm \
ninja \
python \
python-markupsafe \
vulkan-headers
```
</details>
<br>
**Fedora packages**
<details>
<summary>Click to expand</summary>
* Run the following command to install the required dependencies:
```sh
sudo dnf install -y \
clang-devel \
cmake \
libpng-devel \
llvm-devel \
ninja-build \
vulkan-headers
```
* It's also important that you install the developer tools and libraries
```sh
sudo dnf groupinstall \
"Development Libraries" "Development Tools"
```
</details>
<br>
Recommended IDEs:
* [CLion](https://www.jetbrains.com/clion/)
* [Visual Studio Code](https://code.visualstudio.com/download/)
## Building
* Clone and initialize the Dusklight repository:
```sh
git clone --recursive https://github.com/TwilitRealm/dusklight.git
git pull git pull
cd dusklight
git submodule update --init --recursive git submodule update --init --recursive
``` ```
#### Building
**CLion (Windows / macOS / Linux)** **CLion (Windows / macOS / Linux)**
Open the project directory in CLion. Enable the appropriate presets for your platform: Open the project directory in CLion. Enable the appropriate presets for your platform:
@@ -178,8 +64,7 @@ cmake --build --preset macos-default-relwithdebinfo
``` ```
Alternate presets available: Alternate presets available:
- `macos-default-debug`: Clang, Debug
* `macos-default-debug`: Clang, Debug
**ninja (Linux)** **ninja (Linux)**
@@ -189,10 +74,9 @@ cmake --build --preset linux-default-relwithdebinfo
``` ```
Alternate presets available: Alternate presets available:
- `linux-default-debug`: GCC, Debug
* `linux-default-debug`: GCC, Debug - `linux-clang-relwithdebinfo`: Clang, RelWithDebInfo
* `linux-clang-relwithdebinfo`: Clang, RelWithDebInfo - `linux-clang-debug`: Clang, Debug
* `linux-clang-debug`: Clang, Debug
**ninja (Windows)** **ninja (Windows)**
@@ -202,27 +86,13 @@ cmake --build --preset windows-msvc-relwithdebinfo
``` ```
Alternate presets available: Alternate presets available:
- `windows-msvc-debug`: MSVC, Debug
- `windows-clang-relwithdebinfo`: Clang-cl, RelWithDebInfo
- `windows-clang-debug`: Clang-cl, Debug
* `windows-msvc-debug`: MSVC, Debug #### Running
* `windows-clang-relwithdebinfo`: Clang-cl, RelWithDebInfo Pass the disc image as a positional argument. Supported formats: ISO (GCM), RVZ, WIA, WBFS, CISO, GCZ
* `windows-clang-debug`: Clang-cl, Debug
## Running
**Windows / Linux**
* Pass the disc image as a positional argument using the `--dvd` flag. Supported formats are: ISO (GCM), RVZ, WIA, WBFS, CISO, GCZ
```sh ```sh
build/{preset}/dusklight --dvd /path/to/game.iso build/{preset}/dusk /path/to/game.rvz
```
**macOS**
macOS builds an `.app` bundle which contains the executable and all necessary resources.
* Pass the disc image as a positional argument using the `--dvd` flag. Supported formats are: ISO (GCM), RVZ, WIA, WBFS, CISO, GCZ
```sh
build/{preset}/Dusklight.app/Contents/MacOS/Dusklight --dvd /path/to/game.iso
``` ```
If no path is specified, Dusk defaults to `game.iso` in the current working directory.
-13
View File
@@ -1,13 +0,0 @@
# Code conventions for Dusk
## Upstream when appropriate
Bug fixes, documentation improvements, code cleanup, etc that also apply to the [original decompilation project](https://github.com/zeldaret/tp) should preferably be PR'd there.
## Properly indicate Dusk-modified code
When modifying original game code (i.e. in decomp) for Dusk's purposes, please clearly delineate such code as being Dusk-specific. Generally, this can be done by using `#if TARGET_PC` and keeping the original code in place. Use `#if AVOID_UB` for Undefined Behavior fixes to the original codebase.
## Miscellaneous things
* The original codebase makes heavy use of global `operator new` and similar overloads to allocate into a strict tree of heaps. This would cause many linkage headaches for us, so effectively all uses of `new` or `delete` in the original game code have been replaced with `JKR_NEW`, `JKR_DELETE`, or similar macros. See `JKRHeap.h` for the full list.
+26 -28
View File
@@ -1,48 +1,46 @@
# Installing Dusklight on iOS via iloader # Installing Dusk on iOS via AltStore
## Prerequisites ## Prerequisites
- A Windows, Linux, or macOS device - Mac with Homebrew installed
- iOS device connected to computer via USB - iPhone connected via USB
- Dusklight IPA file (download the latest `Dusklight-vX.X.X-ios-arm64.ipa` from the [releases page](https://github.com/TwilitRealm/dusklight/releases)) - Dusk IPA file (download the latest `Dusk-vX.X.X-ios-arm64.ipa` from the [releases page](https://github.com/TwilitRealm/dusk/releases))
- Legally acquired game disc - `GZ2E01` (Gamecube USA) or `GZ2PE01` (Gamecube PAL) - Game disc - `GZ2E01` (Gamecube USA) or `GZ2PE01` (Gamecube PAL)
## 1. Install iloader ## 1. Install AltServer
- Executable bundles can be installed from [iloader's main page](https://iloader.app/) or [their GitHub](https://github.com/nab138/iloader) for Windows, Linux, and macOS. ```sh
- Windows WILL require iTunes to be installed brew install altserver
- Linux WILL require usbmuxd to be installed, this is installed by default in most distros though open -a AltServer
```
AltServer will appear in your menu bar.
## 2. Enable Developer Mode (iOS 16+) ## 2. Enable Developer Mode (iOS 16+)
- On your iPhone, go to **Settings > Privacy & Security > Developer Mode** - On your iPhone, go to **Settings > Privacy & Security > Developer Mode**
- Toggle it on, put in your device passcode, and restart when prompted - Toggle it on and restart when prompted
## 3. Install Dusklight on Your iPhone ## 3. Install AltStore on Your iPhone
1. Sign into your Apple ID (this is required for registering app IDs, it is sent securely directly to Apple and not stored by iloader) - Click AltServer in the menu bar
* You may be prompted to put in a code from your iOS device if you have 2FA enabled, do so - Click **Install AltStore > [Your iPhone]**
2. Plug in your iOS device via USB into your PC. If you're missing a dependency, an error pop-up will tell you to install it - Enter your Apple ID credentials when prompted
* You will need to hit `Refresh` after plugging it in at this stage so that it can be detected, it does not automatically refresh - On your iPhone, go to **Settings > General > VPN & Device Management**
3. Leave settings unchanged (the Anisette server should stay Sidestore (.io)) - Tap your Apple ID under "Developer App" and tap **Trust**
3.(a) Installing SideStore directly is not required, but provides you a way to install Dusklight on your phone without being plugged into a computer later
4. Press `Import IPA` and choose your downloaded `Dusklight-v.X.X.X-ios-arm64.ipa`, it will begin installing on your device
**NOTE:** *At various stages, you may be prompted to trust your device, do so*
## 3. Getting Dusklight trusted
When installing sideloaded iOS applications, at first you will need to manually trust the app due to Apple's security policies
* Go to **Settings > General > VPN & Device Management**
* Tap the Apple ID you signed into iloader with under "Developer App" and tap **Trust**
* Tap **Allow** on the pop-up
## 4. Copy Files to Your iPhone ## 4. Copy Files to Your iPhone
Transfer the game disc (and optionally, the Dusklight IPA) to your iPhone so they are accessible in the Files app. A few ways to do this: Transfer the IPA and game disc to your iPhone so they're accessible in the Files app. A few ways to do this:
- **AirDrop** - Right-click the files on your Mac and choose Share > AirDrop - **AirDrop** - Right-click the files on your Mac and choose Share > AirDrop
- **iCloud Drive** - Place files in iCloud Drive on your Mac and they'll sync to Files on your iPhone - **iCloud Drive** - Place files in iCloud Drive on your Mac and they'll sync to Files on your iPhone
- **USB transfer** - Connect your iPhone and drag files via Finder's sidebar - **USB transfer** - Connect your iPhone and drag files via Finder's sidebar
- **Cloud storage** - Upload to Google Drive, Dropbox, etc. and download on your iPhone - **Cloud storage** - Upload to Google Drive, Dropbox, etc. and download on your iPhone
You may now use Dusklight on iOS and iPadOS! ## 5. Install via AltStore
- Open **AltStore** on your iPhone
- Go to the **My Apps** tab
- Tap the **+** button (top left)
- Open the **Files** app and select the `.ipa` file
+1 -1
+3 -10
View File
@@ -1411,7 +1411,6 @@ set(DOLPHIN_FILES
) )
set(DUSK_FILES set(DUSK_FILES
include/dusk/action_bindings.h
include/dusk/endian_gx.hpp include/dusk/endian_gx.hpp
include/dusk/config.hpp include/dusk/config.hpp
include/dusk/dvd_asset.hpp include/dusk/dvd_asset.hpp
@@ -1421,8 +1420,6 @@ set(DUSK_FILES
src/dusk/asserts.cpp src/dusk/asserts.cpp
src/dusk/config.cpp src/dusk/config.cpp
src/dusk/crash_reporting.cpp src/dusk/crash_reporting.cpp
src/dusk/data.cpp
src/dusk/data.hpp
src/dusk/endian.cpp src/dusk/endian.cpp
src/dusk/extras.c src/dusk/extras.c
src/dusk/file_select.cpp src/dusk/file_select.cpp
@@ -1438,7 +1435,6 @@ set(DUSK_FILES
src/dusk/layout.cpp src/dusk/layout.cpp
src/dusk/logging.cpp src/dusk/logging.cpp
src/dusk/settings.cpp src/dusk/settings.cpp
src/dusk/speedrun.cpp
src/dusk/stubs.cpp src/dusk/stubs.cpp
src/dusk/update_check.cpp src/dusk/update_check.cpp
src/dusk/update_check.hpp src/dusk/update_check.hpp
@@ -1448,16 +1444,18 @@ set(DUSK_FILES
src/dusk/imgui/ImGuiConsole.cpp src/dusk/imgui/ImGuiConsole.cpp
src/dusk/imgui/ImGuiEngine.cpp src/dusk/imgui/ImGuiEngine.cpp
src/dusk/imgui/ImGuiEngine.hpp src/dusk/imgui/ImGuiEngine.hpp
src/dusk/imgui/ImGuiMenuGame.cpp
src/dusk/imgui/ImGuiMenuGame.hpp
src/dusk/imgui/ImGuiBloomWindow.cpp src/dusk/imgui/ImGuiBloomWindow.cpp
src/dusk/imgui/ImGuiBloomWindow.hpp src/dusk/imgui/ImGuiBloomWindow.hpp
src/dusk/imgui/ImGuiMenuTools.cpp src/dusk/imgui/ImGuiMenuTools.cpp
src/dusk/imgui/ImGuiMenuTools.hpp src/dusk/imgui/ImGuiMenuTools.hpp
src/dusk/imgui/ImGuiActorSpawner.cpp
src/dusk/imgui/ImGuiProcessOverlay.cpp src/dusk/imgui/ImGuiProcessOverlay.cpp
src/dusk/imgui/ImGuiCameraOverlay.cpp src/dusk/imgui/ImGuiCameraOverlay.cpp
src/dusk/imgui/ImGuiHeapOverlay.cpp src/dusk/imgui/ImGuiHeapOverlay.cpp
src/dusk/imgui/ImGuiControllerOverlay.cpp src/dusk/imgui/ImGuiControllerOverlay.cpp
src/dusk/imgui/ImGuiStubLog.cpp src/dusk/imgui/ImGuiStubLog.cpp
src/dusk/imgui/ImGuiMapLoader.cpp
src/dusk/imgui/ImGuiSaveEditor.cpp src/dusk/imgui/ImGuiSaveEditor.cpp
src/dusk/imgui/ImGuiStateShare.hpp src/dusk/imgui/ImGuiStateShare.hpp
src/dusk/imgui/ImGuiStateShare.cpp src/dusk/imgui/ImGuiStateShare.cpp
@@ -1496,8 +1494,6 @@ set(DUSK_FILES
src/dusk/ui/prelaunch.hpp src/dusk/ui/prelaunch.hpp
src/dusk/ui/preset.cpp src/dusk/ui/preset.cpp
src/dusk/ui/preset.hpp src/dusk/ui/preset.hpp
src/dusk/ui/reporting.cpp
src/dusk/ui/reporting.hpp
src/dusk/ui/select_button.cpp src/dusk/ui/select_button.cpp
src/dusk/ui/select_button.hpp src/dusk/ui/select_button.hpp
src/dusk/ui/settings.cpp src/dusk/ui/settings.cpp
@@ -1508,8 +1504,6 @@ set(DUSK_FILES
src/dusk/ui/tab_bar.hpp src/dusk/ui/tab_bar.hpp
src/dusk/ui/ui.cpp src/dusk/ui/ui.cpp
src/dusk/ui/ui.hpp src/dusk/ui/ui.hpp
src/dusk/ui/warp.cpp
src/dusk/ui/warp.hpp
src/dusk/ui/window.cpp src/dusk/ui/window.cpp
src/dusk/ui/window.hpp src/dusk/ui/window.hpp
src/dusk/achievements.cpp src/dusk/achievements.cpp
@@ -1524,7 +1518,6 @@ set(DUSK_FILES
src/dusk/discord.hpp src/dusk/discord.hpp
src/dusk/discord_presence.cpp src/dusk/discord_presence.cpp
src/dusk/version.cpp src/dusk/version.cpp
src/dusk/action_bindings.cpp
) )
set(DUSK_HTTP_BACKEND_FILES set(DUSK_HTTP_BACKEND_FILES
+23 -209
View File
@@ -4,216 +4,30 @@
}; };
outputs = { self, nixpkgs }: outputs = { self, nixpkgs }:
let let
supportedSystems = [ pkgs = import nixpkgs { system = "x86_64-linux"; };
"x86_64-linux" dusk = pkgs.stdenv.mkDerivation {
"aarch64-linux" name = "dusk";
"x86_64-darwin" src = ./.;
"aarch64-darwin" nativeBuildInputs = [
]; pkgs.cmake
forAllSystems = nixpkgs.lib.genAttrs supportedSystems; pkgs.pkg-config
pkgsFor = system: import nixpkgs { inherit system; }; pkgs.wayland
];
# Dependencies that are not packaged in nixpkgs (used by the Linux package build): buildInputs = [
buildSources = pkgs: { pkgs.libGL
dawn-src = pkgs.fetchzip { pkgs.libX11
url = "https://github.com/encounter/dawn-build/releases/download/v20260423.175430/dawn-linux-x86_64.tar.gz"; pkgs.libXcursor
hash = "sha256-HXfKTLHtMPwupnFnaflCARtXVPuS/0PoCePXidjE5xs="; pkgs.libxi
stripRoot = false; pkgs.libxcb
}; pkgs.libxrandr
nod-src = pkgs.fetchzip { pkgs.libxscrnsaver
url = "https://github.com/encounter/nod/releases/download/v2.0.0-alpha.8/libnod-linux-x86_64.tar.gz"; pkgs.libxtst
hash = "sha256-mUqvLsbsqaZ+HAjMmHYPYO+MgtanGRTw7Gzn5uXR5rE="; pkgs.libjpeg8
stripRoot = false; pkgs.libxkbcommon
}; pkgs.libglvnd
# The version of imgui on nixpkgs does not map cleanly. ];
imgui-src = pkgs.fetchFromGitHub {
owner = "ocornut";
repo = "imgui";
rev = "v1.91.9b-docking";
hash = "sha256-mQOJ6jCN+7VopgZ61yzaCnt4R1QLrW7+47xxMhFRHLQ=";
};
sqlite-src = pkgs.fetchzip {
url = "https://sqlite.org/2026/sqlite-amalgamation-3510300.zip";
hash = "sha256-pNMR8zxaaqfAzQ0AQBOXMct4usdjey1Q0Gnitg06UhM=";
};
rmlui-src = pkgs.fetchzip {
url = "https://github.com/mikke89/RmlUi/archive/f9b8c9e2935d5df2c7dff2c190d3968e99b0c3dc.tar.gz";
hash = "sha256-g4O/JZUrrcseOz8o2QJRt+2CeuiLnVeuDJc906xvuIg=";
};
}; };
# Dusklight Actual (Linux x86_64 only — relies on prebuilt dawn/nod binaries)
mkDusklight = pkgs:
let srcs = buildSources pkgs;
versionSuffix = if self ? shortRev && self.shortRev != null
then "nix-${self.shortRev}"
else "nix-dirty";
in
pkgs.stdenv.mkDerivation {
name = "dusklight";
src = ./.;
postUnpack = ''
sed -i '/add_subdirectory(tests)/d' $sourceRoot/extern/aurora/CMakeLists.txt
'';
# Remove last line to re-enable tests
cmakeFlags = [
"-DDUSK_VERSION_OVERRIDE=${versionSuffix}"
"-DFETCHCONTENT_FULLY_DISCONNECTED=ON"
"-DFETCHCONTENT_SOURCE_DIR_CXXOPTS=${pkgs.cxxopts.src}"
"-DFETCHCONTENT_SOURCE_DIR_JSON=${pkgs.nlohmann_json.src}"
"-DFETCHCONTENT_SOURCE_DIR_DAWN_PREBUILT=${srcs.dawn-src}"
"-DFETCHCONTENT_SOURCE_DIR_XXHASH=${pkgs.xxHash.src}"
"-DFETCHCONTENT_SOURCE_DIR_FMT=${pkgs.fmt.src}"
"-DFETCHCONTENT_SOURCE_DIR_TRACY=${pkgs.tracy.src}"
"-DAURORA_SDL3_PROVIDER=system"
"-DFETCHCONTENT_SOURCE_DIR_NOD_PREBUILT=${srcs.nod-src}"
"-DAURORA_NOD_PROVIDER=package"
"-DFETCHCONTENT_SOURCE_DIR_FREETYPE=${pkgs.freetype.src}"
"-DFETCHCONTENT_SOURCE_DIR_ZSTD=${pkgs.zstd.src}"
"-DFETCHCONTENT_SOURCE_DIR_SQLITE3=${srcs.sqlite-src}"
"-DFETCHCONTENT_SOURCE_DIR_IMGUI=${srcs.imgui-src}"
"-DFETCHCONTENT_SOURCE_DIR_RMLUI=${srcs.rmlui-src}"
"-DCMAKE_CROSSCOMPILING=ON" # Tests are not working as I didn't want to work through getting google's test suite working as well. This is the only guard I could find to disable it.
];
installPhase = ''
mkdir -p $out/bin
cp dusklight $out/bin/dusklight
cp -r ./res $out/bin/res
mkdir -p $out/share/applications
cp $src/platforms/freedesktop/dusklight.desktop $out/share/applications/dusklight.desktop
for size in 16 32 48 64 128 256 512 1024; do
install -Dm644 $src/platforms/freedesktop/''${size}x''${size}/apps/dusklight.png \
$out/share/icons/hicolor/''${size}x''${size}/apps/dusklight.png
done
'';
nativeBuildInputs = [
pkgs.cmake
pkgs.pkg-config
pkgs.wayland
];
buildInputs = [
pkgs.libGL
pkgs.libX11
pkgs.libXcursor
pkgs.libxi
pkgs.libxcb
pkgs.libxrandr
pkgs.libxscrnsaver
pkgs.libxtst
pkgs.libjpeg8
pkgs.libxkbcommon
pkgs.libglvnd
pkgs.cxxopts
pkgs.abseil-cpp
pkgs.sdl3
pkgs.fmt
pkgs.tracy
pkgs.freetype
pkgs.zstd
];
};
# Tooling common to every supported host (Linux and macOS).
commonDevTools = pkgs: [
pkgs.cmake
pkgs.ninja
pkgs.pkg-config
pkgs.git
pkgs.python3
pkgs.python3Packages.markupsafe
pkgs.rustc
pkgs.cargo
pkgs.sccache
];
# Linux-only system libraries — mirrors the apt deps from .github/workflows/build.yml
# so the cmake presets resolve the same set of headers as CI.
linuxDevDeps = pkgs: [
# Compilers / linkers
pkgs.clang
pkgs.lld
# C/C++ utilities
pkgs.curl
pkgs.openssl
pkgs.zlib
pkgs.libpng
pkgs.libjpeg_turbo
pkgs.freetype
pkgs.zstd
pkgs.fmt
pkgs.tracy
pkgs.cxxopts
pkgs.abseil-cpp
pkgs.sdl3
pkgs.ncurses
pkgs.libunwind
pkgs.libusb1
pkgs.fuse
# Wayland / display server
pkgs.wayland
pkgs.wayland-protocols
pkgs.libxkbcommon
pkgs.libdecor
# OpenGL / Vulkan
pkgs.libGL
pkgs.libGLU
pkgs.libglvnd
pkgs.vulkan-headers
pkgs.vulkan-loader
# X11
pkgs.libX11
pkgs.libxcb
pkgs.libXcursor
pkgs.libxi
pkgs.libxrandr
pkgs.libxscrnsaver
pkgs.libxtst
pkgs.libxinerama
# Audio
pkgs.alsa-lib
pkgs.libpulseaudio
pkgs.pipewire
# System integration
pkgs.dbus
pkgs.udev
pkgs.gtk3
];
# On macOS we deliberately avoid pulling Nix's cc-wrapper so CMake picks up
# Apple Clang and the Xcode SDK directly, matching the macOS CI workflow.
mkDarwinShell = pkgs:
pkgs.mkShellNoCC {
packages = commonDevTools pkgs;
shellHook = ''
echo "Dusklight dev shell (macOS)"
echo "Requires Xcode Command Line Tools for Apple Clang and the macOS SDK."
echo "Configure: cmake --preset macos-default-relwithdebinfo"
echo "Build: cmake --build --preset macos-default-relwithdebinfo"
'';
};
mkLinuxShell = pkgs:
pkgs.mkShell {
packages = (commonDevTools pkgs) ++ (linuxDevDeps pkgs);
shellHook = ''
echo "Dusklight dev shell (Linux)"
echo "Configure: cmake --preset linux-default-relwithdebinfo"
echo " cmake --preset linux-clang-relwithdebinfo"
echo "Build: cmake --build --preset <preset>"
'';
};
mkDevShell = pkgs:
if pkgs.stdenv.isDarwin
then mkDarwinShell pkgs
else mkLinuxShell pkgs;
in { in {
packages.x86_64-linux.default = mkDusklight (pkgsFor "x86_64-linux"); packages.x86_64-linux.default = dusk;
devShells = forAllSystems (system: {
default = mkDevShell (pkgsFor system);
});
}; };
} }
-4
View File
@@ -196,11 +196,7 @@ public:
/* 0x108 */ int mSkipTimer; /* 0x108 */ int mSkipTimer;
/* 0x10C */ int mSkipParameter; /* 0x10C */ int mSkipParameter;
/* 0x110 */ BOOL mIsSkipFade; /* 0x110 */ BOOL mIsSkipFade;
#if TARGET_PC
/* 0x114 */ char mSkipEventName[21];
#else
/* 0x114 */ char mSkipEventName[20]; /* 0x114 */ char mSkipEventName[20];
#endif
/* 0x128 */ u8 mCompulsory; /* 0x128 */ u8 mCompulsory;
/* 0x129 */ bool mRoomInfoSet; /* 0x129 */ bool mRoomInfoSet;
/* 0x12C */ int mRoomNo; /* 0x12C */ int mRoomNo;
-3
View File
@@ -223,9 +223,6 @@ private:
/* 0x8F */ u8 field_0x8f; /* 0x8F */ u8 field_0x8f;
/* 0x90 */ u8 field_0x90; /* 0x90 */ u8 field_0x90;
/* 0x91 */ u8 field_0x91; /* 0x91 */ u8 field_0x91;
#if TARGET_PC
bool previousMirror;
#endif
}; // Size: 0x94 }; // Size: 0x94
class dMap_HIO_list_c : public dMpath_HIO_n::hioList_c { class dMap_HIO_list_c : public dMpath_HIO_n::hioList_c {
-43
View File
@@ -1,43 +0,0 @@
#pragma once
#include <unordered_map>
#include "dusk/config_var.hpp"
namespace dusk {
enum class ActionBinds {
FIRST_PERSON_CAMERA,
CALL_MIDNA,
OPEN_DUSKLIGHT_MENU,
TURBO_SPEED_BUTTON,
COUNT,
};
struct ActionBindData {
std::array<config::ActionBindConfigVar, 4>* configVars{};
std::string actionName{};
};
struct ActionBindPressData {
bool pressedCurFrame{false};
bool pressedPrevFrame{false};
};
using ActionBindsMap = std::unordered_map<ActionBinds, ActionBindData>;
ActionBindsMap& getActionBinds();
bool isActionBound(ActionBinds action, u32 port);
void updateActionBindings();
bool getActionBindTrig(ActionBinds action, u32 port);
bool getActionBindHold(ActionBinds action, u32 port);
bool getActionBindHoldAnyPort(ActionBinds action);
int getActionBindButton(ActionBinds action, u32 port);
}
+1 -6
View File
@@ -7,12 +7,7 @@ namespace dusk {
* *
* This gets used for file paths and such, and cannot be changed! * This gets used for file paths and such, and cannot be changed!
*/ */
constexpr auto AppName = "Dusklight"; constexpr auto AppName = "Dusk";
/**
* Previous AppName to migrate data from.
*/
constexpr auto LegacyAppName = "Dusk";
/** /**
* \brief The internal organization name for the game. * \brief The internal organization name for the game.
-11
View File
@@ -1,19 +1,8 @@
#pragma once #pragma once
#include <cmath>
#include <dolphin/types.h> #include <dolphin/types.h>
namespace dusk::audio { namespace dusk::audio {
// Converts a 0-1 volume to a linear amplitude multiplier.
// The curve is -4 dB per 10% step: 100% = 0 dB, 90% = -4 dB, ..., 0% = -inf dB
inline f32 MasterVolumeToLinear(f32 v) {
if (v <= 0.0f) {
return 0.0f;
}
return std::pow(10.0f, (v - 1.0f) * 2.0f);
}
/** /**
* Initialize the audio system and start playing audio. * Initialize the audio system and start playing audio.
*/ */
-2
View File
@@ -5,7 +5,6 @@
#include <m_Do/m_Do_MemCardRWmng.h> #include <m_Do/m_Do_MemCardRWmng.h>
#include <m_Do/m_Do_MemCard.h> #include <m_Do/m_Do_MemCard.h>
#include <d/actor/d_a_alink.h>
void noAutoSave(); void noAutoSave();
void triggerAutoSave(); void triggerAutoSave();
@@ -14,6 +13,5 @@ void enterAutoSave();
void autoSaving(); void autoSaving();
void waitingForWrite(); void waitingForWrite();
void endAutoSave(); void endAutoSave();
void toggleAutoSave(bool enabled);
#endif #endif
-13
View File
@@ -1,7 +1,6 @@
#ifndef DUSK_CONFIG_HPP #ifndef DUSK_CONFIG_HPP
#define DUSK_CONFIG_HPP #define DUSK_CONFIG_HPP
#include <functional>
#include <stdexcept> #include <stdexcept>
#include "nlohmann/json.hpp" #include "nlohmann/json.hpp"
#include "config_var.hpp" #include "config_var.hpp"
@@ -112,18 +111,6 @@ void Save();
*/ */
ConfigVarBase* GetConfigVar(std::string_view name); ConfigVarBase* GetConfigVar(std::string_view name);
/**
* \brief Resets all custom action bindings for a specific port to nothing
*
* @param port The port to be cleared of action bindings
*/
void ClearAllActionBindings(int port);
/**
* \brief Call a function on every registered CVar.
*/
void EnumerateRegistered(std::function<void(ConfigVarBase&)> callback);
template <ConfigValue T> template <ConfigValue T>
const ConfigImplBase* GetConfigImpl() { const ConfigImplBase* GetConfigImpl() {
static ConfigImpl<T> config; static ConfigImpl<T> config;
-61
View File
@@ -48,13 +48,6 @@ enum class ConfigVarLayer : u8 {
* Will not get saved to config. * Will not get saved to config.
*/ */
Override, Override,
/**
* The CVar is temporarily overridden by speedrun mode.
* Will not get saved to config. Cleared when speedrun mode is disabled.
* Lower priority than Override, so launch args still win.
*/
Speedrun,
}; };
class ConfigImplBase; class ConfigImplBase;
@@ -120,12 +113,6 @@ public:
* This is necessary to make it legal to access. * This is necessary to make it legal to access.
*/ */
void markRegistered(); void markRegistered();
/**
* Clear a speedrun-mode override if one is active on this CVar.
* Safe to call on any CVar, no-op if not at the Speedrun layer.
*/
virtual void clearSpeedrunOverride() {}
}; };
template <typename T> template <typename T>
@@ -175,7 +162,6 @@ class ConfigVar : public ConfigVarBase {
T defaultValue; T defaultValue;
T value; T value;
T overrideValue; T overrideValue;
ConfigVarLayer priorLayer = ConfigVarLayer::Default;
public: public:
/** /**
@@ -203,7 +189,6 @@ public:
case ConfigVarLayer::Value: case ConfigVarLayer::Value:
return value; return value;
case ConfigVarLayer::Override: case ConfigVarLayer::Override:
case ConfigVarLayer::Speedrun:
return overrideValue; return overrideValue;
default: default:
abort(); abort();
@@ -254,54 +239,8 @@ public:
overrideValue = std::move(newValue); overrideValue = std::move(newValue);
layer = ConfigVarLayer::Override; layer = ConfigVarLayer::Override;
} }
/**
* \brief Give a CVar a speedrun-mode override value.
*
* Lower priority than a launch-arg override. Cleared when speedrun mode is disabled.
* The overridden value will not get saved to config.
*
* @param newValue The new value the CVar will get.
*/
void setSpeedrunValue(T newValue) {
checkRegistered();
if (layer != ConfigVarLayer::Override) {
priorLayer = layer;
overrideValue = std::move(newValue);
layer = ConfigVarLayer::Speedrun;
}
}
void clearOverride() {
checkRegistered();
if (layer == ConfigVarLayer::Override) {
overrideValue = {};
layer = ConfigVarLayer::Value;
}
}
void clearSpeedrunOverride() override {
checkRegistered();
if (layer == ConfigVarLayer::Speedrun) {
overrideValue = {};
layer = priorLayer;
}
}
/**
* \brief Get the user-persisted value, ignoring any temporary overrides.
*
* Used by Save() to write the correct value even when a speedrun override is active.
*/
[[nodiscard]] constexpr const T& getValueForSave() const noexcept {
checkRegistered();
const ConfigVarLayer effectiveLayer = (layer == ConfigVarLayer::Speedrun) ? priorLayer : layer;
return effectiveLayer == ConfigVarLayer::Default ? defaultValue : value;
}
}; };
using ActionBindConfigVar = ConfigVar<int>;
} }
#endif // DUSK_CONFIG_VAR_HPP #endif // DUSK_CONFIG_VAR_HPP
+4 -13
View File
@@ -1,17 +1,8 @@
#pragma once #pragma once
namespace dusk::crash_reporting { namespace dusk {
enum class Consent { void InitializeCrashReporting();
Unavailable, void ShutdownCrashReporting();
Unknown,
Given,
Revoked,
};
void initialize(); } // namespace dusk
void shutdown();
Consent get_consent();
void set_consent(bool enabled);
} // namespace dusk::crash_reporting
-22
View File
@@ -227,28 +227,6 @@ struct BE<Mtx> {
} }
}; };
typedef f32 Mtx23[2][3];
template <>
struct BE<Mtx23> {
BE<f32> contents[2][3];
auto& operator[](int x) {
return contents[x];
}
auto& operator[](int x) const {
return contents[x];
}
void to_host(Mtx23& mtx) const {
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 3; j++) {
mtx[i][j] = contents[i][j];
}
}
}
};
template<typename T> template<typename T>
void be_swap(T& val) { void be_swap(T& val) {
val = BE<T>::swap(val); val = BE<T>::swap(val);
+1 -3
View File
@@ -4,7 +4,6 @@
#include <stdbool.h> #include <stdbool.h>
#include <stddef.h> #include <stddef.h>
#include <stdint.h> #include <stdint.h>
#include "settings.h"
class camera_process_class; class camera_process_class;
class view_class; class view_class;
@@ -18,8 +17,7 @@ void ensure_initialized();
void begin_record(); void begin_record();
void end_record(); void end_record();
void begin_sim_tick(); void begin_sim_tick();
uint64_t sim_tick_seq(); void begin_frame(bool enabled, bool is_sim_frame, float step);
void begin_frame(FrameInterpMode mode, bool is_sim_frame, float step);
void interpolate(); void interpolate();
float get_interpolation_step(); float get_interpolation_step();
+1
View File
@@ -14,6 +14,7 @@ constexpr const char* SHOW_DEBUG_OVERLAY = "F3";
constexpr const char* SHOW_HEAP_VIEWER = "F4"; constexpr const char* SHOW_HEAP_VIEWER = "F4";
constexpr const char* SHOW_PLAYER_INFO = "F5"; constexpr const char* SHOW_PLAYER_INFO = "F5";
constexpr const char* SHOW_SAVE_EDITOR = "F6"; constexpr const char* SHOW_SAVE_EDITOR = "F6";
constexpr const char* SHOW_MAP_LOADER = "F7";
constexpr const char* SHOW_STATE_SHARE = "F8"; constexpr const char* SHOW_STATE_SHARE = "F8";
constexpr const char* SHOW_DEBUG_CAMERA = "F9"; constexpr const char* SHOW_DEBUG_CAMERA = "F9";
constexpr const char* SHOW_AUDIO_DEBUG = "F10"; constexpr const char* SHOW_AUDIO_DEBUG = "F10";
+5 -9
View File
@@ -1,13 +1,14 @@
#ifndef DUSK_IO_HPP #ifndef DUSK_IO_HPP
#define DUSK_IO_HPP #define DUSK_IO_HPP
#include <filesystem>
#include <vector> #include <vector>
#include <filesystem>
// I can't believe it's 2026 and neither SDL (no error codes) nor // I can't believe it's 2026 and neither SDL (no error codes) nor
// C++ (no error codes) have a file system API functional enough for me to use. // C++ (no error codes) have a file system API functional enough for me to use.
// Here you go, this one's inspired by C#. I only wrote the functions I need. // Here you go, this one's inspired by C#. I only wrote the functions I need.
namespace dusk::io { namespace dusk::io {
/** /**
@@ -82,7 +83,9 @@ public:
/** /**
* Get direct access to the underlying FILE* handle. * Get direct access to the underlying FILE* handle.
*/ */
[[nodiscard]] void* GetFileHandle() const noexcept { return file; } [[nodiscard]] void* GetFileHandle() const noexcept {
return file;
}
/** /**
* Write data to the file. * Write data to the file.
@@ -92,14 +95,7 @@ public:
FILE* ToInner(); FILE* ToInner();
}; };
/**
* Converts a std::filesystem::path to a std::string, UTF-8, without exploding on Windows.
*/
inline std::string fs_path_to_string(const std::filesystem::path& path) {
const auto u8str = path.u8string();
return {reinterpret_cast<const char*>(u8str.c_str())};
} }
} // namespace dusk::io
#endif // DUSK_IO_HPP #endif // DUSK_IO_HPP
+28 -18
View File
@@ -1,26 +1,36 @@
#ifndef DUSK_MAIN_H #ifndef DUSK_MAIN_H
#define DUSK_MAIN_H #define DUSK_MAIN_H
#include <filesystem> #if defined(__APPLE__)
#include <TargetConditionals.h>
namespace dusk {
extern bool IsRunning;
extern bool IsShuttingDown;
extern bool IsGameLaunched;
extern bool RestartRequested;
extern std::filesystem::path ConfigPath;
extern std::filesystem::path CachePath;
#if defined(__ANDROID__) || (defined(TARGET_OS_IOS) && TARGET_OS_IOS) || \
(defined(TARGET_OS_TV) && TARGET_OS_TV)
inline constexpr bool SupportsProcessRestart = false;
#else
inline constexpr bool SupportsProcessRestart = true;
#endif #endif
void RequestRestart() noexcept; #include <filesystem>
} // namespace dusk #if defined(_WIN32) || \
(defined(__APPLE__) && !TARGET_OS_IOS && !TARGET_OS_TV && !TARGET_OS_MACCATALYST) || \
(defined(__linux__) && !defined(__ANDROID__))
#define DUSK_CAN_OPEN_DATA_FOLDER 1
#else
#define DUSK_CAN_OPEN_DATA_FOLDER 0
#endif
namespace dusk {
extern bool IsRunning;
extern bool IsShuttingDown;
extern bool IsGameLaunched;
extern bool RestartRequested;
extern std::filesystem::path ConfigPath;
#if defined(__ANDROID__) || (defined(TARGET_OS_IOS) && TARGET_OS_IOS) || \
(defined(TARGET_OS_TV) && TARGET_OS_TV)
inline constexpr bool SupportsProcessRestart = false;
#else
inline constexpr bool SupportsProcessRestart = true;
#endif
void RequestRestart() noexcept;
bool OpenDataFolder();
}
#endif // DUSK_MAIN_H #endif // DUSK_MAIN_H
+3 -49
View File
@@ -1,8 +1,6 @@
#ifndef DUSK_CONFIG_H #ifndef DUSK_CONFIG_H
#define DUSK_CONFIG_H #define DUSK_CONFIG_H
#include <array>
#include "dusk/config_var.hpp" #include "dusk/config_var.hpp"
namespace dusk { namespace dusk {
@@ -15,11 +13,6 @@ enum class BloomMode : int {
Dusk = 2, Dusk = 2,
}; };
enum class Resampler : int {
Bilinear = 0,
Area = 1,
};
enum class GameLanguage : u8 { enum class GameLanguage : u8 {
English = OS_LANGUAGE_ENGLISH, English = OS_LANGUAGE_ENGLISH,
German = OS_LANGUAGE_GERMAN, German = OS_LANGUAGE_GERMAN,
@@ -39,12 +32,6 @@ enum class GyroMode : u8 {
Mouse = 1, Mouse = 1,
}; };
enum class FrameInterpMode : u8 {
Off = 0,
Capped = 1,
Unlimited = 2,
};
namespace config { namespace config {
template <> template <>
struct ConfigEnumRange<BloomMode> { struct ConfigEnumRange<BloomMode> {
@@ -52,12 +39,6 @@ struct ConfigEnumRange<BloomMode> {
static constexpr auto max = BloomMode::Dusk; static constexpr auto max = BloomMode::Dusk;
}; };
template <>
struct ConfigEnumRange<Resampler> {
static constexpr auto min = Resampler::Bilinear;
static constexpr auto max = Resampler::Area;
};
template <> template <>
struct ConfigEnumRange<GameLanguage> { struct ConfigEnumRange<GameLanguage> {
static constexpr auto min = GameLanguage::English; static constexpr auto min = GameLanguage::English;
@@ -75,13 +56,7 @@ struct ConfigEnumRange<GyroMode> {
static constexpr auto min = GyroMode::Sensor; static constexpr auto min = GyroMode::Sensor;
static constexpr auto max = GyroMode::Mouse; static constexpr auto max = GyroMode::Mouse;
}; };
}
template <>
struct ConfigEnumRange<FrameInterpMode> {
static constexpr auto min = FrameInterpMode::Off;
static constexpr auto max = FrameInterpMode::Unlimited;
};
} // namespace config
// Persistent user settings // Persistent user settings
@@ -95,7 +70,6 @@ struct UserSettings {
ConfigVar<bool> lockAspectRatio; ConfigVar<bool> lockAspectRatio;
ConfigVar<bool> enableFpsOverlay; ConfigVar<bool> enableFpsOverlay;
ConfigVar<int> fpsOverlayCorner; ConfigVar<int> fpsOverlayCorner;
ConfigVar<int> maxFrameRate;
} video; } video;
struct { struct {
@@ -141,20 +115,16 @@ struct UserSettings {
ConfigVar<bool> enableLinkDollRotation; ConfigVar<bool> enableLinkDollRotation;
ConfigVar<bool> enableAchievementToasts; ConfigVar<bool> enableAchievementToasts;
ConfigVar<bool> enableControllerToasts; ConfigVar<bool> enableControllerToasts;
ConfigVar<bool> enableDiscordPresence;
// Graphics // Graphics
ConfigVar<BloomMode> bloomMode; ConfigVar<BloomMode> bloomMode;
ConfigVar<float> bloomMultiplier; ConfigVar<float> bloomMultiplier;
ConfigVar<bool> disableWaterRefraction; ConfigVar<bool> disableWaterRefraction;
ConfigVar<bool> enableTextureReplacements; ConfigVar<bool> enableFrameInterpolation;
ConfigVar<FrameInterpMode> enableFrameInterpolation;
ConfigVar<int> internalResolutionScale; ConfigVar<int> internalResolutionScale;
ConfigVar<int> shadowResolutionMultiplier; ConfigVar<int> shadowResolutionMultiplier;
ConfigVar<Resampler> resampler;
ConfigVar<bool> enableDepthOfField; ConfigVar<bool> enableDepthOfField;
ConfigVar<bool> enableMapBackground; ConfigVar<bool> enableMapBackground;
ConfigVar<bool> disableCutscenePillarboxing;
// Audio // Audio
ConfigVar<bool> noLowHpSound; ConfigVar<bool> noLowHpSound;
@@ -174,8 +144,6 @@ struct UserSettings {
ConfigVar<bool> freeCamera; ConfigVar<bool> freeCamera;
ConfigVar<bool> invertCameraXAxis; ConfigVar<bool> invertCameraXAxis;
ConfigVar<bool> invertCameraYAxis; ConfigVar<bool> invertCameraYAxis;
ConfigVar<bool> invertFirstPersonXAxis;
ConfigVar<bool> invertFirstPersonYAxis;
ConfigVar<float> freeCameraSensitivity; ConfigVar<float> freeCameraSensitivity;
ConfigVar<bool> debugFlyCam; ConfigVar<bool> debugFlyCam;
ConfigVar<bool> debugFlyCamLockEvents; ConfigVar<bool> debugFlyCamLockEvents;
@@ -184,7 +152,6 @@ struct UserSettings {
// Cheats // Cheats
ConfigVar<bool> infiniteHearts; ConfigVar<bool> infiniteHearts;
ConfigVar<bool> infiniteArrows; ConfigVar<bool> infiniteArrows;
ConfigVar<bool> infiniteSeeds;
ConfigVar<bool> infiniteBombs; ConfigVar<bool> infiniteBombs;
ConfigVar<bool> infiniteOil; ConfigVar<bool> infiniteOil;
ConfigVar<bool> infiniteOxygen; ConfigVar<bool> infiniteOxygen;
@@ -195,25 +162,19 @@ struct UserSettings {
ConfigVar<bool> alwaysGreatspin; ConfigVar<bool> alwaysGreatspin;
ConfigVar<bool> enableFastIronBoots; ConfigVar<bool> enableFastIronBoots;
ConfigVar<bool> canTransformAnywhere; ConfigVar<bool> canTransformAnywhere;
ConfigVar<bool> fastRoll;
ConfigVar<bool> fastSpinner; ConfigVar<bool> fastSpinner;
ConfigVar<bool> freeMagicArmor; ConfigVar<bool> freeMagicArmor;
ConfigVar<bool> invincibleEnemies;
// Technical // Technical
ConfigVar<bool> restoreWiiGlitches; ConfigVar<bool> restoreWiiGlitches;
// Controls // Controls
ConfigVar<bool> enableTurboKeybind; ConfigVar<bool> enableTurboKeybind;
ConfigVar<bool> enableResetKeybind;
// Tools // Tools
ConfigVar<bool> speedrunMode; ConfigVar<bool> speedrunMode;
ConfigVar<bool> liveSplitEnabled; ConfigVar<bool> liveSplitEnabled;
ConfigVar<bool> showSpeedrunRTATimer;
ConfigVar<bool> recordingMode; ConfigVar<bool> recordingMode;
ConfigVar<bool> showInputViewer;
ConfigVar<bool> showInputViewerGyro;
} game; } game;
struct { struct {
@@ -223,18 +184,11 @@ struct UserSettings {
ConfigVar<bool> skipPreLaunchUI; ConfigVar<bool> skipPreLaunchUI;
ConfigVar<bool> showPipelineCompilation; ConfigVar<bool> showPipelineCompilation;
ConfigVar<bool> wasPresetChosen; ConfigVar<bool> wasPresetChosen;
ConfigVar<bool> enableCrashReporting;
ConfigVar<bool> checkForUpdates; ConfigVar<bool> checkForUpdates;
ConfigVar<int> cardFileType; ConfigVar<int> cardFileType;
ConfigVar<bool> enableAdvancedSettings; ConfigVar<bool> enableAdvancedSettings;
} backend; } backend;
// Arrays of size 4 for 4 ports
struct {
std::array<ActionBindConfigVar, 4> firstPersonCamera;
std::array<ActionBindConfigVar, 4> callMidna;
std::array<ActionBindConfigVar, 4> openDusklightMenu;
std::array<ActionBindConfigVar, 4> turboSpeedButton;
} actionBindings;
}; };
UserSettings& getSettings(); UserSettings& getSettings();
-41
View File
@@ -1,41 +0,0 @@
#pragma once
#include <aurora/aurora.h>
namespace dusk {
struct SpeedrunInfo {
void startRun() {
m_isRunStarted = true;
m_startTimestamp = OSGetTime();
}
void stopRun() {
m_isRunStarted = false;
m_endTimestamp = OSGetTime() - m_startTimestamp;
}
void reset() {
m_isRunStarted = false;
m_startTimestamp = 0;
m_endTimestamp = 0;
m_isPauseIGT = false;
m_loadStartTimestamp = 0;
m_totalLoadTime = 0;
m_igtTimer = 0;
}
bool m_isRunStarted = false;
OSTime m_startTimestamp = 0;
OSTime m_endTimestamp = 0;
bool m_isPauseIGT = false;
OSTime m_loadStartTimestamp = 0;
OSTime m_totalLoadTime = 0;
OSTime m_igtTimer = 0;
};
extern SpeedrunInfo m_speedrunInfo;
void resetForSpeedrunMode();
} // namespace dusk
+4 -40
View File
@@ -17,24 +17,16 @@
#include <shellapi.h> #include <shellapi.h>
#include <intrin.h> #include <intrin.h>
#endif #endif
#ifdef __APPLE__
#include <mach/mach_time.h>
#if defined(__x86_64__) || defined(__i386__)
#include <immintrin.h>
#endif
#endif
class Limiter { class Limiter {
public: public:
using duration_t = Uint64; using duration_t = Uint64;
void Reset() { void Reset() { m_oldTime = SDL_GetTicksNS(); }
m_oldTime = SDL_GetTicksNS();
}
duration_t Sleep(duration_t targetFrameTime) { void Sleep(duration_t targetFrameTime) {
if (targetFrameTime == 0) { if (targetFrameTime == 0) {
return 0; return;
} }
const Uint64 start = SDL_GetTicksNS(); const Uint64 start = SDL_GetTicksNS();
@@ -49,8 +41,6 @@ public:
} }
} }
Reset(); Reset();
return adjustedSleepTime;
} }
duration_t SleepTime(duration_t targetFrameTime) { duration_t SleepTime(duration_t targetFrameTime) {
@@ -84,6 +74,7 @@ private:
if (!initialized || numSleeps++ % 1000 == 0) { if (!initialized || numSleeps++ % 1000 == 0) {
LARGE_INTEGER freq; LARGE_INTEGER freq;
if (QueryPerformanceFrequency(&freq) == 0) { if (QueryPerformanceFrequency(&freq) == 0) {
DuskLog.warn("QueryPerformanceFrequency failed: {}", GetLastError());
return; return;
} }
countPerNs = static_cast<double>(freq.QuadPart) / 1e9; countPerNs = static_cast<double>(freq.QuadPart) / 1e9;
@@ -107,33 +98,6 @@ private:
#endif #endif
} while (current.QuadPart - start.QuadPart < ticksToWait); } while (current.QuadPart - start.QuadPart < ticksToWait);
} }
#elif defined (__APPLE__)
void NanoSleep(const duration_t duration) {
// Hybrid approach using Apple Mach
uint64_t start_mach = mach_absolute_time();
mach_timebase_info_data_t timebase_info;
mach_timebase_info(&timebase_info);
uint64_t total_mach_ticks = (duration * timebase_info.denom) / timebase_info.numer;
uint64_t target_mach = start_mach + total_mach_ticks;
uint64_t buffer_ns = 2'000'000ULL;
uint64_t buffer_mach_ticks = (buffer_ns * timebase_info.denom) / timebase_info.numer;
if (total_mach_ticks > buffer_mach_ticks) {
uint64_t sleep_until_mach = target_mach - buffer_mach_ticks;
mach_wait_until(sleep_until_mach);
}
while (mach_absolute_time() < target_mach) {
#if defined(__aarch64__) || defined(__arm__)
asm volatile("yield" ::: "memory"); // Hardware hint, not a scheduler hint.
#else
_mm_pause();
#endif
}
}
#else #else
void NanoSleep(const duration_t duration) { SDL_DelayPrecise(duration); } void NanoSleep(const duration_t duration) { SDL_DelayPrecise(duration); }
#endif #endif
+1 -1
View File
@@ -108,7 +108,7 @@ struct fopAcM_search_prm {
struct fOpAcm_HIO_entry_c : public mDoHIO_entry_c { struct fOpAcm_HIO_entry_c : public mDoHIO_entry_c {
virtual ~fOpAcm_HIO_entry_c() {} virtual ~fOpAcm_HIO_entry_c() {}
#if DEBUG && !TARGET_PC #if DEBUG
void removeHIO(const fopAc_ac_c* i_this) { removeHIO(*i_this); } void removeHIO(const fopAc_ac_c* i_this) { removeHIO(*i_this); }
void removeHIO(const fopAc_ac_c& i_this) { removeHIO(i_this.base); } void removeHIO(const fopAc_ac_c& i_this) { removeHIO(i_this.base); }
void removeHIO(const fopEn_enemy_c& i_this) { removeHIO(i_this.base); } void removeHIO(const fopEn_enemy_c& i_this) { removeHIO(i_this.base); }
@@ -116,7 +116,7 @@ private:
* *
*/ */
struct J2DIndTexMtxInfo { struct J2DIndTexMtxInfo {
/* 0x00 */ BE(Mtx23) mMtx; /* 0x00 */ Mtx23 mMtx;
/* 0x18 */ s8 mScaleExp; /* 0x18 */ s8 mScaleExp;
J2DIndTexMtxInfo& operator=(const J2DIndTexMtxInfo& other) { J2DIndTexMtxInfo& operator=(const J2DIndTexMtxInfo& other) {
@@ -287,28 +287,28 @@ template <typename T>
class JASPoolAllocObject { class JASPoolAllocObject {
public: public:
#if TARGET_PC #if TARGET_PC
static void* operator new(size_t n, JKRHeapToken) IF_DUSK(noexcept) { static void* operator new(size_t n, JKRHeapToken) {
return operator new(n); return operator new(n);
} }
#endif #endif
static void* operator new(size_t n) IF_DUSK(noexcept) { static void* operator new(size_t n) {
#if PLATFORM_GCN #if PLATFORM_GCN
JASMemPool<T>& memPool_ = getMemPool_(); JASMemPool<T>& memPool_ = getMemPool_();
#endif #endif
return memPool_.alloc(n); return memPool_.alloc(n);
} }
static void* operator new(size_t n, void* ptr) IF_DUSK(noexcept) { static void* operator new(size_t n, void* ptr) {
return ptr; return ptr;
} }
#if TARGET_PC #if TARGET_PC
static void operator delete(void* ptr, size_t n, JKRHeapToken) IF_DUSK(noexcept) { static void operator delete(void* ptr, size_t n, JKRHeapToken) {
operator delete(ptr, n); operator delete(ptr, n);
} }
#endif #endif
static void operator delete(void* ptr, size_t n) IF_DUSK(noexcept) { static void operator delete(void* ptr, size_t n) {
#if PLATFORM_GCN #if PLATFORM_GCN
JASMemPool<T>& memPool_ = getMemPool_(); JASMemPool<T>& memPool_ = getMemPool_();
#endif #endif
@@ -402,28 +402,28 @@ template <typename T>
class JASPoolAllocObject_MultiThreaded { class JASPoolAllocObject_MultiThreaded {
public: public:
#if TARGET_PC #if TARGET_PC
static void* operator new(size_t n, JKRHeapToken) IF_DUSK(noexcept) { static void* operator new(size_t n, JKRHeapToken) {
return operator new(n); return operator new(n);
} }
#endif #endif
static void* operator new(size_t n) IF_DUSK(noexcept) { static void* operator new(size_t n) {
#if PLATFORM_GCN #if PLATFORM_GCN
JASMemPool_MultiThreaded<T>& memPool_ = getMemPool(); JASMemPool_MultiThreaded<T>& memPool_ = getMemPool();
#endif #endif
return memPool_.alloc(n); return memPool_.alloc(n);
} }
static void* operator new(size_t n, void* ptr) IF_DUSK(noexcept) { static void* operator new(size_t n, void* ptr) {
return ptr; return ptr;
} }
#if TARGET_PC #if TARGET_PC
static void operator delete(void* ptr, size_t n, JKRHeapToken) IF_DUSK(noexcept) { static void operator delete(void* ptr, size_t n, JKRHeapToken) {
return operator delete(ptr, n); return operator delete(ptr, n);
} }
#endif #endif
static void operator delete(void* ptr, size_t n) IF_DUSK(noexcept) { static void operator delete(void* ptr, size_t n) {
#if PLATFORM_GCN #if PLATFORM_GCN
JASMemPool_MultiThreaded<T>& memPool_ = getMemPool(); JASMemPool_MultiThreaded<T>& memPool_ = getMemPool();
#endif #endif
+15 -19
View File
@@ -237,11 +237,11 @@ enum class JKRHeapToken {
Dummy Dummy
}; };
inline void* operator new(size_t, JKRHeapToken, void* where) noexcept { inline void* operator new(size_t, JKRHeapToken, void* where) {
return where; return where;
} }
inline void* operator new[](size_t, JKRHeapToken, void* where) noexcept { inline void* operator new[](size_t, JKRHeapToken, void* where) {
return where; return where;
} }
@@ -264,21 +264,21 @@ inline void* operator new[](size_t, JKRHeapToken, void* where) noexcept {
#define JKR_HEAP_TOKEN_PARAM #define JKR_HEAP_TOKEN_PARAM
#endif #endif
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept); void* operator new(size_t size JKR_HEAP_TOKEN_PARAM);
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, int alignment) IF_DUSK(noexcept); void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, int alignment);
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment) IF_DUSK(noexcept); void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment);
// On PC, these new[] overloads are only used to catch usages of JKR_NEW with []. // On PC, these new[] overloads are only used to catch usages of JKR_NEW with [].
void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept); void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM);
void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM, int alignment) IF_DUSK(noexcept); void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM, int alignment);
void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment) IF_DUSK(noexcept); void* operator new[](size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment);
void operator delete(void* ptr JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept); void operator delete(void* ptr JKR_HEAP_TOKEN_PARAM);
void operator delete[](void* ptr JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept); void operator delete[](void* ptr JKR_HEAP_TOKEN_PARAM);
#if TARGET_PC #if TARGET_PC
template<typename T> template<typename T>
void jkrDelete(T* ptr) IF_DUSK(noexcept) { void jkrDelete(T* ptr) {
if (ptr == nullptr) { if (ptr == nullptr) {
return; return;
} }
@@ -298,7 +298,7 @@ void jkrDelete(T* ptr) IF_DUSK(noexcept) {
} }
template<> template<>
inline void jkrDelete(void* ptr) IF_DUSK(noexcept) { inline void jkrDelete(void* ptr) {
if (ptr == nullptr) { if (ptr == nullptr) {
return; return;
} }
@@ -322,7 +322,7 @@ constexpr bool newArgsHasCustomAlignment() {
} }
template<typename T, typename... Args> template<typename T, typename... Args>
T* jkrNewArray(size_t count, std::in_place_type_t<T>, Args&&... args) IF_DUSK(noexcept) { T* jkrNewArray(size_t count, std::in_place_type_t<T>, Args&&... args) {
size_t allocSize = count * sizeof(T); size_t allocSize = count * sizeof(T);
if constexpr (!std::is_trivially_destructible<T>()) { if constexpr (!std::is_trivially_destructible<T>()) {
static_assert( static_assert(
@@ -333,10 +333,6 @@ T* jkrNewArray(size_t count, std::in_place_type_t<T>, Args&&... args) IF_DUSK(no
} }
void* ptr = operator new(allocSize, JKRHeapToken::Dummy, args...); void* ptr = operator new(allocSize, JKRHeapToken::Dummy, args...);
if (!ptr) {
return nullptr;
}
T* dataPtr; T* dataPtr;
if constexpr (!std::is_trivially_destructible<T>()) { if constexpr (!std::is_trivially_destructible<T>()) {
auto length = static_cast<size_t*>(ptr); auto length = static_cast<size_t*>(ptr);
@@ -356,7 +352,7 @@ T* jkrNewArray(size_t count, std::in_place_type_t<T>, Args&&... args) IF_DUSK(no
} }
template<typename T> template<typename T>
void jkrDeleteArray(T* pointer) IF_DUSK(noexcept) { void jkrDeleteArray(T* pointer) {
if (pointer == nullptr) { if (pointer == nullptr) {
return; return;
} }
@@ -376,7 +372,7 @@ void jkrDeleteArray(T* pointer) IF_DUSK(noexcept) {
} }
template<> template<>
inline void jkrDeleteArray(void* pointer) IF_DUSK(noexcept) { inline void jkrDeleteArray(void* pointer) {
if (pointer == nullptr) { if (pointer == nullptr) {
return; return;
} }
-6
View File
@@ -68,14 +68,8 @@ void J2DIndTevStage::load(u8 tevStage) {
} }
void J2DIndTexMtx::load(u8 indTexMtx) { void J2DIndTexMtx::load(u8 indTexMtx) {
#ifdef TARGET_PC
Mtx23 mtx;
mIndTexMtxInfo.mMtx.to_host(mtx);
GXSetIndTexMtx((GXIndTexMtxID)(GX_ITM_0 + indTexMtx), mtx, mIndTexMtxInfo.mScaleExp);
#else
GXSetIndTexMtx((GXIndTexMtxID)(GX_ITM_0 + indTexMtx), mIndTexMtxInfo.mMtx, GXSetIndTexMtx((GXIndTexMtxID)(GX_ITM_0 + indTexMtx), mIndTexMtxInfo.mMtx,
mIndTexMtxInfo.mScaleExp); mIndTexMtxInfo.mScaleExp);
#endif
} }
void J2DIndTexCoordScale::load(u8 indTexStage) { void J2DIndTexCoordScale::load(u8 indTexStage) {
+7 -7
View File
@@ -370,28 +370,28 @@ constexpr auto FRAME_PERIOD = std::chrono::duration_cast<std::chrono::nanosecond
constexpr auto RETRACE_PERIOD = FRAME_PERIOD / 2; constexpr auto RETRACE_PERIOD = FRAME_PERIOD / 2;
static void waitPrecise(Limiter& limiter, Limiter::duration_t targetNs) { static void waitPrecise(Limiter& limiter, Limiter::duration_t targetNs) {
const auto sleepTime = limiter.Sleep(targetNs); const auto sleepTime = limiter.SleepTime(targetNs);
dusk::frameUsagePct = dusk::frameUsagePct =
100.0f * (1.0f - static_cast<float>(sleepTime) / static_cast<float>(targetNs)); 100.0f * (1.0f - static_cast<float>(sleepTime) / static_cast<float>(targetNs));
limiter.Sleep(targetNs);
} }
#endif #endif
static void waitForTick(u32 p1, u16 p2) { static void waitForTick(u32 p1, u16 p2) {
#if TARGET_PC #if TARGET_PC
static Limiter limiter; if (dusk::getSettings().game.enableFrameInterpolation && !dusk::getTransientSettings().skipFrameRateLimit) {
dusk::frameUsagePct = 0.f;
if (dusk::frame_interp::is_enabled() && !dusk::getTransientSettings().skipFrameRateLimit) { return;
dusk::frameUsagePct = 0.f;
return;
} }
if (dusk::getTransientSettings().skipFrameRateLimit) { if (dusk::getTransientSettings().skipFrameRateLimit) {
p1 = OS_TIMER_CLOCK / 120; p1 = OS_TIMER_CLOCK / 120;
} }
#if TARGET_PC
if (fopOvlpM_IsPeek() && dusk::getTransientSettings().stateShareLoadActive) { if (fopOvlpM_IsPeek() && dusk::getTransientSettings().stateShareLoadActive) {
return; return;
} }
#endif
ZoneScopedC(tracy::Color::DimGray); ZoneScopedC(tracy::Color::DimGray);
#endif #endif
+8 -8
View File
@@ -559,7 +559,7 @@ void* operator new(size_t size) {
return JKRHeap::alloc(size, 4, NULL); return JKRHeap::alloc(size, 4, NULL);
} }
#else #else
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM) noexcept { void* operator new(size_t size JKR_HEAP_TOKEN_PARAM) {
if (sCurrentHeap == NULL) { if (sCurrentHeap == NULL) {
return fallback_alloc(size, 0, false); return fallback_alloc(size, 0, false);
} }
@@ -576,7 +576,7 @@ void* operator new(size_t size, int alignment) {
return JKRHeap::alloc(size, alignment, NULL); return JKRHeap::alloc(size, alignment, NULL);
} }
#else #else
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, int alignment) noexcept { void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, int alignment) {
void* mem = JKRHeap::alloc(size, alignment, nullptr); void* mem = JKRHeap::alloc(size, alignment, nullptr);
if (mem == nullptr) { if (mem == nullptr) {
return fallback_alloc(size, abs(alignment), true); return fallback_alloc(size, abs(alignment), true);
@@ -585,7 +585,7 @@ void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, int alignment) noexcept {
} }
#endif #endif
void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment) IF_DUSK(noexcept) { void* operator new(size_t size JKR_HEAP_TOKEN_PARAM, JKRHeap* heap, int alignment) {
void* mem = JKRHeap::alloc(size, alignment, heap); void* mem = JKRHeap::alloc(size, alignment, heap);
#if TARGET_PC #if TARGET_PC
if (mem == nullptr) { if (mem == nullptr) {
@@ -600,7 +600,7 @@ void* operator new[](size_t size) {
return JKRHeap::alloc(size, 4, NULL); return JKRHeap::alloc(size, 4, NULL);
} }
#else #else
void* operator new[](size_t JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept) { void* operator new[](size_t JKR_HEAP_TOKEN_PARAM) {
OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead"); OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead");
} }
#endif #endif
@@ -610,12 +610,12 @@ void* operator new[](size_t size, int alignment) {
return JKRHeap::alloc(size, alignment, NULL); return JKRHeap::alloc(size, alignment, NULL);
} }
#else #else
void* operator new[](size_t JKR_HEAP_TOKEN_PARAM, int) IF_DUSK(noexcept) { void* operator new[](size_t JKR_HEAP_TOKEN_PARAM, int) {
OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead"); OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead");
} }
#endif #endif
void* operator new[](size_t JKR_HEAP_TOKEN_PARAM, JKRHeap*, int) IF_DUSK(noexcept) { void* operator new[](size_t JKR_HEAP_TOKEN_PARAM, JKRHeap*, int) {
OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead"); OSPanic(__FILE__, __LINE__, "Allocation should go through JKR_NEW_ARRAY instead");
} }
@@ -624,7 +624,7 @@ void operator delete(void* ptr) {
JKRHeap::free(ptr, NULL); JKRHeap::free(ptr, NULL);
} }
#else #else
void operator delete(void* ptr JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept) { void operator delete(void* ptr JKR_HEAP_TOKEN_PARAM) {
if (ptr == NULL) if (ptr == NULL)
return; return;
JKRHeap* heap = JKRHeap::findFromRoot(ptr); JKRHeap* heap = JKRHeap::findFromRoot(ptr);
@@ -645,7 +645,7 @@ void operator delete[](void* ptr) {
JKRHeap::free(ptr, NULL); JKRHeap::free(ptr, NULL);
} }
#else #else
void operator delete[](void* ptr JKR_HEAP_TOKEN_PARAM) IF_DUSK(noexcept) { void operator delete[](void* ptr JKR_HEAP_TOKEN_PARAM) {
if (ptr == NULL) if (ptr == NULL)
return; return;
JKRHeap* heap = JKRHeap::findFromRoot(ptr); JKRHeap* heap = JKRHeap::findFromRoot(ptr);
@@ -655,7 +655,7 @@ value_or_fun:
value: value:
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled() && u <= 5 && if (dusk::getSettings().game.enableFrameInterpolation && u <= 5 &&
(operation == data::UNK_0x2 || operation == data::UNK_0x3 || operation == data::UNK_0x12)) (operation == data::UNK_0x2 || operation == data::UNK_0x3 || operation == data::UNK_0x12))
{ {
dusk::frame_interp::request_presentation_sync(); dusk::frame_interp::request_presentation_sync();
@@ -666,7 +666,7 @@ value:
value_n: value_n:
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled() && if (dusk::getSettings().game.enableFrameInterpolation &&
(pN == TAdaptor_camera::sauVariableValue_3_POSITION_XYZ || pN == TAdaptor_camera::sauVariableValue_3_TARGET_POSITION_XYZ) && (pN == TAdaptor_camera::sauVariableValue_3_POSITION_XYZ || pN == TAdaptor_camera::sauVariableValue_3_TARGET_POSITION_XYZ) &&
(operation == data::UNK_0x2 || operation == data::UNK_0x3 || operation == data::UNK_0x12)) (operation == data::UNK_0x2 || operation == data::UNK_0x3 || operation == data::UNK_0x12))
{ {
-7
View File
@@ -4,10 +4,6 @@
#include <cmath> #include <cmath>
#include "os_report.h" #include "os_report.h"
#if TARGET_PC
#include "dusk/action_bindings.h"
#endif
u32 JUTGamePad::CRumble::sChannelMask[4] = { u32 JUTGamePad::CRumble::sChannelMask[4] = {
PAD_CHAN0_BIT, PAD_CHAN0_BIT,
PAD_CHAN1_BIT, PAD_CHAN1_BIT,
@@ -89,9 +85,6 @@ u32 JUTGamePad::sRumbleSupported;
u32 JUTGamePad::read() { u32 JUTGamePad::read() {
sRumbleSupported = PADRead(mPadStatus); sRumbleSupported = PADRead(mPadStatus);
#if TARGET_PC
dusk::updateActionBindings();
#endif
switch (sClampMode) { switch (sClampMode) {
case EClampStick: case EClampStick:
+1 -1
View File
@@ -1,6 +1,6 @@
# Android Shell # Android Shell
This directory contains a minimal SDLActivity-based Android app wrapper for Dusklight. This directory contains a minimal SDLActivity-based Android app wrapper for Dusk.
## Prerequisites ## Prerequisites
+1 -1
View File
@@ -3,7 +3,7 @@ plugins {
} }
def duskRepoDir = rootProject.projectDir.parentFile.parentFile def duskRepoDir = rootProject.projectDir.parentFile.parentFile
def duskGeneratedAssetsDir = layout.buildDirectory.dir('generated/assets/dusklight').get().asFile def duskGeneratedAssetsDir = layout.buildDirectory.dir('generated/assets/dusk').get().asFile
def syncDuskAssets = tasks.register('syncDuskAssets', Sync) { def syncDuskAssets = tasks.register('syncDuskAssets', Sync) {
from(new File(duskRepoDir, 'res')) { from(new File(duskRepoDir, 'res')) {
into 'res' into 'res'
@@ -1,16 +1,12 @@
package dev.twilitrealm.dusk; package dev.twilitrealm.dusk;
import android.app.ActionBar; import android.app.ActionBar;
import android.app.Activity;
import android.content.ActivityNotFoundException;
import android.content.ClipData; import android.content.ClipData;
import android.content.Intent; import android.content.Intent;
import android.database.Cursor; import android.database.Cursor;
import android.net.Uri; import android.net.Uri;
import android.os.Build; import android.os.Build;
import android.os.Bundle; import android.os.Bundle;
import android.os.Environment;
import android.provider.DocumentsContract;
import android.provider.OpenableColumns; import android.provider.OpenableColumns;
import android.util.Log; import android.util.Log;
import android.view.View; import android.view.View;
@@ -26,13 +22,6 @@ import java.util.List;
public class DuskActivity extends SDLActivity { public class DuskActivity extends SDLActivity {
private static final String TAG = "DuskActivity"; private static final String TAG = "DuskActivity";
private static final int FOLDER_DIALOG_REQUEST_CODE = 0x4455;
private static final String EXTERNAL_STORAGE_AUTHORITY =
"com.android.externalstorage.documents";
private long folderDialogUserdata = 0;
private static native void nativeFolderDialogResult(long userdata, String path, String error);
private static String[] splitArgs(String raw) { private static String[] splitArgs(String raw) {
List<String> out = new ArrayList<>(); List<String> out = new ArrayList<>();
@@ -158,154 +147,9 @@ public class DuskActivity extends SDLActivity {
if (resultCode == RESULT_OK) { if (resultCode == RESULT_OK) {
persistUriPermissions(data); persistUriPermissions(data);
} }
if (requestCode == FOLDER_DIALOG_REQUEST_CODE) {
finishFolderDialog(resultCode, data);
return;
}
super.onActivityResult(requestCode, resultCode, data); super.onActivityResult(requestCode, resultCode, data);
} }
public boolean showFolderDialog(long userdata) {
if (userdata == 0 || folderDialogUserdata != 0) {
return false;
}
folderDialogUserdata = userdata;
runOnUiThread(() -> {
Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT_TREE);
intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION |
Intent.FLAG_GRANT_WRITE_URI_PERMISSION |
Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION |
Intent.FLAG_GRANT_PREFIX_URI_PERMISSION);
try {
startActivityForResult(intent, FOLDER_DIALOG_REQUEST_CODE);
} catch (ActivityNotFoundException e) {
Log.w(TAG, "Unable to open folder dialog.", e);
finishFolderDialog(Activity.RESULT_CANCELED, null);
}
});
return true;
}
private void finishFolderDialog(int resultCode, Intent data) {
long userdata = folderDialogUserdata;
folderDialogUserdata = 0;
if (userdata == 0) {
return;
}
if (resultCode == RESULT_OK && data != null && data.getData() != null) {
String path = getRealPathForUri(data.getData());
if (path != null && !path.isEmpty()) {
nativeFolderDialogResult(userdata, path, null);
} else {
nativeFolderDialogResult(
userdata, null, "Selected folder is not available as a filesystem path");
}
return;
}
nativeFolderDialogResult(userdata, null, null);
}
private String getRealPathForUri(Uri uri) {
if (uri == null) {
return null;
}
String scheme = uri.getScheme();
if ("file".equals(scheme)) {
return uri.getPath();
}
if (!"content".equals(scheme) ||
!EXTERNAL_STORAGE_AUTHORITY.equals(uri.getAuthority()) ||
Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT)
{
return null;
}
try {
return getExternalStoragePathForDocumentId(getExternalStorageDocumentId(uri));
} catch (IllegalArgumentException e) {
Log.w(TAG, "Unable to resolve URI: " + uri, e);
return null;
}
}
private static String getExternalStorageDocumentId(Uri uri) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && isTreeDocumentUri(uri)) {
return DocumentsContract.getTreeDocumentId(uri);
}
return DocumentsContract.getDocumentId(uri);
}
private static boolean isTreeDocumentUri(Uri uri) {
List<String> segments = uri.getPathSegments();
return segments.size() >= 2 && "tree".equals(segments.get(0));
}
private String getExternalStoragePathForDocumentId(String documentId) {
if (documentId == null || documentId.isEmpty()) {
return null;
}
if (documentId.startsWith("raw:")) {
return documentId.substring("raw:".length());
}
String[] parts = documentId.split(":", 2);
String volumeId = parts[0];
String relativePath = parts.length > 1 ? parts[1] : "";
File root = getExternalStorageRoot(volumeId);
if (root == null) {
return null;
}
return relativePath.isEmpty()
? root.getAbsolutePath()
: new File(root, relativePath).getAbsolutePath();
}
private File getExternalStorageRoot(String volumeId) {
if ("primary".equalsIgnoreCase(volumeId)) {
return Environment.getExternalStorageDirectory();
}
if ("home".equalsIgnoreCase(volumeId)) {
return new File(
Environment.getExternalStorageDirectory(), Environment.DIRECTORY_DOCUMENTS);
}
File[] externalFilesDirs = getExternalFilesDirs(null);
if (externalFilesDirs != null) {
for (File externalFilesDir : externalFilesDirs) {
File root = getStorageRootForExternalFilesDir(externalFilesDir);
if (root != null && volumeId.equalsIgnoreCase(root.getName())) {
return root;
}
}
}
File fallback = new File("/storage", volumeId);
return fallback.exists() ? fallback : null;
}
private File getStorageRootForExternalFilesDir(File externalFilesDir) {
if (externalFilesDir == null) {
return null;
}
String path = externalFilesDir.getAbsolutePath();
int androidDir = path.indexOf("/Android/");
if (androidDir <= 0) {
return null;
}
return new File(path.substring(0, androidDir));
}
private void persistUriPermissions(Intent data) { private void persistUriPermissions(Intent data) {
if (data == null) { if (data == null) {
return; return;
@@ -14,22 +14,15 @@ import android.provider.DocumentsContract.Root;
import android.provider.DocumentsProvider; import android.provider.DocumentsProvider;
import android.webkit.MimeTypeMap; import android.webkit.MimeTypeMap;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.ByteArrayOutputStream;
import java.io.File; import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException; import java.io.FileNotFoundException;
import java.io.IOException; import java.io.IOException;
import java.nio.charset.StandardCharsets;
public class DuskDocumentsProvider extends DocumentsProvider { public class DuskDocumentsProvider extends DocumentsProvider {
public static final String AUTHORITY = "dev.twilitrealm.dusk.documents"; public static final String AUTHORITY = "dev.twilitrealm.dusk.documents";
private static final String ROOT_ID = "dusk"; private static final String ROOT_ID = "dusk";
private static final String ROOT_DOCUMENT_ID = "root"; private static final String ROOT_DOCUMENT_ID = "root";
private static final String LOCATION_DESCRIPTOR_NAME = "data_location.json";
private static final String DIRECTORY_MIME_TYPE = Document.MIME_TYPE_DIR; private static final String DIRECTORY_MIME_TYPE = Document.MIME_TYPE_DIR;
private static final String[] DEFAULT_ROOT_PROJECTION = new String[] { private static final String[] DEFAULT_ROOT_PROJECTION = new String[] {
@@ -53,19 +46,13 @@ public class DuskDocumentsProvider extends DocumentsProvider {
@Override @Override
public boolean onCreate() { public boolean onCreate() {
if (!isCustomDataPathEnabled()) { ensureUserDirectories();
ensureUserDirectories();
}
return true; return true;
} }
@Override @Override
public Cursor queryRoots(String[] projection) throws FileNotFoundException { public Cursor queryRoots(String[] projection) throws FileNotFoundException {
final MatrixCursor result = new MatrixCursor(resolveRootProjection(projection)); final MatrixCursor result = new MatrixCursor(resolveRootProjection(projection));
if (isCustomDataPathEnabled()) {
return result;
}
final File root = getRootDirectory(); final File root = getRootDirectory();
final MatrixCursor.RowBuilder row = result.newRow(); final MatrixCursor.RowBuilder row = result.newRow();
@@ -235,14 +222,9 @@ public class DuskDocumentsProvider extends DocumentsProvider {
} }
private File getRootDirectory() throws FileNotFoundException { private File getRootDirectory() throws FileNotFoundException {
if (isCustomDataPathEnabled()) {
throw new FileNotFoundException(
"Dusk DocumentsProvider is disabled while a custom data path is configured");
}
final File root = getContext().getFilesDir(); final File root = getContext().getFilesDir();
if (root == null) { if (root == null) {
throw new FileNotFoundException("Dusklight files directory is unavailable"); throw new FileNotFoundException("Dusk files directory is unavailable");
} }
return root; return root;
} }
@@ -259,7 +241,7 @@ public class DuskDocumentsProvider extends DocumentsProvider {
final String relativePath = documentId.substring(ROOT_DOCUMENT_ID.length() + 1); final String relativePath = documentId.substring(ROOT_DOCUMENT_ID.length() + 1);
final File file = new File(root, relativePath); final File file = new File(root, relativePath);
if (!isInside(root, file)) { if (!isInside(root, file)) {
throw new FileNotFoundException("Document escapes Dusklight files directory: " + documentId); throw new FileNotFoundException("Document escapes Dusk files directory: " + documentId);
} }
if (!file.exists()) { if (!file.exists()) {
throw new FileNotFoundException("Document does not exist: " + documentId); throw new FileNotFoundException("Document does not exist: " + documentId);
@@ -273,7 +255,7 @@ public class DuskDocumentsProvider extends DocumentsProvider {
return ROOT_DOCUMENT_ID; return ROOT_DOCUMENT_ID;
} }
if (!isInside(root, file)) { if (!isInside(root, file)) {
throw new FileNotFoundException("File escapes Dusklight files directory: " + file); throw new FileNotFoundException("File escapes Dusk files directory: " + file);
} }
final String rootPath = canonicalPath(root); final String rootPath = canonicalPath(root);
@@ -291,42 +273,6 @@ public class DuskDocumentsProvider extends DocumentsProvider {
new File(root, "EUR/Card A").mkdirs(); new File(root, "EUR/Card A").mkdirs();
} }
private boolean isCustomDataPathEnabled() {
if (getContext() == null) {
return false;
}
final File filesDir = getContext().getFilesDir();
if (filesDir == null) {
return false;
}
final File descriptor = new File(filesDir, LOCATION_DESCRIPTOR_NAME);
if (!descriptor.isFile()) {
return false;
}
try {
final JSONObject json = new JSONObject(readText(descriptor));
return "custom".equals(json.optString("mode", "default"));
} catch (IOException | JSONException e) {
return false;
}
}
private static String readText(File file) throws IOException {
try (FileInputStream input = new FileInputStream(file);
ByteArrayOutputStream output = new ByteArrayOutputStream())
{
byte[] buffer = new byte[4096];
int bytesRead;
while ((bytesRead = input.read(buffer)) != -1) {
output.write(buffer, 0, bytesRead);
}
return output.toString(StandardCharsets.UTF_8.name());
}
}
private static String[] resolveRootProjection(String[] projection) { private static String[] resolveRootProjection(String[] projection) {
return projection != null ? projection : DEFAULT_ROOT_PROJECTION; return projection != null ? projection : DEFAULT_ROOT_PROJECTION;
} }
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<resources> <resources>
<string name="app_name">Dusklight</string> <string name="app_name">Dusk</string>
<string name="documents_provider_root_name">Dusklight Data</string> <string name="documents_provider_root_name">Dusk Data</string>
<string name="documents_provider_summary">Saves, texture packs, settings, and logs</string> <string name="documents_provider_summary">Saves, texture packs, settings, and logs</string>
</resources> </resources>
Vendored Executable → Regular
View File
+1 -1
View File
@@ -14,5 +14,5 @@ dependencyResolutionManagement {
} }
} }
rootProject.name = "dusklight-android" rootProject.name = "dusk-android"
include ':app' include ':app'

Before

Width:  |  Height:  |  Size: 928 KiB

After

Width:  |  Height:  |  Size: 928 KiB

Before

Width:  |  Height:  |  Size: 29 KiB

After

Width:  |  Height:  |  Size: 29 KiB

Before

Width:  |  Height:  |  Size: 1014 B

After

Width:  |  Height:  |  Size: 1014 B

Before

Width:  |  Height:  |  Size: 90 KiB

After

Width:  |  Height:  |  Size: 90 KiB

Before

Width:  |  Height:  |  Size: 2.7 KiB

After

Width:  |  Height:  |  Size: 2.7 KiB

Before

Width:  |  Height:  |  Size: 5.3 KiB

After

Width:  |  Height:  |  Size: 5.3 KiB

Before

Width:  |  Height:  |  Size: 279 KiB

After

Width:  |  Height:  |  Size: 279 KiB

Before

Width:  |  Height:  |  Size: 8.7 KiB

After

Width:  |  Height:  |  Size: 8.7 KiB

+9
View File
@@ -0,0 +1,9 @@
[Desktop Entry]
Name=Dusk
GenericName=Dusk
Comment=The Legend of Zelda: Twilight Princess
Exec=dusk
Icon=dusk
Terminal=false
Type=Application
Categories=Game;
-9
View File
@@ -1,9 +0,0 @@
[Desktop Entry]
Name=Dusklight
GenericName=Dusklight
Comment=PC port of a classic adventure game
Exec=dusklight
Icon=dusklight
Terminal=false
Type=Application
Categories=Game;
-2
View File
@@ -83,7 +83,5 @@
<true/> <true/>
<key>LSSupportsOpeningDocumentsInPlace</key> <key>LSSupportsOpeningDocumentsInPlace</key>
<true/> <true/>
<key>LSSupportsGameMode</key>
<true/>
</dict> </dict>
</plist> </plist>
+1 -5
View File
@@ -13,7 +13,7 @@
<key>CFBundleExecutable</key> <key>CFBundleExecutable</key>
<string>${MACOSX_BUNDLE_EXECUTABLE_NAME}</string> <string>${MACOSX_BUNDLE_EXECUTABLE_NAME}</string>
<key>CFBundleIconFile</key> <key>CFBundleIconFile</key>
<string>Dusklight</string> <string>Dusk</string>
<key>CFBundleIconName</key> <key>CFBundleIconName</key>
<string>Dusk</string> <string>Dusk</string>
<key>CFBundleIdentifier</key> <key>CFBundleIdentifier</key>
@@ -28,9 +28,5 @@
<string>${MACOSX_BUNDLE_SHORT_VERSION_STRING}</string> <string>${MACOSX_BUNDLE_SHORT_VERSION_STRING}</string>
<key>NSHighResolutionCapable</key> <key>NSHighResolutionCapable</key>
<true/> <true/>
<key>LSApplicationCategoryType</key>
<string>public.app-category.adventure-games</string>
<key>LSSupportsGameMode</key>
<true/>
</dict> </dict>
</plist> </plist>
-2
View File
@@ -45,7 +45,5 @@
<string>LaunchScreen</string> <string>LaunchScreen</string>
<key>UIUserInterfaceStyle</key> <key>UIUserInterfaceStyle</key>
<string>Automatic</string> <string>Automatic</string>
<key>LSSupportsGameMode</key>
<true />
</dict> </dict>
</plist> </plist>
@@ -24,9 +24,9 @@ BEGIN
VALUE "CompanyName", "@DUSK_COMPANY_NAME@\0" VALUE "CompanyName", "@DUSK_COMPANY_NAME@\0"
VALUE "FileDescription", "@DUSK_FILE_DESCRIPTION@\0" VALUE "FileDescription", "@DUSK_FILE_DESCRIPTION@\0"
VALUE "FileVersion", "@DUSK_VERSION_STRING@\0" VALUE "FileVersion", "@DUSK_VERSION_STRING@\0"
VALUE "InternalName", "dusklight\0" VALUE "InternalName", "dusk\0"
VALUE "LegalCopyright", "@DUSK_COPYRIGHT@\0" VALUE "LegalCopyright", "@DUSK_COPYRIGHT@\0"
VALUE "OriginalFilename", "dusklight.exe\0" VALUE "OriginalFilename", "dusk.exe\0"
VALUE "ProductName", "@DUSK_PRODUCT_NAME@\0" VALUE "ProductName", "@DUSK_PRODUCT_NAME@\0"
VALUE "ProductVersion", "@DUSK_VERSION_STRING@\0" VALUE "ProductVersion", "@DUSK_VERSION_STRING@\0"
END END
File diff suppressed because it is too large Load Diff
Binary file not shown.

After

Width:  |  Height:  |  Size: 457 KiB

BIN
View File
Binary file not shown.

Before

Width:  |  Height:  |  Size: 642 KiB

After

Width:  |  Height:  |  Size: 340 KiB

-35
View File
@@ -58,10 +58,6 @@ toast:active {
background-color: rgba(45, 43, 26, 80%); background-color: rgba(45, 43, 26, 80%);
}*/ }*/
b {
font-weight: bold;
}
toast heading { toast heading {
display: flex; display: flex;
gap: 18dp; gap: 18dp;
@@ -205,37 +201,6 @@ fps {
white-space: nowrap; white-space: nowrap;
} }
speedrun-timer {
display: none;
position: absolute;
bottom: 0;
right: 0;
z-index: 99;
background-color: rgba(0, 0, 0, 65%);
padding: 2dp 4dp;
pointer-events: none;
font-family: "Noto Mono";
font-size: 16dp;
color: #ffffff;
white-space: nowrap;
}
speedrun-timer[open] {
display: block;
}
speedrun-rta {
display: none;
}
speedrun-rta[open] {
display: block;
}
speedrun-igt {
display: block;
}
fps[open] { fps[open] {
display: block; display: block;
} }
+9 -8
View File
@@ -65,10 +65,10 @@ menu {
right: auto; right: auto;
top: 50%; top: 50%;
transform: translateY(-50%); transform: translateY(-50%);
/* Scale based on a reference screen width, 856/1216 */ /* Scale based on a reference screen width, 428/1216 */
width: 70.394736vw; width: 35.230264vw;
min-width: 428dp; min-width: 428dp;
max-width: 50vw; max-width: 856dp;
height: auto; height: auto;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
@@ -83,8 +83,9 @@ body.mirrored menu {
hero { hero {
display: flex; display: flex;
flex-direction: column; flex-direction: column;
justify-content: center;
align-items: flex-start; align-items: flex-start;
gap: 4dp; gap: 8dp;
} }
body.mirrored hero { body.mirrored hero {
@@ -95,19 +96,19 @@ hero img {
width: 100%; width: 100%;
} }
eyebrow { .eyebrow {
font-family: "Alegreya SC"; font-family: "Alegreya SC";
font-size: 32dp; font-size: 32dp;
} }
@media (min-width: 1216dp) { @media (min-width: 1216dp) {
eyebrow { .eyebrow {
/* Same logic as .menu, 32/1216 */ /* Same logic as .menu, 32/1216 */
font-size: 2.631579vw; font-size: 2.631579vw;
} }
} }
eyebrow span { .eyebrow span {
font-weight: bold; font-weight: bold;
} }
@@ -436,7 +437,7 @@ body.animate-in .intro-item {
decorator: horizontal-gradient(#FEE685FF #FEE68500); decorator: horizontal-gradient(#FEE685FF #FEE68500);
} }
eyebrow { .eyebrow {
display: none; display: none;
} }
-15
View File
@@ -14,10 +14,6 @@ body {
color: #E0DBC8; color: #E0DBC8;
} }
b {
font-weight: bold;
}
window { window {
display: flex; display: flex;
flex-flow: column; flex-flow: column;
@@ -109,12 +105,6 @@ window content pane:last-of-type > div {
line-height: 1.625; line-height: 1.625;
} }
.data-folder-current {
display: block;
font-size: 16dp;
color: rgba(224, 219, 200, 65%);
}
window content pane > spacer { window content pane > spacer {
display: block; display: block;
/* Completes the 24dp bottom inset after the pane's 8dp gap. */ /* Completes the 24dp bottom inset after the pane's 8dp gap. */
@@ -209,11 +199,6 @@ button:not(:disabled):active {
box-shadow: #C2A42D 0 0 0 2dp; box-shadow: #C2A42D 0 0 0 2dp;
} }
button:disabled {
opacity: 0.35;
cursor: default;
}
button.modal-btn { button.modal-btn {
flex: 1 1 0; flex: 1 1 0;
text-align: center; text-align: center;
+16 -59
View File
@@ -51,13 +51,10 @@
#include "d/actor/d_a_ni.h" #include "d/actor/d_a_ni.h"
#include "d/d_s_play.h" #include "d/d_s_play.h"
#if TARGET_PC
#include "dusk/action_bindings.h"
#include "dusk/frame_interpolation.h" #include "dusk/frame_interpolation.h"
#include "dusk/settings.h" #include "dusk/settings.h"
#include "res/Object/Alink.h" #include "res/Object/Alink.h"
#include <cstring> #include <cstring>
#endif
static int daAlink_Create(fopAc_ac_c* i_this); static int daAlink_Create(fopAc_ac_c* i_this);
static int daAlink_Delete(daAlink_c* i_this); static int daAlink_Delete(daAlink_c* i_this);
@@ -5990,7 +5987,7 @@ void daAlink_c::setItemMatrix(int param_0) {
mDoMtx_stack_c::XrotS(-0x8000); mDoMtx_stack_c::XrotS(-0x8000);
#ifdef TARGET_PC #ifdef TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
Mtx boot_mtx; Mtx boot_mtx;
mDoMtx_concat(mpLinkModel->getAnmMtx(0x18), mDoMtx_stack_c::get(), boot_mtx); mDoMtx_concat(mpLinkModel->getAnmMtx(0x18), mDoMtx_stack_c::get(), boot_mtx);
mpLinkBootModels[1]->setAnmMtx(1, boot_mtx); mpLinkBootModels[1]->setAnmMtx(1, boot_mtx);
@@ -7562,7 +7559,12 @@ void daAlink_c::setBlendMoveAnime(f32 i_morf) {
f32 sp2C; f32 sp2C;
f32 sp28 = mpHIO->mMove.m.mFootPositionRatio; f32 sp28 = mpHIO->mMove.m.mFootPositionRatio;
BOOL sp24 = checkEventRun(); BOOL sp24 = checkEventRun();
BOOL sp20 = checkBootsMoveAnime(1) IF_DUSK(&& !dusk::getSettings().game.enableFastIronBoots); BOOL sp20 = checkBootsMoveAnime(1);
#if TARGET_PC
if (dusk::getSettings().game.enableFastIronBoots) {
sp20 = FALSE;
}
#endif
f32 var_f29; f32 var_f29;
@@ -8075,7 +8077,7 @@ void daAlink_c::setBlendAtnBackMoveAnime(f32 i_morf) {
daAlink_ANM var_r27; daAlink_ANM var_r27;
daAlink_ANM var_r29; daAlink_ANM var_r29;
if (checkBootsMoveAnime(1) IF_DUSK(&& !dusk::getSettings().game.enableFastIronBoots)) { if (checkBootsMoveAnime(1)) {
mMaxSpeed = mpHIO->mAtnMove.m.mMaxBackwardsSpeed; mMaxSpeed = mpHIO->mAtnMove.m.mMaxBackwardsSpeed;
var_f27 = mpHIO->mAtnMove.m.mMinBackWalkFrame; var_f27 = mpHIO->mAtnMove.m.mMinBackWalkFrame;
var_f31 = mpHIO->mAtnMove.m.mBackWalkChangeRate; var_f31 = mpHIO->mAtnMove.m.mBackWalkChangeRate;
@@ -9361,12 +9363,6 @@ BOOL daAlink_c::spActionTrigger() {
} }
BOOL daAlink_c::midnaTalkTrigger() const { BOOL daAlink_c::midnaTalkTrigger() const {
#if TARGET_PC
// If we have a custom bind for Midna, check that instead
if (dusk::isActionBound(dusk::ActionBinds::CALL_MIDNA, 0)) {
return dusk::getActionBindTrig(dusk::ActionBinds::CALL_MIDNA, 0);
}
#endif
return mItemTrigger & BTN_Z; return mItemTrigger & BTN_Z;
} }
@@ -16118,9 +16114,6 @@ int daAlink_c::procSlideLand() {
int daAlink_c::procFrontRollInit() { int daAlink_c::procFrontRollInit() {
BOOL is_guard_anime = checkUpperGuardAnime(); BOOL is_guard_anime = checkUpperGuardAnime();
#ifdef TARGET_PC
const f32 fastRollMultiplier = dusk::getSettings().game.fastRoll ? 2.0f : 1.0f;
#endif
if (mProcID == PROC_FRONT_ROLL && mDemo.getDemoMode() == daPy_demo_c::DEMO_FRONT_ROLL_e) { if (mProcID == PROC_FRONT_ROLL && mDemo.getDemoMode() == daPy_demo_c::DEMO_FRONT_ROLL_e) {
return 0; return 0;
@@ -16136,16 +16129,10 @@ int daAlink_c::procFrontRollInit() {
roll_anm_speed = mpHIO->mFrontRoll.m.mRollAnm.mStartFrame; roll_anm_speed = mpHIO->mFrontRoll.m.mRollAnm.mStartFrame;
} }
setSingleAnime(ANM_FRONT_ROLL, setSingleAnime(ANM_FRONT_ROLL, mpHIO->mFrontRoll.m.mRollAnm.mSpeed, roll_anm_speed,
#ifdef TARGET_PC
mpHIO->mFrontRoll.m.mRollAnm.mSpeed * fastRollMultiplier,
#else
mpHIO->mFrontRoll.m.mRollAnm.mSpeed,
#endif
roll_anm_speed,
mpHIO->mFrontRoll.m.mRollAnm.mEndFrame, mpHIO->mFrontRoll.m.mRollAnm.mEndFrame,
mpHIO->mFrontRoll.m.mRollAnm.mInterpolation); mpHIO->mFrontRoll.m.mRollAnm.mInterpolation);
mNormalSpeed = speedF * mpHIO->mFrontRoll.m.mSpeedRate + mpHIO->mFrontRoll.m.mInitSpeed; mNormalSpeed = speedF * mpHIO->mFrontRoll.m.mSpeedRate + mpHIO->mFrontRoll.m.mInitSpeed;
f32 max_speed = mpHIO->mFrontRoll.m.mInitSpeed + mpHIO->mMove.m.mMaxSpeed * mpHIO->mFrontRoll.m.mSpeedRate; f32 max_speed = mpHIO->mFrontRoll.m.mInitSpeed + mpHIO->mMove.m.mMaxSpeed * mpHIO->mFrontRoll.m.mSpeedRate;
@@ -16158,20 +16145,11 @@ int daAlink_c::procFrontRollInit() {
} }
if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) { if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) {
#if TARGET_PC mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
if (!(dusk::getSettings().game.enableFastIronBoots))
#endif
{
mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
}
} else if (checkHeavyStateOn(TRUE, TRUE)) { } else if (checkHeavyStateOn(TRUE, TRUE)) {
mNormalSpeed *= mHeavySpeedMultiplier; mNormalSpeed *= mHeavySpeedMultiplier;
} }
#ifdef TARGET_PC
mNormalSpeed *= fastRollMultiplier;
#endif
current.angle.y = shape_angle.y; current.angle.y = shape_angle.y;
voiceStart(Z2SE_AL_V_BACKTEN); voiceStart(Z2SE_AL_V_BACKTEN);
mProcVar2.field_0x300c = 0; mProcVar2.field_0x300c = 0;
@@ -16302,13 +16280,8 @@ int daAlink_c::procFrontRollCrashInit() {
speed.y = mpHIO->mFrontRoll.m.mCrashSpeedV; speed.y = mpHIO->mFrontRoll.m.mCrashSpeedV;
if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) { if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) {
#if TARGET_PC mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
if (!(dusk::getSettings().game.enableFastIronBoots)) speed.y *= mpHIO->mItem.mIronBoots.m.mWaterVelocityY;
#endif
{
mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
speed.y *= mpHIO->mItem.mIronBoots.m.mWaterVelocityY;
}
} }
ANGLE_ADD_2(current.angle.y, 0x8000); ANGLE_ADD_2(current.angle.y, 0x8000);
@@ -16402,9 +16375,6 @@ int daAlink_c::procFrontRollSuccess() {
int daAlink_c::procSideRollInit(int param_0) { int daAlink_c::procSideRollInit(int param_0) {
BOOL is_prev_guardAnm = checkUpperGuardAnime(); BOOL is_prev_guardAnm = checkUpperGuardAnime();
#ifdef TARGET_PC
const f32 fastRollMultiplier = dusk::getSettings().game.fastRoll ? 2.0f : 1.0f;
#endif
if (!commonProcInitNotSameProc(PROC_SIDE_ROLL)) { if (!commonProcInitNotSameProc(PROC_SIDE_ROLL)) {
return 0; return 0;
@@ -16421,30 +16391,17 @@ int daAlink_c::procSideRollInit(int param_0) {
current.angle.y = shape_angle.y + -0x4000; current.angle.y = shape_angle.y + -0x4000;
} }
setSingleAnime(anmID, setSingleAnime(anmID, mpHIO->mGuard.mTurnMove.m.mSideRollAnmSpeed,
#ifdef TARGET_PC
mpHIO->mGuard.mTurnMove.m.mSideRollAnmSpeed * fastRollMultiplier,
#else
mpHIO->mGuard.mTurnMove.m.mSideRollAnmSpeed,
#endif
mpHIO->mGuard.mTurnMove.m.mTurnAnm.mStartFrame, mpHIO->mGuard.mTurnMove.m.mTurnAnm.mStartFrame,
mpHIO->mGuard.mTurnMove.m.mTurnAnm.mEndFrame, mpHIO->mGuard.mTurnMove.m.mTurnAnm.mEndFrame,
mpHIO->mGuard.mTurnMove.m.mTurnAnm.mInterpolation); mpHIO->mGuard.mTurnMove.m.mTurnAnm.mInterpolation);
mNormalSpeed = mpHIO->mGuard.mTurnMove.m.mSideRollSpeed; mNormalSpeed = mpHIO->mGuard.mTurnMove.m.mSideRollSpeed;
if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) { if (checkNoResetFlg0(FLG0_WATER_IN_MOVE)) {
#if TARGET_PC mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
if (!(dusk::getSettings().game.enableFastIronBoots))
#endif
{
mNormalSpeed *= mpHIO->mItem.mIronBoots.m.mWaterVelocityX;
}
} else if (checkHeavyStateOn(TRUE, TRUE)) { } else if (checkHeavyStateOn(TRUE, TRUE)) {
mNormalSpeed *= mHeavySpeedMultiplier; mNormalSpeed *= mHeavySpeedMultiplier;
} }
#ifdef TARGET_PC
mNormalSpeed *= fastRollMultiplier;
#endif
setFootEffectProcType(0); setFootEffectProcType(0);
field_0x2f9d = 4; field_0x2f9d = 4;
@@ -19767,7 +19724,7 @@ int daAlink_c::draw() {
dComIfGd_getOpaListDark()->entryImm(mpHookChain, 0); dComIfGd_getOpaListDark()->entryImm(mpHookChain, 0);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled() && if (dusk::getSettings().game.enableFrameInterpolation &&
mEquipItem == dItemNo_IRONBALL_e && mEquipItem == dItemNo_IRONBALL_e &&
mIronBallChainPos != NULL && mIronBallChainAngle != NULL) mIronBallChainPos != NULL && mIronBallChainAngle != NULL)
{ {
-1
View File
@@ -25,7 +25,6 @@
#include "dusk/imgui/ImGuiConsole.hpp" #include "dusk/imgui/ImGuiConsole.hpp"
#include "dusk/settings.h" #include "dusk/settings.h"
#include "dusk/speedrun.h"
BOOL daAlink_c::checkEventRun() const { BOOL daAlink_c::checkEventRun() const {
return dComIfGp_event_runCheck() || checkPlayerDemoMode(); return dComIfGp_event_runCheck() || checkPlayerDemoMode();
+3 -6
View File
@@ -12,7 +12,6 @@
#if TARGET_PC #if TARGET_PC
#include "dusk/gyro.h" #include "dusk/gyro.h"
#include "dusk/action_bindings.h"
#endif #endif
bool daAlink_c::checkNoSubjectModeCamera() { bool daAlink_c::checkNoSubjectModeCamera() {
@@ -120,8 +119,8 @@ BOOL daAlink_c::setBodyAngleToCamera() {
var_f31 /= dComIfGp_getCameraZoomScale(field_0x317c); var_f31 /= dComIfGp_getCameraZoomScale(field_0x317c);
} }
shape_angle.y = shape_angle.y + (var_f31 * cM_ssin(mStickAngle) IF_DUSK(* (dusk::getSettings().game.invertFirstPersonXAxis ? -1.0f : 1.0f))); shape_angle.y = shape_angle.y + (var_f31 * cM_ssin(mStickAngle));
sp8 = mBodyAngle.x + (var_f31 * cM_scos(mStickAngle) IF_DUSK(* (dusk::getSettings().game.invertFirstPersonYAxis ? -1.0f : 1.0f))); sp8 = mBodyAngle.x + (var_f31 * cM_scos(mStickAngle));
if (checkNotItemSinkLimit() && sp8 > 0 && sp8 > mBodyAngle.x) { if (checkNotItemSinkLimit() && sp8 > 0 && sp8 > mBodyAngle.x) {
sp8 = mBodyAngle.x; sp8 = mBodyAngle.x;
@@ -193,9 +192,7 @@ BOOL daAlink_c::subjectCancelTrigger() {
BOOL daAlink_c::checkSubjectEnd(BOOL i_isPlaySe) { BOOL daAlink_c::checkSubjectEnd(BOOL i_isPlaySe) {
setDoStatus(BUTTON_STATUS_BACK); setDoStatus(BUTTON_STATUS_BACK);
// Allow pressing the first person binding to also leave first person if (checkEventRun() || checkEquipAnime() || doTrigger() || checkSetItemTrigger(dItemNo_HAWK_EYE_e) || subjectCancelTrigger() || checkEndResetFlg0(ERFLG0_FORCE_SUBJECT_CANCEL) || dComIfGp_checkCameraAttentionStatus(field_0x317c, 0x2000)) {
if (IF_DUSK(dusk::getActionBindTrig(dusk::ActionBinds::FIRST_PERSON_CAMERA, 0)) ||
checkEventRun() || checkEquipAnime() || doTrigger() || checkSetItemTrigger(dItemNo_HAWK_EYE_e) || subjectCancelTrigger() || checkEndResetFlg0(ERFLG0_FORCE_SUBJECT_CANCEL) || dComIfGp_checkCameraAttentionStatus(field_0x317c, 0x2000)) {
if (i_isPlaySe) { if (i_isPlaySe) {
seStartSystem(Z2SE_SUBJ_VIEW_OUT); seStartSystem(Z2SE_SUBJ_VIEW_OUT);
} }
+1 -6
View File
@@ -77,12 +77,7 @@ int daAlink_c::loadModelDVD() {
mpWlMidnaHairModel = NULL; mpWlMidnaHairModel = NULL;
if (!checkNoResetFlg2(FLG2_UNK_280000)) { if (!checkNoResetFlg2(FLG2_UNK_280000)) {
if (!dComIfG_resDelete(&mPhaseReq, mArcName)) { dComIfG_resDelete(&mPhaseReq, mArcName);
#if TARGET_PC
// resDelete no-ops if load was in-progress; force-unregister before freeAll
dComIfG_deleteObjectResMain(mArcName);
#endif
}
cPhs_Reset(&mPhaseReq); cPhs_Reset(&mPhaseReq);
mpArcHeap->freeAll(); mpArcHeap->freeAll();
-6
View File
@@ -8723,12 +8723,6 @@ int daAlink_c::procWolfCargoCarry() {
return checkNextActionWolf(0); return checkNextActionWolf(0);
} }
#if TARGET_PC
if (field_0x280c.getActor() == NULL) {
return checkNextActionWolf(0);
}
#endif
mDoMtx_stack_c::copy(((e_yc_class*)field_0x280c.getActor())->getLegR3Mtx()); mDoMtx_stack_c::copy(((e_yc_class*)field_0x280c.getActor())->getLegR3Mtx());
mDoMtx_stack_c::transM(-9.0f, -7.0f, -30.0f); mDoMtx_stack_c::transM(-9.0f, -7.0f, -30.0f);
mDoMtx_stack_c::multVecZero(&current.pos); mDoMtx_stack_c::multVecZero(&current.pos);
+1 -1
View File
@@ -397,7 +397,7 @@ static int daB_GND_Draw(b_gnd_class* i_this) {
i_this->field_0x21e8.update(2, l_color, &a_this->tevStr); i_this->field_0x21e8.update(2, l_color, &a_this->tevStr);
dComIfGd_set3DlineMat(&i_this->field_0x21e8); dComIfGd_set3DlineMat(&i_this->field_0x21e8);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mReinsInterpCurrValid) { if (i_this->mReinsInterpCurrValid) {
memcpy(i_this->mReinsInterpPrev, i_this->mReinsInterpCurr, sizeof(i_this->mReinsInterpCurr)); memcpy(i_this->mReinsInterpPrev, i_this->mReinsInterpCurr, sizeof(i_this->mReinsInterpCurr));
memcpy(i_this->mReinsTexInterpPrev, i_this->mReinsTexInterpCurr, sizeof(i_this->mReinsTexInterpCurr)); memcpy(i_this->mReinsTexInterpPrev, i_this->mReinsTexInterpCurr, sizeof(i_this->mReinsTexInterpCurr));
-22
View File
@@ -674,29 +674,7 @@ static int daE_ARROW_Create(fopAc_ac_c* i_this) {
} }
int phase_state = dComIfG_resLoad(&a_this->mPhase, a_this->mResName); int phase_state = dComIfG_resLoad(&a_this->mPhase, a_this->mResName);
#if TARGET_PC
static int s_create_frames = 0;
static bool s_first_arrow = true;
static fpc_ProcID s_last_scene_id = 0;
s_create_frames++;
fpc_ProcID cur_scene_id = dStage_roomControl_c::getProcID();
if (cur_scene_id != s_last_scene_id) {
s_first_arrow = true;
s_last_scene_id = cur_scene_id;
}
if (phase_state == cPhs_COMPLEATE_e && s_first_arrow && s_create_frames < 4) {
return cPhs_INIT_e;
}
#endif
if (phase_state == cPhs_COMPLEATE_e) { if (phase_state == cPhs_COMPLEATE_e) {
#if TARGET_PC
s_create_frames = 0;
s_first_arrow = false;
#endif
a_this->mArrowType = fopAcM_GetParam(a_this) & 0xF; a_this->mArrowType = fopAcM_GetParam(a_this) & 0xF;
a_this->mFlags = fopAcM_GetParam(a_this) & 0xF0; a_this->mFlags = fopAcM_GetParam(a_this) & 0xF0;
+1 -1
View File
@@ -116,7 +116,7 @@ static int daE_DB_Draw(e_db_class* i_this) {
i_this->stalkLine.update(12, l_color, &actor->tevStr); i_this->stalkLine.update(12, l_color, &actor->tevStr);
dComIfGd_set3DlineMat(&i_this->stalkLine); dComIfGd_set3DlineMat(&i_this->stalkLine);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mStalkLineInterpCurrValid) { if (i_this->mStalkLineInterpCurrValid) {
memcpy(i_this->mStalkLineInterpPrev, i_this->mStalkLineInterpCurr, sizeof(i_this->mStalkLineInterpCurr)); memcpy(i_this->mStalkLineInterpPrev, i_this->mStalkLineInterpCurr, sizeof(i_this->mStalkLineInterpCurr));
i_this->mStalkLineInterpPrevValid = true; i_this->mStalkLineInterpPrevValid = true;
+1 -1
View File
@@ -103,7 +103,7 @@ static int daE_HB_Draw(e_hb_class* i_this) {
i_this->stalkLine.update(12, l_color, &actor->tevStr); i_this->stalkLine.update(12, l_color, &actor->tevStr);
dComIfGd_set3DlineMat(&i_this->stalkLine); dComIfGd_set3DlineMat(&i_this->stalkLine);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mStalkLineInterpCurrValid) { if (i_this->mStalkLineInterpCurrValid) {
memcpy(i_this->mStalkLineInterpPrev, i_this->mStalkLineInterpCurr, sizeof(i_this->mStalkLineInterpCurr)); memcpy(i_this->mStalkLineInterpPrev, i_this->mStalkLineInterpCurr, sizeof(i_this->mStalkLineInterpCurr));
i_this->mStalkLineInterpPrevValid = true; i_this->mStalkLineInterpPrevValid = true;
+1 -1
View File
@@ -105,7 +105,7 @@ static int daE_MB_Draw(e_mb_class* i_this) {
i_this->mRopeMat.update(16, l_color, &a_this->tevStr); i_this->mRopeMat.update(16, l_color, &a_this->tevStr);
dComIfGd_set3DlineMat(&i_this->mRopeMat); dComIfGd_set3DlineMat(&i_this->mRopeMat);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mRopeInterpCurrValid) { if (i_this->mRopeInterpCurrValid) {
memcpy(i_this->mRopeInterpPrev, i_this->mRopeInterpCurr, sizeof(i_this->mRopeInterpCurr)); memcpy(i_this->mRopeInterpPrev, i_this->mRopeInterpCurr, sizeof(i_this->mRopeInterpCurr));
i_this->mRopeInterpPrevValid = true; i_this->mRopeInterpPrevValid = true;
-18
View File
@@ -157,21 +157,6 @@ static void* s_h_sub(void* i_actor, void* i_data) {
return NULL; return NULL;
} }
#if TARGET_PC
static void sort_target_info_by_id() {
for (int i = 1; i < target_info_count; i++) {
void* key = target_info[i];
fpc_ProcID key_id = fopAcM_GetID(key);
int j = i - 1;
while (j >= 0 && fopAcM_GetID(target_info[j]) > key_id) {
target_info[j + 1] = target_info[j];
j--;
}
target_info[j + 1] = key;
}
}
#endif
static daPillar_c* search_hasira(e_mk_class* i_this) { static daPillar_c* search_hasira(e_mk_class* i_this) {
fopEn_enemy_c* actor = (fopEn_enemy_c*)&i_this->actor; fopEn_enemy_c* actor = (fopEn_enemy_c*)&i_this->actor;
daPillar_c* pillar_p; daPillar_c* pillar_p;
@@ -185,9 +170,6 @@ static daPillar_c* search_hasira(e_mk_class* i_this) {
if (i_this->firstHasiraFlag == 0) { if (i_this->firstHasiraFlag == 0) {
i_this->firstHasiraFlag++; i_this->firstHasiraFlag++;
#if TARGET_PC
sort_target_info_by_id();
#endif
return (daPillar_c*)target_info[TREG_S(7) + 5]; return (daPillar_c*)target_info[TREG_S(7) + 5];
} }
-6
View File
@@ -7053,12 +7053,6 @@ static int daE_RD_IsDelete(e_rd_class*) {
} }
static int daE_RD_Delete(e_rd_class* i_this) { static int daE_RD_Delete(e_rd_class* i_this) {
#if TARGET_PC
if (boss == i_this) {
boss = NULL;
}
#endif
fopEn_enemy_c* enemy = (fopEn_enemy_c*)&i_this->enemy; fopEn_enemy_c* enemy = (fopEn_enemy_c*)&i_this->enemy;
fopAcM_RegisterDeleteID(i_this, "E_RD"); fopAcM_RegisterDeleteID(i_this, "E_RD");
+1 -8
View File
@@ -117,13 +117,6 @@ static void daE_S1_interp_callback(bool isSimFrame, void* pUserWork) {
dst[i] = p0 + (p1 - p0) * alpha; dst[i] = p0 + (p1 - p0) * alpha;
} }
} }
GXColor line_color;
line_color.r = JREG_S(0) + 5;
line_color.g = JREG_S(1) + 10;
line_color.b = JREG_S(2) + 10;
line_color.a = 0xFF;
i_this->mLineMat.update(16, line_color, &i_this->tevStr);
} }
#endif #endif
@@ -161,7 +154,7 @@ static int daE_S1_Draw(e_s1_class* i_this) {
dComIfGd_set3DlineMatDark(&i_this->mLineMat); dComIfGd_set3DlineMatDark(&i_this->mLineMat);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mHairInterpCurrValid) { if (i_this->mHairInterpCurrValid) {
memcpy(i_this->mHairInterpPrev, i_this->mHairInterpCurr, sizeof(i_this->mHairInterpCurr)); memcpy(i_this->mHairInterpPrev, i_this->mHairInterpCurr, sizeof(i_this->mHairInterpCurr));
i_this->mHairInterpPrevValid = true; i_this->mHairInterpPrevValid = true;
+1 -1
View File
@@ -535,7 +535,7 @@ static int daE_WB_Draw(e_wb_class* i_this) {
i_this->himo_tex.update(2, l_color, &actor->tevStr); i_this->himo_tex.update(2, l_color, &actor->tevStr);
dComIfGd_set3DlineMat(&i_this->himo_tex); dComIfGd_set3DlineMat(&i_this->himo_tex);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->himo_interp_curr_valid) { if (i_this->himo_interp_curr_valid) {
memcpy(i_this->himo_mat_interp_prev, i_this->himo_mat_interp_curr, sizeof(i_this->himo_mat_interp_curr)); memcpy(i_this->himo_mat_interp_prev, i_this->himo_mat_interp_curr, sizeof(i_this->himo_mat_interp_curr));
memcpy(i_this->himo_tex_interp_prev, i_this->himo_tex_interp_curr, sizeof(i_this->himo_tex_interp_curr)); memcpy(i_this->himo_tex_interp_prev, i_this->himo_tex_interp_curr, sizeof(i_this->himo_tex_interp_curr));
+1 -1
View File
@@ -107,7 +107,7 @@ static s32 daE_YD_Draw(e_yd_class* i_this) {
i_this->mLineMat.update(12, l_color, &i_this->actor.tevStr); i_this->mLineMat.update(12, l_color, &i_this->actor.tevStr);
dComIfGd_set3DlineMat(&i_this->mLineMat); dComIfGd_set3DlineMat(&i_this->mLineMat);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mLineMatInterpCurrValid) { if (i_this->mLineMatInterpCurrValid) {
memcpy(i_this->mLineMatInterpPrev, i_this->mLineMatInterpCurr, sizeof(i_this->mLineMatInterpCurr)); memcpy(i_this->mLineMatInterpPrev, i_this->mLineMatInterpCurr, sizeof(i_this->mLineMatInterpCurr));
i_this->mLineMatInterpPrevValid = true; i_this->mLineMatInterpPrevValid = true;
+1 -9
View File
@@ -139,7 +139,6 @@ static BOOL pl_check(e_yg_class* i_this, f32 i_dist) {
#if TARGET_PC #if TARGET_PC
static void daE_YG_interp_callback(bool isSimFrame, void* pUserWork) { static void daE_YG_interp_callback(bool isSimFrame, void* pUserWork) {
e_yg_class* i_this = (e_yg_class*)pUserWork; e_yg_class* i_this = (e_yg_class*)pUserWork;
fopAc_ac_c* actor = (fopAc_ac_c*)&i_this->actor;
if (!i_this->mTentacleInterpPrevValid || !i_this->mTentacleInterpCurrValid) { if (!i_this->mTentacleInterpPrevValid || !i_this->mTentacleInterpCurrValid) {
return; return;
} }
@@ -153,13 +152,6 @@ static void daE_YG_interp_callback(bool isSimFrame, void* pUserWork) {
dst[i] = p0 + (p1 - p0) * alpha; dst[i] = p0 + (p1 - p0) * alpha;
} }
} }
GXColor color;
color.r = JREG_S(0) + 20;
color.g = JREG_S(1) + 20;
color.b = JREG_S(2) + 20;
color.a = 0xFF;
i_this->mLineMat.update(10, color, &actor->tevStr);
} }
#endif #endif
@@ -191,7 +183,7 @@ static int daE_YG_Draw(e_yg_class* i_this) {
dComIfGd_set3DlineMatDark(&i_this->mLineMat); dComIfGd_set3DlineMatDark(&i_this->mLineMat);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mTentacleInterpCurrValid) { if (i_this->mTentacleInterpCurrValid) {
memcpy(i_this->mTentacleInterpPrev, i_this->mTentacleInterpCurr, sizeof(i_this->mTentacleInterpCurr)); memcpy(i_this->mTentacleInterpPrev, i_this->mTentacleInterpCurr, sizeof(i_this->mTentacleInterpCurr));
i_this->mTentacleInterpPrevValid = true; i_this->mTentacleInterpPrevValid = true;
+1 -1
View File
@@ -135,7 +135,7 @@ static int daE_YH_Draw(e_yh_class* i_this) {
i_this->mLine.update(12, l_color, &a_this->tevStr); i_this->mLine.update(12, l_color, &a_this->tevStr);
dComIfGd_set3DlineMat(&i_this->mLine); dComIfGd_set3DlineMat(&i_this->mLine);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (i_this->mLineInterpCurrValid) { if (i_this->mLineInterpCurrValid) {
memcpy(i_this->mLineInterpPrev, i_this->mLineInterpCurr, sizeof(i_this->mLineInterpCurr)); memcpy(i_this->mLineInterpPrev, i_this->mLineInterpCurr, sizeof(i_this->mLineInterpCurr));
i_this->mLineInterpPrevValid = true; i_this->mLineInterpPrevValid = true;
+5 -11
View File
@@ -22,7 +22,6 @@
#if TARGET_PC #if TARGET_PC
#include "dusk/dusk.h" #include "dusk/dusk.h"
#include "dusk/frame_interpolation.h"
namespace { namespace {
// FRAME INTERP NOTE: Sim tick control point snapshots for interpolation // FRAME INTERP NOTE: Sim tick control point snapshots for interpolation
@@ -33,7 +32,6 @@ int s_horseReinSimNumPrev;
int s_horseReinSimNumCurr; int s_horseReinSimNumCurr;
bool s_horseReinSimPrevValid; bool s_horseReinSimPrevValid;
bool s_horseReinSimCurrValid; bool s_horseReinSimCurrValid;
uint64_t s_horseReinSimRolledSeq;
} // namespace } // namespace
#endif #endif
@@ -3035,14 +3033,10 @@ void daHorse_c::copyReinPos() {
} }
#if TARGET_PC #if TARGET_PC
if (field_0x1204 > 0) { if (field_0x1204 > 0) {
const uint64_t simSeq = dusk::frame_interp::sim_tick_seq(); if (s_horseReinSimCurrValid && s_horseReinSimNumCurr > 0) {
if (simSeq != s_horseReinSimRolledSeq) { memcpy(s_horseReinSimPrev, s_horseReinSimCurr, s_horseReinSimNumCurr * sizeof(cXyz));
s_horseReinSimRolledSeq = simSeq; s_horseReinSimNumPrev = s_horseReinSimNumCurr;
if (s_horseReinSimCurrValid && s_horseReinSimNumCurr > 0) { s_horseReinSimPrevValid = true;
memcpy(s_horseReinSimPrev, s_horseReinSimCurr, s_horseReinSimNumCurr * sizeof(cXyz));
s_horseReinSimNumPrev = s_horseReinSimNumCurr;
s_horseReinSimPrevValid = true;
}
} }
memcpy(s_horseReinSimCurr, m_reinLine.getPos(0), field_0x1204 * sizeof(cXyz)); memcpy(s_horseReinSimCurr, m_reinLine.getPos(0), field_0x1204 * sizeof(cXyz));
s_horseReinSimNumCurr = field_0x1204; s_horseReinSimNumCurr = field_0x1204;
@@ -3165,7 +3159,7 @@ void daHorse_c::setReinPosNormalSubstance() {
#if TARGET_PC #if TARGET_PC
void daHorse_c::lerpControlPoints(f32 alpha) { void daHorse_c::lerpControlPoints(f32 alpha) {
// FRAME INTERP NOTE: Currently only lerping points for Epona's reins. Need a more global solution. // FRAME INTERP NOTE: Currently only lerping points for Epona's reins. Need a more global solution.
if (!dusk::frame_interp::is_enabled() || !s_horseReinSimPrevValid || !s_horseReinSimCurrValid) { if (!dusk::getSettings().game.enableFrameInterpolation || !s_horseReinSimPrevValid || !s_horseReinSimCurrValid) {
return; return;
} }
const int nCurr = s_horseReinSimNumCurr; const int nCurr = s_horseReinSimNumCurr;
-4
View File
@@ -1967,11 +1967,7 @@ static void demo_camera_shop(npc_henna_class* i_this) {
i_this->mMsgFlow.init(actor, 0x365, 0, NULL); i_this->mMsgFlow.init(actor, 0x365, 0, NULL);
/* dSv_event_flag_c::KORO2_ALLCLEAR - Fishing - After all stages (8-8) of roll goal game cleared */ /* dSv_event_flag_c::KORO2_ALLCLEAR - Fishing - After all stages (8-8) of roll goal game cleared */
dComIfGs_onEventBit(dSv_event_flag_c::saveBitLabels[0x335]); dComIfGs_onEventBit(dSv_event_flag_c::saveBitLabels[0x335]);
#if TARGET_PC
dComIfGp_setItemRupeeCount(dComIfGs_getRupeeMax());
#else
dComIfGp_setItemRupeeCount(1000); dComIfGp_setItemRupeeCount(1000);
#endif
} else if ((lbl_82_bss_91 & 0x38) == 0) { } else if ((lbl_82_bss_91 & 0x38) == 0) {
i_this->mMsgFlow.init(actor, 0x34f, 0, NULL); i_this->mMsgFlow.init(actor, 0x34f, 0, NULL);
/* dSv_event_flag_c::F_0469 - Fishing Pond - Reserved for fishing */ /* dSv_event_flag_c::F_0469 - Fishing Pond - Reserved for fishing */
+1 -2
View File
@@ -299,8 +299,7 @@ int daObjDrop_c::modeParentWait() {
#if TARGET_PC #if TARGET_PC
static inline BOOL checkGetCargoRide() { static inline BOOL checkGetCargoRide() {
if (daPy_getPlayerActorClass()->checkCargoCarry() && if ((daPy_getPlayerActorClass()->checkCargoCarry() && strcmp(dComIfGp_getStartStageName(), "F_SP112") == 0) ||
strcmp(dComIfGp_getStartStageName(), "F_SP112") == 0 &&
dComIfGs_isLightDropGetFlag(dComIfGp_getStartStageDarkArea())) dComIfGs_isLightDropGetFlag(dComIfGp_getStartStageDarkArea()))
{ {
return true; return true;
+1 -1
View File
@@ -325,7 +325,7 @@ int daObjFchain_c::draw() {
dComIfGd_getOpaListDark()->entryImm(&mShape, 0); dComIfGd_getOpaListDark()->entryImm(&mShape, 0);
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (mChainInterpCurrValid) { if (mChainInterpCurrValid) {
memcpy(mChainInterpPrev, mChainInterpCurr, sizeof(mChainInterpCurr)); memcpy(mChainInterpPrev, mChainInterpCurr, sizeof(mChainInterpCurr));
mChainInterpPrevValid = true; mChainInterpPrevValid = true;
+1 -1
View File
@@ -493,7 +493,7 @@ int daObjKLift00_c::Draw() {
dComIfGd_setList(); dComIfGd_setList();
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
if (mChainInterpCurrValid) { if (mChainInterpCurrValid) {
memcpy(mChainInterpPrev, mChainInterpCurr, mNumChains * sizeof(cXyz)); memcpy(mChainInterpPrev, mChainInterpCurr, mNumChains * sizeof(cXyz));
mChainInterpPrevValid = true; mChainInterpPrevValid = true;
+2 -2
View File
@@ -170,7 +170,7 @@ int daTitle_c::Execute() {
} }
#ifdef TARGET_PC #ifdef TARGET_PC
if (!dusk::frame_interp::is_enabled()) { if (!dusk::getSettings().game.enableFrameInterpolation) {
#endif #endif
dMenu_Collect3D_c::setViewPortOffsetY(0.0f); dMenu_Collect3D_c::setViewPortOffsetY(0.0f);
#ifdef TARGET_PC #ifdef TARGET_PC
@@ -354,7 +354,7 @@ void daTitle_c::fastLogoDispInit() {
mProcID = 5; mProcID = 5;
#ifdef TARGET_PC #ifdef TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
dusk::frame_interp::request_presentation_sync(); dusk::frame_interp::request_presentation_sync();
} }
#endif #endif
+3 -6
View File
@@ -11,9 +11,7 @@
#include "d/d_msg_string.h" #include "d/d_msg_string.h"
#include "dusk/livesplit.h" #include "dusk/livesplit.h"
#include "dusk/imgui/ImGuiConsole.hpp" #include "dusk/imgui/ImGuiConsole.hpp"
#include "dusk/speedrun.h"
#include "m_Do/m_Do_controller_pad.h" #include "m_Do/m_Do_controller_pad.h"
#include <dusk/autosave.h>
dBrightCheck_c::dBrightCheck_c(JKRArchive* i_archive) { dBrightCheck_c::dBrightCheck_c(JKRArchive* i_archive) {
mArchive = i_archive; mArchive = i_archive;
@@ -143,16 +141,15 @@ void dBrightCheck_c::modeMove() {
if (mDoCPd_c::getTrigA(PAD_1) || mDoCPd_c::getTrigStart(PAD_1)) { if (mDoCPd_c::getTrigA(PAD_1) || mDoCPd_c::getTrigStart(PAD_1)) {
mDoAud_seStart(Z2SE_ENTER_GAME, NULL, 0, 0); mDoAud_seStart(Z2SE_ENTER_GAME, NULL, 0, 0);
#ifdef TARGET_PC #ifdef TARGET_PC
dusk::speedrun::start();
if (dusk::getSettings().game.speedrunMode && !dusk::getSettings().game.hideTvSettingsScreen) { if (dusk::getSettings().game.speedrunMode && !dusk::getSettings().game.hideTvSettingsScreen) {
// start a new run if a run isn't already in progress // start a new run if a run isn't already in progress
if (!dusk::m_speedrunInfo.m_isRunStarted) { if (!dusk::m_speedrunInfo.m_isRunStarted) {
dusk::resetForSpeedrunMode(); dusk::ImGuiMenuGame::resetForSpeedrunMode();
dusk::m_speedrunInfo.startRun(); dusk::m_speedrunInfo.startRun();
dusk::speedrun::start();
} }
} }
toggleAutoSave(true);
#endif #endif
mCompleteCheck = true; mCompleteCheck = true;
mMode = MODE_WAIT_e; mMode = MODE_WAIT_e;
+60 -97
View File
@@ -31,7 +31,6 @@
#if TARGET_PC #if TARGET_PC
#include "dusk/frame_interpolation.h" #include "dusk/frame_interpolation.h"
#include "dusk/logging.h" #include "dusk/logging.h"
#include "dusk/action_bindings.h"
#include "imgui.h" #include "imgui.h"
#endif #endif
@@ -839,12 +838,6 @@ void dCamera_c::updatePad() {
mTrigB = mDoCPd_c::getTrigB(mPadID) ? true : false; mTrigB = mDoCPd_c::getTrigB(mPadID) ? true : false;
#if TARGET_PC #if TARGET_PC
// If our custom action binding is triggered, and we're not already in first person, go into first person
if (dusk::getActionBindTrig(dusk::ActionBinds::FIRST_PERSON_CAMERA, mPadID) && mGear != -1) {
setComStat(0x1000);
mGear = 0;
}
if (mCamParam.mManualMode) { if (mCamParam.mManualMode) {
return; return;
} }
@@ -884,8 +877,7 @@ void dCamera_c::updatePad() {
if (mPadInfo.mCStick.mLastPosY < -mCamSetup.mCStick.SwTHH()) { if (mPadInfo.mCStick.mLastPosY < -mCamSetup.mCStick.SwTHH()) {
if (mCStickYState != -1) { if (mCStickYState != -1) {
// Don't use regular first person trigger if custom mapping is set if (mGear == -1 && mCurMode == 4) {
if (mGear == -1 && mCurMode == 4 IF_DUSK(&& !dusk::isActionBound(dusk::ActionBinds::FIRST_PERSON_CAMERA, mPadID))) {
mGear = 0; mGear = 0;
setComStat(0x2000); setComStat(0x2000);
} else if (mGear == 0 && sp6C) { } else if (mGear == 0 && sp6C) {
@@ -896,8 +888,7 @@ void dCamera_c::updatePad() {
mCStickYState = -1; mCStickYState = -1;
} else if (mPadInfo.mCStick.mLastPosY > mCamSetup.mCStick.SwTHH()) { } else if (mPadInfo.mCStick.mLastPosY > mCamSetup.mCStick.SwTHH()) {
if (mCStickYState != 1) { if (mCStickYState != 1) {
// Don't use regular first person trigger if custom mapping is set if (mGear == 0 && sp6B) {
if (mGear == 0 && sp6B IF_DUSK(&& !dusk::isActionBound(dusk::ActionBinds::FIRST_PERSON_CAMERA, mPadID))) {
setComStat(0x1000); setComStat(0x1000);
} else if (mGear == 1) { } else if (mGear == 1) {
mGear = 0; mGear = 0;
@@ -7657,11 +7648,7 @@ bool dCamera_c::freeCamera() {
cXyz camMovement = {mPadInfo.mCStick.mLastPosX, mPadInfo.mCStick.mLastPosY, 0.0f}; cXyz camMovement = {mPadInfo.mCStick.mLastPosX, mPadInfo.mCStick.mLastPosY, 0.0f};
f32 magnitude = sqrt(mPadInfo.mCStick.mLastPosX * mPadInfo.mCStick.mLastPosX + mPadInfo.mCStick.mLastPosY * mPadInfo.mCStick.mLastPosY); f32 magnitude = sqrt(mPadInfo.mCStick.mLastPosX * mPadInfo.mCStick.mLastPosX + mPadInfo.mCStick.mLastPosY * mPadInfo.mCStick.mLastPosY);
// If we aren't in manual cam mode, don't trigger it if the player tries to hit C-up if (mPadInfo.mCStick.mLastPosX != 0 || mPadInfo.mCStick.mLastPosY != 0) {
// for first person unless they have first person bound to a custom binding
if ((dusk::isActionBound(dusk::ActionBinds::FIRST_PERSON_CAMERA, mPadID) && mPadInfo.mCStick.mLastPosY != 0) ||
mPadInfo.mCStick.mLastPosX != 0 || mPadInfo.mCStick.mLastPosY < 0 || (mCamParam.mManualMode == 1 && mPadInfo.mCStick.mLastPosY != 0))
{
mCamParam.mManualMode = 1; mCamParam.mManualMode = 1;
camMovement = camMovement.normalize(); camMovement = camMovement.normalize();
camMovement.y *= dusk::getSettings().game.invertCameraYAxis ? 1.0f : -1.0f; camMovement.y *= dusk::getSettings().game.invertCameraYAxis ? 1.0f : -1.0f;
@@ -10431,7 +10418,7 @@ bool dCamera_c::eventCamera(s32 param_0) {
#endif #endif
#if TARGET_PC #if TARGET_PC
if (dusk::frame_interp::is_enabled()) { if (dusk::getSettings().game.enableFrameInterpolation) {
switch (var_r29) { switch (var_r29) {
case 3: case 3:
case 4: case 4:
@@ -11244,62 +11231,6 @@ cXyz dCamera_c::Center() {
return mCenter + mShake.field_0x24; return mCenter + mShake.field_0x24;
} }
#ifdef TARGET_PC
f32 get_target_trim_height(camera_process_class* i_this) {
const auto camera = &i_this->mCamera;
if (camera->mCurState != 2) {
switch (camera->mTrimSize) {
case 0:
case 4:
return 0.0f;
case 1:
return camera->mCamSetup.VistaTrimHeight();
case 2:
case 3:
return camera->mCamSetup.CinemaScopeTrimHeight();
default:
return camera->mTrimHeight;
}
}
return camera->mTrimHeight;
}
void widezoom_correction(camera_process_class* i_this, float trim_height) {
camera_class* camera = (camera_class*)i_this;
dDlst_window_c* window = get_window(camera);
view_port_class* viewport = window->getViewPort();
auto trim_width = 0.0f;
if (mDoGph_gInf_c::isWideZoom()) {
const auto target_ar = FB_WIDTH_BASE / (FB_HEIGHT_BASE - trim_height * 2.0f);
const auto target_ar_real =
FB_WIDTH_BASE / (FB_HEIGHT_BASE - get_target_trim_height(i_this) * 2.0f);
const auto current_ar = camera->view.aspect;
if (current_ar < target_ar) {
trim_height = FB_HEIGHT_BASE / 2.0f * (1.0f - current_ar / target_ar);
} else {
trim_height = 0.0f;
trim_width = FB_WIDTH_BASE / 2.0f * (1.0f - target_ar_real / current_ar);
}
if (dusk::frame_interp::is_sim_frame()) {
constexpr auto base_ar =
static_cast<f32>(FB_WIDTH_BASE) / static_cast<f32>(FB_HEIGHT_BASE);
const auto ar_corr = base_ar / std::min(current_ar, target_ar_real);
camera->view.fovy =
MTXRadToDeg(2.0f * atanf(tanf(MTXDegToRad(camera->view.fovy) * 0.5f) * ar_corr));
}
}
trim_width *= viewport->width / FB_WIDTH_BASE;
trim_height *= viewport->height / FB_HEIGHT_BASE;
window->setScissor(trim_width, trim_height, viewport->width - trim_width * 2.0f,
viewport->height - trim_height * 2.0f);
}
#endif
static int camera_execute(camera_process_class* i_this) { static int camera_execute(camera_process_class* i_this) {
preparation(i_this); preparation(i_this);
@@ -11320,28 +11251,6 @@ static int camera_execute(camera_process_class* i_this) {
store(i_this); store(i_this);
#ifdef TARGET_PC #ifdef TARGET_PC
widezoom_correction(i_this, i_this->mCamera.TrimHeight());
if (dusk::frame_interp::is_enabled()) {
dusk::frame_interp::add_interpolation_callback([](bool _, void* pUserWork) {
const auto i_this = static_cast<camera_process_class*>(pUserWork);
const auto camera = &i_this->mCamera;
const auto trim_size = camera->mTrimSize;
if (camera->mCurState != 2 && trim_size >= 0 && trim_size <= 3) {
// derive trim height at previous tick using current camera state
const auto target = get_target_trim_height(i_this);
const auto step = dusk::frame_interp::get_interpolation_step();
const auto cur = camera->TrimHeight();
const auto prev = (4.0f * cur - target) / 3.0f;
const auto trim_height = prev + (cur - prev) * step;
widezoom_correction(i_this, trim_height);
}
}, i_this);
}
// record new camera for our sim frame // record new camera for our sim frame
dusk::frame_interp::record_camera(i_this, get_camera_id(i_this)); dusk::frame_interp::record_camera(i_this, get_camera_id(i_this));
// interpolate the view now so that this sim frame's view matrix matches what // interpolate the view now so that this sim frame's view matrix matches what
@@ -11353,6 +11262,26 @@ static int camera_execute(camera_process_class* i_this) {
return 1; return 1;
} }
#ifdef TARGET_PC
void set_ar_corrected_trim(dDlst_window_c* window, float trim_height) {
const auto viewport = window->getViewPort();
if (mDoGph_gInf_c::isWideZoom()) {
const auto target_ar = FB_WIDTH / (FB_HEIGHT - trim_height * 2.0f);
const auto current_ar = mDoGph_gInf_c::m_safeWidthF / mDoGph_gInf_c::m_safeHeightF;
if (current_ar < target_ar) {
trim_height = FB_HEIGHT / 2.0f * (1.0f - current_ar / target_ar);
} else {
trim_height = 0.0f;
}
}
trim_height *= viewport->height / FB_HEIGHT;
window->setScissor(0.0f, trim_height, viewport->width, viewport->height - trim_height * 2.0f);
}
#endif
static int camera_draw(camera_process_class* i_this) { static int camera_draw(camera_process_class* i_this) {
camera_class* a_this = (camera_class*)i_this; camera_class* a_this = (camera_class*)i_this;
dCamera_c* body = &i_this->mCamera; dCamera_c* body = &i_this->mCamera;
@@ -11405,8 +11334,42 @@ static int camera_draw(camera_process_class* i_this) {
} }
#endif #endif
#if !TARGET_PC #if TARGET_PC
// trim handling moved to camera_execute for PC set_ar_corrected_trim(window, body->TrimHeight());
if (dusk::getSettings().game.enableFrameInterpolation) {
dusk::frame_interp::add_interpolation_callback([](bool _, void* pUserWork) {
const auto i_this = static_cast<camera_process_class*>(pUserWork);
const auto camera = &i_this->mCamera;
const auto trim_size = camera->mTrimSize;
if (camera->mCurState != 2 && trim_size >= 0 && trim_size <= 3) {
// derive trim height at previous tick using current camera state
f32 target;
switch (trim_size) {
case 0:
target = 0.0f;
break;
case 1:
target = camera->mCamSetup.VistaTrimHeight();
break;
case 2:
case 3:
target = camera->mCamSetup.CinemaScopeTrimHeight();
break;
}
const auto step = dusk::frame_interp::get_interpolation_step();
const auto cur = camera->TrimHeight();
const auto prev = (4.0f * cur - target) / 3.0f;
const auto trim_height = prev + (cur - prev) * step;
set_ar_corrected_trim(get_window((camera_class*)i_this), trim_height);
}
}, i_this);
}
#else
int trim_height = body->TrimHeight(); int trim_height = body->TrimHeight();
window->setScissor(0.0f, trim_height, FB_WIDTH, FB_HEIGHT - trim_height * 2.0f); window->setScissor(0.0f, trim_height, FB_WIDTH, FB_HEIGHT - trim_height * 2.0f);
-8
View File
@@ -15,7 +15,6 @@
#include "f_op/f_op_actor_mng.h" #include "f_op/f_op_actor_mng.h"
#if TARGET_PC #if TARGET_PC
#include "dusk/achievements.h" #include "dusk/achievements.h"
#include "dusk/settings.h"
#endif #endif
static int plCutLRC[58] = { static int plCutLRC[58] = {
@@ -430,13 +429,6 @@ fopAc_ac_c* cc_at_check(fopAc_ac_c* i_enemy, dCcU_AtInfo* i_AtInfo) {
} }
} }
#if TARGET_PC
if (dusk::getSettings().game.invincibleEnemies &&
fopAcM_GetGroup(i_enemy) == fopAc_ENEMY_e) {
i_AtInfo->mAttackPower = 0;
}
#endif
if (i_AtInfo->mAttackPower != 0) { if (i_AtInfo->mAttackPower != 0) {
i_enemy->health -= i_AtInfo->mAttackPower; i_enemy->health -= i_AtInfo->mAttackPower;
} }
-8
View File
@@ -19,7 +19,6 @@
#include "d/d_timer.h" #include "d/d_timer.h"
#include "f_op/f_op_msg_mng.h" #include "f_op/f_op_msg_mng.h"
#include "f_op/f_op_scene_mng.h" #include "f_op/f_op_scene_mng.h"
#include "m_Do/m_Do_MemCard.h"
#include "m_Do/m_Do_Reset.h" #include "m_Do/m_Do_Reset.h"
#include "m_Do/m_Do_controller_pad.h" #include "m_Do/m_Do_controller_pad.h"
#include "m_Do/m_Do_graphic.h" #include "m_Do/m_Do_graphic.h"
@@ -1239,13 +1238,6 @@ BOOL dComIfG_resetToOpening(scene_class* i_scene) {
} }
#endif #endif
#ifdef TARGET_PC
if (!mDoMemCd_isCardCommNone()) {
return 0;
}
g_mDoMemCd_control.SaveSync();
#endif
dComIfG_changeOpeningScene(i_scene, fpcNm_OPENING_SCENE_e); dComIfG_changeOpeningScene(i_scene, fpcNm_OPENING_SCENE_e);
mDoAud_bgmStop(30); mDoAud_bgmStop(30);
mDoAud_resetProcess(); mDoAud_resetProcess();
-4
View File
@@ -3882,11 +3882,7 @@ bool dCamera_c::hintTalkEvCamera() {
cSAngle acStack_1fc(20.0f); cSAngle acStack_1fc(20.0f);
for (i = 0; i < 2; i++) { for (i = 0; i < 2; i++) {
#if AVOID_UB
for (j = 0; j < 10; j++) {
#else
for (j = 0; j < 12; j++) { for (j = 0; j < 12; j++) {
#endif
cSAngle acStack_200(local_b0[j] * fVar22); cSAngle acStack_200(local_b0[j] * fVar22);
hintTalk->mDirection.U(acStack_1f8 + acStack_200); hintTalk->mDirection.U(acStack_1f8 + acStack_200);
hintTalk->mDirection.V(((hintTalk->field_0x28.V() * acStack_200.Cos()) * 0.2f) + acStack_1fc); hintTalk->mDirection.V(((hintTalk->field_0x28.V() * acStack_200.Cos()) * 0.2f) + acStack_1fc);
+1 -10
View File
@@ -36,7 +36,6 @@
#include "dusk/imgui/ImGuiBloomWindow.hpp" #include "dusk/imgui/ImGuiBloomWindow.hpp"
#include "dusk/settings.h" #include "dusk/settings.h"
#include "dusk/frame_interpolation.h" #include "dusk/frame_interpolation.h"
#include "dusk/game_clock.h"
#endif #endif
static void GxXFog_set(); static void GxXFog_set();
@@ -2269,7 +2268,6 @@ void dKy_calc_color_set(GXColorS10* out_color_p, color_RGB_class* color_a_start_
color_b_start_p->b, color_b_end_p->b, blend_ratio, add_col.b, scale); color_b_start_p->b, color_b_end_p->b, blend_ratio, add_col.b, scale);
} }
void dScnKy_env_light_c::setLight() { void dScnKy_env_light_c::setLight() {
f32 color_ratio; f32 color_ratio;
@@ -2515,14 +2513,7 @@ void dScnKy_env_light_c::setLight() {
static s16 S_fuwan_sin; static s16 S_fuwan_sin;
f32 sin = cM_ssin(S_fuwan_sin); f32 sin = cM_ssin(S_fuwan_sin);
S_fuwan_sin += (s16)cM_rndF(2000.0f) + 500;
#if TARGET_PC
const f32 deltaTime = dusk::game_clock::consume_interval(this);
const f32 timeScale = deltaTime / dusk::game_clock::period_for_original_frames(1.0f);
S_fuwan_sin += (s16)((cM_rndF(2000.0f) + 500) * timeScale);
#else
S_fuwan_sin += (s16)cM_rndF(2000.0f) + 500;
#endif
blure_size += (u8)(sin * (0.2f * blure_size)); blure_size += (u8)(sin * (0.2f * blure_size));
} }
+1 -26
View File
@@ -152,7 +152,7 @@ u8 STControl::checkTrigger() {
field_0x22 = -field_0x24; field_0x22 = -field_0x24;
} }
} }
#if !TARGET_PC
if (!(mDirectionTrig & 3)) { if (!(mDirectionTrig & 3)) {
Xinit(); Xinit();
} }
@@ -160,35 +160,10 @@ u8 STControl::checkTrigger() {
if (!(mDirectionTrig & 0xC)) { if (!(mDirectionTrig & 0xC)) {
Yinit(); Yinit();
} }
#endif
} else { } else {
mDirectionTrig = 0; mDirectionTrig = 0;
#if !TARGET_PC
Xinit(); Xinit();
Yinit(); Yinit();
#endif
#if TARGET_PC
if (mDoCPd_c::getHoldLeft(PAD_1)) {
mDirectionTrig |= TRIG_LEFT;
}
if (mDoCPd_c::getHoldRight(PAD_1)) {
mDirectionTrig |= TRIG_RIGHT;
}
if (mDoCPd_c::getHoldUp(PAD_1)) {
mDirectionTrig |= TRIG_UP;
}
if (mDoCPd_c::getHoldDown(PAD_1)) {
mDirectionTrig |= TRIG_DOWN;
}
}
if (!(mDirectionTrig & 3)) {
Xinit();
}
if (!(mDirectionTrig & 0xC)) {
Yinit();
#endif
} }
if ((field_0x0d & mDirectionTrig & 3) && field_0x0e > 0) { if ((field_0x0d & mDirectionTrig & 3) && field_0x0e > 0) {
-14
View File
@@ -1141,9 +1141,6 @@ dMap_c::dMap_c(int width, int height, int param_2, int param_3) {
field_0x91 = 0; field_0x91 = 0;
m_mySelfPointer = this; m_mySelfPointer = this;
#endif #endif
#if TARGET_PC
previousMirror = dusk::getSettings().game.enableMirrorMode;
#endif
m_res = JKR_NEW_ARGS (0x20) dMap_prm_res_s; m_res = JKR_NEW_ARGS (0x20) dMap_prm_res_s;
JUT_ASSERT(2559, m_res != NULL); JUT_ASSERT(2559, m_res != NULL);
@@ -1582,17 +1579,6 @@ bool dMap_c::isDrawRoomIcon(int param_0, int param_1) const {
} }
void dMap_c::_move(f32 i_centerX, f32 i_centerZ, int i_roomNo, f32 param_3) { void dMap_c::_move(f32 i_centerX, f32 i_centerZ, int i_roomNo, f32 param_3) {
#if TARGET_PC
bool currentMirror = dusk::getSettings().game.enableMirrorMode;
if (currentMirror != previousMirror) {
previousMirror = currentMirror;
if (currentMirror) {
mCenterX -= 2.0f * mPackX;
} else {
mCenterX += 2.0f * mPackX;
}
}
#endif
if (mStayRoomNo == -1) { if (mStayRoomNo == -1) {
mStayRoomNo = i_roomNo; mStayRoomNo = i_roomNo;
field_0x80 = mStayRoomNo; field_0x80 = mStayRoomNo;

Some files were not shown because too many files have changed in this diff Show More