mirror of
https://github.com/visualboyadvance-m/visualboyadvance-m
synced 2025-10-05 23:52:49 +02:00
Compare commits
97 Commits
test-widge
...
disable-li
Author | SHA1 | Date | |
---|---|---|---|
|
4d1b3cffaf | ||
|
2ab707c0ca | ||
|
4dba928765 | ||
|
3d6550d161 | ||
|
3cf12f2594 | ||
|
de1ec01c78 | ||
|
295abb9cd0 | ||
|
8260b62482 | ||
|
d18c6f115f | ||
|
d36f80b5e6 | ||
|
44aa859e6d | ||
|
5a2d3a6f95 | ||
|
d6b939c428 | ||
|
8b8be7d4a8 | ||
|
72364fd1a4 | ||
|
c6da07feb3 | ||
|
94979eff97 | ||
|
e8494b56d1 | ||
|
c85397518b | ||
|
cf2339822d | ||
|
dcb9ccca90 | ||
|
a8ec85d536 | ||
|
611f3a3409 | ||
|
b6da6c490c | ||
|
9d20ce9b59 | ||
|
709a322337 | ||
|
cdfd37fc4e | ||
|
4f8d0a8867 | ||
|
b22e9fb709 | ||
|
4e2799b582 | ||
|
7fa90531e6 | ||
|
e1c2ecc584 | ||
|
4c450ab360 | ||
|
d5e1a1f36b | ||
|
821b9176bd | ||
|
9031103c9a | ||
|
557f897ead | ||
|
c8a4f66cf8 | ||
|
ddc93ec6e1 | ||
|
ab38ae8f24 | ||
|
d337688fa7 | ||
|
3eea90afb6 | ||
|
b3952d74a8 | ||
|
be09125d52 | ||
|
f264e7f807 | ||
|
fe0791762a | ||
|
61f427dec1 | ||
|
d619ee2bb1 | ||
|
7128e6dd08 | ||
|
0decffea8d | ||
|
9b60e17746 | ||
|
26207038c9 | ||
|
90867bc802 | ||
|
7f49cd33ad | ||
|
d8342d3d67 | ||
|
12e840a8fa | ||
|
6ca609ac7e | ||
|
2b8f9f71ff | ||
|
e76cef79d2 | ||
|
7f06428df8 | ||
|
e4a9340409 | ||
|
5d7023a5d6 | ||
|
3bd7c918cc | ||
|
67e4944cdb | ||
|
df4ff16e2c | ||
|
d4805065b3 | ||
|
e39b1f2c53 | ||
|
73b65a6553 | ||
|
9e556e6a56 | ||
|
11e73f2c61 | ||
|
e97b0448b7 | ||
|
aa6ed14b2a | ||
|
2ce20c4f59 | ||
|
e4ef4aa625 | ||
|
cf5cb40cb9 | ||
|
c450d14311 | ||
|
41572be3f2 | ||
|
4f8da1c574 | ||
|
32091669d4 | ||
|
abd72a5b2e | ||
|
7e6349b19f | ||
|
0782be749e | ||
|
a7b545ab1a | ||
|
1a564f900c | ||
|
3d4e03f85f | ||
|
fc17209ac7 | ||
|
38877ef209 | ||
|
8691a15be8 | ||
|
961fd0304c | ||
|
e2cf6ecba6 | ||
|
7a0826a60c | ||
|
d516683a77 | ||
|
834c7de86c | ||
|
4f1a5dd726 | ||
|
5766b9b9c7 | ||
|
5d8426d317 | ||
|
63ec3528f1 |
2
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
2
.github/ISSUE_TEMPLATE/bug_report.yml
vendored
@@ -11,7 +11,7 @@ body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Please try the nightly build from: https://nightly.vba-m.com and factory resetting the emulator from the Help menu.
|
||||
Please try the nightly build from: https://nightly.visualboyadvance-m.org and factory resetting the emulator from the Help menu.
|
||||
On Linux build master from source or use the edge snap.
|
||||
And last but not least, search for existing reports via the filters bar on the issues page.
|
||||
- type: markdown
|
||||
|
2
.github/ISSUE_TEMPLATE/config.yml
vendored
2
.github/ISSUE_TEMPLATE/config.yml
vendored
@@ -1,7 +1,7 @@
|
||||
blank_issues_enabled: false
|
||||
contact_links:
|
||||
- name: VBA-M Forum
|
||||
url: https://board.vba-m.com/
|
||||
url: https://board.visualboyadvance-m.org/
|
||||
about: For general questions and support please join our forum or our
|
||||
- name: VBA-M IRC Channel
|
||||
url: https://web.libera.chat/#vba-m
|
||||
|
2
.github/ISSUE_TEMPLATE/feature.yml
vendored
2
.github/ISSUE_TEMPLATE/feature.yml
vendored
@@ -14,7 +14,7 @@ body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Please try a nightly build from: https://nightly.vba-m.com to see if your idea has already been implemented.
|
||||
Please try a nightly build from: https://nightly.visualboyadvance-m.org to see if your idea has already been implemented.
|
||||
On Linux build master from source or use the edge snap.
|
||||
And last but not least, search for existing requests via the filters bar on the issues page.
|
||||
- type: textarea
|
||||
|
4
.github/workflows/macos-build.yml
vendored
4
.github/workflows/macos-build.yml
vendored
@@ -1,4 +1,4 @@
|
||||
name: macOS Latest Build
|
||||
name: macOS Latest
|
||||
on: [push, pull_request]
|
||||
|
||||
jobs:
|
||||
@@ -60,4 +60,4 @@ jobs:
|
||||
- if: matrix.build_options == 'default'
|
||||
name: Run tests
|
||||
run: >-
|
||||
nix-shell --command 'cd build && ctest -j'
|
||||
nix-shell --command 'cd build && ctest -j --output-on-failure'
|
||||
|
2
.github/workflows/msys2-build.yml
vendored
2
.github/workflows/msys2-build.yml
vendored
@@ -1,4 +1,4 @@
|
||||
name: MSYS2 Build
|
||||
name: MSYS2
|
||||
on: [push, pull_request]
|
||||
|
||||
jobs:
|
||||
|
7
.github/workflows/ubuntu-build.yml
vendored
7
.github/workflows/ubuntu-build.yml
vendored
@@ -1,4 +1,4 @@
|
||||
name: Ubuntu Latest Build
|
||||
name: Ubuntu Latest
|
||||
on: [push, pull_request]
|
||||
|
||||
jobs:
|
||||
@@ -45,6 +45,9 @@ jobs:
|
||||
run: >-
|
||||
bash installdeps; if [ "${{ matrix.build_compiler }}" = clang ]; then sudo apt -y install clang; fi
|
||||
|
||||
- name: Install xvfb
|
||||
run: sudo apt -y install xvfb
|
||||
|
||||
# CMake build
|
||||
- if: matrix.build_options != 'libretro'
|
||||
name: Configure CMake
|
||||
@@ -65,4 +68,4 @@ jobs:
|
||||
# Run tests
|
||||
- if: matrix.build_options == 'default'
|
||||
name: Run tests
|
||||
run: cd build && ctest -j
|
||||
run: cd build && xvfb-run ctest -j --output-on-failure
|
||||
|
4
.github/workflows/visual-studio-build.yml
vendored
4
.github/workflows/visual-studio-build.yml
vendored
@@ -1,4 +1,4 @@
|
||||
name: Visual Studio Build
|
||||
name: Visual Studio
|
||||
on: [push, pull_request]
|
||||
|
||||
jobs:
|
||||
@@ -57,4 +57,4 @@ jobs:
|
||||
# Run tests
|
||||
- if: matrix.build_options == 'default' && matrix.msvc_arch != 'amd64_arm64'
|
||||
name: Run tests
|
||||
run: cd build && ctest -j
|
||||
run: cd build && ctest -j --output-on-failure
|
||||
|
10
.gitmodules
vendored
10
.gitmodules
vendored
@@ -1,4 +1,6 @@
|
||||
[submodule "dependencies"]
|
||||
path = dependencies
|
||||
url = https://github.com/visualboyadvance-m/dependencies.git
|
||||
branch = master
|
||||
[submodule "win32-deps"]
|
||||
path = win32-deps
|
||||
url = https://github.com/visualboyadvance-m/win32-deps.git
|
||||
[submodule "third_party/googletest"]
|
||||
path = third_party/googletest
|
||||
url = https://github.com/google/googletest.git
|
||||
|
62
CHANGELOG.md
62
CHANGELOG.md
@@ -4,6 +4,68 @@ All notable changes to this project will be documented in this file.
|
||||
The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/)
|
||||
and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## [2.1.11] - 2024-09-15
|
||||
|
||||
==========================
|
||||
* 3eea90af - build: set BUILD_TESTING=OFF when not git checkout [rkitover]
|
||||
* b3952d74 - build: fix ENABLE_LIRC=ON [rkitover]
|
||||
* f264e7f8 - Fix Help -> Translations URL [rkitover]
|
||||
* 61f427de - Write shortcuts in the proper section (#1335) [Steelskin]
|
||||
* d619ee2b - build: fix installing GoogleTest [rkitover]
|
||||
* 26207038 - Update WinSparkle to 0.8.1 and add ARM64 [rkitover]
|
||||
|
||||
## [2.1.10] - 2024-09-08
|
||||
|
||||
==========================
|
||||
* 7f06428d - Disable dialog position save/restore on wxGTK (#1331) [Steelskin]
|
||||
* e4ef4aa6 - Propagate key events (#1323) [Steelskin]
|
||||
* e2cf6ecb - Add option to mute sound during speedup [rkitover]
|
||||
* d516683a - build: fix for wx using GTK2 [rkitover]
|
||||
* 834c7de8 - build: update macOS builder dists [rkitover]
|
||||
* fc82e062 - build: do not build SDL bin on Windows or macOS [rkitover]
|
||||
* d543784a - [UserInput] Filter key events globally [steelskin]
|
||||
* 902c6c8e - [UserInput] Only process shortcut commands once [steelskin]
|
||||
* b7765092 - [bindings] Set default shortcut for recent file 3 [steelskin]
|
||||
* cc65ef28 - doc: add system requirements to README.md [danialhorton]
|
||||
* 32627f6b - [Dialogs] Save and restore dialog positions [steelskin]
|
||||
* 41952d06 - build: update macOS linker tool to 1.5 [rkitover]
|
||||
* 0c39a5ba - build: override FindGettext to not update po files [rkitover]
|
||||
* 1b77d659 - build: update macOS build to ffmpeg 7.0 [rkitover]
|
||||
* 8d08223d - build: fix compatibility with older ffmpeg [rkitover]
|
||||
* af6028a9 - build: fix build for nix on macOS [rkitover]
|
||||
* b52edf52 - build: fix building on macOS with Homebrew [rkitover]
|
||||
* 6766b9ca - build: fix ffmpeg 7.x compat [rkitover]
|
||||
* 795f25bb - build: fix nix deps for OpenGL [rkitover]
|
||||
* 647be137 - gba: set cpsr=spsr when switching to FIQ mode [40356555+Aikku93]
|
||||
* 8abe3e79 - build: remove -lgcc from static link flags [rkitover]
|
||||
* f4835674 - [Audio] Rework audio devices enumeration [steelskin]
|
||||
* 775a571f - build: fix detecting Visual Studio default vcpkg [rkitover]
|
||||
* 64abd3e8 - [Audio] Remove manual memory allocations [steelskin]
|
||||
* 047ad277 - [Dialogs] Prevent viewers from causing a crash [steelskin]
|
||||
* 045c98d8 - build: only use -Werror=lto-type-mismatch on gcc [rkitover]
|
||||
* 3518dc6a - build: fix LTO on Linux [rkitover]
|
||||
* cc9a03ce - Add toggle: SDL GameController mode for joysticks [rkitover]
|
||||
* 8576733c - [Build] Remove lingering references to OpenAl [steelskin]
|
||||
* 05561922 - build: fix MSYS2 check [rkitover]
|
||||
* d9432ebb - build: fix build on MINGW{64,32}/UCRT64 on MSYS2 [rkitover]
|
||||
* f57cad67 - build: fix static linking on MSYS2 CLANG64 [rkitover]
|
||||
* 23e15734 - build: set wxWidgets_DIR with vcpkg [rkitover]
|
||||
* 98b51910 - [Build] Remove ENABLE_NLS, fix TRANSLATIONS_ONLY [steelskin]
|
||||
* a565cea8 - [Build] Remove the OpenGL check [steelskin]
|
||||
* f96e42fe - build: cmake refactor and improvements [Steelskin]
|
||||
* 07e49025 - Fix most remaining release warnings (#1243) [Steelskin]
|
||||
* 18b97b43 - Fix various build warnings (#1242) [Steelskin]
|
||||
* 13a16eb7 - Fix various warnings in filters and headers (#1241) [Steelskin]
|
||||
* f46da1c5 - build: remove our version of FindSDL2.cmake [rkitover]
|
||||
* 404e9a1a - build: add clang to ./installdeps for MSYS2 [rkitover]
|
||||
* 613bd403 - Make menu more reasonably organized (#1230) [wwrustc]
|
||||
* 215e3c5a - build: use find_program() to find powershell [rkitover]
|
||||
* e5aa685f - build: don't use wx utils as UNIX cmds on Windows [rkitover]
|
||||
* 9e4c8e17 - build: fix gentoo dependency namespaces [68k]
|
||||
* 5f853b99 - Update metainfo.xml to new standards [jhonny.oliveira]
|
||||
* e7d135db - Update links to new domain visualboyadvance-m.org [rkitover]
|
||||
* 60fc096f - build: add libglu-devel for solus in installdeps [rkitover]
|
||||
|
||||
## [2.1.9] - 2024-02-03
|
||||
=======================
|
||||
* 84b0a3e3 - Remove SDL sound driver [rkitover]
|
||||
|
@@ -5,6 +5,13 @@ set(CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake)
|
||||
|
||||
if(WIN32)
|
||||
include(RemoveStrawberryPerlFromPATH)
|
||||
|
||||
find_program(POWERSHELL
|
||||
NAMES powershell.exe pwsh.exe
|
||||
HINTS "/Windows/System32/WindowsPowerShell/v1.0"
|
||||
REQUIRED)
|
||||
else()
|
||||
find_program(POWERSHELL pwsh)
|
||||
endif()
|
||||
|
||||
if(UPDATE_APPCAST)
|
||||
@@ -23,15 +30,6 @@ set(VCPKG_DEPS_OPTIONAL
|
||||
faudio ENABLE_FAUDIO
|
||||
)
|
||||
|
||||
if(WIN32)
|
||||
find_program(POWERSHELL
|
||||
NAMES powershell.exe pwsh.exe
|
||||
HINTS "/Windows/System32/WindowsPowerShell/v1.0"
|
||||
REQUIRED)
|
||||
else()
|
||||
find_program(POWERSHELL pwsh)
|
||||
endif()
|
||||
|
||||
include(Set-Toolchain-vcpkg)
|
||||
|
||||
# Use ccache if available and not already enabled on the command line.
|
||||
@@ -54,7 +52,7 @@ if(GIT_FOUND AND WIN32)
|
||||
# Win32 deps submodule
|
||||
set(SUBMODULE_MANUAL_UPDATE FALSE)
|
||||
|
||||
if(EXISTS "${CMAKE_SOURCE_DIR}/.git" AND NOT EXISTS "${CMAKE_SOURCE_DIR}/dependencies/mingw-xaudio/include")
|
||||
if(EXISTS "${CMAKE_SOURCE_DIR}/.git" AND NOT EXISTS "${CMAKE_SOURCE_DIR}/win32-deps/mingw-xaudio/include")
|
||||
set(SUBMODULE_MANUAL_UPDATE TRUE)
|
||||
execute_process(
|
||||
COMMAND "${GIT_EXECUTABLE}" submodule update --init --remote --recursive
|
||||
@@ -63,7 +61,7 @@ if(GIT_FOUND AND WIN32)
|
||||
)
|
||||
endif()
|
||||
|
||||
if(NOT EXISTS "${CMAKE_SOURCE_DIR}/dependencies/mingw-xaudio/include")
|
||||
if(NOT EXISTS "${CMAKE_SOURCE_DIR}/win32-deps/mingw-xaudio/include")
|
||||
if(NOT (SUBMODULE_MANUAL_UPDATE AND SUBMODULE_UPDATE_STATUS EQUAL 0))
|
||||
message(FATAL_ERROR "Please pull in git submodules, e.g.\nrun: git submodule update --init --remote --recursive")
|
||||
endif()
|
||||
@@ -85,16 +83,29 @@ include(Options)
|
||||
include(Toolchain)
|
||||
include(Dependencies)
|
||||
|
||||
# Disable tests when not in a git checkout.
|
||||
if(NOT EXISTS "${CMAKE_SOURCE_DIR}/.git")
|
||||
set(BUILD_TESTING OFF)
|
||||
endif()
|
||||
|
||||
# Configure gtest
|
||||
if(BUILD_TESTING)
|
||||
FetchContent_Declare(googletest
|
||||
URL https://github.com/google/googletest/archive/2d16ed055d09c3689d44b272adc097393de948a0.zip
|
||||
)
|
||||
|
||||
set(gtest_force_shared_crt ON CACHE BOOL "" FORCE)
|
||||
FetchContent_MakeAvailable(googletest)
|
||||
set(INSTALL_GTEST OFF CACHE BOOL "" FORCE)
|
||||
|
||||
include(GoogleTest)
|
||||
if(NOT EXISTS third_party/googletest/CMakeLists.txt)
|
||||
execute_process(
|
||||
COMMAND git submodule update --init --recursive -- third_party/googletest
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
endif()
|
||||
|
||||
if(EXISTS third_party/googletest/CMakeLists.txt)
|
||||
add_subdirectory(./third_party/googletest)
|
||||
include(GoogleTest)
|
||||
else()
|
||||
set(BUILD_TESTING OFF)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(NOT CMAKE_PREFIX_PATH AND (NOT ("$ENV{CMAKE_PREFIX_PATH}" STREQUAL "")))
|
||||
@@ -107,11 +118,6 @@ elseif(NOT CMAKE_BUILD_TYPE MATCHES "^(Release|Debug|RelWithDebInfo|MinSizeRel)$
|
||||
message(FATAL_ERROR "Invalid CMAKE_BUILD_TYPE: '${CMAKE_BUILD_TYPE}', must be one of: 'Release', 'Debug', 'RelWithDebInfo' or 'MinSizeRel'")
|
||||
endif()
|
||||
|
||||
# Link debug libs for RelWithDebInfo
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo")
|
||||
set(CMAKE_MAP_IMPORTED_CONFIG_RELWITHDEBINFO "Debug")
|
||||
endif()
|
||||
|
||||
set(MSYS OFF)
|
||||
if(NOT "$ENV{MSYSTEM_PREFIX}" STREQUAL "")
|
||||
set(MSYS ON)
|
||||
@@ -192,5 +198,5 @@ set(CPACK_SOURCE_GENERATOR "TGZ")
|
||||
set(CPACK_PACKAGE_VERSION_MAJOR "2")
|
||||
set(CPACK_PACKAGE_VERSION_MINOR "0")
|
||||
set(CPACK_PACKAGE_VERSION_PATCH "0-Git-${COMMITHASH}")
|
||||
list(APPEND CPACK_SOURCE_IGNORE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/dependencies")
|
||||
list(APPEND CPACK_SOURCE_IGNORE_FILES "${CMAKE_CURRENT_SOURCE_DIR}/win32-deps")
|
||||
include(CPack)
|
||||
|
@@ -9,17 +9,15 @@
|
||||
- [Commit Message](#commit-message)
|
||||
- [Collaboration on a Branch](#collaboration-on-a-branch)
|
||||
- [Commits from Maintainers](#commits-from-maintainers)
|
||||
- [Strings, Character Sets and Translations](#strings-character-sets-and-translations)
|
||||
- [Pulling Updated Translations](#pulling-updated-translations)
|
||||
- [Translations Message Catalog](#translations-message-catalog)
|
||||
- [Interaction with non-wxWidgets Code](#interaction-with-non-wxwidgets-code)
|
||||
- [Windows Native Development Environment Setup](#windows-native-development-environment-setup)
|
||||
- [Miscellaneous](#miscellaneous)
|
||||
- [Debug Messages](#debug-messages)
|
||||
- [Release Process](#release-process)
|
||||
- [Environment](#environment)
|
||||
- [Certificates](#certificates)
|
||||
- [Release Commit and Tag](#release-commit-and-tag)
|
||||
- [64-bit Windows Binary](#64-bit-windows-binary)
|
||||
- [32-bit Windows Binary](#32-bit-windows-binary)
|
||||
- [64-bit Mac Binary](#64-bit-mac-binary)
|
||||
- [ARM64 Windows Binary](#arm64-windows-binary)
|
||||
- [macOS Binary](#macos-binary)
|
||||
- [Final steps](#final-steps)
|
||||
|
||||
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
|
||||
@@ -53,11 +51,12 @@ Follow the following steps to process newly submitted issues:
|
||||
- An issue is resolved by closing it in github. A commit that fixes the issue
|
||||
should have the following line near the end of the body of the commit message:
|
||||
```
|
||||
- Fix #999.
|
||||
Fix #999.
|
||||
```
|
||||
This will automatically close the issue and assign the closing commit in the
|
||||
github metadata when it is merged to master. The issue can be reopened if
|
||||
needed.
|
||||
|
||||
- A commit that is work towards resolving an issue, should have the issue number
|
||||
preceded by a pound sign either at the end of a commit message title, if it is
|
||||
of primary relevance to the issue, or the body otherwise.
|
||||
@@ -70,7 +69,7 @@ Follow these guidelines always:
|
||||
|
||||
https://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html
|
||||
|
||||
the description of your work should be in the **commit message NOT the pull
|
||||
, the description of your work should be in the **commit message NOT the pull
|
||||
request description**.
|
||||
|
||||
The title line must be no more than 50 characters and the description must be
|
||||
@@ -95,16 +94,21 @@ other projects, fewer is better.
|
||||
The commit title line should be prefixed with an area, unless it involves the
|
||||
wxWidgets GUI app, in which case it should **NOT** have a prefix.
|
||||
|
||||
If the commit is a user-facing functionality change or enhancement, the title
|
||||
line of the commit must be a non-technical description of this change. For
|
||||
example "Mute on speedup" because this will go into the changelog.
|
||||
|
||||
The text after the area prefix should not be capitalized.
|
||||
|
||||
Please use one of these area prefixes otherwise:
|
||||
Please use one of these area prefixes for non-main-GUI-app commits:
|
||||
|
||||
- doc: documentation, README.md etc.
|
||||
- build: cmake, installdeps, preprocessor compatibility defines, etc.
|
||||
- gb-core: the GameBoy emulator core
|
||||
- gba-core: the GameBoy Advance emulator core
|
||||
- build: cmake, installdeps, preprocessor compatibility defines, compatibility
|
||||
headers, etc.
|
||||
- gb: the GameBoy emulator core
|
||||
- gba: the GameBoy Advance emulator core
|
||||
- libretro: the libretro core glue and build
|
||||
- sdl-app: anything for the SDL app
|
||||
- sdl: anything for the SDL port
|
||||
- translations: anything related to translations
|
||||
|
||||
. Add other areas here if needed.
|
||||
@@ -138,137 +142,79 @@ things in mind:
|
||||
better to edit the history than to add more commits. Never add commits fixing
|
||||
previous commits, only improving or adding to them.
|
||||
|
||||
- To update when someone else (very rudely you might say) did a `push -f`, `pull
|
||||
--rebase` will **USUALLY** work. Verify the log, and if necessary do this
|
||||
instead:
|
||||
|
||||
- To update when someone else updated the branch with a `push -f`
|
||||
```bash
|
||||
git status # should be clean, with your work having been already pushed
|
||||
git fetch --all --prune
|
||||
git reset --hard origin/<branch-name>
|
||||
```
|
||||
.
|
||||
|
||||
While actively working on a branch, keep it rebased on top of master.
|
||||
- While actively working on a branch, keep it rebased on top of master.
|
||||
|
||||
#### Commits from Maintainers
|
||||
|
||||
Maintainers have the power to commit directly to master. This power must be
|
||||
used responsibly, something I fail to do myself often, and will try to improve
|
||||
upon.
|
||||
Maintainers and project members have the power to commit directly to master.
|
||||
This power must be used responsibly.
|
||||
|
||||
Make your most earnest attempt to follow these general guidelines to keep our
|
||||
Make your best attempt to follow these general guidelines to keep our
|
||||
history clean:
|
||||
|
||||
- Things that are a straight fix or improvement that does not require discussion
|
||||
- Things that are a minor fix or improvement that does not require discussion
|
||||
can be committed directly, keeping the following guidelines in mind.
|
||||
|
||||
- Bigger new features, code refactors and changes in architecture should go
|
||||
through the PR process.
|
||||
|
||||
- Push code changes to a branch first, so they can run through the CI.
|
||||
Differences in what different compilers allow is a problem that comes up
|
||||
**VERY** frequently. As well as incompatibilities between different
|
||||
configurations for both the C++ code and any supporting code.
|
||||
- Push code changes to a branch first, so they can run through the CI. When you
|
||||
open the commit in GitHub there is a little icon in the upper left corner that
|
||||
shows the CI status for this commit. Differences in what different compilers
|
||||
allow is a problem that comes up **VERY** frequently. As well as
|
||||
incompatibilities between different configurations for both the C++ code and
|
||||
any supporting code.
|
||||
|
||||
### Miscellaneous
|
||||
|
||||
### Strings, Character Sets and Translations
|
||||
#### Debug Messages
|
||||
|
||||
#### Pulling Updated Translations
|
||||
We have an override for `wxLogDebug()` to make it work even in non-debug builds
|
||||
of wx and on windows, even in mintty.
|
||||
|
||||
Once in a while it is necessary to pull new and updated translations from
|
||||
transifex.
|
||||
|
||||
For this you need the transifex client, available for Windows as well from
|
||||
chocolatey as `transifex-client`.
|
||||
|
||||
To pull translations run:
|
||||
|
||||
```bash
|
||||
tx pull -af
|
||||
```
|
||||
|
||||
then check `git status` and if any message catalogs were updated, commit the
|
||||
result as:
|
||||
|
||||
```bash
|
||||
git commit -a --signoff -S -m'Transifex pull.'
|
||||
git push
|
||||
```
|
||||
|
||||
#### Translations Message Catalog
|
||||
|
||||
Strings that need to be translated by our wonderful translators on transifex
|
||||
(thank you guys very much) need to be enclosed in `_("...")`, for example:
|
||||
It works like `printf()`, e.g.:
|
||||
|
||||
```cpp
|
||||
wxLogError(_("error: something very wrong"));
|
||||
int foo = 42;
|
||||
wxLogDebug(wxT("the value of foo = %d"), foo);
|
||||
```
|
||||
|
||||
The next time you run cmake after adding a string to be translated, the `.pot`
|
||||
message catalog source will be regenerated, and you will see a loud message
|
||||
telling you to push to transifex.
|
||||
|
||||
Strings in the XRC XML GUI definition files are automatically added to the
|
||||
message catalog as well.
|
||||
|
||||
If you are working on a branch or a PR, don't push to transifex until it has
|
||||
been merged to master.
|
||||
|
||||
Once it is, push it with:
|
||||
|
||||
```bash
|
||||
tx push -s
|
||||
```
|
||||
|
||||
#### Interaction with non-wxWidgets Code
|
||||
|
||||
Use our `UTF8(...)` function to force any `wxString` to UTF-8 for use by other
|
||||
libraries, screen output or OS APIs. For example:
|
||||
From the core etc. the usual:
|
||||
|
||||
```cpp
|
||||
fprintf(STDERR, "Error: %s\n", UTF8(err_msg));
|
||||
fprintf(stderr, "...", ...);
|
||||
```
|
||||
, will work fine.
|
||||
|
||||
There is one exception to this, when using `wxString::Printf()` and such, you
|
||||
can't pass another `wxString` to the `%s` format directly, use something like
|
||||
this:
|
||||
|
||||
```cpp
|
||||
wxString err;
|
||||
err.Printf("Cannot read file: %s", fname.wc_str());
|
||||
```
|
||||
|
||||
this uses the `wchar_t` UTF-16 representation on Windows and does nothing
|
||||
elsewhere.
|
||||
|
||||
For calling Windows APIs with strings, use the wide char `W` variants and the
|
||||
`wc_str()` method as well.
|
||||
|
||||
### Windows Native Development Environment Setup
|
||||
|
||||
This guide has been moved to:
|
||||
|
||||
https://github.com/rkitover/windows-dev-guide
|
||||
You need a debug build for this to work or to even have a console on Windows.
|
||||
Pass `-DCMAKE_BUILD_TYPE=Debug` to cmake.
|
||||
|
||||
### Release Process
|
||||
|
||||
#### Environment
|
||||
#### GnuPG Key
|
||||
|
||||
The variable `VBAM_NO_PAUSE`, if set, will cause cmake to not pause before gpg
|
||||
signing operations, you want to set this if you've disabled your gpg passphrase
|
||||
to not require interaction during release builds.
|
||||
You will need to create a GnuPG key for signing your commits and release tags,
|
||||
and upload it to a keyserver.
|
||||
|
||||
gpg set up with your key is helpful for the release process on all environments
|
||||
where a binary is built, but you can also make the detached signature files
|
||||
yourself at the end of the process.
|
||||
Make sure to install GnuPG on all environments where you will be making commits
|
||||
and tags.
|
||||
|
||||
For codesigning windows binaries, put your certificate into
|
||||
`~/.codesign/windows_comodo.pkcs12`.
|
||||
#### Certificates
|
||||
|
||||
On Mac the 'Developer ID Application' certificate stored in your login keychain
|
||||
is used, `keychain unlock` will prompt you for your login keychain password, to
|
||||
avoid that set the `LOGIN_KEYCHAIN_PASSWORD` environment variable to your
|
||||
password.
|
||||
Make sure you have set up a Windows code signing certificate with the right
|
||||
password and a Mac 'Developer ID Application' certificate.
|
||||
|
||||
Put the Windows certificate into `~/.codesign/windows_comodo.pkcs12` as a PKCS12
|
||||
file that is password protected, and put the password for it into
|
||||
`~/.codesign/windows_comodo.pkcs12.password`.
|
||||
|
||||
#### Release Commit and Tag
|
||||
|
||||
@@ -280,8 +226,10 @@ tag:
|
||||
mkdir build && cd build
|
||||
cmake .. -DTAG_RELEASE=TRUE
|
||||
```
|
||||
, follow the instructions to edit the `CHANGELOG.md` and then push the release:
|
||||
|
||||
then push the release:
|
||||
To reiterate, **make sure you edit the `CHANGELOG.md`** to remove any
|
||||
non-user-facing changes before you make the release commit.
|
||||
|
||||
```bash
|
||||
git push
|
||||
@@ -296,84 +244,126 @@ cmake .. -DTAG_RELEASE=UNDO
|
||||
|
||||
#### 64-bit Windows Binary
|
||||
|
||||
For this you will preferably need the powershell environment setup described
|
||||
earlier, however you can use a regular Visual Studio 64 bit native developer
|
||||
command prompt as well.
|
||||
For this you will preferably need the PowerShell environment setup described
|
||||
[here](https://github.com/rkitover/windows-dev-guide), or by starting the `x64
|
||||
Native Tools Command Prompt` from your Start Menu.
|
||||
|
||||
```powershell
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -DVCPKG_TARGET_TRIPLET=x64-windows-static -DCMAKE_BUILD_TYPE=Release -DUPSTREAM_RELEASE=TRUE -G Ninja
|
||||
mkdir build-msvc64
|
||||
cd build-msvc64
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Release -DUPSTREAM_RELEASE=TRUE -G Ninja
|
||||
ninja
|
||||
```
|
||||
|
||||
Collect the following files for the release:
|
||||
|
||||
- `visualboyadvance-m-Win-64bit.zip`
|
||||
- `visualboyadvance-m-Win-64bit.zip.asc`
|
||||
- `visualboyadvance-m-Win-x86_64.zip`
|
||||
- `translations.zip`
|
||||
- `translations.zip.asc`
|
||||
|
||||
Repeat the process for the debug build, with `-DCMAKE_BUILD_TYPE=Debug` and
|
||||
collect this file:
|
||||
|
||||
- `visualboyadvance-m-Win-x86_64-debug.zip`
|
||||
.
|
||||
|
||||
#### 32-bit Windows Binary
|
||||
|
||||
For this the optimal environment is a linux distribution with the mingw
|
||||
toolchain, I use fedora.
|
||||
The 32-bit build is a legacy build for Windows XP compatibility. You will need
|
||||
the MinGW toolchain to build it. The easiest method is to use the MINGW32 MSYS2
|
||||
environment.
|
||||
|
||||
You can set up a shell on a fedora distribution with docker as described here:
|
||||
Make sure the Visual Studio `signtool.exe` is in your path, you can start MSYS2
|
||||
with an inherited `PATH` from a Visual Studio enabled environment or add it to
|
||||
your shell configuration.
|
||||
|
||||
https://gist.github.com/rkitover/6379764c619c10e829e4b2fa0ae243fd
|
||||
|
||||
If using fedora, the cross script will install all necessary dependencies, if
|
||||
not install the base toolchain (mingw gcc, binutils, winpthreads) using the
|
||||
preferred method for your distribution, you can also use mxe for this.
|
||||
|
||||
https://mxe.cc/
|
||||
First install dependencies with:
|
||||
|
||||
```bash
|
||||
sh tools/win/linux-cross-builder -32
|
||||
./installdeps
|
||||
```
|
||||
|
||||
You can also use msys2 on Windows, this is not recommended:
|
||||
. Then build the 32-bit binary as follows:
|
||||
|
||||
```bash
|
||||
sh tools/win/msys2-builder -32
|
||||
mkdir build-mingw32
|
||||
cd build-mingw32
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Release -DUPSTREAM_RELEASE=TRUE -G Ninja
|
||||
ninja
|
||||
```
|
||||
. Collect this file for the release:
|
||||
|
||||
To set up msys2, see this guide:
|
||||
- `visualboyadvance-m-Win-x86_32.zip`
|
||||
|
||||
https://gist.github.com/rkitover/d008324309044fc0cc742bdb16064454
|
||||
. Then repeat the process for the debug build with `-DCMAKE_BUILD_TYPE=Debug`,
|
||||
and collect this file:
|
||||
|
||||
Collect the following files from `~/vbam-build-mingw32/project` if using linux,
|
||||
or `~/vbam-build-msys2-x86_64/project` if using msys2:
|
||||
- `visualboyadvance-m-Win-x86_32-debug.zip`
|
||||
.
|
||||
|
||||
- `visualboyadvance-m-Win-32bit.zip`
|
||||
- `visualboyadvance-m-Win-32bit.zip.asc`
|
||||
#### ARM64 Windows Binary
|
||||
|
||||
#### 64-bit Mac Binary
|
||||
You will need the MSVC ARM64 cross toolchain to build this binary, if you used
|
||||
the install script from [here](https://github.com/rkitover/windows-dev-guide)
|
||||
you will have it installed, otherwise run Visual Studio Installer and install
|
||||
the component.
|
||||
|
||||
To enter the ARM64 cross environment, edit the PowerShell profile described
|
||||
[here](https://github.com/rkitover/windows-dev-guide) or use the `vcvarsall.bat`
|
||||
script with the `amd64_arm64` argument as described
|
||||
[here](https://learn.microsoft.com/en-us/cpp/build/building-on-the-command-line?view=msvc-170).
|
||||
|
||||
From there the process is the same as for the 64-bit build, collect the
|
||||
following files for the release:
|
||||
|
||||
- `visualboyadvance-m-Win-arm64.zip`
|
||||
- 'visualboyadvance-m-Win-arm64-debug.zip'
|
||||
.
|
||||
|
||||
#### macOS Binary
|
||||
|
||||
Install the latest Xcode for your OS.
|
||||
|
||||
You will need bash and (optionally) gpg from homebrew (which you will also need
|
||||
to install):
|
||||
|
||||
```bash
|
||||
brew install bash gnupg
|
||||
```
|
||||
You will need bash from Homebrew/nix/MacPorts/whatever to run the build script.
|
||||
|
||||
You will need a codesigning certificate from Apple, which you will be able to
|
||||
generate once you join their developer program. This is the certificate of the
|
||||
type 'Developer ID Application' stored in your login keychain. `keychain
|
||||
unlock` will prompt you for your login keychain password, to avoid that set the
|
||||
`LOGIN_KEYCHAIN_PASSWORD` environment variable to your password.
|
||||
generate once you join their developer program from XCode. This is the
|
||||
certificate of the type 'Developer ID Application' stored in your login
|
||||
keychain.
|
||||
|
||||
If you are not using a GUI session, you will need to use a method to unlock your
|
||||
login keychain before building so that your codesigning certificate can be used.
|
||||
Adding the certificate and key to the System keychain is also a method that some
|
||||
people use.
|
||||
|
||||
To unlock your keychain on login, you can add something like this to your
|
||||
`~/.zshrc`:
|
||||
|
||||
```bash
|
||||
/usr/local/bin/bash tools/osx/builder -64
|
||||
security unlock-keychain -p "$(cat ~/.login-keychain-password)" login.keychain
|
||||
```
|
||||
, with your login password in that file.
|
||||
|
||||
For notarization to work, you will need to create an app-specific password on
|
||||
https://appleid.apple.com , get your Team ID from your Apple Developer account,
|
||||
and store them with this command:
|
||||
|
||||
```bash
|
||||
xcrun notarytool store-credentials AC_PASSWORD \
|
||||
--apple-id you@domain.com \
|
||||
--team-id <DeveloperTeamID> \
|
||||
--password <secret_app_specific_2FA_password>
|
||||
```
|
||||
. Once all of this is set up, run:
|
||||
|
||||
```bash
|
||||
tools/osx/builder
|
||||
```
|
||||
, this will take a while because it builds all of the dependencies.
|
||||
|
||||
Collect the following files from `~/vbam-build-mac-64bit/project`:
|
||||
|
||||
- `visualboyadvance-m-Mac-64bit.zip`
|
||||
- `visualboyadvance-m-Mac-64bit.zip.asc`
|
||||
- `visualboyadvance-m-Mac-x86_64.zip`
|
||||
- `visualboyadvance-m-Mac-x86_64-debug.zip`
|
||||
.
|
||||
|
||||
#### Final steps
|
||||
|
||||
@@ -381,27 +371,26 @@ Go to the github releases tab, and make a release for the tag you pushed
|
||||
earlier.
|
||||
|
||||
Put any notes to users and distro maintainers into the description as well as
|
||||
the entries from `CHANGELOG.md` generated earlier from git by the release
|
||||
commit script.
|
||||
the generated entries from `CHANGELOG.md` you edited earlier.
|
||||
|
||||
Upload all files collected during the earlier builds, the complete list is:
|
||||
|
||||
|
||||
- `translations.zip`
|
||||
- `translations.zip.asc`
|
||||
- `visualboyadvance-m-Mac-64bit.zip`
|
||||
- `visualboyadvance-m-Mac-64bit.zip.asc`
|
||||
- `visualboyadvance-m-Win-32bit.zip`
|
||||
- `visualboyadvance-m-Win-32bit.zip.asc`
|
||||
- `visualboyadvance-m-Win-64bit.zip`
|
||||
- `visualboyadvance-m-Win-64bit.zip.asc`
|
||||
- `visualboyadvance-m-Win-x86_64.zip`
|
||||
- `visualboyadvance-m-Win-x86_64-debug.zip`
|
||||
- `visualboyadvance-m-Win-x86_32.zip`
|
||||
- `visualboyadvance-m-Win-x86_32-debug.zip`
|
||||
- `visualboyadvance-m-Win-arm64.zip`
|
||||
- 'visualboyadvance-m-Win-arm64-debug.zip'
|
||||
- `visualboyadvance-m-Mac-x86_64.zip`
|
||||
- `visualboyadvance-m-Mac-x86_64-debug.zip`
|
||||
|
||||
Update the winsparkle appcast.xml by running this cmake command:
|
||||
Update the winsparkle `appcast.xml` by running this cmake command:
|
||||
|
||||
```bash
|
||||
cmake .. -DUPDATE_APPCAST=TRUE
|
||||
```
|
||||
|
||||
follow the instructions to push the change to the web data repo.
|
||||
, follow the instructions to push the change to the web data repo.
|
||||
|
||||
Announce the release on reddit r/emulation and the forum.
|
||||
|
172
README.md
172
README.md
@@ -19,8 +19,6 @@
|
||||
|
||||
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
|
||||
|
||||
[](https://gitter.im/visualboyadvance-m/Lobby)
|
||||
|
||||
Our bridged Discord server is [Here](https://discord.gg/EpfxEuGMKH).
|
||||
|
||||
We are also on *`#vba-m`* on [Libera IRC](https://libera.chat/) which has a [Web
|
||||
@@ -59,35 +57,39 @@ Factory Reset`.
|
||||
|
||||
## System Requirements
|
||||
|
||||
Windows 7, 8.1 or 10/11, Linux distro's or macOS.
|
||||
Windows XP, Vista, 7, 8.1 or 10/11, Linux distros or macOS.
|
||||
|
||||
2Ghz x86 (or x86-64) Intel Core 2 or AMD Athlon processor with SSE, Snapdragon 835
|
||||
or newer CPU compatible with Arm for Windows.
|
||||
|
||||
2Ghz x86(or x86-64) Intel Core 2 or AMD Athlon processor with SSE, Snapdragon 835
|
||||
or newer cpu compatible with Arm for Windows.
|
||||
- Just a guideline, lower clock speeds and Celeron processors may be able to run at full
|
||||
speed on lower settings, and Linux based ARM Operating systems have wider cpu support.
|
||||
speed on lower settings, and Linux based ARM Operating systems have wider CPU support.
|
||||
|
||||
DirectX June 2010 Redist [Full](https://www.microsoft.com/en-au/download/details.aspx?id=8109) / [Websetup](https://www.microsoft.com/en-au/download/details.aspx?id=35) for Xaudio (Remember to uncheck Bing on the websetup)
|
||||
DirectX June 2010 Redist
|
||||
[Full](https://www.microsoft.com/en-au/download/details.aspx?id=8109) /
|
||||
[Websetup](https://www.microsoft.com/en-au/download/details.aspx?id=35) for
|
||||
Xaudio (Remember to uncheck Bing on the websetup.)
|
||||
|
||||
## Building
|
||||
|
||||
The basic formula to build vba-m is:
|
||||
|
||||
```shell
|
||||
```bash
|
||||
cd ~ && mkdir src && cd src
|
||||
git clone https://github.com/visualboyadvance-m/visualboyadvance-m.git
|
||||
cd visualboyadvance-m
|
||||
./installdeps
|
||||
|
||||
# ./installdeps will give you build instructions, which will be similar to:
|
||||
./installdeps # On Linux or macOS
|
||||
|
||||
mkdir build && cd build
|
||||
cmake .. -G Ninja
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Release -G Ninja
|
||||
ninja
|
||||
```
|
||||
|
||||
`./installdeps` is supported on MSys2, Linux (Debian/Ubuntu, Fedora, Arch,
|
||||
Solus, OpenSUSE, Gentoo and RHEL/CentOS) and Mac OS X (homebrew, macports or
|
||||
fink.)
|
||||
`./installdeps` is supported on MSYS2, Linux (Debian/Ubuntu, Fedora, Arch,
|
||||
Solus, OpenSUSE, Gentoo and RHEL/CentOS) and Mac OS X (homebrew, MacPorts or
|
||||
Fink.)
|
||||
|
||||
## Building a Libretro core
|
||||
|
||||
@@ -98,7 +100,7 @@ cd src/libretro
|
||||
make -j`nproc`
|
||||
```
|
||||
|
||||
Copy vbam_libretro.so to your RetroArch cores directory.
|
||||
Copy `vbam_libretro.so` to your RetroArch cores directory.
|
||||
|
||||
## Visual Studio Support
|
||||
|
||||
@@ -118,14 +120,16 @@ environment loaded.
|
||||
Using your own user-wide installation of vcpkg is supported, just make sure the
|
||||
environment variable `VCPKG_ROOT` is set.
|
||||
|
||||
To build in the visual studio command prompt, use something like this:
|
||||
To build in the Visual Studio `x64 Native Tools Command Prompt`, use something
|
||||
like this:
|
||||
|
||||
```
|
||||
mkdir build
|
||||
cd build
|
||||
cmake .. -DVCPKG_TARGET_TRIPLET=x64-windows-static -DCMAKE_BUILD_TYPE=Debug -G Ninja
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Release -G Ninja
|
||||
ninja
|
||||
```
|
||||
.
|
||||
|
||||
## Visual Studio Code Support
|
||||
|
||||
@@ -163,7 +167,7 @@ And the following development libraries:
|
||||
- [gettext](https://www.gnu.org/software/gettext/) and gettext-tools
|
||||
- [SDL2](https://www.libsdl.org/) (required)
|
||||
- [SFML](https://www.sfml-dev.org/) (optional, for link)
|
||||
- [OpenAL](https://www.openal.org/) or [openal-soft](https://kcat.strangesoft.net/openal.html) (required, a sound interface)
|
||||
- [openal-soft](https://kcat.strangesoft.net/openal.html) (required, a sound interface)
|
||||
- [wxWidgets](https://wxwidgets.org/) (required for GUI, 2.8 and non-stl builds are no longer supported)
|
||||
|
||||
On Linux and similar, you also need the version of GTK your wxWidgets is linked
|
||||
@@ -183,61 +187,47 @@ This is supported on Fedora, Arch, Solus and MSYS2.
|
||||
may be `win32` which is an alias for `mingw-w64-i686` to target 32 bit Windows,
|
||||
or `mingw-w64-x86_64` for 64 bit Windows targets.
|
||||
|
||||
The target is implicit on MSys2 depending on which MINGW shell you started (the
|
||||
The target is implicit on MSYS2 depending on which MINGW shell you started (the
|
||||
value of `$MSYSTEM`.)
|
||||
|
||||
On Debian/Ubuntu this uses the MXE apt repository and works quite well.
|
||||
|
||||
On Fedora it can build using the Fedora MinGW packages, albeit with wx 2.8, no
|
||||
OpenGL support, and no Link support for lack of SFML.
|
||||
|
||||
On Arch it currently doesn't work at all because the AUR stuff is completely
|
||||
broken, I will at some point redo the arch stuff to use MXE as well.
|
||||
|
||||
## CMake Options
|
||||
|
||||
The CMake code tries to guess reasonable defaults for options, but you can
|
||||
override them, for example:
|
||||
|
||||
```shell
|
||||
cmake .. -DENABLE_LINK=NO -G Ninja
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Release -DENABLE_LINK=NO -G Ninja
|
||||
```
|
||||
|
||||
Of particular interest is making **Release** or **Debug** builds, the default
|
||||
mode is **Release**, to make a **Debug** build use something like:
|
||||
|
||||
```shell
|
||||
cmake .. -DCMAKE_BUILD_TYPE=Debug -G Ninja
|
||||
```
|
||||
|
||||
Here is the complete list:
|
||||
. Here is the complete list:
|
||||
|
||||
| **CMake Option** | **What it Does** | **Defaults** |
|
||||
|-----------------------|----------------------------------------------------------------------|-----------------------|
|
||||
| ENABLE_SDL | Build the SDL port | OFF |
|
||||
| ENABLE_WX | Build the wxWidgets port | ON |
|
||||
| ENABLE_DEBUGGER | Enable the debugger | ON |
|
||||
| ENABLE_ASM_CORE | Enable x86 ASM CPU cores (**BUGGY AND DANGEROUS**) | OFF |
|
||||
| ENABLE_ASM | Enable the following two ASM options | ON for 32 bit builds |
|
||||
| ENABLE_ASM_SCALERS | Enable x86 ASM graphic filters | ON for 32 bit builds |
|
||||
| ENABLE_MMX | Enable MMX | ON for 32 bit builds |
|
||||
| ENABLE_LINK | Enable GBA linking functionality (requires SFML) | AUTO |
|
||||
| ENABLE_LIRC | Enable LIRC support | OFF |
|
||||
| ENABLE_FFMPEG | Enable ffmpeg A/V recording | AUTO |
|
||||
| ENABLE_ONLINEUPDATES | Enable online update checks | ON |
|
||||
| ENABLE_LTO | Compile with Link Time Optimization (gcc and clang only) | ON for release build |
|
||||
| ENABLE_GBA_LOGGING | Enable extended GBA logging | ON |
|
||||
| ENABLE_DIRECT3D | Direct3D rendering for wxWidgets (Windows, **NOT IMPLEMENTED!!!**) | ON |
|
||||
| ENABLE_XAUDIO2 | Enable xaudio2 sound output for wxWidgets (Windows only) | ON |
|
||||
| ENABLE_ASAN | Enable libasan sanitizers (by default address, only in debug mode) | OFF |
|
||||
| UPSTREAM_RELEASE | Do some release tasks, like codesigning, making zip and gpg sigs. | OFF |
|
||||
| BUILD_TESTING | Build the tests and enable ctest support. | ON |
|
||||
| VBAM_STATIC | Try link all libs statically (the following are set to ON if ON) | OFF |
|
||||
| SDL2_STATIC | Try to link static SDL2 libraries | OFF |
|
||||
| SFML_STATIC_LIBRARIES | Try to link static SFML libraries | OFF |
|
||||
| FFMPEG_STATIC | Try to link static ffmpeg libraries | OFF |
|
||||
| OPENAL_STATIC | Try to link static OpenAL libraries | OFF |
|
||||
| TRANSLATIONS_ONLY | Build only the translations.zip and nothing else | OFF |
|
||||
| `ENABLE_SDL` | Build the SDL port | OFF |
|
||||
| `ENABLE_WX` | Build the wxWidgets port | ON |
|
||||
| `ENABLE_DEBUGGER` | Enable the debugger | ON |
|
||||
| `ENABLE_ASM_CORE` | Enable x86 ASM CPU cores (**BUGGY AND DANGEROUS**) | OFF |
|
||||
| `ENABLE_ASM` | Enable the following two ASM options | ON for 32 bit builds |
|
||||
| `ENABLE_ASM_SCALERS` | Enable x86 ASM graphic filters | ON for 32 bit builds |
|
||||
| `ENABLE_MMX` | Enable MMX | ON for 32 bit builds |
|
||||
| `ENABLE_LINK` | Enable GBA linking functionality (requires SFML) | AUTO |
|
||||
| `ENABLE_LIRC` | Enable LIRC support | OFF |
|
||||
| `ENABLE_FFMPEG` | Enable ffmpeg A/V recording | AUTO |
|
||||
| `ENABLE_ONLINEUPDATES` | Enable online update checks | ON |
|
||||
| `ENABLE_LTO` | Compile with Link Time Optimization (gcc and clang only) | ON for release build |
|
||||
| `ENABLE_GBA_LOGGING` | Enable extended GBA logging | ON |
|
||||
| `ENABLE_XAUDIO2` | Enable xaudio2 sound output for wxWidgets (Windows only) | ON |
|
||||
| `ENABLE_FAUDIO` | Enable faudio sound output for wxWidgets, | ON, not 32 bit Win |
|
||||
| `ENABLE_ASAN` | Enable libasan sanitizers (by default address, only in debug mode) | OFF |
|
||||
| `UPSTREAM_RELEASE` | Do some release tasks, like codesigning, making zip and gpg sigs. | OFF |
|
||||
| `BUILD_TESTING` | Build the tests and enable ctest support. | ON |
|
||||
| `VBAM_STATIC` | Try link all libs statically (the following are set to ON if ON) | OFF |
|
||||
| `SDL2_STATIC` | Try to link static SDL2 libraries | OFF |
|
||||
| `SFML_STATIC_LIBRARIES` | Try to link static SFML libraries | OFF |
|
||||
| `FFMPEG_STATIC` | Try to link static ffmpeg libraries | OFF |
|
||||
| `OPENAL_STATIC` | Try to link static OpenAL libraries | OFF |
|
||||
| `TRANSLATIONS_ONLY` | Build only the translations.zip and nothing else | OFF |
|
||||
|
||||
Note for distro packagers, we use the CMake module
|
||||
[GNUInstallDirs](https://cmake.org/cmake/help/v2.8.12/cmake.html#module:GNUInstallDirs)
|
||||
@@ -247,52 +237,6 @@ On Unix to use a different version of wxWidgets, set
|
||||
`wxWidgets_CONFIG_EXECUTABLE` to the path to the `wx-config` script you want to
|
||||
use.
|
||||
|
||||
## MSys2 Notes
|
||||
|
||||
To run the resulting binary, you can simply type:
|
||||
|
||||
```shell
|
||||
./visualboyadvance-m
|
||||
```
|
||||
|
||||
in the shell where you built it.
|
||||
|
||||
If you built with `-DCMAKE_BUILD_TYPE=Debug`, you will get a console app and
|
||||
will see debug messages, even in mintty.
|
||||
|
||||
If you want to start the binary from e.g. a shortcut or Explorer, you will need
|
||||
to put `c:\msys64\mingw32\bin` for 32 bit builds and `c:\msys64\mingw64\bin`
|
||||
for 64 bit builds in your PATH (to edit system PATH, go to Control Panel ->
|
||||
System -> Advanced system settings -> Environment Variables.)
|
||||
|
||||
If you want to package the binary, you will need to include the MinGW DLLs it
|
||||
depends on, they can install to the same directory as the binary.
|
||||
|
||||
Our own builds are static.
|
||||
|
||||
## Debug Messages
|
||||
|
||||
We have an override for `wxLogDebug()` to make it work even in non-debug builds
|
||||
of wx and on windows, even in mintty.
|
||||
|
||||
It works like `printf()`, e.g.:
|
||||
|
||||
```cpp
|
||||
int foo = 42;
|
||||
wxLogDebug(wxT("the value of foo = %d"), foo);
|
||||
```
|
||||
|
||||
From the core etc. the usual:
|
||||
|
||||
```cpp
|
||||
fprintf(stderr, "...", ...);
|
||||
```
|
||||
|
||||
will work fine.
|
||||
|
||||
You need a debug build for this to work or to even have a console on Windows.
|
||||
Pass `-DCMAKE_BUILD_TYPE=Debug` to cmake.
|
||||
|
||||
## Reporting Crash Bugs
|
||||
|
||||
If the emulator crashes and you wish to report the bug, a backtrace made with
|
||||
@@ -311,27 +255,25 @@ do something such as:
|
||||
```shell
|
||||
ulimit -c unlimited
|
||||
```
|
||||
|
||||
in your shell to enable coredump files.
|
||||
, in your shell to enable core files.
|
||||
|
||||
[This
|
||||
post](https://ask.fedoraproject.org/en/question/98776/where-is-core-dump-located/?answer=98779#post-id-98779)
|
||||
explains how to retrieve core dump on Fedora Linux (and possibly other
|
||||
distributions.)
|
||||
explains how to retrieve core dump on some distributions, when they are managed
|
||||
by systemd.
|
||||
|
||||
Once you have the core dump file, open it with `gdb`, for example:
|
||||
Once you have the core file, open it with `gdb`, for example:
|
||||
|
||||
```shell
|
||||
gdb -c core ./visualboyadvance-m
|
||||
```
|
||||
|
||||
In the `gdb` shell, to print the backtrace, type:
|
||||
. In the `gdb` shell, to start the process and print the backtrace, type:
|
||||
|
||||
```
|
||||
run
|
||||
bt
|
||||
```
|
||||
|
||||
This may be a bit of a hassle, but it helps us out immensely.
|
||||
. This may be a bit of a hassle, but it helps us out immensely.
|
||||
|
||||
## Contributing
|
||||
|
||||
|
@@ -56,9 +56,11 @@ if(CMAKE_SYSTEM_PROCESSOR MATCHES "[xX]86|i[3-9]86|[aA][mM][dD]64")
|
||||
endif()
|
||||
elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "[aA][aA][rR][cC][hH]|[aA][rR][mM]")
|
||||
if(CMAKE_C_SIZEOF_DATA_PTR EQUAL 4) # 32 bit
|
||||
set(ARM32 ON)
|
||||
set(ARCH_NAME arm32)
|
||||
set(WINARCH arm)
|
||||
elseif(CMAKE_C_SIZEOF_DATA_PTR EQUAL 8)
|
||||
set(ARM64 ON)
|
||||
set(ARCH_NAME arm64)
|
||||
set(WINARCH arm64)
|
||||
endif()
|
||||
|
@@ -23,7 +23,7 @@ if(CMAKE_TOOLCHAIN_FILE MATCHES "vcpkg")
|
||||
if(VCPKG_TARGET_TRIPLET MATCHES -static)
|
||||
set(arch_suffix -static)
|
||||
endif()
|
||||
if(CMAKE_BUILD_TYPE MATCHES "^(Debug|RelWithDebInfo)$")
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
set(path_prefix debug)
|
||||
endif()
|
||||
set(installed_prefix ${_VCPKG_INSTALLED_DIR}/${WINARCH}-windows${arch_suffix}/${path_prefix})
|
||||
|
@@ -1,110 +0,0 @@
|
||||
#.rst:
|
||||
# FindOpenAL
|
||||
# ----------
|
||||
#
|
||||
#
|
||||
#
|
||||
# Locate OpenAL This module defines OPENAL_LIBRARY OPENAL_FOUND, if
|
||||
# false, do not try to link to OpenAL OPENAL_INCLUDE_DIR, where to find
|
||||
# the headers
|
||||
#
|
||||
# $OPENALDIR is an environment variable that would correspond to the
|
||||
# ./configure --prefix=$OPENALDIR used in building OpenAL.
|
||||
#
|
||||
# Created by Eric Wing. This was influenced by the FindSDL.cmake
|
||||
# module.
|
||||
|
||||
#=============================================================================
|
||||
# Copyright 2005-2009 Kitware, Inc.
|
||||
#
|
||||
# Distributed under the OSI-approved BSD License (the "License");
|
||||
# see accompanying file Copyright.txt for details.
|
||||
#
|
||||
# This software is distributed WITHOUT ANY WARRANTY; without even the
|
||||
# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
||||
# See the License for more information.
|
||||
#=============================================================================
|
||||
# (To distribute this file outside of CMake, substitute the full
|
||||
# License text for the above reference.)
|
||||
|
||||
# This makes the presumption that you are include al.h like
|
||||
# #include "al.h"
|
||||
# and not
|
||||
# #include <AL/al.h>
|
||||
# The reason for this is that the latter is not entirely portable.
|
||||
# Windows/Creative Labs does not by default put their headers in AL/ and
|
||||
# OS X uses the convention <OpenAL/al.h>.
|
||||
#
|
||||
# For Windows, Creative Labs seems to have added a registry key for their
|
||||
# OpenAL 1.1 installer. I have added that key to the list of search paths,
|
||||
# however, the key looks like it could be a little fragile depending on
|
||||
# if they decide to change the 1.00.0000 number for bug fix releases.
|
||||
# Also, they seem to have laid down groundwork for multiple library platforms
|
||||
# which puts the library in an extra subdirectory. Currently there is only
|
||||
# Win32 and I have hardcoded that here. This may need to be adjusted as
|
||||
# platforms are introduced.
|
||||
# The OpenAL 1.0 installer doesn't seem to have a useful key I can use.
|
||||
# I do not know if the Nvidia OpenAL SDK has a registry key.
|
||||
#
|
||||
# For OS X, remember that OpenAL was added by Apple in 10.4 (Tiger).
|
||||
# To support the framework, I originally wrote special framework detection
|
||||
# code in this module which I have now removed with CMake's introduction
|
||||
# of native support for frameworks.
|
||||
# In addition, OpenAL is open source, and it is possible to compile on Panther.
|
||||
# Furthermore, due to bugs in the initial OpenAL release, and the
|
||||
# transition to OpenAL 1.1, it is common to need to override the built-in
|
||||
# framework.
|
||||
# Per my request, CMake should search for frameworks first in
|
||||
# the following order:
|
||||
# ~/Library/Frameworks/OpenAL.framework/Headers
|
||||
# /Library/Frameworks/OpenAL.framework/Headers
|
||||
# /System/Library/Frameworks/OpenAL.framework/Headers
|
||||
#
|
||||
# On OS X, this will prefer the Framework version (if found) over others.
|
||||
# People will have to manually change the cache values of
|
||||
# OPENAL_LIBRARY to override this selection or set the CMake environment
|
||||
# CMAKE_INCLUDE_PATH to modify the search paths.
|
||||
|
||||
find_path(OPENAL_INCLUDE_DIR al.h
|
||||
HINTS
|
||||
ENV OPENALDIR
|
||||
PATH_SUFFIXES AL OpenAL
|
||||
PATHS
|
||||
~/Library/Frameworks
|
||||
/Library/Frameworks
|
||||
/sw # Fink
|
||||
/opt/local # DarwinPorts
|
||||
/opt/csw # Blastwave
|
||||
/opt
|
||||
[HKEY_LOCAL_MACHINE\\SOFTWARE\\Creative\ Labs\\OpenAL\ 1.1\ Software\ Development\ Kit\\1.00.0000;InstallDir]
|
||||
)
|
||||
|
||||
if(CMAKE_SIZEOF_VOID_P EQUAL 8)
|
||||
set(_OpenAL_ARCH_DIR libs/Win64)
|
||||
else()
|
||||
set(_OpenAL_ARCH_DIR libs/Win32)
|
||||
endif()
|
||||
|
||||
find_library(OPENAL_LIBRARY
|
||||
NAMES OpenAL al openal OpenAL32
|
||||
HINTS
|
||||
ENV OPENALDIR
|
||||
PATH_SUFFIXES lib64 lib libs64 libs ${_OpenAL_ARCH_DIR}
|
||||
PATHS
|
||||
~/Library/Frameworks
|
||||
/Library/Frameworks
|
||||
/sw
|
||||
/opt/local
|
||||
/opt/csw
|
||||
/opt
|
||||
[HKEY_LOCAL_MACHINE\\SOFTWARE\\Creative\ Labs\\OpenAL\ 1.1\ Software\ Development\ Kit\\1.00.0000;InstallDir]
|
||||
)
|
||||
|
||||
unset(_OpenAL_ARCH_DIR)
|
||||
|
||||
# handle the QUIETLY and REQUIRED arguments and set OPENAL_FOUND to TRUE if
|
||||
# all listed variables are TRUE
|
||||
include(FindPackageHandleStandardArgs)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS(OpenAL DEFAULT_MSG OPENAL_LIBRARY OPENAL_INCLUDE_DIR)
|
||||
|
||||
mark_as_advanced(OPENAL_LIBRARY OPENAL_INCLUDE_DIR)
|
@@ -10,10 +10,6 @@ if(NOT EXISTS "${CMAKE_SOURCE_DIR}/.git")
|
||||
message(FATAL_ERROR "releases can only be done from a git clone")
|
||||
endif()
|
||||
|
||||
if(NOT GIT_FOUND)
|
||||
message(FATAL_ERROR "git is required to make a release")
|
||||
endif()
|
||||
|
||||
find_program(GPG_EXECUTABLE gpg)
|
||||
|
||||
if(NOT GPG_EXECUTABLE)
|
||||
@@ -35,7 +31,7 @@ function(make_release_commit_and_tag)
|
||||
# First make sure we are on master.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} rev-parse --short --abbrev-ref=strict HEAD
|
||||
COMMAND git rev-parse --short --abbrev-ref=strict HEAD
|
||||
OUTPUT_VARIABLE git_branch
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
@@ -46,7 +42,7 @@ function(make_release_commit_and_tag)
|
||||
endif()
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} status --porcelain=2
|
||||
COMMAND git status --porcelain=2
|
||||
OUTPUT_VARIABLE git_status
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
@@ -59,7 +55,7 @@ function(make_release_commit_and_tag)
|
||||
endif()
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} tag --sort=-v:refname
|
||||
COMMAND git tag --sort=-v:refname
|
||||
OUTPUT_VARIABLE git_tags
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
@@ -80,7 +76,7 @@ function(make_release_commit_and_tag)
|
||||
endif()
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} log ${git_last_tag}.. "--pretty=format:* %h - %s [%aL]"
|
||||
COMMAND git log ${git_last_tag}.. "--pretty=format:* %h - %s [%aL]"
|
||||
OUTPUT_VARIABLE release_log
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
@@ -90,17 +86,17 @@ function(make_release_commit_and_tag)
|
||||
|
||||
if(TAG_RELEASE STREQUAL UNDO)
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} tag -d ${git_last_tag}
|
||||
COMMAND git tag -d ${git_last_tag}
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} reset HEAD~1
|
||||
COMMAND git reset HEAD~1
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} checkout HEAD CHANGELOG.md
|
||||
COMMAND git checkout HEAD CHANGELOG.md
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
|
||||
@@ -212,45 +208,37 @@ Ignore the following cmake error.
|
||||
)
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} add CHANGELOG.md
|
||||
COMMAND git add CHANGELOG.md
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
|
||||
# Make the release commit.
|
||||
message(FATAL_ERROR "
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} commit -m "release ${new_tag}" --signoff -S
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
Release prepared.
|
||||
|
||||
# Make release tag.
|
||||
Edit CHANGELOG.md to remove any non-user-facing commits, and optionally add any
|
||||
release notes.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} tag -s -m${new_tag} ${new_tag}
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
)
|
||||
Run the following commands to commit the change:
|
||||
|
||||
message(FATAL_ERROR [=[
|
||||
|
||||
Release commit and tag generated.
|
||||
|
||||
**** IF YOU ARE SURE YOU WANT TO RELEASE ****
|
||||
|
||||
Run the following commands to push the release commit and tag:
|
||||
|
||||
git push
|
||||
git push --tags
|
||||
|
||||
**** TO UNDO THE RELEASE ****
|
||||
git commit -m'release ${new_tag}' --signoff -S
|
||||
git tag -s -m'${new_tag}' ${new_tag}
|
||||
|
||||
To rollback these changes, run this command:
|
||||
|
||||
cmake .. -DTAG_RELEASE=UNDO
|
||||
|
||||
Ignore the "configuration incomplete" message following, this mode does not
|
||||
==== IF YOU ARE SURE YOU WANT TO RELEASE, THIS **CANNOT** BE REVERSED ====
|
||||
|
||||
Run the following to push the release commit and tag:
|
||||
|
||||
git push
|
||||
git push --tags
|
||||
|
||||
Ignore the 'configuration incomplete' message following, this mode does not
|
||||
build anything.
|
||||
|
||||
]=])
|
||||
")
|
||||
endfunction()
|
||||
|
||||
make_release_commit_and_tag()
|
||||
|
@@ -72,26 +72,24 @@ if(TRANSLATIONS_ONLY)
|
||||
set(ENABLE_LINK_DEFAULT OFF)
|
||||
else()
|
||||
find_package(SFML 2.4 COMPONENTS network system)
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "RelWithDebInfo")
|
||||
if(SFML_STATIC_LIBRARIES AND SFML_NETWORK_LIBRARY_STATIC_DEBUG AND SFML_SYSTEM_LIBRARY_STATIC_DEBUG)
|
||||
set(SFML_LIBRARIES ${SFML_NETWORK_LIBRARY_STATIC_DEBUG} ${SFML_SYSTEM_LIBRARY_STATIC_DEBUG})
|
||||
elseif(SFML_NETWORK_LIBRARY_DYNAMIC_DEBUG AND SFML_SYSTEM_LIBRARY_DYNAMIC_DEBUG)
|
||||
set(SFML_LIBRARIES ${SFML_NETWORK_LIBRARY_DYNAMIC_DEBUG} ${SFML_SYSTEM_LIBRARY_DYNAMIC_DEBUG})
|
||||
endif()
|
||||
endif()
|
||||
set(ENABLE_LINK_DEFAULT OFF)
|
||||
if(SFML_FOUND)
|
||||
set(ENABLE_LINK_DEFAULT ON)
|
||||
endif()
|
||||
endif()
|
||||
option(ENABLE_LINK "Enable GBA linking functionality" ${ENABLE_LINK_DEFAULT})
|
||||
option(ENABLE_LINK "Enable GBA linking functionality (BROKEN)" ${ENABLE_LINK_DEFAULT})
|
||||
|
||||
if(ENABLE_LINK)
|
||||
# Always disable link for now as SFML 2 is broken and we don't have a replacement yet.
|
||||
set(ENABLE_LINK OFF CACHE BOOL "Enable GBA linking functionality (BROKEN)" FORCE)
|
||||
endif()
|
||||
|
||||
# FFMpeg
|
||||
set(FFMPEG_DEFAULT OFF)
|
||||
set(FFMPEG_COMPONENTS AVCODEC AVFORMAT SWSCALE AVUTIL SWRESAMPLE)
|
||||
set(FFMPEG_COMPONENT_VERSIONS AVCODEC>=58.18.100 AVFORMAT>=58.12.100 SWSCALE>=5.1.100 AVUTIL>=56.14.100 SWRESAMPLE>=3.1.100)
|
||||
|
||||
if(NOT TRANSLATIONS_ONLY AND NOT DEFINED ENABLE_FFMPEG OR ENABLE_FFMPEG)
|
||||
if(NOT TRANSLATIONS_ONLY AND (NOT DEFINED ENABLE_FFMPEG OR ENABLE_FFMPEG) AND (NOT (X86 AND MINGW)))
|
||||
set(FFMPEG_DEFAULT ON)
|
||||
|
||||
find_package(FFmpeg COMPONENTS ${FFMPEG_COMPONENTS})
|
||||
|
@@ -10,19 +10,28 @@ if(NOT DEFINED VCPKG_TARGET_TRIPLET)
|
||||
# Check if we are in an MSVC environment.
|
||||
find_program(cl_exe_path NAME cl.exe HINTS ENV PATH)
|
||||
|
||||
if($ENV{CXX} MATCHES "cl.exe$" OR cl_exe_path)
|
||||
if(ENV{CXX} MATCHES "cl.exe$" OR cl_exe_path)
|
||||
# Infer the architecture from the LIB folders.
|
||||
foreach(LIB $ENV{LIB})
|
||||
if(${LIB} MATCHES "x64$")
|
||||
foreach(lib $ENV{LIB})
|
||||
if(lib MATCHES "x64$")
|
||||
set(VBAM_VCPKG_PLATFORM "x64-windows-static")
|
||||
break()
|
||||
endif()
|
||||
if(${LIB} MATCHES "x86$")
|
||||
if(lib MATCHES "x86$")
|
||||
set(VBAM_VCPKG_PLATFORM "x86-windows-static")
|
||||
break()
|
||||
endif()
|
||||
if(${LIB} MATCHES "ARM64$")
|
||||
if(lib MATCHES "ARM64$")
|
||||
set(VBAM_VCPKG_PLATFORM "arm64-windows-static")
|
||||
|
||||
foreach(path $ENV{PATH})
|
||||
if(path MATCHES "[Hh]ost[Xx]64")
|
||||
set(VCPKG_HOST_TRIPLET "x64-windows-static" CACHE STRING "Vcpkg host triplet" FORCE)
|
||||
set(VCPKG_USE_HOST_TOOLS ON CACHE BOOL "Use vcpkg host tools" FORCE)
|
||||
break()
|
||||
endif()
|
||||
endforeach()
|
||||
|
||||
break()
|
||||
endif()
|
||||
endforeach()
|
||||
@@ -51,6 +60,28 @@ if(NOT DEFINED VCPKG_TARGET_TRIPLET)
|
||||
message(STATUS "Inferred VCPKG_TARGET_TRIPLET=${VCPKG_TARGET_TRIPLET}")
|
||||
endif()
|
||||
|
||||
function(vcpkg_seconds)
|
||||
if(CMAKE_HOST_SYSTEM MATCHES Windows OR ((NOT DEFINED CMAKE_HOST_SYSTEM) AND WIN32))
|
||||
execute_process(
|
||||
COMMAND cmd /c echo %TIME:~0,8%
|
||||
OUTPUT_VARIABLE time
|
||||
)
|
||||
else()
|
||||
execute_process(
|
||||
COMMAND date +%H:%M:%S
|
||||
OUTPUT_VARIABLE time
|
||||
)
|
||||
endif()
|
||||
|
||||
string(SUBSTRING "${time}" 0 2 hours)
|
||||
string(SUBSTRING "${time}" 3 2 minutes)
|
||||
string(SUBSTRING "${time}" 6 2 secs)
|
||||
|
||||
math(EXPR seconds "(${hours} * 60 * 60) + (${minutes} * 60) + ${secs}")
|
||||
|
||||
set(seconds ${seconds} PARENT_SCOPE)
|
||||
endfunction()
|
||||
|
||||
function(vcpkg_check_git_status git_status)
|
||||
# The VS vcpkg component cannot be written to without elevation.
|
||||
if(NOT git_status EQUAL 0 AND NOT VCPKG_ROOT MATCHES "Visual Studio")
|
||||
@@ -545,14 +576,4 @@ endfunction()
|
||||
|
||||
vcpkg_set_toolchain()
|
||||
|
||||
# Make vcpkg use debug libs for RelWithDebInfo
|
||||
set(orig_build_type ${CMAKE_BUILD_TYPE})
|
||||
|
||||
if(CMAKE_BUILD_TYPE STREQUAL RelWithDebInfo)
|
||||
set(CMAKE_BUILD_TYPE Debug)
|
||||
endif()
|
||||
|
||||
include(${VCPKG_ROOT}/scripts/buildsystems/vcpkg.cmake)
|
||||
|
||||
set(CMAKE_BUILD_TYPE ${orig_build_type})
|
||||
unset(orig_build_type)
|
||||
|
@@ -7,8 +7,10 @@ if(UPSTREAM_RELEASE)
|
||||
# Require and optimize for Core2 level support, tune for generic.
|
||||
add_compile_options(-march=core2 -mtune=generic)
|
||||
elseif(X86_32)
|
||||
# Optimize for pentium-mmx and tune for generic for older builds.
|
||||
add_compile_options(-march=pentium-mmx -mtune=generic)
|
||||
# Optimize for pentiumi3 and tune for generic for Windows XP builds.
|
||||
set(WINXP TRUE)
|
||||
add_compile_options(-march=pentium3 -mtune=generic)
|
||||
add_compile_definitions(-DWINXP)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
@@ -46,7 +48,7 @@ if(NOT ENABLE_ASM) # inline asm is not allowed with -fPIC
|
||||
endif()
|
||||
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
add_compile_options(-ggdb3 -Og -fno-omit-frame-pointer -Wall -Wextra)
|
||||
add_compile_options(-ggdb3 -fno-omit-frame-pointer -Wall -Wextra)
|
||||
else()
|
||||
add_compile_options(-Ofast -fomit-frame-pointer)
|
||||
endif()
|
||||
|
@@ -3,8 +3,8 @@ if (NOT MINGW)
|
||||
endif()
|
||||
|
||||
# this has to run after the toolchain is initialized.
|
||||
include_directories("${CMAKE_SOURCE_DIR}/dependencies/mingw-include")
|
||||
include_directories("${CMAKE_SOURCE_DIR}/dependencies/mingw-xaudio/include")
|
||||
include_directories("${CMAKE_SOURCE_DIR}/win32-deps/mingw-include")
|
||||
include_directories("${CMAKE_SOURCE_DIR}/win32-deps/mingw-xaudio/include")
|
||||
|
||||
# Add Winsock as the last library linked because of broken link precedence.
|
||||
set(CMAKE_CXX_LINK_EXECUTABLE "${CMAKE_CXX_LINK_EXECUTABLE} -lws2_32")
|
||||
|
@@ -10,7 +10,7 @@ if(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
include_directories("${CMAKE_SOURCE_DIR}/dependencies/msvc")
|
||||
include_directories("${CMAKE_SOURCE_DIR}/win32-deps/msvc")
|
||||
|
||||
add_compile_definitions(
|
||||
_FORCENAMELESSUNION
|
||||
|
@@ -16,7 +16,7 @@ Ignore the following cmake error.
|
||||
# Get last tag.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} tag --sort=-v:refname
|
||||
COMMAND git tag --sort=-v:refname
|
||||
OUTPUT_VARIABLE git_tags
|
||||
OUTPUT_STRIP_TRAILING_WHITESPACE
|
||||
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
|
||||
@@ -43,7 +43,7 @@ Ignore the following cmake error.
|
||||
# Clone repo.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} clone git@github.com:visualboyadvance-m/visualboyadvance-m.github.io web-data
|
||||
COMMAND git clone git@github.com:visualboyadvance-m/visualboyadvance-m.github.io web-data
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
|
||||
)
|
||||
|
||||
@@ -103,21 +103,21 @@ Ignore the following cmake error.
|
||||
)
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} add appcast.xml
|
||||
COMMAND git add appcast.xml
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/web-data
|
||||
)
|
||||
|
||||
# Commit the change.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} commit -m "release ${new_tag}" --signoff -S
|
||||
COMMAND git commit -m "release ${new_tag}" --signoff -S
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/web-data
|
||||
)
|
||||
|
||||
# Make release tag.
|
||||
|
||||
execute_process(
|
||||
COMMAND ${GIT_EXECUTABLE} tag -s -m${new_tag} ${new_tag}
|
||||
COMMAND git tag -s -m${new_tag} ${new_tag}
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/web-data
|
||||
)
|
||||
|
||||
|
@@ -2,7 +2,7 @@ with import <nixpkgs> {};
|
||||
stdenv.mkDerivation {
|
||||
name = "visualboyadvance-m";
|
||||
buildInputs = if stdenv.isDarwin then
|
||||
[ ninja cmake gcc nasm faudio gettext libintl pkg-config zip sfml zlib openal ffmpeg wxGTK32 SDL2 pcre pcre2 darwin.apple_sdk.frameworks.System darwin.apple_sdk.frameworks.IOKit darwin.apple_sdk.frameworks.Carbon darwin.apple_sdk.frameworks.Cocoa darwin.apple_sdk.frameworks.QuartzCore darwin.apple_sdk.frameworks.AudioToolbox darwin.apple_sdk.frameworks.OpenGL darwin.apple_sdk.frameworks.OpenAL llvmPackages_latest.clang llvmPackages_latest.bintools ]
|
||||
[ ninja cmake nasm faudio gettext libintl pkg-config zip zlib openal ffmpeg wxGTK32 SDL2 pcre pcre2 darwin.apple_sdk.frameworks.System darwin.apple_sdk.frameworks.IOKit darwin.apple_sdk.frameworks.Carbon darwin.apple_sdk.frameworks.Cocoa darwin.apple_sdk.frameworks.QuartzCore darwin.apple_sdk.frameworks.AudioToolbox darwin.apple_sdk.frameworks.OpenGL darwin.apple_sdk.frameworks.OpenAL llvmPackages_latest.clang llvmPackages_latest.bintools ]
|
||||
else
|
||||
[ ninja cmake gcc nasm faudio gettext libintl pkg-config zip sfml zlib openal ffmpeg wxGTK32 libGL libGLU glfw SDL2 gtk3-x11 pcre pcre2 util-linuxMinimal libselinux libsepol libthai libdatrie xorg.libXdmcp xorg.libXtst libxkbcommon epoxy dbus at-spi2-core ];
|
||||
[ ninja cmake gcc clang llvm llvmPackages.libcxx nasm faudio gettext libintl pkg-config zip zlib openal ffmpeg wxGTK32 libGL libGLU glfw SDL2 gtk3-x11 pcre pcre2 util-linuxMinimal libselinux libsepol libthai libdatrie xorg.libXdmcp xorg.libXtst libxkbcommon libepoxy dbus at-spi2-core ];
|
||||
}
|
||||
|
Submodule dependencies deleted from e8ce758a98
11
installdeps
11
installdeps
@@ -799,12 +799,10 @@ suse_installdeps() {
|
||||
|
||||
tools="make cmake ccache nasm gettext-tools pkg-config ccache zip sfml2-devel ninja"
|
||||
|
||||
libs="gcc gcc-c++ libSDL2-devel wxWidgets-3_0-devel openal-soft-devel" # ffmpeg-devel
|
||||
|
||||
# ffmpeg requires packman repos
|
||||
libs="gcc gcc-c++ libSDL2-devel wxGTK3-3_2-devel openal-soft-devel ffmpeg-7-libavcodec-devel ffmpeg-7-libavdevice-devel ffmpeg-7-libavfilter-devel ffmpeg-7-libavformat-devel ffmpeg-7-libavutil-devel ffmpeg-7-libpostproc-devel ffmpeg-7-libswresample-devel ffmpeg-7-libswscale-devel"
|
||||
|
||||
if [ "$target" = m32 ]; then
|
||||
libs=$(echo "$libs" | sed -E 's/([^ ]) ([^ ])/\1-32bit \2/g; s/$/-32bit/;')
|
||||
error '32 bit cross builds are no longer supported on OpenSUSE'
|
||||
fi
|
||||
|
||||
check sudo zypper in -y $tools $libs
|
||||
@@ -1118,9 +1116,12 @@ windows_installdeps() {
|
||||
*i686*)
|
||||
pkgs="$pkgs nasm"
|
||||
;;
|
||||
*)
|
||||
pkgs="$pkgs FAudio"
|
||||
;;
|
||||
esac
|
||||
|
||||
pkgs="$pkgs SDL2 sfml FAudio wxWidgets3.2 zlib binutils cmake crt-git headers-git make pkgconf tools-git windows-default-manifest libmangle-git ninja gdb ccache openal"
|
||||
pkgs="$pkgs SDL2 sfml wxWidgets3.2 zlib binutils cmake crt-git headers-git make pkgconf tools-git windows-default-manifest libmangle-git ninja gdb ccache openal"
|
||||
|
||||
case "$target" in
|
||||
*x86_64)
|
||||
|
641
po/wxvbam/bg.po
641
po/wxvbam/bg.po
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/br.po
641
po/wxvbam/br.po
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/cs.po
641
po/wxvbam/cs.po
File diff suppressed because it is too large
Load Diff
994
po/wxvbam/de.po
994
po/wxvbam/de.po
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/el.po
641
po/wxvbam/el.po
File diff suppressed because it is too large
Load Diff
670
po/wxvbam/es.po
670
po/wxvbam/es.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/gl.po
641
po/wxvbam/gl.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
776
po/wxvbam/id.po
776
po/wxvbam/id.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/ja.po
641
po/wxvbam/ja.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
1167
po/wxvbam/ko_KR.po
1167
po/wxvbam/ko_KR.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/nb.po
641
po/wxvbam/nb.po
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/nl.po
641
po/wxvbam/nl.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
738
po/wxvbam/sv.po
738
po/wxvbam/sv.po
File diff suppressed because it is too large
Load Diff
641
po/wxvbam/tr.po
641
po/wxvbam/tr.po
File diff suppressed because it is too large
Load Diff
621
po/wxvbam/uk.po
621
po/wxvbam/uk.po
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,5 +1,13 @@
|
||||
add_library(vbam-components-filters OBJECT)
|
||||
|
||||
unset(extra_src)
|
||||
if(WINXP)
|
||||
list(APPEND extra_src
|
||||
${CMAKE_SOURCE_DIR}/third_party/quake3-sqrt/quake3-sqrt.h
|
||||
)
|
||||
target_include_directories(vbam-components-filters PRIVATE ${CMAKE_SOURCE_DIR}/third_party/quake3-sqrt)
|
||||
endif()
|
||||
|
||||
target_sources(vbam-components-filters
|
||||
PRIVATE
|
||||
internal/2xSaI.cpp
|
||||
@@ -17,6 +25,7 @@ target_sources(vbam-components-filters
|
||||
internal/xBRZ/xbrz_config.h
|
||||
internal/xBRZ/xbrz_tools.h
|
||||
internal/xbrzfilter.cpp
|
||||
${extra_src}
|
||||
|
||||
PUBLIC
|
||||
filters.h
|
||||
|
@@ -21,6 +21,10 @@
|
||||
#include <cmath> //std::sqrt
|
||||
#include "xbrz_tools.h"
|
||||
|
||||
#ifdef WINXP
|
||||
#include "quake3-sqrt.h"
|
||||
#endif
|
||||
|
||||
// some gcc versions lie about having this C++17 feature
|
||||
#define static_assert(x) static_assert(x, "assertion failed")
|
||||
|
||||
@@ -66,7 +70,9 @@ uint32_t gradientARGB(uint32_t pixFront, uint32_t pixBack) //find intermediate c
|
||||
|
||||
inline double fastSqrt(double n)
|
||||
{
|
||||
#if (defined(__GNUC__) || defined(__clang__)) && (defined(__x86_64__) || defined(__i386__))
|
||||
#ifdef WINXP
|
||||
return quake3_sqrt((float)n);
|
||||
#elif (defined(__GNUC__) || defined(__clang__)) && (defined(__x86_64__) || defined(__i386__))
|
||||
__asm__ ("fsqrt" : "+t" (n));
|
||||
return n;
|
||||
#elif defined(_MSC_VER) && defined(_M_IX86)
|
||||
|
@@ -60,3 +60,5 @@ target_link_libraries(vbam-core-base
|
||||
PRIVATE vbam-fex stb-image
|
||||
PUBLIC ${ZLIB_LIBRARY}
|
||||
)
|
||||
|
||||
add_subdirectory(test)
|
||||
|
@@ -17,7 +17,7 @@
|
||||
#define VBAM_IMMEDIATE_CRASH_DETAIL() __builtin_trap()
|
||||
#define VBAM_INTRINSIC_UNREACHABLE_DETAIL() __builtin_unreachable()
|
||||
|
||||
#elif defined(_MSC_VER) // defined(__GNUC__) || defined(__clang__)
|
||||
#elif defined(_MSC_VER) // defined(__GNUC__) || defined(__clang__)
|
||||
|
||||
// MSVC.
|
||||
#define VBAM_IMMEDIATE_CRASH_DETAIL() __debugbreak()
|
||||
@@ -33,29 +33,25 @@
|
||||
#define VBAM_STRINGIFY(x) VBAM_STRINGIFY_DETAIL(x)
|
||||
|
||||
#define VBAM_REQUIRE_SEMICOLON_DETAIL() \
|
||||
static_assert(true, "Require a semicolon after macros invocation.")
|
||||
static_assert(true, "Require a semicolon after macros invocation.")
|
||||
|
||||
#define VBAM_CHECK(condition) \
|
||||
if (!(condition)) { \
|
||||
fputs("CHECK failed at " __FILE__ ":" VBAM_STRINGIFY(__LINE__) ": " #condition "\n", stderr); \
|
||||
VBAM_IMMEDIATE_CRASH_DETAIL(); \
|
||||
} \
|
||||
VBAM_REQUIRE_SEMICOLON_DETAIL()
|
||||
|
||||
#define VBAM_NOTREACHED_MESSAGE_DETAIL() \
|
||||
fputs("NOTREACHED code reached at " __FILE__ ":" VBAM_STRINGIFY(__LINE__) "\n", stderr)
|
||||
#define VBAM_CHECK(condition) \
|
||||
if (!(condition)) { \
|
||||
fputs("CHECK failed at " __FILE__ ":" VBAM_STRINGIFY(__LINE__) ": " #condition "\n", \
|
||||
stderr); \
|
||||
VBAM_IMMEDIATE_CRASH_DETAIL(); \
|
||||
} \
|
||||
VBAM_REQUIRE_SEMICOLON_DETAIL()
|
||||
|
||||
#if defined(DEBUG)
|
||||
|
||||
#define VBAM_NOTREACHED() \
|
||||
VBAM_NOTREACHED_MESSAGE_DETAIL(); \
|
||||
VBAM_IMMEDIATE_CRASH_DETAIL()
|
||||
#define VBAM_NOTREACHED() \
|
||||
fputs("NOTREACHED code reached at " __FILE__ ":" VBAM_STRINGIFY(__LINE__) "\n", stderr); \
|
||||
VBAM_IMMEDIATE_CRASH_DETAIL()
|
||||
|
||||
#else // defined(DEBUG)
|
||||
|
||||
#define VBAM_NOTREACHED() \
|
||||
VBAM_NOTREACHED_MESSAGE_DETAIL(); \
|
||||
VBAM_INTRINSIC_UNREACHABLE_DETAIL()
|
||||
#define VBAM_NOTREACHED() VBAM_INTRINSIC_UNREACHABLE_DETAIL()
|
||||
|
||||
#endif // defined(DEBUG)
|
||||
|
||||
|
@@ -59,6 +59,7 @@ extern struct CoreOptions {
|
||||
bool speedHack = false;
|
||||
bool speedup = false;
|
||||
bool speedup_throttle_frame_skip = false;
|
||||
bool speedup_mute = true;
|
||||
int cheatsEnabled = 1;
|
||||
int cpuDisableSfx = 0;
|
||||
int cpuSaveType = 0;
|
||||
@@ -69,7 +70,7 @@ extern struct CoreOptions {
|
||||
int skipSaveGameBattery = 1;
|
||||
int skipSaveGameCheats = 0;
|
||||
int useBios = 0;
|
||||
int winGbPrinterEnabled = 1;
|
||||
int gbPrinterEnabled = 0;
|
||||
uint32_t speedup_throttle = 100;
|
||||
uint32_t speedup_frame_skip = 9;
|
||||
uint32_t throttle = 100;
|
||||
@@ -125,4 +126,4 @@ extern int systemSpeed;
|
||||
#define SYSTEM_SAVE_UPDATED 30
|
||||
#define SYSTEM_SAVE_NOT_UPDATED 0
|
||||
|
||||
#endif // VBAM_CORE_BASE_SYSTEM_H_
|
||||
#endif // VBAM_CORE_BASE_SYSTEM_H_
|
||||
|
12
src/core/base/test/CMakeLists.txt
Normal file
12
src/core/base/test/CMakeLists.txt
Normal file
@@ -0,0 +1,12 @@
|
||||
# This defines the `vbam-core-base-test` library.
|
||||
|
||||
if(NOT BUILD_TESTING)
|
||||
return()
|
||||
endif()
|
||||
|
||||
add_library(vbam-core-base-test
|
||||
INTERFACE
|
||||
notreached.h)
|
||||
|
||||
target_link_libraries(vbam-core-base-test
|
||||
INTERFACE GTest::gtest)
|
22
src/core/base/test/notreached.h
Normal file
22
src/core/base/test/notreached.h
Normal file
@@ -0,0 +1,22 @@
|
||||
#ifndef VBAM_CORE_BASE_TEST_NOTREACHED_H_
|
||||
#define VBAM_CORE_BASE_TEST_NOTREACHED_H_
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#if defined(DEBUG)
|
||||
|
||||
#define VBAM_EXPECT_NOTREACHED(statement) EXPECT_DEATH(statement, "NOTREACHED")
|
||||
|
||||
#else // defined(DEBUG)
|
||||
|
||||
// There is no way to test this in release builds as the compiler might optimize
|
||||
// this code path away. Eat the statement to avoid unused variable warnings.
|
||||
#define VBAM_EXPECT_NOTREACHED(statement) \
|
||||
if constexpr (false) { \
|
||||
statement; \
|
||||
} \
|
||||
static_assert(true, "")
|
||||
|
||||
#endif // defined(DEBUG)
|
||||
|
||||
#endif // VBAM_CORE_BASE_TEST_NOTREACHED_H_
|
@@ -1416,7 +1416,7 @@ void gbWriteMemory(uint16_t address, uint8_t value)
|
||||
EmuReseted = false;
|
||||
gbMemory[0xff02] = value;
|
||||
if (gbSerialOn && (GetLinkMode() == LINK_GAMEBOY_IPC || GetLinkMode() == LINK_GAMEBOY_SOCKET
|
||||
|| GetLinkMode() == LINK_DISCONNECTED || coreOptions.winGbPrinterEnabled)) {
|
||||
|| GetLinkMode() == LINK_DISCONNECTED || coreOptions.gbPrinterEnabled)) {
|
||||
|
||||
gbSerialTicks = GBSERIAL_CLOCK_TICKS;
|
||||
|
||||
@@ -2969,8 +2969,13 @@ void gbReset()
|
||||
inBios = true;
|
||||
} else if (gbHardware & 0xa) {
|
||||
// Set compatibility mode if it is a DMG ROM.
|
||||
const uint8_t gbcFlag = g_gbCartData.SupportsCGB() ? 0x80 : 0x00;
|
||||
gbMemory[0xff6c] = 0xfe | gbcFlag;
|
||||
if (g_gbCartData.SupportsCGB()) {
|
||||
// OPRI with bit 0 set to 0 = CGB mode.
|
||||
gbMemory[0xff6c] = 0xfe;
|
||||
} else {
|
||||
// OPRI with bit 0 set to 1 = DMG mode.
|
||||
gbMemory[0xff6c] = 0xff;
|
||||
}
|
||||
}
|
||||
|
||||
gbLine99Ticks = 1;
|
||||
|
@@ -3845,6 +3845,8 @@ void CPULoop(int ticks)
|
||||
bool turbo_button_pressed = (joy >> 10) & 1;
|
||||
#ifndef __LIBRETRO__
|
||||
static uint32_t last_throttle;
|
||||
static bool current_volume_saved = false;
|
||||
static float current_volume;
|
||||
|
||||
if (turbo_button_pressed) {
|
||||
if (coreOptions.speedup_frame_skip)
|
||||
@@ -3859,10 +3861,23 @@ void CPULoop(int ticks)
|
||||
if (coreOptions.speedup_throttle_frame_skip)
|
||||
framesToSkip += static_cast<int>(std::ceil(double(coreOptions.speedup_throttle) / 100.0) - 1);
|
||||
}
|
||||
|
||||
if (coreOptions.speedup_mute && !current_volume_saved) {
|
||||
current_volume = soundGetVolume();
|
||||
current_volume_saved = true;
|
||||
soundSetVolume(0);
|
||||
}
|
||||
}
|
||||
else if (speedup_throttle_set) {
|
||||
soundSetThrottle(DowncastU16(last_throttle));
|
||||
speedup_throttle_set = false;
|
||||
else {
|
||||
if (current_volume_saved) {
|
||||
soundSetVolume(current_volume);
|
||||
current_volume_saved = false;
|
||||
}
|
||||
|
||||
if (speedup_throttle_set) {
|
||||
soundSetThrottle(DowncastU16(last_throttle));
|
||||
speedup_throttle_set = false;
|
||||
}
|
||||
}
|
||||
#else
|
||||
if (turbo_button_pressed)
|
||||
|
@@ -1822,6 +1822,16 @@ static INSN_REGPARM void thumbE0(uint32_t opcode)
|
||||
busPrefetchCount = 0;
|
||||
}
|
||||
|
||||
static INSN_REGPARM void thumbE8(uint32_t opcode)
|
||||
{
|
||||
#ifdef GBA_LOGGING
|
||||
// TODO: This is (erroneously) used by some Wii U VC ROMs. We should have a configuration
|
||||
// toggle to enable the correct hardware behavior, which would be to call CPUUndefinedException.
|
||||
if (systemVerbose & VERBOSE_UNDEFINED)
|
||||
log("Undefined Wii U THUMB instruction %04x at %08x (ignored)\n", opcode, armNextPC - 2);
|
||||
#endif
|
||||
}
|
||||
|
||||
// BLL #offset (forward)
|
||||
static INSN_REGPARM void thumbF0(uint32_t opcode)
|
||||
{
|
||||
@@ -1979,7 +1989,7 @@ static insnfunc_t thumbInsnTable[1024] = {
|
||||
thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0,
|
||||
thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0,
|
||||
thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0, thumbE0,
|
||||
thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, // E8
|
||||
thumbE8, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, // E8
|
||||
thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI,
|
||||
thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI,
|
||||
thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI, thumbUI,
|
||||
|
4
src/gb-over.ini
Normal file
4
src/gb-over.ini
Normal file
@@ -0,0 +1,4 @@
|
||||
# Game Boy Overrrides
|
||||
|
||||
[ALLEY WAY]
|
||||
gbPrinter = 0
|
@@ -590,7 +590,7 @@ void retro_init(void)
|
||||
coreOptions.parseDebug = true;
|
||||
coreOptions.cheatsEnabled = 0;
|
||||
coreOptions.skipSaveGameBattery = 0;
|
||||
coreOptions.winGbPrinterEnabled = 0;
|
||||
coreOptions.gbPrinterEnabled = 0;
|
||||
|
||||
struct retro_log_callback log;
|
||||
struct retro_rumble_interface rumble;
|
||||
|
@@ -31,8 +31,8 @@ if(MSVC)
|
||||
# We should probably use an external library for this.
|
||||
target_sources(vbam
|
||||
PRIVATE
|
||||
${CMAKE_SOURCE_DIR}/dependencies/msvc/getopt.c
|
||||
${CMAKE_SOURCE_DIR}/dependencies/msvc/getopt.h
|
||||
${CMAKE_SOURCE_DIR}/win32-deps/msvc/getopt.c
|
||||
${CMAKE_SOURCE_DIR}/win32-deps/msvc/getopt.h
|
||||
)
|
||||
endif()
|
||||
|
||||
@@ -61,7 +61,7 @@ endif()
|
||||
|
||||
if(ENABLE_LIRC)
|
||||
target_link_libraries(vbam lirc_client)
|
||||
target_compile_definitions(vbam VBAM_ENABLE_LIRC)
|
||||
target_compile_definitions(vbam PUBLIC VBAM_ENABLE_LIRC)
|
||||
endif()
|
||||
|
||||
if(WIN32)
|
||||
@@ -71,15 +71,15 @@ endif()
|
||||
# Installation scripts.
|
||||
install(
|
||||
PROGRAMS ${PROJECT_BINARY_DIR}/vbam${CMAKE_EXECUTABLE_SUFFIX}
|
||||
DESTINATION ${CMAKE_INSTALL_FULL_BINDIR}
|
||||
DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
)
|
||||
install(
|
||||
FILES ${CMAKE_CURRENT_LIST_DIR}/vbam.cfg-example
|
||||
DESTINATION ${CMAKE_INSTALL_FULL_SYSCONFDIR}
|
||||
DESTINATION ${CMAKE_INSTALL_SYSCONFDIR}
|
||||
RENAME vbam.cfg
|
||||
)
|
||||
|
||||
if(UNIX)
|
||||
# man pages.
|
||||
install(FILES ${CMAKE_SOURCE_DIR}/src/debian/vbam.6 DESTINATION ${CMAKE_INSTALL_FULL_MANDIR}/man6)
|
||||
install(FILES ${CMAKE_SOURCE_DIR}/src/debian/vbam.6 DESTINATION ${CMAKE_INSTALL_MANDIR}/man6)
|
||||
endif()
|
||||
|
@@ -98,7 +98,8 @@ enum named_opts
|
||||
OPT_SOUND_FILTERING,
|
||||
OPT_SPEEDUP_THROTTLE,
|
||||
OPT_SPEEDUP_FRAME_SKIP,
|
||||
OPT_NO_SPEEDUP_THROTTLE_FRAME_SKIP
|
||||
OPT_NO_SPEEDUP_THROTTLE_FRAME_SKIP,
|
||||
OPT_NO_SPEEDUP_MUTE
|
||||
};
|
||||
|
||||
#define SOUND_MAX_VOLUME 2.0
|
||||
@@ -188,7 +189,7 @@ struct option argOptions[] = {
|
||||
{ "gb-emulator-type", required_argument, 0, OPT_GB_EMULATOR_TYPE },
|
||||
{ "gb-frame-skip", required_argument, 0, OPT_GB_FRAME_SKIP },
|
||||
{ "gb-palette-option", required_argument, 0, OPT_GB_PALETTE_OPTION },
|
||||
{ "gb-printer", no_argument, &coreOptions.winGbPrinterEnabled, 1 },
|
||||
{ "gb-printer", no_argument, &coreOptions.gbPrinterEnabled, 1 },
|
||||
{ "gdb", required_argument, 0, 'G' },
|
||||
{ "help", no_argument, &optPrintUsage, 1 },
|
||||
{ "ifb-filter", required_argument, 0, 'I' },
|
||||
@@ -232,9 +233,10 @@ struct option argOptions[] = {
|
||||
{ "speedup-throttle", required_argument, 0, OPT_SPEEDUP_THROTTLE },
|
||||
{ "speedup-frame-skip", required_argument, 0, OPT_SPEEDUP_FRAME_SKIP },
|
||||
{ "no-speedup-throttle-frame-skip", no_argument, 0, OPT_NO_SPEEDUP_THROTTLE_FRAME_SKIP },
|
||||
{ "no-speedup-mute", no_argument, 0, OPT_NO_SPEEDUP_MUTE },
|
||||
{ "use-bios", no_argument, &coreOptions.useBios, 1 },
|
||||
{ "verbose", required_argument, 0, 'v' },
|
||||
{ "win-gb-printer-enabled", no_argument, &coreOptions.winGbPrinterEnabled, 1 },
|
||||
{ "win-gb-printer-enabled", no_argument, &coreOptions.gbPrinterEnabled, 1 },
|
||||
|
||||
|
||||
{ NULL, no_argument, NULL, 0 }
|
||||
@@ -347,8 +349,9 @@ void LoadConfig()
|
||||
coreOptions.speedup_throttle = ReadPref("speedupThrottle", 100);
|
||||
coreOptions.speedup_frame_skip = ReadPref("speedupFrameSkip", 9);
|
||||
coreOptions.speedup_throttle_frame_skip = ReadPref("speedupThrottleFrameSkip", 0);
|
||||
coreOptions.speedup_mute = ReadPref("speedupMute", 1);
|
||||
coreOptions.useBios = ReadPrefHex("useBiosGBA");
|
||||
coreOptions.winGbPrinterEnabled = ReadPref("gbPrinter", 0);
|
||||
coreOptions.gbPrinterEnabled = ReadPref("gbPrinter", 0);
|
||||
|
||||
int soundQuality = (ReadPrefHex("soundQuality", 1));
|
||||
switch (soundQuality) {
|
||||
@@ -990,6 +993,9 @@ int ReadOpts(int argc, char ** argv)
|
||||
case OPT_NO_SPEEDUP_THROTTLE_FRAME_SKIP:
|
||||
coreOptions.speedup_throttle_frame_skip = false;
|
||||
break;
|
||||
case OPT_NO_SPEEDUP_MUTE:
|
||||
coreOptions.speedup_mute = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return op;
|
||||
|
@@ -364,6 +364,10 @@ mirroringEnabled=1
|
||||
saveType=1
|
||||
mirroringEnabled=1
|
||||
|
||||
# Higurashi no Nakukoroni (Japan)
|
||||
[HGRS]
|
||||
saveType=2
|
||||
|
||||
# Koro Koro Puzzle - Happy Panechu! (Japan)
|
||||
[KHPJ]
|
||||
saveType=4
|
||||
|
@@ -31,6 +31,8 @@ set(VBAM_WX_COMMON
|
||||
dialogs/joypad-config.h
|
||||
dialogs/sound-config.cpp
|
||||
dialogs/sound-config.h
|
||||
dialogs/speedup-config.cpp
|
||||
dialogs/speedup-config.h
|
||||
drawing.h
|
||||
extra-translations.cpp
|
||||
gfxviewers.cpp
|
||||
@@ -46,33 +48,6 @@ set(VBAM_WX_COMMON
|
||||
viewsupt.h
|
||||
wayland.cpp
|
||||
wayland.h
|
||||
# from external source with minor modifications
|
||||
widgets/checkedlistctrl.cpp
|
||||
widgets/checkedlistctrl.h
|
||||
widgets/client-data.h
|
||||
widgets/dpi-support.h
|
||||
widgets/event-handler-provider.h
|
||||
widgets/group-check-box.cpp
|
||||
widgets/group-check-box.h
|
||||
widgets/keep-on-top-styler.cpp
|
||||
widgets/keep-on-top-styler.h
|
||||
widgets/option-validator.cpp
|
||||
widgets/option-validator.h
|
||||
widgets/render-plugin.cpp
|
||||
widgets/render-plugin.h
|
||||
widgets/user-input-ctrl.cpp
|
||||
widgets/user-input-ctrl.h
|
||||
widgets/user-input-event.cpp
|
||||
widgets/user-input-event.h
|
||||
widgets/sdl-poller.cpp
|
||||
widgets/sdl-poller.h
|
||||
widgets/shortcut-menu-bar.cpp
|
||||
widgets/shortcut-menu-bar.h
|
||||
widgets/utils.cpp
|
||||
widgets/utils.h
|
||||
widgets/webupdatedef.h
|
||||
widgets/wxmisc.h
|
||||
widgets/wxmisc.cpp
|
||||
wxhead.h
|
||||
wxlogdebug.h
|
||||
wxvbam.cpp
|
||||
@@ -84,6 +59,7 @@ set(VBAM_WX_COMMON
|
||||
${VBAM_GENERATED_DIR}/wx/builtin-over.h
|
||||
${VBAM_GENERATED_DIR}/wx/cmdhandlers.h
|
||||
${VBAM_GENERATED_DIR}/wx/cmd-evtable.h
|
||||
${VBAM_GENERATED_DIR}/wx/gb-builtin-over.h
|
||||
)
|
||||
|
||||
if(NOT ZIP_PROGRAM)
|
||||
@@ -166,7 +142,7 @@ endif()
|
||||
|
||||
# wxWidgets configuration.
|
||||
set(wxWidgets_USE_UNICODE ON)
|
||||
if(CMAKE_BUILD_TYPE MATCHES "^(Debug|RelWithDebInfo)$")
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
set(wxWidgets_USE_DEBUG ON) # noop if wx is compiled with --disable-debug, like in Mac Homebrew atm
|
||||
endif()
|
||||
if(VBAM_STATIC)
|
||||
@@ -187,6 +163,13 @@ if(NOT wxWidgets_FOUND)
|
||||
set(ENABLE_OPENGL FALSE)
|
||||
endif()
|
||||
|
||||
# Fixup wxWidgets paths for vcpkg debug builds.
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug" AND CMAKE_TOOLCHAIN_FILE MATCHES "vcpkg")
|
||||
set(wxWidgets_ROOT_DIR "${wxWidgets_ROOT_DIR}/debug" CACHE INTERNAL "wxWidgets root directory" FORCE)
|
||||
string(REGEX REPLACE "/lib$" "/debug/lib" wxWidgets_LIB_DIR "${wxWidgets_LIB_DIR}")
|
||||
set(wxWidgets_LIB_DIR "${wxWidgets_LIB_DIR}" CACHE INTERNAL "wxWidgets library directory" FORCE)
|
||||
endif()
|
||||
|
||||
# Find OpenAL (required).
|
||||
find_package(OpenAL REQUIRED)
|
||||
|
||||
@@ -253,6 +236,9 @@ function(configure_wx_target target)
|
||||
endif()
|
||||
endfunction()
|
||||
|
||||
# Core emulator.
|
||||
_add_link_libraries(vbam-core)
|
||||
|
||||
# Nonstd.
|
||||
_add_link_libraries(nonstd-lib)
|
||||
_add_include_directories(${NONSTD_INCLUDE_DIR})
|
||||
@@ -262,13 +248,17 @@ function(configure_wx_target target)
|
||||
_add_include_directories(${wxWidgets_INCLUDE_DIRS})
|
||||
_add_compile_options(${wxWidgets_CXX_FLAGS})
|
||||
_add_compile_definitions(${wxWidgets_DEFINITIONS})
|
||||
if(CMAKE_BUILD_TYPE MATCHES "^(Debug|RelWithDebInfo)$")
|
||||
if(CMAKE_BUILD_TYPE STREQUAL "Debug")
|
||||
_add_compile_definitions(${wxWidgets_DEFINITIONS_DEBUG})
|
||||
endif()
|
||||
|
||||
# OpenAL.
|
||||
if(OPENAL_STATIC)
|
||||
_add_compile_definitions(AL_LIBTYPE_STATIC)
|
||||
|
||||
if(WIN32)
|
||||
list(APPEND OPENAL_LIBRARY avrt)
|
||||
endif()
|
||||
endif()
|
||||
_add_include_directories(${OPENAL_INCLUDE_DIR})
|
||||
_add_link_libraries(${OPENAL_LIBRARY})
|
||||
@@ -284,9 +274,15 @@ function(configure_wx_target target)
|
||||
if(MSVC)
|
||||
_add_link_libraries(FAudio::FAudio)
|
||||
else()
|
||||
_add_link_libraries(FAudio)
|
||||
if(WIN32)
|
||||
if(MINGW AND VBAM_STATIC)
|
||||
_add_link_libraries(FAudio.a)
|
||||
else()
|
||||
_add_link_libraries(FAudio)
|
||||
endif()
|
||||
_add_link_libraries(dxguid uuid winmm ole32 advapi32 user32 mfplat mfreadwrite mfuuid propsys)
|
||||
else()
|
||||
_add_link_libraries(FAudio)
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
@@ -311,6 +307,7 @@ endfunction()
|
||||
# Sub-projects.
|
||||
add_subdirectory(test)
|
||||
add_subdirectory(config)
|
||||
add_subdirectory(widgets)
|
||||
|
||||
set(VBAM_ICON visualboyadvance-m.icns)
|
||||
set(VBAM_ICON_PATH ${CMAKE_CURRENT_SOURCE_DIR}/icons/${VBAM_ICON})
|
||||
@@ -326,13 +323,13 @@ target_include_directories(visualboyadvance-m PRIVATE ${SDL2_INCLUDE_DIRS})
|
||||
|
||||
target_link_libraries(
|
||||
visualboyadvance-m
|
||||
vbam-core
|
||||
vbam-components-draw-text
|
||||
vbam-components-filters
|
||||
vbam-components-filters-agb
|
||||
vbam-components-filters-interframe
|
||||
vbam-components-user-config
|
||||
vbam-wx-config
|
||||
vbam-wx-widgets
|
||||
)
|
||||
|
||||
# adjust link command when making a static binary for gcc
|
||||
@@ -401,20 +398,11 @@ if(WIN32)
|
||||
# Disable the auto-generated manifest from CMake.
|
||||
target_link_options(visualboyadvance-m PRIVATE "/MANIFEST:NO")
|
||||
endif()
|
||||
|
||||
# wxWidgets fails to bring in its dependency.
|
||||
find_library(PCRE_LIB pcre2-16 REQUIRED)
|
||||
target_link_libraries(visualboyadvance-m ${PCRE_LIB})
|
||||
endif()
|
||||
|
||||
if(APPLE)
|
||||
target_sources(visualboyadvance-m PRIVATE
|
||||
macsupport.mm
|
||||
widgets/dpi-support-mac.mm
|
||||
)
|
||||
else()
|
||||
target_sources(visualboyadvance-m PRIVATE
|
||||
widgets/dpi-support.cpp
|
||||
)
|
||||
endif()
|
||||
|
||||
@@ -536,7 +524,7 @@ host_compile(${CMAKE_CURRENT_SOURCE_DIR}/bin2c.c ${BIN2C})
|
||||
|
||||
# Override wxrc when cross-compiling.
|
||||
if(CMAKE_HOST_WIN32 AND CMAKE_CROSSCOMPILING)
|
||||
set(WXRC ${CMAKE_SOURCE_DIR}/dependencies/wxrc/wxrc.exe)
|
||||
set(WXRC ${CMAKE_SOURCE_DIR}/win32-deps/wxrc/wxrc.exe)
|
||||
endif()
|
||||
|
||||
# Configure wxrc.
|
||||
@@ -659,6 +647,12 @@ add_custom_command(
|
||||
DEPENDS ${CMAKE_SOURCE_DIR}/src/vba-over.ini ${BIN2C}
|
||||
)
|
||||
|
||||
add_custom_command(
|
||||
OUTPUT ${VBAM_GENERATED_DIR}/wx/gb-builtin-over.h
|
||||
COMMAND ${BIN2C} ${CMAKE_SOURCE_DIR}/src/gb-over.ini ${VBAM_GENERATED_DIR}/wx/gb-builtin-over.h gb_builtin_over
|
||||
DEPENDS ${CMAKE_SOURCE_DIR}/src/gb-over.ini ${BIN2C}
|
||||
)
|
||||
|
||||
set(VBAM_LOCALIZABLE_FILES ${VBAM_WX_COMMON} ${VBAM_LOCALIZABLE_WX_CONFIG_FILES})
|
||||
list(APPEND VBAM_LOCALIZABLE_FILES
|
||||
audio/internal/dsound.cpp
|
||||
@@ -681,9 +675,9 @@ if(APPLE)
|
||||
set(CMAKE_INSTALL_RPATH "@loader_path/../Frameworks")
|
||||
endif()
|
||||
|
||||
if(WIN32 AND (X86_64 OR X86_32) AND ENABLE_ONLINEUPDATES)
|
||||
if(WIN32 AND (X86_64 OR ARM64 OR X86_32) AND ENABLE_ONLINEUPDATES)
|
||||
if(NOT DEFINED WINSPARKLE_BIN_RELEASE_DIR)
|
||||
set(WINSPARKLE_BIN_RELEASE_DIR ${CMAKE_SOURCE_DIR}/dependencies/WinSparkle-0.6.0)
|
||||
set(WINSPARKLE_BIN_RELEASE_DIR ${CMAKE_SOURCE_DIR}/win32-deps/WinSparkle-0.8.1)
|
||||
endif()
|
||||
|
||||
target_include_directories(
|
||||
@@ -692,9 +686,11 @@ if(WIN32 AND (X86_64 OR X86_32) AND ENABLE_ONLINEUPDATES)
|
||||
)
|
||||
|
||||
if(X86_64)
|
||||
set(WINSPARKLE_DLL ${CMAKE_SOURCE_DIR}/dependencies/WinSparkle-0.6.0/x64/Release/WinSparkle.dll)
|
||||
else()
|
||||
set(WINSPARKLE_DLL ${CMAKE_SOURCE_DIR}/dependencies/WinSparkle-0.6.0/Release/WinSparkle.dll)
|
||||
set(WINSPARKLE_DLL ${WINSPARKLE_BIN_RELEASE_DIR}/x64/Release/WinSparkle.dll)
|
||||
elseif(ARM64)
|
||||
set(WINSPARKLE_DLL ${WINSPARKLE_BIN_RELEASE_DIR}/ARM64/Release/WinSparkle.dll)
|
||||
elseif(X86_32)
|
||||
set(WINSPARKLE_DLL ${WINSPARKLE_BIN_RELEASE_DIR}/Release/WinSparkle.dll)
|
||||
endif()
|
||||
|
||||
configure_file(autoupdater/wxmsw/winsparkle-path.h.in ${CMAKE_BINARY_DIR}/winsparkle-path.h)
|
||||
@@ -803,7 +799,7 @@ endif()
|
||||
if(UPSTREAM_RELEASE AND WIN32)
|
||||
set(home "$ENV{HOME}")
|
||||
|
||||
if((MSVC OR NOT CMAKE_CROSSCOMPILING) AND NOT DEFINED ENV{MSYSTEM_PREFIX})
|
||||
if(NOT home OR ((MSVC OR NOT CMAKE_CROSSCOMPILING) AND NOT DEFINED ENV{MSYSTEM_PREFIX}))
|
||||
set(home "$ENV{USERPROFILE}")
|
||||
endif()
|
||||
|
||||
@@ -811,8 +807,9 @@ if(UPSTREAM_RELEASE AND WIN32)
|
||||
string(REGEX REPLACE "\\\\" "/" home "${home}")
|
||||
|
||||
set(cert "${home}/.codesign/windows_comodo.pkcs12")
|
||||
file(STRINGS "${home}/.codesign/windows_comodo.pkcs12.password" cert_password)
|
||||
|
||||
if(EXISTS "${cert}")
|
||||
if(EXISTS "${cert}" AND cert_password)
|
||||
find_program(OSSLSIGNCODE_PROGRAM osslsigncode)
|
||||
find_program(SIGNTOOL_PROGRAM signtool)
|
||||
|
||||
@@ -821,7 +818,7 @@ if(UPSTREAM_RELEASE AND WIN32)
|
||||
TARGET visualboyadvance-m
|
||||
POST_BUILD
|
||||
COMMAND ${CMAKE_COMMAND} -E rename visualboyadvance-m.exe visualboyadvance-m-unsigned.exe
|
||||
COMMAND ${OSSLSIGNCODE_PROGRAM} sign -pkcs12 ${cert} -pass "vbam3!13" -t http://timestamp.digicert.com -n visualboyadvance-m -i https://github.com/visualboyadvance-m/visualboyadvance-m -in visualboyadvance-m-unsigned.exe -out visualboyadvance-m.exe
|
||||
COMMAND ${OSSLSIGNCODE_PROGRAM} sign -pkcs12 ${cert} -pass "${cert_password}" -t http://timestamp.digicert.com -n visualboyadvance-m -i https://github.com/visualboyadvance-m/visualboyadvance-m -in visualboyadvance-m-unsigned.exe -out visualboyadvance-m.exe
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
|
||||
)
|
||||
elseif(SIGNTOOL_PROGRAM)
|
||||
@@ -829,7 +826,7 @@ if(UPSTREAM_RELEASE AND WIN32)
|
||||
TARGET visualboyadvance-m
|
||||
POST_BUILD
|
||||
COMMAND ${CMAKE_COMMAND} -E copy visualboyadvance-m.exe visualboyadvance-m-unsigned.exe
|
||||
COMMAND ${SIGNTOOL_PROGRAM} sign /f ${cert} /fd certHash /td certHash /p "vbam3!13" /tr http://timestamp.digicert.com /du https://github.com/visualboyadvance-m/visualboyadvance-m /a visualboyadvance-m.exe
|
||||
COMMAND ${SIGNTOOL_PROGRAM} sign /f ${cert} /fd certHash /td certHash /p "${cert_password}" /tr http://timestamp.digicert.com /du https://github.com/visualboyadvance-m/visualboyadvance-m /a visualboyadvance-m.exe
|
||||
WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
|
||||
)
|
||||
endif()
|
||||
@@ -1034,13 +1031,13 @@ install(
|
||||
# Installation scripts.
|
||||
install(
|
||||
PROGRAMS ${PROJECT_BINARY_DIR}/visualboyadvance-m${CMAKE_EXECUTABLE_SUFFIX}
|
||||
DESTINATION ${CMAKE_INSTALL_FULL_BINDIR}
|
||||
DESTINATION ${CMAKE_INSTALL_BINDIR}
|
||||
)
|
||||
install(
|
||||
FILES ${CMAKE_SOURCE_DIR}/src/vba-over.ini
|
||||
DESTINATION ${CMAKE_INSTALL_FULL_DATADIR}/vbam
|
||||
DESTINATION ${CMAKE_INSTALL_DATADIR}/vbam
|
||||
)
|
||||
|
||||
if (UNIX)
|
||||
install(FILES ${CMAKE_SOURCE_DIR}/src/debian/visualboyadvance-m.6 DESTINATION ${CMAKE_INSTALL_FULL_MANDIR}/man6)
|
||||
install(FILES ${CMAKE_SOURCE_DIR}/src/debian/visualboyadvance-m.6 DESTINATION ${CMAKE_INSTALL_MANDIR}/man6)
|
||||
endif()
|
||||
|
@@ -20,6 +20,7 @@
|
||||
#include "core/base/system.h"
|
||||
#include "core/gba/gbaGlobals.h"
|
||||
#include "wx/config/option-proxy.h"
|
||||
#include "wx/config/strutils.h"
|
||||
|
||||
namespace audio {
|
||||
namespace internal {
|
||||
@@ -27,7 +28,7 @@ namespace internal {
|
||||
namespace {
|
||||
|
||||
int FAGetDev(FAudio* fa) {
|
||||
const wxString& audio_device = OPTION(kSoundAudioDevice);
|
||||
const wxString audio_device = OPTION(kSoundAudioDevice).Get();
|
||||
if (audio_device.empty()) {
|
||||
// Just use the default device.
|
||||
return 0;
|
||||
@@ -47,7 +48,7 @@ int FAGetDev(FAudio* fa) {
|
||||
if (hr != 0) {
|
||||
continue;
|
||||
}
|
||||
const wxString device_id(reinterpret_cast<wchar_t*>(dd.DeviceID));
|
||||
const wxString device_id = config::utf16_to_utf8(dd.DeviceID);
|
||||
if (audio_device == device_id) {
|
||||
return i;
|
||||
}
|
||||
@@ -119,8 +120,6 @@ public:
|
||||
FAudio_Output();
|
||||
~FAudio_Output();
|
||||
|
||||
void device_change();
|
||||
|
||||
private:
|
||||
void close();
|
||||
|
||||
@@ -193,10 +192,6 @@ void FAudio_Output::close() {
|
||||
}
|
||||
}
|
||||
|
||||
void FAudio_Output::device_change() {
|
||||
device_changed = true;
|
||||
}
|
||||
|
||||
bool FAudio_Output::init(long sampleRate) {
|
||||
if (failed || initialized)
|
||||
return false;
|
||||
@@ -488,8 +483,11 @@ std::vector<AudioDevice> GetFAudioDevices() {
|
||||
}
|
||||
|
||||
std::vector<AudioDevice> devices;
|
||||
#if defined(__WXMSW__)
|
||||
// Add a separate default device on Windows.
|
||||
devices.reserve(dev_count + 1);
|
||||
devices.push_back({_("Default device"), wxEmptyString});
|
||||
#endif
|
||||
|
||||
for (uint32_t i = 0; i < dev_count; i++) {
|
||||
FAudioDeviceDetails dd;
|
||||
@@ -498,9 +496,9 @@ std::vector<AudioDevice> GetFAudioDevices() {
|
||||
continue;
|
||||
}
|
||||
|
||||
const wxString display_name(reinterpret_cast<wchar_t*>(dd.DisplayName));
|
||||
const wxString device_id(reinterpret_cast<wchar_t*>(dd.DeviceID));
|
||||
|
||||
// Convert to UTF-8.
|
||||
const wxString display_name = config::utf16_to_utf8(dd.DisplayName);
|
||||
const wxString device_id = config::utf16_to_utf8(dd.DeviceID);
|
||||
devices.push_back({display_name, device_id});
|
||||
}
|
||||
|
||||
|
@@ -126,7 +126,7 @@ static void toggleBitVar(bool *menuValue, int *globalVar, int mask)
|
||||
EVT_HANDLER(wxID_OPEN, "Open ROM...")
|
||||
{
|
||||
static int open_ft = 0;
|
||||
const wxString& gba_rom_dir = OPTION(kGBAROMDir);
|
||||
const wxString gba_rom_dir = OPTION(kGBAROMDir);
|
||||
|
||||
// FIXME: ignore if non-existent or not a dir
|
||||
wxString pats = _(
|
||||
@@ -158,7 +158,7 @@ EVT_HANDLER(wxID_OPEN, "Open ROM...")
|
||||
EVT_HANDLER(OpenGB, "Open GB...")
|
||||
{
|
||||
static int open_ft = 0;
|
||||
const wxString& gb_rom_dir = OPTION(kGBROMDir);
|
||||
const wxString gb_rom_dir = OPTION(kGBROMDir);
|
||||
|
||||
// FIXME: ignore if non-existent or not a dir
|
||||
wxString pats = _(
|
||||
@@ -185,7 +185,7 @@ EVT_HANDLER(OpenGB, "Open GB...")
|
||||
EVT_HANDLER(OpenGBC, "Open GBC...")
|
||||
{
|
||||
static int open_ft = 0;
|
||||
const wxString& gbc_rom_dir = OPTION(kGBGBCROMDir);
|
||||
const wxString gbc_rom_dir = OPTION(kGBGBCROMDir);
|
||||
|
||||
// FIXME: ignore if non-existent or not a dir
|
||||
wxString pats = _(
|
||||
@@ -1990,7 +1990,7 @@ EVT_HANDLER(GameBoyAdvanceConfigure, "Game Boy Advance options...")
|
||||
XRCCTRL(*dlg, "GameCode", wxControl)
|
||||
->SetLabel(s);
|
||||
cmt = wxString((const char*)&g_rom[0xa0], wxConvLibc, 12);
|
||||
wxFileConfig* cfg = wxGetApp().overrides;
|
||||
wxFileConfig* cfg = wxGetApp().overrides_.get();
|
||||
|
||||
if (cfg->HasGroup(s)) {
|
||||
cfg->SetPath(s);
|
||||
@@ -2024,7 +2024,7 @@ EVT_HANDLER(GameBoyAdvanceConfigure, "Game Boy Advance options...")
|
||||
if (panel->game_type() == IMAGE_GBA) {
|
||||
agbPrintEnable(OPTION(kPrefAgbPrint));
|
||||
wxString s = wxString((const char*)&g_rom[0xac], wxConvLibc, 4);
|
||||
wxFileConfig* cfg = wxGetApp().overrides;
|
||||
wxFileConfig* cfg = wxGetApp().overrides_.get();
|
||||
bool chg;
|
||||
|
||||
if (cfg->HasGroup(s)) {
|
||||
@@ -2219,7 +2219,7 @@ EVT_HANDLER(FAQ, "VBA-M support forum")
|
||||
|
||||
EVT_HANDLER(Translate, "Translations")
|
||||
{
|
||||
wxLaunchDefaultBrowser(wxT("http://www.transifex.com/projects/p/vba-m"));
|
||||
wxLaunchDefaultBrowser(wxT("https://explore.transifex.com/bgk/vba-m/"));
|
||||
}
|
||||
|
||||
// was About
|
||||
@@ -2297,7 +2297,7 @@ EVT_HANDLER(RetainAspect, "Retain aspect ratio when resizing")
|
||||
|
||||
EVT_HANDLER(Printer, "Enable printer emulation")
|
||||
{
|
||||
GetMenuOptionInt("Printer", &coreOptions.winGbPrinterEnabled, 1);
|
||||
GetMenuOptionInt("Printer", &coreOptions.gbPrinterEnabled, 1);
|
||||
#if (defined __WIN32__ || defined _WIN32)
|
||||
#ifndef NO_LINK
|
||||
gbSerialFunction = gbStartLink;
|
||||
@@ -2305,7 +2305,7 @@ EVT_HANDLER(Printer, "Enable printer emulation")
|
||||
gbSerialFunction = NULL;
|
||||
#endif
|
||||
#endif
|
||||
if (coreOptions.winGbPrinterEnabled)
|
||||
if (coreOptions.gbPrinterEnabled)
|
||||
gbSerialFunction = gbPrinterSend;
|
||||
|
||||
update_opts();
|
||||
|
@@ -1,5 +1,5 @@
|
||||
# This defines the vbam-wx-config target and the
|
||||
# `VBAM_LOCALIZABLE_WX_CONFIG_FILES` variable, containing the list of
|
||||
# `VBAM_LOCALIZABLE_WX_CONFIG_FILES` variable, containing the list of
|
||||
# localizable files in the vbam-wx-config target.
|
||||
|
||||
# I don't like duplicating/triplicating code, so I only declare
|
||||
@@ -61,15 +61,9 @@ target_sources(vbam-wx-config
|
||||
user-input.h
|
||||
)
|
||||
|
||||
target_link_libraries(vbam-wx-config
|
||||
PUBLIC
|
||||
nonstd-lib
|
||||
vbam-core
|
||||
)
|
||||
|
||||
configure_wx_target(vbam-wx-config)
|
||||
|
||||
if (BUILD_TESTING)
|
||||
if(BUILD_TESTING)
|
||||
add_executable(vbam-wx-config-tests
|
||||
bindings-test.cpp
|
||||
command-test.cpp
|
||||
@@ -79,10 +73,12 @@ if (BUILD_TESTING)
|
||||
user-input-test.cpp
|
||||
)
|
||||
target_link_libraries(vbam-wx-config-tests
|
||||
vbam-core
|
||||
# Test deps.
|
||||
vbam-core-fake
|
||||
vbam-wx-config
|
||||
vbam-wx-fake-opts
|
||||
|
||||
# Target deps.
|
||||
vbam-wx-config
|
||||
GTest::gtest_main
|
||||
)
|
||||
|
||||
|
@@ -31,7 +31,6 @@ LIST(SORT EVLINES)
|
||||
STRING(REGEX REPLACE ",\n\$" "\n" EVLINES "${EVLINES}")
|
||||
FILE(APPEND "${CMDTAB}" ${EVLINES})
|
||||
FILE(APPEND "${CMDTAB}" "};\n")
|
||||
FILE(APPEND "${CMDTAB}" "const int ncmds = sizeof(cmdtab) / sizeof(cmdtab[0]);\n")
|
||||
|
||||
# cmdhandlers.h contains prototypes for all handlers
|
||||
FILE(WRITE "${EVPROTO}" "// Generated from cmdevents.cpp; do not edit\n")
|
||||
|
@@ -135,7 +135,8 @@ TEST_F(GamepadTest, NonDefaultInput) {
|
||||
const config::KeyboardInput f1(WXK_F1);
|
||||
|
||||
// Assign F1 to "Up".
|
||||
bindings()->AssignInputToCommand(f1, config::GameCommand(config::GameJoy(0), config::GameKey::Up));
|
||||
bindings()->AssignInputToCommand(f1,
|
||||
config::GameCommand(config::GameJoy(0), config::GameKey::Up));
|
||||
|
||||
// Press F1, the up key should be pressed.
|
||||
EXPECT_TRUE(gamepad()->OnInputPressed(f1));
|
||||
|
@@ -312,7 +312,7 @@ std::array<Option, kNbOptions>& Option::All() {
|
||||
Option(OptionID::kPrefFlashSize, &g_owned_opts.flash_size, 0, 1),
|
||||
Option(OptionID::kPrefFrameSkip, &g_owned_opts.frame_skip, -1, 9),
|
||||
Option(OptionID::kPrefGBPaletteOption, &gbPaletteOption, 0, 2),
|
||||
Option(OptionID::kPrefGBPrinter, &coreOptions.winGbPrinterEnabled, 0, 1),
|
||||
Option(OptionID::kPrefGBPrinter, &coreOptions.gbPrinterEnabled, 0, 1),
|
||||
Option(OptionID::kPrefGDBBreakOnLoad, &g_owned_opts.gdb_break_on_load),
|
||||
Option(OptionID::kPrefGDBPort, &gopts.gdb_port, 0, 65535),
|
||||
#ifndef NO_LINK
|
||||
@@ -328,9 +328,10 @@ std::array<Option, kNbOptions>& Option::All() {
|
||||
Option(OptionID::kPrefSkipSaveGameCheats, &coreOptions.skipSaveGameCheats, 0, 1),
|
||||
Option(OptionID::kPrefSkipSaveGameBattery, &coreOptions.skipSaveGameBattery, 0, 1),
|
||||
Option(OptionID::kPrefThrottle, &coreOptions.throttle, 0, 450),
|
||||
Option(OptionID::kPrefSpeedupThrottle, &coreOptions.speedup_throttle, 0, 3000),
|
||||
Option(OptionID::kPrefSpeedupFrameSkip, &coreOptions.speedup_frame_skip, 0, 300),
|
||||
Option(OptionID::kPrefSpeedupThrottle, &coreOptions.speedup_throttle, 0, 450),
|
||||
Option(OptionID::kPrefSpeedupFrameSkip, &coreOptions.speedup_frame_skip, 0, 40),
|
||||
Option(OptionID::kPrefSpeedupThrottleFrameSkip, &coreOptions.speedup_throttle_frame_skip),
|
||||
Option(OptionID::kPrefSpeedupMute, &coreOptions.speedup_mute),
|
||||
Option(OptionID::kPrefUseBiosGB, &g_owned_opts.use_bios_file_gb),
|
||||
Option(OptionID::kPrefUseBiosGBA, &g_owned_opts.use_bios_file_gba),
|
||||
Option(OptionID::kPrefUseBiosGBC, &g_owned_opts.use_bios_file_gbc),
|
||||
@@ -531,6 +532,8 @@ const std::array<OptionData, kNbOptions + 1> kAllOptionsData = {
|
||||
"throttle)")},
|
||||
OptionData{"preferences/speedupThrottleFrameSkip", "",
|
||||
_("Use frame skip for speedup throttle")},
|
||||
OptionData{"preferences/speedupMute", "",
|
||||
_("Mute sound during speedup")},
|
||||
OptionData{"preferences/useBiosGB", "BootRomGB", _("Use the specified BIOS file for Game Boy")},
|
||||
OptionData{"preferences/useBiosGBA", "BootRomEn", _("Use the specified BIOS file")},
|
||||
OptionData{"preferences/useBiosGBC", "BootRomGBC",
|
||||
|
@@ -99,6 +99,7 @@ enum class OptionID {
|
||||
kPrefSpeedupThrottle,
|
||||
kPrefSpeedupFrameSkip,
|
||||
kPrefSpeedupThrottleFrameSkip,
|
||||
kPrefSpeedupMute,
|
||||
kPrefUseBiosGB,
|
||||
kPrefUseBiosGBA,
|
||||
kPrefUseBiosGBC,
|
||||
|
@@ -3,6 +3,8 @@
|
||||
#include "core/base/check.h"
|
||||
#include "wx/config/option.h"
|
||||
|
||||
#include "core/base/check.h"
|
||||
|
||||
namespace config {
|
||||
|
||||
// An Option::Observer that calls a callback when an option has changed.
|
||||
|
@@ -103,6 +103,7 @@ static constexpr std::array<Option::Type, kNbOptions> kOptionsTypes = {
|
||||
/*kPrefSpeedupThrottle*/ Option::Type::kUnsigned,
|
||||
/*kPrefSpeedupFrameSkip*/ Option::Type::kUnsigned,
|
||||
/*kPrefSpeedupThrottleFrameSkip*/ Option::Type::kBool,
|
||||
/*kPrefSpeedupMute*/ Option::Type::kBool,
|
||||
/*kPrefUseBiosGB*/ Option::Type::kBool,
|
||||
/*kPrefUseBiosGBA*/ Option::Type::kBool,
|
||||
/*kPrefUseBiosGBC*/ Option::Type::kBool,
|
||||
@@ -174,11 +175,43 @@ private:
|
||||
Option* option_;
|
||||
};
|
||||
|
||||
template <typename T>
|
||||
class OptionProxyNumeric {
|
||||
public:
|
||||
virtual T Get() const = 0;
|
||||
virtual bool Set(T value) = 0;
|
||||
virtual T Min() const = 0;
|
||||
virtual T Max() const = 0;
|
||||
|
||||
bool operator++() { return *this += 1; }
|
||||
bool operator--() { return *this -= 1; }
|
||||
bool operator++(int) { return *this += 1; }
|
||||
bool operator--(int) { return *this -= 1; }
|
||||
bool operator+=(T value) {
|
||||
const T new_value = Get() + value;
|
||||
if (new_value > Max()) {
|
||||
return Set(Max());
|
||||
} else {
|
||||
return Set(new_value);
|
||||
}
|
||||
}
|
||||
bool operator-=(T value) {
|
||||
const T new_value = Get() - value;
|
||||
if (new_value < Min()) {
|
||||
return Set(Min());
|
||||
} else {
|
||||
return Set(new_value);
|
||||
}
|
||||
}
|
||||
|
||||
operator T() const { return Get(); }
|
||||
};
|
||||
|
||||
template <OptionID ID>
|
||||
class OptionProxy<
|
||||
ID,
|
||||
typename std::enable_if<kOptionsTypes[static_cast<size_t>(ID)] ==
|
||||
Option::Type::kDouble>::type> {
|
||||
Option::Type::kDouble>::type> : public OptionProxyNumeric<double> {
|
||||
public:
|
||||
OptionProxy() : option_(Option::ByID(ID)) {}
|
||||
~OptionProxy() = default;
|
||||
@@ -187,9 +220,7 @@ public:
|
||||
bool Set(double value) { return option_->SetDouble(value); }
|
||||
double Min() const { return option_->GetDoubleMin(); }
|
||||
double Max() const { return option_->GetDoubleMax(); }
|
||||
|
||||
bool operator=(double value) { return Set(value); }
|
||||
operator double() const { return Get(); }
|
||||
|
||||
private:
|
||||
Option* option_;
|
||||
@@ -199,7 +230,7 @@ template <OptionID ID>
|
||||
class OptionProxy<
|
||||
ID,
|
||||
typename std::enable_if<kOptionsTypes[static_cast<size_t>(ID)] ==
|
||||
Option::Type::kInt>::type> {
|
||||
Option::Type::kInt>::type> : public OptionProxyNumeric<int32_t> {
|
||||
public:
|
||||
OptionProxy() : option_(Option::ByID(ID)) {}
|
||||
~OptionProxy() = default;
|
||||
@@ -208,25 +239,7 @@ public:
|
||||
bool Set(int32_t value) { return option_->SetInt(value); }
|
||||
int32_t Min() const { return option_->GetIntMin(); }
|
||||
int32_t Max() const { return option_->GetIntMax(); }
|
||||
|
||||
bool operator=(int32_t value) { return Set(value); }
|
||||
bool operator+=(int32_t value) {
|
||||
const int new_value = Get() + value;
|
||||
if (new_value > Max()) {
|
||||
return Set(Max());
|
||||
} else {
|
||||
return Set(new_value);
|
||||
}
|
||||
}
|
||||
bool operator-=(int32_t value) {
|
||||
const int new_value = Get() - value;
|
||||
if (new_value < Min()) {
|
||||
return Set(Min());
|
||||
} else {
|
||||
return Set(new_value);
|
||||
}
|
||||
}
|
||||
operator int32_t() const { return Get(); }
|
||||
|
||||
private:
|
||||
Option* option_;
|
||||
@@ -236,7 +249,7 @@ template <OptionID ID>
|
||||
class OptionProxy<
|
||||
ID,
|
||||
typename std::enable_if<kOptionsTypes[static_cast<size_t>(ID)] ==
|
||||
Option::Type::kUnsigned>::type> {
|
||||
Option::Type::kUnsigned>::type> : public OptionProxyNumeric<uint32_t> {
|
||||
public:
|
||||
OptionProxy() : option_(Option::ByID(ID)) {}
|
||||
~OptionProxy() = default;
|
||||
@@ -245,9 +258,7 @@ public:
|
||||
bool Set(uint32_t value) { return option_->SetUnsigned(value); }
|
||||
uint32_t Min() const { return option_->GetUnsignedMin(); }
|
||||
uint32_t Max() const { return option_->GetUnsignedMax(); }
|
||||
|
||||
bool operator=(int32_t value) { return Set(value); }
|
||||
operator int32_t() const { return Get(); }
|
||||
bool operator=(uint32_t value) { return Set(value); }
|
||||
|
||||
private:
|
||||
Option* option_;
|
||||
|
@@ -353,3 +353,109 @@ TEST(OptionProxyTest, MatchingTypes) {
|
||||
EXPECT_EQ(option->type(), proxy_type);
|
||||
}
|
||||
}
|
||||
|
||||
TEST(OptionProxyTest, NumericOperators) {
|
||||
wxLogNull disable_logging;
|
||||
|
||||
int32_t int_opt = OPTION(kDispMaxThreads);
|
||||
|
||||
int_opt++;
|
||||
OPTION(kDispMaxThreads)++;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
int_opt--;
|
||||
OPTION(kDispMaxThreads)--;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
++int_opt;
|
||||
OPTION(kDispMaxThreads)++;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
--int_opt;
|
||||
OPTION(kDispMaxThreads)--;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
int_opt += 2;
|
||||
OPTION(kDispMaxThreads) += 2;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
int_opt -= 2;
|
||||
OPTION(kDispMaxThreads) -= 2;
|
||||
EXPECT_EQ(int_opt, OPTION(kDispMaxThreads));
|
||||
|
||||
OPTION(kDispMaxThreads) = OPTION(kDispMaxThreads).Max();
|
||||
OPTION(kDispMaxThreads)++;
|
||||
EXPECT_EQ(OPTION(kDispMaxThreads), OPTION(kDispMaxThreads).Max());
|
||||
|
||||
OPTION(kDispMaxThreads) = OPTION(kDispMaxThreads).Min();
|
||||
OPTION(kDispMaxThreads)--;
|
||||
EXPECT_EQ(OPTION(kDispMaxThreads), OPTION(kDispMaxThreads).Min());
|
||||
|
||||
uint32_t unsigned_opt = OPTION(kJoyDefault);
|
||||
|
||||
unsigned_opt++;
|
||||
OPTION(kJoyDefault)++;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
unsigned_opt--;
|
||||
OPTION(kJoyDefault)--;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
++unsigned_opt;
|
||||
OPTION(kJoyDefault)++;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
--unsigned_opt;
|
||||
OPTION(kJoyDefault)--;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
unsigned_opt += 2;
|
||||
OPTION(kJoyDefault) += 2;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
unsigned_opt -= 2;
|
||||
OPTION(kJoyDefault) -= 2;
|
||||
EXPECT_EQ(unsigned_opt, OPTION(kJoyDefault));
|
||||
|
||||
OPTION(kJoyDefault) = OPTION(kJoyDefault).Max();
|
||||
OPTION(kJoyDefault)++;
|
||||
EXPECT_EQ(OPTION(kJoyDefault), OPTION(kJoyDefault).Max());
|
||||
|
||||
OPTION(kJoyDefault) = OPTION(kJoyDefault).Min();
|
||||
OPTION(kJoyDefault)--;
|
||||
EXPECT_EQ(OPTION(kJoyDefault), OPTION(kJoyDefault).Min());
|
||||
|
||||
double double_opt = OPTION(kDispScale);
|
||||
|
||||
double_opt++;
|
||||
OPTION(kDispScale)++;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
double_opt--;
|
||||
OPTION(kDispScale)--;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
++double_opt;
|
||||
OPTION(kDispScale)++;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
--double_opt;
|
||||
OPTION(kDispScale)--;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
double_opt += 2;
|
||||
OPTION(kDispScale) += 2;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
double_opt -= 2;
|
||||
OPTION(kDispScale) -= 2;
|
||||
EXPECT_EQ(double_opt, OPTION(kDispScale));
|
||||
|
||||
OPTION(kDispScale) = OPTION(kDispScale).Max();
|
||||
OPTION(kDispScale)++;
|
||||
EXPECT_EQ(OPTION(kDispScale), OPTION(kDispScale).Max());
|
||||
|
||||
OPTION(kDispScale) = OPTION(kDispScale).Min();
|
||||
OPTION(kDispScale)--;
|
||||
EXPECT_EQ(OPTION(kDispScale), OPTION(kDispScale).Min());
|
||||
}
|
||||
|
@@ -94,3 +94,91 @@ TEST(StrSplitWithSepTest, MultipleSepTokens) {
|
||||
EXPECT_EQ(vec[4], "baz");
|
||||
EXPECT_EQ(vec[5], "|-|");
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, Basic) {
|
||||
const std::vector<uint16_t> utf16 = {'f', 'o', 'o', 0};
|
||||
auto vec = config::utf16_to_utf8_vector(utf16.data());
|
||||
|
||||
ASSERT_EQ(vec.size(), 3);
|
||||
|
||||
EXPECT_EQ(vec[0], 'f');
|
||||
EXPECT_EQ(vec[1], 'o');
|
||||
EXPECT_EQ(vec[2], 'o');
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, MultiByte) {
|
||||
// U+20AC EURO SIGN.
|
||||
const std::vector<uint16_t> utf16 = {0x20AC, 0};
|
||||
auto vec = config::utf16_to_utf8_vector(utf16.data());
|
||||
|
||||
ASSERT_EQ(vec.size(), 3);
|
||||
|
||||
EXPECT_EQ(vec[0], 0xE2);
|
||||
EXPECT_EQ(vec[1], 0x82);
|
||||
EXPECT_EQ(vec[2], 0xAC);
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, DualMultiByte) {
|
||||
// This is a variant of the above to test the buffer reset is done properly.
|
||||
const std::vector<uint16_t> utf16 = {0x20AC, 0x20AC, 0};
|
||||
auto vec = config::utf16_to_utf8_vector(utf16.data());
|
||||
|
||||
ASSERT_EQ(vec.size(), 6);
|
||||
|
||||
EXPECT_EQ(vec[0], 0xE2);
|
||||
EXPECT_EQ(vec[1], 0x82);
|
||||
EXPECT_EQ(vec[2], 0xAC);
|
||||
EXPECT_EQ(vec[3], 0xE2);
|
||||
EXPECT_EQ(vec[4], 0x82);
|
||||
EXPECT_EQ(vec[5], 0xAC);
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, SurrogatePair) {
|
||||
// U+1F914 THINKING FACE.
|
||||
const std::vector<uint16_t> utf16 = {0xD83E, 0xDD14, 0};
|
||||
auto vec = config::utf16_to_utf8_vector(utf16.data());
|
||||
|
||||
ASSERT_EQ(vec.size(), 4);
|
||||
|
||||
EXPECT_EQ(vec[0], 0xF0);
|
||||
EXPECT_EQ(vec[1], 0x9F);
|
||||
EXPECT_EQ(vec[2], 0xA4);
|
||||
EXPECT_EQ(vec[3], 0x94);
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, InvalidSurrogatePair) {
|
||||
// U+D800 HIGH SURROGATE.
|
||||
const std::vector<uint16_t> utf16 = {0xD800, 0};
|
||||
EXPECT_DEATH(config::utf16_to_utf8_vector(utf16.data()), ".*");
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, InvalidSurrogatePair2) {
|
||||
// U+D800 HIGH SURROGATE followed by U+0020 SPACE.
|
||||
const std::vector<uint16_t> utf16 = {0xD800, 0x0020, 0};
|
||||
EXPECT_DEATH(config::utf16_to_utf8_vector(utf16.data()), ".*");
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, InvalidSurrogatePair3) {
|
||||
// U+D800 HIGH SURROGATE followed by U+D800 HIGH SURROGATE.
|
||||
const std::vector<uint16_t> utf16 = {0xD800, 0xD800, 0};
|
||||
EXPECT_DEATH(config::utf16_to_utf8_vector(utf16.data()), ".*");
|
||||
}
|
||||
|
||||
TEST(UTF16ToUTF8Test, FullString) {
|
||||
// "foo€🤔"
|
||||
const std::vector<uint16_t> utf16 = {'f', 'o', 'o', 0x20AC, 0xD83E, 0xDD14, 0};
|
||||
auto vec = config::utf16_to_utf8_vector(utf16.data());
|
||||
|
||||
ASSERT_EQ(vec.size(), 10);
|
||||
|
||||
EXPECT_EQ(vec[0], 'f');
|
||||
EXPECT_EQ(vec[1], 'o');
|
||||
EXPECT_EQ(vec[2], 'o');
|
||||
EXPECT_EQ(vec[3], 0xE2);
|
||||
EXPECT_EQ(vec[4], 0x82);
|
||||
EXPECT_EQ(vec[5], 0xAC);
|
||||
EXPECT_EQ(vec[6], 0xF0);
|
||||
EXPECT_EQ(vec[7], 0x9F);
|
||||
EXPECT_EQ(vec[8], 0xA4);
|
||||
EXPECT_EQ(vec[9], 0x94);
|
||||
}
|
||||
|
@@ -1,7 +1,11 @@
|
||||
#include "wx/config/strutils.h"
|
||||
|
||||
#include <cstdint>
|
||||
|
||||
#include <wx/tokenzr.h>
|
||||
|
||||
#include "core/base/check.h"
|
||||
|
||||
namespace config {
|
||||
|
||||
// From: https://stackoverflow.com/a/7408245/262458
|
||||
@@ -37,4 +41,50 @@ wxArrayString str_split_with_sep(const wxString& text, const wxString& sep)
|
||||
return str_split(text, sep, true);
|
||||
}
|
||||
|
||||
std::vector<uint8_t> utf16_to_utf8_vector(const uint16_t* utf16) {
|
||||
std::vector<uint8_t> out;
|
||||
for (size_t i = 0; utf16[i]; i++) {
|
||||
const uint16_t c = utf16[i];
|
||||
if (c < 0x80) {
|
||||
out.push_back(c);
|
||||
} else if (c < 0x800) {
|
||||
out.push_back(0xC0 | (c >> 6));
|
||||
out.push_back(0x80 | (c & 0x3F));
|
||||
} else if (c < 0xD800 || c >= 0xE000) {
|
||||
// Regular 3-byte UTF-8 character.
|
||||
out.push_back(0xE0 | (c >> 12));
|
||||
out.push_back(0x80 | ((c >> 6) & 0x3F));
|
||||
out.push_back(0x80 | (c & 0x3F));
|
||||
} else {
|
||||
// Surrogate pair, construct the original code point.
|
||||
const uint32_t high = c;
|
||||
|
||||
// The next code unit must be a low surrogate.
|
||||
i++;
|
||||
const uint32_t low = utf16[i];
|
||||
VBAM_CHECK(low);
|
||||
VBAM_CHECK(low >= 0xDC00 && low < 0xE000);
|
||||
|
||||
const uint32_t codepoint = 0x10000 + ((high & 0x3FF) << 10) + (low & 0x3FF);
|
||||
|
||||
// Convert to UTF-8.
|
||||
out.push_back(0xF0 | (codepoint >> 18));
|
||||
out.push_back(0x80 | ((codepoint >> 12) & 0x3F));
|
||||
out.push_back(0x80 | ((codepoint >> 6) & 0x3F));
|
||||
out.push_back(0x80 | (codepoint & 0x3F));
|
||||
}
|
||||
}
|
||||
return out;
|
||||
}
|
||||
|
||||
wxString utf16_to_utf8(const uint16_t* utf16) {
|
||||
std::vector<uint8_t> output_vector = utf16_to_utf8_vector(utf16);
|
||||
return wxString::FromUTF8(reinterpret_cast<const char*>(output_vector.data()),
|
||||
output_vector.size());
|
||||
}
|
||||
|
||||
wxString utf16_to_utf8(const int16_t* utf16) {
|
||||
return utf16_to_utf8(reinterpret_cast<const uint16_t*>(utf16));
|
||||
}
|
||||
|
||||
} // namespace config
|
||||
|
@@ -1,6 +1,9 @@
|
||||
#ifndef VBAM_WX_CONFIG_STRUTILS_H_
|
||||
#define VBAM_WX_CONFIG_STRUTILS_H_
|
||||
|
||||
#include <cstdint>
|
||||
#include <vector>
|
||||
|
||||
#include <wx/string.h>
|
||||
#include <wx/arrstr.h>
|
||||
|
||||
@@ -14,6 +17,14 @@ wxArrayString str_split(const wxString& text, const wxString& sep, bool empty_to
|
||||
// 'A', ',' and 'B' will be in the output.
|
||||
wxArrayString str_split_with_sep(const wxString& text, const wxString& sep);
|
||||
|
||||
// Converts a null-terminated array of UTF-16 code units to a vector of UTF-8 code units.
|
||||
// This will assert if the input is not a valid UTF-16 string.
|
||||
std::vector<uint8_t> utf16_to_utf8_vector(const uint16_t* utf16);
|
||||
|
||||
// Convenience functions to convert a null-terminated array of UTF-16 code units to a wxString.
|
||||
wxString utf16_to_utf8(const uint16_t* utf16);
|
||||
wxString utf16_to_utf8(const int16_t* utf16);
|
||||
|
||||
} // namespace config
|
||||
|
||||
#endif // VBAM_WX_CONFIG_STRUTILS_H_
|
||||
|
@@ -145,9 +145,11 @@ AccelConfig::AccelConfig(wxWindow* parent,
|
||||
PopulateTreeWithMenu(&command_to_item_id_, tree_, id, menu->GetMenu(i), recents,
|
||||
menu->GetMenuLabelText(i) + '\n');
|
||||
}
|
||||
tree_->ExpandAll();
|
||||
tree_->SelectItem(menu_id);
|
||||
|
||||
// Set a minimum size for the tree so the default dialog size is reasonable.
|
||||
tree_->SetMinSize(wxSize(300, 300));
|
||||
|
||||
int w, h;
|
||||
current_keys_->GetTextExtent("CTRL-ALT-SHIFT-ENTER", &w, &h);
|
||||
wxSize size(w, h);
|
||||
@@ -177,6 +179,14 @@ AccelConfig::AccelConfig(wxWindow* parent,
|
||||
Bind(wxEVT_BUTTON, &AccelConfig::OnResetAll, this, XRCID("ResetAll"));
|
||||
Bind(wxEVT_TEXT, &AccelConfig::OnKeyInput, this, key_input_->GetId());
|
||||
|
||||
#if !WX_RESIZE_DIALOGS
|
||||
// On wxGTK, the dialog resizing is broken, so we need to set a fixed size.
|
||||
SetWindowStyle(GetWindowStyle() & ~wxRESIZE_BORDER);
|
||||
const wxSize dialog_size(800, 800);
|
||||
SetMinSize(dialog_size);
|
||||
SetMaxSize(dialog_size);
|
||||
#endif // !WX_RESIZE_DIALOGS
|
||||
|
||||
// And fit everything nicely.
|
||||
Fit();
|
||||
}
|
||||
|
@@ -38,15 +38,19 @@ private:
|
||||
return;
|
||||
}
|
||||
|
||||
#if WX_RESIZE_DIALOGS
|
||||
const wxRect dialog_rect = this->Get()->GetRect();
|
||||
this->SaveValue("x", dialog_rect.x);
|
||||
this->SaveValue("y", dialog_rect.y);
|
||||
this->SaveValue("width", dialog_rect.width);
|
||||
this->SaveValue("height", dialog_rect.height);
|
||||
#endif // WX_RESIZE_DIALOGS
|
||||
}
|
||||
|
||||
bool Restore() override {
|
||||
dialog_shown_ = true;
|
||||
|
||||
#if WX_RESIZE_DIALOGS
|
||||
wxRect dialog_rect(0, 0, 0, 0);
|
||||
if (!this->RestoreValue("x", &dialog_rect.x)) {
|
||||
return false;
|
||||
@@ -62,6 +66,7 @@ private:
|
||||
};
|
||||
|
||||
this->Get()->SetSize(dialog_rect);
|
||||
#endif // WX_RESIZE_DIALOGS
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@@ -8,6 +8,13 @@
|
||||
|
||||
#include "core/base/check.h"
|
||||
|
||||
#if defined(__WXGTK__)
|
||||
// Moving and resizing dialogs does not work properly on wxGTK.
|
||||
#define WX_RESIZE_DIALOGS 0
|
||||
#else
|
||||
#define WX_RESIZE_DIALOGS 1
|
||||
#endif
|
||||
|
||||
namespace dialogs {
|
||||
|
||||
class BaseDialog : public wxDialog {
|
||||
|
@@ -330,7 +330,7 @@ void DisplayConfig::PopulatePluginOptions() {
|
||||
plugin_selector_->Clear();
|
||||
plugin_selector_->Append(_("None"), new wxStringClientData());
|
||||
|
||||
const wxString& selected_plugin = OPTION(kDispFilterPlugin);
|
||||
const wxString selected_plugin = OPTION(kDispFilterPlugin);
|
||||
bool is_plugin_selected = false;
|
||||
|
||||
for (const wxString& plugin : plugins) {
|
||||
|
148
src/wx/dialogs/speedup-config.cpp
Normal file
148
src/wx/dialogs/speedup-config.cpp
Normal file
@@ -0,0 +1,148 @@
|
||||
#include "wx/dialogs/speedup-config.h"
|
||||
|
||||
#include <wx/checkbox.h>
|
||||
#include <wx/spinctrl.h>
|
||||
#include <wx/xrc/xmlres.h>
|
||||
|
||||
#include "core/base/check.h"
|
||||
#include "wx/config/option-proxy.h"
|
||||
#include "wx/dialogs/base-dialog.h"
|
||||
#include "wx/widgets/option-validator.h"
|
||||
|
||||
// This dialog has a spin control representing the speedup value as it feels
|
||||
// like to the user. Values below 450 can be an actual throttle or a number of
|
||||
// frames to skip depending on whether the Frame Skip checkbox is checked. The
|
||||
// number of frames is the spin control value divided by 100, for example 300
|
||||
// with the Frame Skip checkbox checked means 3 frames to skip. Values above 450
|
||||
// are always the number of frames to skip, for example 900 means 9 frames to skip.
|
||||
//
|
||||
// The config option SpeedupThrottle is the throttle value, if frame skip is
|
||||
// used it is 0. The config option SpeedupFrameSkip is the number of frames to
|
||||
// skip, if throttle is used it is 0. The config option SpeedupThrottleFrameSkip
|
||||
// represents the Frame Skip checkbox for values under 450, that is if they are
|
||||
// interpreted as a frame skip or a throttle.
|
||||
|
||||
namespace dialogs {
|
||||
|
||||
bool SpeedupConfigValidator::TransferToWindow() {
|
||||
uint32_t opt_frame_skip = OPTION(kPrefSpeedupFrameSkip);
|
||||
uint32_t opt_throttle = OPTION(kPrefSpeedupThrottle);
|
||||
bool opt_throttle_frame_skip = OPTION(kPrefSpeedupThrottleFrameSkip);
|
||||
|
||||
auto dialog = static_cast<SpeedupConfig*>(GetWindow());
|
||||
|
||||
dialog->prev_frame_skip_cb_ = opt_throttle_frame_skip;
|
||||
|
||||
if (opt_frame_skip != 0) {
|
||||
dialog->speedup_throttle_spin_->SetValue(opt_frame_skip * 100);
|
||||
dialog->prev_throttle_spin_ = opt_frame_skip * 100;
|
||||
|
||||
dialog->frame_skip_cb_->SetValue(true);
|
||||
dialog->frame_skip_cb_->Disable();
|
||||
} else {
|
||||
dialog->speedup_throttle_spin_->SetValue(opt_throttle);
|
||||
dialog->prev_throttle_spin_ = opt_throttle;
|
||||
|
||||
dialog->frame_skip_cb_->SetValue(opt_throttle_frame_skip);
|
||||
|
||||
if (opt_throttle != 0)
|
||||
dialog->frame_skip_cb_->Enable();
|
||||
else
|
||||
dialog->frame_skip_cb_->Disable();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SpeedupConfigValidator::TransferFromWindow() {
|
||||
auto dialog = static_cast<SpeedupConfig*>(GetWindow());
|
||||
uint32_t val = dialog->speedup_throttle_spin_->GetValue();
|
||||
|
||||
if (val == 0) {
|
||||
OPTION(kPrefSpeedupThrottle) = 0;
|
||||
OPTION(kPrefSpeedupFrameSkip) = 0;
|
||||
OPTION(kPrefSpeedupThrottleFrameSkip) = false;
|
||||
} else if (val <= OPTION(kPrefSpeedupThrottle).Max()) {
|
||||
OPTION(kPrefSpeedupThrottle) = val;
|
||||
OPTION(kPrefSpeedupFrameSkip) = 0;
|
||||
OPTION(kPrefSpeedupThrottleFrameSkip) = dialog->frame_skip_cb_->GetValue();
|
||||
} else { // val > throttle_max
|
||||
OPTION(kPrefSpeedupThrottle) = 100;
|
||||
OPTION(kPrefSpeedupFrameSkip) = val / 100;
|
||||
OPTION(kPrefSpeedupThrottleFrameSkip) = false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// static
|
||||
SpeedupConfig* SpeedupConfig::NewInstance(wxWindow* parent) {
|
||||
VBAM_CHECK(parent);
|
||||
return new SpeedupConfig(parent);
|
||||
}
|
||||
|
||||
SpeedupConfig::SpeedupConfig(wxWindow* parent)
|
||||
: BaseDialog(parent, "SpeedupConfig") {
|
||||
|
||||
speedup_throttle_spin_ = GetValidatedChild<wxSpinCtrl>("SpeedupThrottleSpin");
|
||||
frame_skip_cb_ = GetValidatedChild<wxCheckBox>("SpeedupThrottleFrameSkip");
|
||||
|
||||
speedup_throttle_spin_->SetRange(OPTION(kPrefSpeedupThrottle).Min(), OPTION(kPrefSpeedupFrameSkip).Max() * 100);
|
||||
|
||||
speedup_throttle_spin_->SetWindowStyle(wxSP_ARROW_KEYS);
|
||||
|
||||
#ifdef wxTE_PROCESS_ENTER
|
||||
speedup_throttle_spin_->SetWindowStyleFlag(wxTE_PROCESS_ENTER);
|
||||
#endif
|
||||
|
||||
GetValidatedChild<wxCheckBox>("SpeedupMute")->SetValidator(widgets::OptionBoolValidator(config::OptionID::kPrefSpeedupMute));
|
||||
|
||||
using namespace std::placeholders;
|
||||
|
||||
Bind(wxEVT_SPIN_UP, std::bind(&SpeedupConfig::SetSpeedupThrottle, this, _1), XRCID("SpeedupThrottleSpin"));
|
||||
Bind(wxEVT_SPIN_DOWN, std::bind(&SpeedupConfig::SetSpeedupThrottle, this, _1), XRCID("SpeedupThrottleSpin"));
|
||||
Bind(wxEVT_SPIN, std::bind(&SpeedupConfig::SetSpeedupThrottle, this, _1), XRCID("SpeedupThrottleSpin"));
|
||||
Bind(wxEVT_TEXT, std::bind(&SpeedupConfig::SetSpeedupThrottle, this, _1), XRCID("SpeedupThrottleSpin"));
|
||||
Bind(wxEVT_CHECKBOX, std::bind(&SpeedupConfig::ToggleSpeedupFrameSkip, this), XRCID("SpeedupThrottleFrameSkip"));
|
||||
|
||||
SetValidator(SpeedupConfigValidator());
|
||||
|
||||
Fit();
|
||||
}
|
||||
|
||||
void SpeedupConfig::SetSpeedupThrottle(wxCommandEvent& evt)
|
||||
{
|
||||
VBAM_CHECK(evt.GetEventObject() == speedup_throttle_spin_);
|
||||
uint32_t val = speedup_throttle_spin_->GetValue();
|
||||
|
||||
if (val == 0) {
|
||||
frame_skip_cb_->SetValue(false);
|
||||
frame_skip_cb_->Disable();
|
||||
} else if (val <= OPTION(kPrefSpeedupThrottle).Max()) {
|
||||
frame_skip_cb_->SetValue(prev_frame_skip_cb_);
|
||||
frame_skip_cb_->Enable();
|
||||
} else { // val > throttle_max
|
||||
if (val > prev_throttle_spin_)
|
||||
val += 100;
|
||||
|
||||
val = std::floor((double)val / 100) * 100;
|
||||
|
||||
uint32_t max = speedup_throttle_spin_->GetMax();
|
||||
|
||||
if (val > max)
|
||||
val = max;
|
||||
|
||||
frame_skip_cb_->SetValue(true);
|
||||
frame_skip_cb_->Disable();
|
||||
}
|
||||
|
||||
speedup_throttle_spin_->SetValue(val);
|
||||
prev_throttle_spin_ = val;
|
||||
}
|
||||
|
||||
void SpeedupConfig::ToggleSpeedupFrameSkip()
|
||||
{
|
||||
prev_frame_skip_cb_ = frame_skip_cb_->GetValue();
|
||||
}
|
||||
|
||||
} // namespace dialogs
|
54
src/wx/dialogs/speedup-config.h
Normal file
54
src/wx/dialogs/speedup-config.h
Normal file
@@ -0,0 +1,54 @@
|
||||
#ifndef VBAM_WX_DIALOGS_SPEEDUP_CONFIG_H_
|
||||
#define VBAM_WX_DIALOGS_SPEEDUP_CONFIG_H_
|
||||
|
||||
// Manages the Speedup/Turbo configuration dialog.
|
||||
//
|
||||
// See the explanation for the implementation in the .cpp file.
|
||||
|
||||
#include <wx/checkbox.h>
|
||||
#include "wx/dialogs/base-dialog.h"
|
||||
#include <wx/spinctrl.h>
|
||||
#include <wx/validate.h>
|
||||
|
||||
namespace dialogs {
|
||||
|
||||
class SpeedupConfigValidator : public wxValidator {
|
||||
public:
|
||||
SpeedupConfigValidator() = default;
|
||||
~SpeedupConfigValidator() override = default;
|
||||
|
||||
bool TransferToWindow() override;
|
||||
bool TransferFromWindow() override;
|
||||
|
||||
bool Validate([[maybe_unused]]wxWindow* parent) override { return true; }
|
||||
|
||||
private:
|
||||
wxObject* Clone() const override { return new SpeedupConfigValidator(); }
|
||||
};
|
||||
|
||||
class SpeedupConfig : public BaseDialog {
|
||||
public:
|
||||
static SpeedupConfig* NewInstance(wxWindow* parent);
|
||||
~SpeedupConfig() override = default;
|
||||
|
||||
void ToggleSpeedupFrameSkip();
|
||||
void ToggleSpeedupMute();
|
||||
void SetSpeedupThrottle(wxCommandEvent& evt);
|
||||
|
||||
private:
|
||||
// The constructor is private so initialization has to be done via the
|
||||
// static method. This is because this class is destroyed when its
|
||||
// owner, `parent` is destroyed. This prevents accidental deletion.
|
||||
SpeedupConfig(wxWindow* parent);
|
||||
|
||||
wxSpinCtrl* speedup_throttle_spin_;
|
||||
wxCheckBox* frame_skip_cb_;
|
||||
bool prev_frame_skip_cb_;
|
||||
unsigned prev_throttle_spin_;
|
||||
|
||||
friend class SpeedupConfigValidator;
|
||||
};
|
||||
|
||||
} // namespace dialogs
|
||||
|
||||
#endif // VBAM_WX_DIALOGS_SPEEDUP_CONFIG_H_
|
@@ -48,6 +48,7 @@
|
||||
#include "wx/dialogs/gb-rom-info.h"
|
||||
#include "wx/dialogs/joypad-config.h"
|
||||
#include "wx/dialogs/sound-config.h"
|
||||
#include "wx/dialogs/speedup-config.h"
|
||||
#include "wx/opts.h"
|
||||
#include "wx/widgets/checkedlistctrl.h"
|
||||
#include "wx/widgets/option-validator.h"
|
||||
@@ -1483,92 +1484,6 @@ public:
|
||||
}
|
||||
} throttle_ctrl;
|
||||
|
||||
static class SpeedupThrottleCtrl_t : public wxEvtHandler {
|
||||
public:
|
||||
wxSpinCtrl* speedup_throttle_spin;
|
||||
wxCheckBox* frame_skip_cb;
|
||||
|
||||
void SetSpeedupThrottle(wxCommandEvent& evt)
|
||||
{
|
||||
unsigned val = speedup_throttle_spin->GetValue();
|
||||
|
||||
evt.Skip(false);
|
||||
|
||||
if (val == 0) {
|
||||
coreOptions.speedup_throttle = 0;
|
||||
coreOptions.speedup_frame_skip = 0;
|
||||
coreOptions.speedup_throttle_frame_skip = false;
|
||||
|
||||
frame_skip_cb->SetValue(false);
|
||||
frame_skip_cb->Disable();
|
||||
|
||||
if (evt.GetEventType() == wxEVT_TEXT)
|
||||
return; // Do not update value if user cleared text box.
|
||||
}
|
||||
else if (val <= 450) {
|
||||
coreOptions.speedup_throttle = val;
|
||||
coreOptions.speedup_frame_skip = 0;
|
||||
|
||||
frame_skip_cb->SetValue(prev_frame_skip_cb);
|
||||
frame_skip_cb->Enable();
|
||||
}
|
||||
else { // val > 450
|
||||
coreOptions.speedup_throttle = 100;
|
||||
coreOptions.speedup_throttle_frame_skip = false;
|
||||
|
||||
unsigned rounded = std::round((double)val / 100) * 100;
|
||||
|
||||
coreOptions.speedup_frame_skip = rounded / 100 - 1;
|
||||
|
||||
// Round up or down to the nearest 100%.
|
||||
// For example, when the up/down buttons are pressed on the spin
|
||||
// control.
|
||||
if ((int)(val - rounded) > 0)
|
||||
coreOptions.speedup_frame_skip++;
|
||||
else if ((int)(val - rounded) < 0)
|
||||
coreOptions.speedup_frame_skip--;
|
||||
|
||||
frame_skip_cb->SetValue(true);
|
||||
frame_skip_cb->Disable();
|
||||
|
||||
val = (coreOptions.speedup_frame_skip + 1) * 100;
|
||||
}
|
||||
|
||||
speedup_throttle_spin->SetValue(val);
|
||||
}
|
||||
|
||||
void SetSpeedupFrameSkip(wxCommandEvent& evt)
|
||||
{
|
||||
(void)evt; // Unused param.
|
||||
|
||||
bool checked = frame_skip_cb->GetValue();
|
||||
|
||||
coreOptions.speedup_throttle_frame_skip = prev_frame_skip_cb = checked;
|
||||
}
|
||||
|
||||
void Init(wxShowEvent& ev)
|
||||
{
|
||||
if (coreOptions.speedup_frame_skip != 0) {
|
||||
speedup_throttle_spin->SetValue((coreOptions.speedup_frame_skip + 1) * 100);
|
||||
frame_skip_cb->SetValue(true);
|
||||
frame_skip_cb->Disable();
|
||||
}
|
||||
else {
|
||||
speedup_throttle_spin->SetValue(coreOptions.speedup_throttle);
|
||||
frame_skip_cb->SetValue(coreOptions.speedup_throttle_frame_skip);
|
||||
|
||||
if (coreOptions.speedup_throttle != 0)
|
||||
frame_skip_cb->Enable();
|
||||
else
|
||||
frame_skip_cb->Disable();
|
||||
}
|
||||
|
||||
ev.Skip();
|
||||
}
|
||||
private:
|
||||
bool prev_frame_skip_cb = coreOptions.speedup_throttle_frame_skip;
|
||||
} speedup_throttle_ctrl;
|
||||
|
||||
/////////////////////////////
|
||||
//Check if a pointer from the XRC file is valid. If it's not, throw an error telling the user.
|
||||
template <typename T>
|
||||
@@ -2376,38 +2291,6 @@ bool MainFrame::BindControls()
|
||||
d->Fit();
|
||||
}
|
||||
|
||||
// SpeedUp Key Config
|
||||
d = LoadXRCDialog("SpeedupConfig");
|
||||
{
|
||||
speedup_throttle_ctrl.frame_skip_cb = SafeXRCCTRL<wxCheckBox>(d, "SpeedupThrottleFrameSkip");
|
||||
speedup_throttle_ctrl.speedup_throttle_spin = SafeXRCCTRL<wxSpinCtrl>(d, "SpeedupThrottleSpin");
|
||||
|
||||
speedup_throttle_ctrl.speedup_throttle_spin->Connect(wxEVT_SPIN_UP,
|
||||
wxCommandEventHandler(SpeedupThrottleCtrl_t::SetSpeedupThrottle),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
speedup_throttle_ctrl.speedup_throttle_spin->Connect(wxEVT_SPIN_DOWN,
|
||||
wxCommandEventHandler(SpeedupThrottleCtrl_t::SetSpeedupThrottle),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
speedup_throttle_ctrl.speedup_throttle_spin->Connect(wxEVT_SPIN,
|
||||
wxCommandEventHandler(SpeedupThrottleCtrl_t::SetSpeedupThrottle),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
speedup_throttle_ctrl.speedup_throttle_spin->Connect(wxEVT_TEXT,
|
||||
wxCommandEventHandler(SpeedupThrottleCtrl_t::SetSpeedupThrottle),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
speedup_throttle_ctrl.frame_skip_cb->Connect(wxEVT_CHECKBOX,
|
||||
wxCommandEventHandler(SpeedupThrottleCtrl_t::SetSpeedupFrameSkip),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
d->Connect(wxEVT_SHOW, wxShowEventHandler(SpeedupThrottleCtrl_t::Init),
|
||||
NULL, &speedup_throttle_ctrl);
|
||||
|
||||
d->Fit();
|
||||
}
|
||||
|
||||
wxMenuItem* suspend_scr_saver_mi = XRCITEM("SuspendScreenSaver");
|
||||
if (suspend_scr_saver_mi)
|
||||
{
|
||||
@@ -2470,6 +2353,7 @@ bool MainFrame::BindControls()
|
||||
dialogs::SoundConfig::NewInstance(this);
|
||||
dialogs::DirectoriesConfig::NewInstance(this);
|
||||
dialogs::JoypadConfig::NewInstance(this, std::bind(&wxvbamApp::bindings, &wxGetApp()));
|
||||
dialogs::SpeedupConfig::NewInstance(this);
|
||||
|
||||
#ifndef NO_LINK
|
||||
d = LoadXRCDialog("LinkConfig");
|
||||
|
@@ -416,11 +416,9 @@ void update_shortcut_opts() {
|
||||
|
||||
// For keyboard shortcuts, it's easier to delete everything and start over.
|
||||
cfg->DeleteGroup("/Keyboard");
|
||||
cfg->SetPath("/Keyboard");
|
||||
for (const auto& iter : wxGetApp().bindings()->GetKeyboardConfiguration()) {
|
||||
cfg->Write(iter.first, iter.second);
|
||||
}
|
||||
cfg->SetPath("/");
|
||||
|
||||
// For joypads, we just compare the strings.
|
||||
bool game_bindings_changed = false;
|
||||
|
@@ -189,19 +189,19 @@ void GameArea::LoadGame(const wxString& name)
|
||||
wxString rp = fnfn.GetPath();
|
||||
|
||||
// can't really decide which dir to use, so try GBA first, then GB
|
||||
const wxString& gba_rom_dir = OPTION(kGBAROMDir);
|
||||
const wxString gba_rom_dir = OPTION(kGBAROMDir);
|
||||
if (!wxGetApp().GetAbsolutePath(gba_rom_dir).empty()) {
|
||||
fnfn.SetPath(wxGetApp().GetAbsolutePath(gba_rom_dir) + '/' + rp);
|
||||
badfile = !fnfn.IsFileReadable();
|
||||
}
|
||||
|
||||
const wxString& gb_rom_dir = OPTION(kGBROMDir);
|
||||
const wxString gb_rom_dir = OPTION(kGBROMDir);
|
||||
if (badfile && !wxGetApp().GetAbsolutePath(gb_rom_dir).empty()) {
|
||||
fnfn.SetPath(wxGetApp().GetAbsolutePath(gb_rom_dir) + '/' + rp);
|
||||
badfile = !fnfn.IsFileReadable();
|
||||
}
|
||||
|
||||
const wxString& gbc_rom_dir = OPTION(kGBGBCROMDir);
|
||||
const wxString gbc_rom_dir = OPTION(kGBGBCROMDir);
|
||||
if (badfile && !wxGetApp().GetAbsolutePath(gbc_rom_dir).empty()) {
|
||||
fnfn.SetPath(wxGetApp().GetAbsolutePath(gbc_rom_dir) + '/' + rp);
|
||||
badfile = !fnfn.IsFileReadable();
|
||||
@@ -287,6 +287,15 @@ void GameArea::LoadGame(const wxString& name)
|
||||
gbApplyPatch(UTF8(pfn.GetFullPath()));
|
||||
}
|
||||
|
||||
// Apply overrides.
|
||||
wxFileConfig* cfg = wxGetApp().gb_overrides_.get();
|
||||
const std::string& title = g_gbCartData.title();
|
||||
if (cfg->HasGroup(title)) {
|
||||
cfg->SetPath(title);
|
||||
coreOptions.gbPrinterEnabled = cfg->Read("gbPrinter", coreOptions.gbPrinterEnabled);
|
||||
cfg->SetPath("/");
|
||||
}
|
||||
|
||||
// start sound; this must happen before CPU stuff
|
||||
gb_effects_config.enabled = OPTION(kSoundGBEnableEffects);
|
||||
gb_effects_config.surround = OPTION(kSoundGBSurround);
|
||||
@@ -359,7 +368,7 @@ void GameArea::LoadGame(const wxString& name)
|
||||
gbaUpdateRomSize(size);
|
||||
}
|
||||
|
||||
wxFileConfig* cfg = wxGetApp().overrides;
|
||||
wxFileConfig* cfg = wxGetApp().overrides_.get();
|
||||
wxString id = wxString((const char*)&g_rom[0xac], wxConvLibc, 4);
|
||||
|
||||
if (cfg->HasGroup(id)) {
|
||||
@@ -456,7 +465,7 @@ void GameArea::LoadGame(const wxString& name)
|
||||
SuspendScreenSaver();
|
||||
|
||||
// probably only need to do this for GB carts
|
||||
if (coreOptions.winGbPrinterEnabled)
|
||||
if (coreOptions.gbPrinterEnabled)
|
||||
gbSerialFunction = gbPrinterSend;
|
||||
|
||||
// probably only need to do this for GBA carts
|
||||
@@ -666,6 +675,9 @@ void GameArea::UnloadGame(bool destruct)
|
||||
if (loaded == IMAGE_GB) {
|
||||
gbCleanUp();
|
||||
gbCheatRemoveAll();
|
||||
|
||||
// Reset overrides.
|
||||
coreOptions.gbPrinterEnabled = OPTION(kPrefGBPrinter);
|
||||
} else if (loaded == IMAGE_GBA) {
|
||||
CPUCleanUp();
|
||||
cheatsDeleteAll(false);
|
||||
@@ -952,10 +964,6 @@ void GameArea::ShowFullScreen(bool full)
|
||||
while (!tlw->popups.empty())
|
||||
tlw->popups.front()->Close();
|
||||
|
||||
// Some kbd accels can send a menu open event without a close event,
|
||||
// this happens on Mac in HiDPI mode for the fullscreen toggle accel.
|
||||
main_frame->SetMenusOpened(false);
|
||||
|
||||
// mouse stays blank whenever full-screen
|
||||
HidePointer();
|
||||
cursz_valid = true;
|
||||
@@ -2368,13 +2376,6 @@ void GLDrawingPanel::AdjustViewport()
|
||||
int x, y;
|
||||
widgets::GetRealPixelClientSize(this, &x, &y);
|
||||
glViewport(0, 0, x, y);
|
||||
|
||||
#ifdef DEBUG
|
||||
// you can use this to check that the gl surface is indeed high res
|
||||
GLint m_viewport[4];
|
||||
glGetIntegerv(GL_VIEWPORT, m_viewport);
|
||||
wxLogDebug(wxT("GL VIEWPORT: %d, %d, %d, %d"), m_viewport[0], m_viewport[1], m_viewport[2], m_viewport[3]);
|
||||
#endif
|
||||
}
|
||||
|
||||
void GLDrawingPanel::RefreshGL()
|
||||
|
@@ -6,10 +6,8 @@ if(NOT BUILD_TESTING)
|
||||
endif()
|
||||
|
||||
add_library(vbam-wx-fake-opts OBJECT)
|
||||
|
||||
target_sources(vbam-wx-fake-opts
|
||||
PRIVATE
|
||||
fake_opts.cpp
|
||||
fake-opts.cpp
|
||||
)
|
||||
|
||||
configure_wx_target(vbam-wx-fake-opts)
|
||||
|
@@ -1,10 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<component type="desktop">
|
||||
<component type="desktop-application">
|
||||
<id>org.visualboyadvance_m.visualboyadvance_m</id>
|
||||
<metadata_license>CC-BY-SA-3.0</metadata_license>
|
||||
<project_license>GPL-2.0</project_license>
|
||||
<content_rating type="oars-1.1"/>
|
||||
<name>VisualBoyAdvance-M</name>
|
||||
<developer id="org.visualboyadvance-m">
|
||||
<name>VisualBoyAdvance-M</name>
|
||||
</developer>
|
||||
<summary>VisualBoyAdvance-M, a high compatibility Gameboy Advance Emulator</summary>
|
||||
<description>
|
||||
<p>
|
||||
|
77
src/wx/widgets/CMakeLists.txt
Normal file
77
src/wx/widgets/CMakeLists.txt
Normal file
@@ -0,0 +1,77 @@
|
||||
# This defines the vbam-wx-widgets target.
|
||||
# This does not export any localizable file as there is no localized string
|
||||
# in this target.
|
||||
|
||||
add_library(vbam-wx-widgets OBJECT)
|
||||
|
||||
target_sources(vbam-wx-widgets
|
||||
PRIVATE
|
||||
# from external source with minor modifications
|
||||
checkedlistctrl.cpp
|
||||
$<IF:$<BOOL:${APPLE}>,dpi-support-mac.mm,dpi-support.cpp>
|
||||
group-check-box.cpp
|
||||
keep-on-top-styler.cpp
|
||||
keyboard-input-handler.cpp
|
||||
option-validator.cpp
|
||||
render-plugin.cpp
|
||||
user-input-ctrl.cpp
|
||||
user-input-event.cpp
|
||||
sdl-poller.cpp
|
||||
shortcut-menu-bar.cpp
|
||||
utils.cpp
|
||||
wxmisc.cpp
|
||||
|
||||
PUBLIC
|
||||
# from external source with minor modifications
|
||||
checkedlistctrl.h
|
||||
client-data.h
|
||||
dpi-support.h
|
||||
event-handler-provider.h
|
||||
group-check-box.h
|
||||
keep-on-top-styler.h
|
||||
keyboard-input-handler.h
|
||||
option-validator.h
|
||||
render-plugin.h
|
||||
user-input-ctrl.h
|
||||
user-input-event.h
|
||||
sdl-poller.h
|
||||
shortcut-menu-bar.h
|
||||
utils.h
|
||||
wxmisc.h
|
||||
)
|
||||
|
||||
target_link_libraries(vbam-wx-widgets PUBLIC vbam-wx-config)
|
||||
configure_wx_target(vbam-wx-widgets)
|
||||
|
||||
if(BUILD_TESTING)
|
||||
add_executable(vbam-wx-widgets-tests
|
||||
client-data-test.cpp
|
||||
group-check-box-test.cpp
|
||||
keep-on-top-styler-test.cpp
|
||||
keyboard-input-handler-test.cpp
|
||||
option-validator-test.cpp
|
||||
user-input-ctrl-test.cpp
|
||||
user-input-event-test.cpp
|
||||
)
|
||||
|
||||
target_link_libraries(vbam-wx-widgets-tests
|
||||
# Test deps.
|
||||
vbam-core-base-test
|
||||
vbam-core-fake
|
||||
vbam-wx-fake-opts
|
||||
vbam-wx-widgets-test-fixture
|
||||
|
||||
# Target deps.
|
||||
vbam-wx-config
|
||||
vbam-wx-widgets
|
||||
GTest::gtest_main
|
||||
GTest::gmock_main
|
||||
)
|
||||
|
||||
configure_wx_target(vbam-wx-widgets-tests)
|
||||
if (NOT CMAKE_CROSSCOMPILING)
|
||||
gtest_discover_tests(vbam-wx-widgets-tests)
|
||||
endif()
|
||||
endif()
|
||||
|
||||
add_subdirectory(test)
|
@@ -13,10 +13,21 @@
|
||||
#define VBAM_WX_WIDGETS_CHECKEDLISTCTRL_H_
|
||||
|
||||
// wxWidgets headers
|
||||
#include "wx/widgets/webupdatedef.h" // for the WXDLLIMPEXP_WEBUPDATE macro
|
||||
#include <wx/imaglist.h>
|
||||
#include <wx/listctrl.h>
|
||||
|
||||
// this will never be part of a DLL
|
||||
#define WXDLLIMPEXP_WEBUPDATE
|
||||
// why would I include it and not enable it?
|
||||
#define wxUSE_CHECKEDLISTCTRL 1
|
||||
// enable customizations:
|
||||
// - include wx/settings.h (bugfix; always enabled)
|
||||
// - make a dynamic class so it can be subclass in xrc
|
||||
// - only make col0 checkable
|
||||
// - use "native" checkbox (also requires CLC_USE_SYSICONS)
|
||||
#define CLC_VBAM_USAGE 1
|
||||
#define CLC_USE_SYSICONS 1
|
||||
|
||||
#if wxUSE_CHECKEDLISTCTRL
|
||||
|
||||
// image indexes (used internally by wxCheckedListCtrl)
|
||||
|
30
src/wx/widgets/client-data-test.cpp
Normal file
30
src/wx/widgets/client-data-test.cpp
Normal file
@@ -0,0 +1,30 @@
|
||||
#include "wx/widgets/client-data.h"
|
||||
|
||||
#include <memory>
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <wx/window.h>
|
||||
|
||||
#include "wx/config/user-input.h"
|
||||
|
||||
namespace widgets {
|
||||
|
||||
// Test the ClientData class with a simple type.
|
||||
TEST(ClientDataTest, Int) {
|
||||
std::unique_ptr<wxWindow> window(std::make_unique<wxWindow>());
|
||||
window->SetClientObject(new ClientData<int>(42));
|
||||
|
||||
EXPECT_EQ(ClientData<int>::From(window.get()), 42);
|
||||
}
|
||||
|
||||
// Test the ClientData class with a complex type.
|
||||
TEST(ClientDataTest, Object) {
|
||||
std::unique_ptr<wxWindow> window(std::make_unique<wxWindow>());
|
||||
window->SetClientObject(new ClientData<config::UserInput>(config::KeyboardInput('4')));
|
||||
|
||||
EXPECT_EQ(ClientData<config::UserInput>::From(window.get()).device(),
|
||||
config::UserInput::Device::Keyboard);
|
||||
}
|
||||
|
||||
} // namespace widgets
|
27
src/wx/widgets/group-check-box-test.cpp
Normal file
27
src/wx/widgets/group-check-box-test.cpp
Normal file
@@ -0,0 +1,27 @@
|
||||
#include "wx/widgets/group-check-box.h"
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <wx/frame.h>
|
||||
#include <wx/sizer.h>
|
||||
#include <wx/xrc/xmlres.h>
|
||||
|
||||
#include "wx/widgets/test/widgets-test.h"
|
||||
|
||||
namespace widgets {
|
||||
|
||||
TEST_F(WidgetsTest, GroupCheckBoxTest) {
|
||||
// Add 2 GroupCheckBoxes to the frame, `frame()` takes ownership here.
|
||||
GroupCheckBox* check_box_1 = new GroupCheckBox(frame(), XRCID("One"), "One");
|
||||
GroupCheckBox* check_box_2 = new GroupCheckBox(frame(), XRCID("Two"), "Two");
|
||||
|
||||
// Tick one checkbox and check the other is unticked.
|
||||
check_box_1->SetValue(true);
|
||||
EXPECT_FALSE(check_box_2->GetValue());
|
||||
|
||||
// And vice-versa.
|
||||
check_box_2->SetValue(true);
|
||||
EXPECT_FALSE(check_box_1->GetValue());
|
||||
}
|
||||
|
||||
} // namespace widgets
|
37
src/wx/widgets/keep-on-top-styler-test.cpp
Normal file
37
src/wx/widgets/keep-on-top-styler-test.cpp
Normal file
@@ -0,0 +1,37 @@
|
||||
#include "wx/widgets/keep-on-top-styler.h"
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
|
||||
#include <wx/frame.h>
|
||||
#include <wx/xrc/xmlres.h>
|
||||
|
||||
#include "wx/config/option-proxy.h"
|
||||
#include "wx/widgets/test/widgets-test.h"
|
||||
|
||||
namespace widgets {
|
||||
|
||||
TEST_F(WidgetsTest, KeepOnTopStyler) {
|
||||
// Enable the keep on top option.
|
||||
OPTION(kDispKeepOnTop) = true;
|
||||
|
||||
// Create a Frame, it should not have the wxSTAY_ON_TOP style.
|
||||
EXPECT_EQ(frame()->GetWindowStyle() & wxSTAY_ON_TOP, 0);
|
||||
|
||||
// Add a KeepOnTopStyler to the frame.
|
||||
KeepOnTopStyler styler(frame());
|
||||
|
||||
// Send the Show event to the frame.
|
||||
wxShowEvent show_event(wxEVT_SHOW, true);
|
||||
frame()->GetEventHandler()->ProcessEvent(show_event);
|
||||
|
||||
// The frame should have the wxSTAY_ON_TOP style.
|
||||
EXPECT_EQ(frame()->GetWindowStyle() & wxSTAY_ON_TOP, wxSTAY_ON_TOP);
|
||||
|
||||
// Disable the keep on top option.
|
||||
OPTION(kDispKeepOnTop) = false;
|
||||
|
||||
// The frame should no longer have the wxSTAY_ON_TOP style.
|
||||
EXPECT_EQ(frame()->GetWindowStyle() & wxSTAY_ON_TOP, 0);
|
||||
}
|
||||
|
||||
} // namespace widgets
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user