mirror of
https://github.com/mitch030504/Wiicompiled_VR_Frame.git
synced 2026-10-06 02:00:14 +02:00
Revise the Markdown docs against the code and the fork's state
Checked every claim that names a setting, default, log line, binding or script against the source, and brought the docs up to date with the Steam Frame build: - README: the recommended settings show their Frame defaults (render scale 0.8, resolution multiplier 1) and add eye-tracked foveation and the refresh rate; the settings panel's gamepad-mode button (both sticks); by-hand release tags moved to frame-beta-2; the AI usage note points at a section that exists. - OPENXR.md: the intro and requirements cover all three backends; the Linux Vulkan backend, its patched Dawn and time conversion; Frame defaults for render scale and culling; the Frame controller profile in the binding list and limitations; foveation on the Frame and its per-map memory; scope of passthrough and tracked hands; Linux log path. - quest-port.md: Known gaps rewritten (it still said the app had not run on a Quest, foveation was off by default, haptics unused and the pack not downloadable); intro names every product sharing the spec. - DISTRIBUTION.md: how this fork's source-only frame-* releases are made. - THIRD-PARTY-NOTICES.md: libco's aarch64 backend, Dawn built from source for the Quest and the Frame, and the tools the Frame installer fetches. - CONTRIBUTING, RELEASE_VALIDATION, android/README, translator/README, building-macos: fork context, broken pointers, list formatting, typos. - aurora-main/README: drop a screenshot that was not vendored. All relative links and anchors resolve. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019HBRGKTE1GnN2ah8gcZKr3
This commit is contained in:
11 files changed
+200
-139
No files matched your search
+12
-10
@@ -1,11 +1,13 @@
|
|||||||
# Contributing to WiiCompiled
|
# Contributing to WiiCompiled
|
||||||
|
|
||||||
Thanks for wanting to help! A few ground rules
|
Thanks for wanting to help! This is the Steam Frame fork of
|
||||||
|
[WiiCompiled OpenXR VR](https://github.com/iChris4/Wiicompiled_VR); it follows upstream's ground
|
||||||
|
rules, below. Changes that are not specific to the Steam Frame are usually better made upstream.
|
||||||
|
|
||||||
## The short version
|
## The short version
|
||||||
|
|
||||||
- Code is judged on quality, not where it came from
|
- Code is judged on quality, not where it came from.
|
||||||
- You must be able understand and be able to explain every line you submit.
|
- You must understand, and be able to explain, every line you submit.
|
||||||
- PR descriptions and responses must be written by you, **not** generated.
|
- PR descriptions and responses must be written by you, **not** generated.
|
||||||
- Accuracy is the bar for anything touching game behavior.
|
- Accuracy is the bar for anything touching game behavior.
|
||||||
|
|
||||||
@@ -31,23 +33,23 @@ That's ok, but rules apply:
|
|||||||
|
|
||||||
## Pull requests
|
## Pull requests
|
||||||
|
|
||||||
- Keep PRs focused. try and keep it at 1 change per PR.
|
- Keep PRs focused: try to keep it to one change per PR. Small PRs get reviewed fast.
|
||||||
Small PRs get reviewed fast.
|
|
||||||
- Explain **what** and **why**. Reference the issue if there is one.
|
- Explain **what** and **why**. Reference the issue if there is one.
|
||||||
- For anything affecting game behavior: identical behavior to real hardware is
|
- For anything affecting game behavior: identical behavior to real hardware is
|
||||||
the goal. Be prepared to show your change doesn't diverge from the original
|
the goal. Be prepared to show your change doesn't diverge from the original
|
||||||
game (hardware comparison, logs, whatever fits).
|
game (hardware comparison, logs, whatever fits).
|
||||||
- Review feedback. It's about the code, not about you ;).
|
- Take review feedback in stride: it's about the code, not about you ;).
|
||||||
|
|
||||||
## Bug reports
|
## Bug reports
|
||||||
|
|
||||||
See the FAQ in the [README](README.md)
|
See [Reporting problems](README.md#reporting-problems) in the README: what you did and saw, plus the
|
||||||
|
run's `console.log`. Problems that also happen on a PC or a Quest belong upstream.
|
||||||
|
|
||||||
## A note on related projects
|
## A note on related projects
|
||||||
|
|
||||||
WiiCompiled, Wheel Wizard, and other projects in this ecosystem are developed
|
WiiCompiled, WiiCompiled OpenXR VR, Wheel Wizard and the other projects in this ecosystem are
|
||||||
independently and each has its **own** contribution rules and all have their own
|
developed independently, and each has its **own** contribution rules, including its own rules on
|
||||||
rules around AI usage. What applies here does not automatically apply there,
|
AI usage. What applies here does not automatically apply there,
|
||||||
and vice versa. Check each project's own CONTRIBUTING file.
|
and vice versa. Check each project's own CONTRIBUTING file.
|
||||||
|
|
||||||
## Legal
|
## Legal
|
||||||
|
|||||||
+19
-1
@@ -1,4 +1,22 @@
|
|||||||
# Windows VR distribution
|
# Distribution
|
||||||
|
|
||||||
|
## Steam Frame releases (this fork)
|
||||||
|
|
||||||
|
Releases here are **source only**: a `frame-<name>` tag (`frame-beta-2`, ...) and GitHub's source
|
||||||
|
archives for it. The game is always built from the player's own clean PAL `RMCP01` disc, so no
|
||||||
|
release, issue or download may carry a disc image, extracted game files, translated game code or a
|
||||||
|
built game executable, and nobody may share one built from their disc.
|
||||||
|
|
||||||
|
To publish one, add its notes as `docs/releases/<tag>.md`, then run **Actions → Steam Frame
|
||||||
|
release → Run workflow** with the tag (`.github/workflows/frame-release.yml`). The workflow creates
|
||||||
|
the tag on the commit it runs on and publishes a pre-release with those notes; pushing a `frame-*`
|
||||||
|
tag runs it as well. The installer (`Launcher/steam-frame-install.sh`) builds the newest release by
|
||||||
|
default, so publish only what has been built and installed on a Frame.
|
||||||
|
|
||||||
|
## Windows (upstream)
|
||||||
|
|
||||||
|
The rest of this file is upstream's process for its Windows installer and is kept for reference.
|
||||||
|
This fork does not publish Windows builds; use upstream's releases for those.
|
||||||
|
|
||||||
Distribute only `WiiCompiled-Setup.exe` and its checksum from
|
Distribute only `WiiCompiled-Setup.exe` and its checksum from
|
||||||
[iChris4/Wiicompiled_VR](https://github.com/iChris4/Wiicompiled_VR/releases), and
|
[iChris4/Wiicompiled_VR](https://github.com/iChris4/Wiicompiled_VR/releases), and
|
||||||
|
|||||||
@@ -1,23 +1,30 @@
|
|||||||
# Experimental OpenXR VR
|
# Experimental OpenXR VR
|
||||||
|
|
||||||
WiiCompiled has an opt-in OpenXR rendering path. The first functional backend is Windows D3D12.
|
WiiCompiled has an opt-in OpenXR rendering path with three backends:
|
||||||
It asks the OpenXR runtime for the required GPU before Aurora creates Dawn, then copies each eye
|
|
||||||
on that same D3D12 device and queue into the acquired OpenXR swapchain images. Eye submission
|
- **Windows D3D12**, the first. It asks the OpenXR runtime for the required GPU before Aurora
|
||||||
stays on the GPU; there is no CPU texture readback and no second graphics device. Windows Vulkan is
|
creates Dawn, then copies each eye on that same D3D12 device and queue into the acquired OpenXR
|
||||||
an opt-in second binding built on the same design: the OpenXR runtime creates Dawn's Vulkan instance
|
swapchain images. Eye submission stays on the GPU; there is no CPU texture readback and no second
|
||||||
and device (`XR_KHR_vulkan_enable2`) and eyes are copied on that same queue. It needs a custom Dawn
|
graphics device.
|
||||||
build; see [Windows Vulkan](#windows-vulkan).
|
- **Vulkan on Windows and Linux**, built on the same design: the OpenXR runtime creates Dawn's
|
||||||
|
Vulkan instance and device (`XR_KHR_vulkan_enable2`) and eyes are copied on that same queue. It
|
||||||
|
needs a Dawn built with Aurora's patches; see [Windows Vulkan](#windows-vulkan). On Linux it is the
|
||||||
|
Steam Frame's native SteamOS build (the [README](README.md)).
|
||||||
|
- **Android Vulkan** for the Meta Quest, where the eyes cross from Dawn's device to the backend's own
|
||||||
|
through AHardwareBuffers; see [`docs/quest-port.md`](docs/quest-port.md).
|
||||||
|
|
||||||
This is an experimental renderer, not yet a release-ready VR mode.
|
This is an experimental renderer, not yet a release-ready VR mode.
|
||||||
|
|
||||||
## Requirements
|
## Requirements
|
||||||
|
|
||||||
- A Windows OpenXR runtime selected as the system's active runtime.
|
- An OpenXR runtime selected as the system's active runtime (SteamVR, Virtual Desktop, Meta's PC
|
||||||
- A connected headset supported by that runtime.
|
runtime, ... on Windows; SteamVR on the Steam Frame), and a connected headset it supports.
|
||||||
- A D3D12-capable GPU and driver accepted by both OpenXR and Dawn, or for the opt-in Vulkan
|
- On Windows, a D3D12-capable GPU and driver accepted by both OpenXR and Dawn, or for the opt-in
|
||||||
binding a Vulkan 1.1+ driver plus the custom Dawn described under [Windows Vulkan](#windows-vulkan).
|
Vulkan binding a Vulkan 1.1+ driver plus the patched Dawn described under
|
||||||
- A build made with `MKW_ENABLE_OPENXR=ON`, which defaults on for Windows and off elsewhere while
|
[Windows Vulkan](#windows-vulkan). On Linux, the patched Dawn from `Launcher/build-dawn-linux.sh`.
|
||||||
the Vulkan bridge remains capability-gated.
|
- A build made with `MKW_ENABLE_OPENXR=ON`, which defaults on for Windows and Android. On Linux it
|
||||||
|
stays opt-in because it needs the patched Dawn: `Launcher/local-build.sh --openxr --dawn-package
|
||||||
|
<dir>`.
|
||||||
|
|
||||||
For managed installation, use [WheelWizard VR](https://github.com/iChris4/WheelWizard_VR/releases/latest)
|
For managed installation, use [WheelWizard VR](https://github.com/iChris4/WheelWizard_VR/releases/latest)
|
||||||
and enable **Settings → Other → WiiCompiled (beta) → Enable WiiCompiled OpenXR VR (beta)**.
|
and enable **Settings → Other → WiiCompiled (beta) → Enable WiiCompiled OpenXR VR (beta)**.
|
||||||
@@ -30,8 +37,8 @@ in `Recomp/UserData/Config.toml`. Both backends use the normal installation's ef
|
|||||||
|
|
||||||
Standalone launches start in VR too: this is the VR build, and `required = false` makes a failed
|
Standalone launches start in VR too: this is the VR build, and `required = false` makes a failed
|
||||||
headset startup fall back to the desktop renderer rather than stop the game. `Config.toml` is
|
headset startup fall back to the desktop renderer rather than stop the game. `Config.toml` is
|
||||||
created with the following defaults, and a configuration that never mentions `enabled` reads the
|
created with the following defaults (a PC build's; the Quest and Steam Frame defaults that differ are
|
||||||
same way:
|
given with each key below), and a configuration that never mentions `enabled` reads the same way:
|
||||||
|
|
||||||
```toml
|
```toml
|
||||||
[vr]
|
[vr]
|
||||||
@@ -142,8 +149,9 @@ settings are ignored. Completed rendering wakes the XR thread immediately. A 50
|
|||||||
still protects pauses and window dragging without eager repeats during rendering.
|
still protects pauses and window dragging without eager repeats during rendering.
|
||||||
|
|
||||||
`render_scale` scales the per-eye size recommended by the OpenXR runtime (0.25 to 2, never above the
|
`render_scale` scales the per-eye size recommended by the OpenXR runtime (0.25 to 2, never above the
|
||||||
runtime's maximum). It defaults to 1.0 on PC and 0.8 on the Quest, whose mobile GPU needs the
|
runtime's maximum). It defaults to 1.0 on PC and 0.8 on the Quest and the Steam Frame, whose mobile
|
||||||
headroom. It is live: **F10 → VR → Render resolution** (also on the headset panel's VR tab) sets it
|
GPUs need the headroom (on the Frame, 1.25 is the panels' native 2160x2160).
|
||||||
|
It is live: **F10 → VR → Render resolution** (also on the headset panel's VR tab) sets it
|
||||||
in percent, applies it when the slider is let go, and saves it. Below the slider, *Each eye* gives
|
in percent, applies it when the slider is let go, and saves it. Below the slider, *Each eye* gives
|
||||||
the left eye's size now and, while they differ, the size the slider's value gives.
|
the left eye's size now and, while they differ, the size the slider's value gives.
|
||||||
|
|
||||||
@@ -187,7 +195,8 @@ immersive stereo view, head tracking and all, but is seen only through a window,
|
|||||||
around it on the Quest; see [The immersive window](#the-immersive-window). `flat_screen` wins when
|
around it on the Quest; see [The immersive window](#the-immersive-window). `flat_screen` wins when
|
||||||
both are set. The settings present the three as one choice, **Race view**: Immersive, Immersive
|
both are set. The settings present the three as one choice, **Race view**: Immersive, Immersive
|
||||||
window or Flat screen.
|
window or Flat screen.
|
||||||
`passthrough` (Quest only, default on) shows the room through the headset's cameras around the
|
`passthrough` (Quest only, default on; the Steam Frame build neither asks for it nor offers it)
|
||||||
|
shows the room through the headset's cameras around the
|
||||||
menu screen and every other virtual screen, instead of black: an `XR_FB_passthrough`
|
menu screen and every other virtual screen, instead of black: an `XR_FB_passthrough`
|
||||||
reconstruction layer submitted under the screen's quad, as PPSSPP VR does, with the blend mode
|
reconstruction layer submitted under the screen's quad, as PPSSPP VR does, with the blend mode
|
||||||
left `OPAQUE`. A fully immersive race never shows it, and the cameras are paused for the race; a
|
left `OPAQUE`. A fully immersive race never shows it, and the cameras are paused for the race; a
|
||||||
@@ -198,8 +207,8 @@ live, from the headset panel's VR tab or the launcher's Settings page. The app d
|
|||||||
So that the room frames the picture rather than black bands, the Quest's menu quad shows only the
|
So that the room frames the picture rather than black bands, the Quest's menu quad shows only the
|
||||||
part of its eye-sized image Aurora draws into (the desktop snapshot, and the in-eye settings
|
part of its eye-sized image Aurora draws into (the desktop snapshot, and the in-eye settings
|
||||||
panel's rectangle), at the same size per pixel, so nothing moves.
|
panel's rectangle), at the same size per pixel, so nothing moves.
|
||||||
`hand_tracking` (Quest only, default off) makes the first-person cockpit's hands follow the
|
`hand_tracking` (standalone headsets, default off; tried on the Quest only) makes the first-person
|
||||||
headset's hand tracking; see "Tracked hands" under
|
cockpit's hands follow the headset's hand tracking; see "Tracked hands" under
|
||||||
[Steering wheel and hand steering](#steering-wheel-and-hand-steering).
|
[Steering wheel and hand steering](#steering-wheel-and-hand-steering).
|
||||||
How each eye is replayed is fixed; the former `stop_at_display_copy`, `skip_copy_clears` and
|
How each eye is replayed is fixed; the former `stop_at_display_copy`, `skip_copy_clears` and
|
||||||
`single_pass_eyes` settings are ignored. An eye ends at the frame's final `GXCopyDisp`, so it holds
|
`single_pass_eyes` settings are ignored. An eye ends at the frame's final `GXCopyDisp`, so it holds
|
||||||
@@ -290,7 +299,8 @@ right A, B, trigger and stick as above, left View as the left menu (+), the left
|
|||||||
`"gamepad"` mode). The table is in the README, Controls.
|
`"gamepad"` mode). The table is in the README, Controls.
|
||||||
|
|
||||||
**Motion.** Each XR frame the aim and grip poses are located at the measured current time
|
**Motion.** Each XR frame the aim and grip poses are located at the measured current time
|
||||||
(`XR_KHR_win32_convert_performance_counter_time`, `XR_KHR_convert_timespec_time` on Android), not
|
(`XR_KHR_win32_convert_performance_counter_time`, `XR_KHR_convert_timespec_time` on Android and
|
||||||
|
Linux), not
|
||||||
the predicted display time, whose extrapolation sprays fast wrist motion. The grip's linear
|
the predicted display time, whose extrapolation sprays fast wrist motion. The grip's linear
|
||||||
velocity, averaged with one derived from its position, is differentiated over XrTime into
|
velocity, averaged with one derived from its position, is differentiated over XrTime into
|
||||||
acceleration; gravity is added and the result is expressed in the aim pose's frame. KPAD's
|
acceleration; gravity is added and the result is expressed in the aim pose's frame. KPAD's
|
||||||
@@ -385,8 +395,9 @@ controllers still open the settings panel with left Y, point at it and toggle th
|
|||||||
with a right thumbstick click; they press no game button, drive no Wii Remote, cannot take hold of
|
with a right thumbstick click; they press no game button, drive no Wii Remote, cannot take hold of
|
||||||
the cockpit's wheel, and the game's rumble does not reach them.
|
the cockpit's wheel, and the game's rumble does not reach them.
|
||||||
|
|
||||||
Bindings are suggested for `oculus/touch_controller` (Quest 2, 3 and Pro) and
|
Bindings are suggested for `oculus/touch_controller` (Quest 2, 3 and Pro), `khr/simple_controller`
|
||||||
`khr/simple_controller`. `mkw_vr_wii_remote_tests` checks the accelerometer frame, the pointer
|
and, where the runtime offers it, `valve/frame_controller_valve` (the Steam Frame).
|
||||||
|
`mkw_vr_wii_remote_tests` checks the accelerometer frame, the pointer
|
||||||
raycast and debounce, the picture placement and the button profile without a headset.
|
raycast and debounce, the picture placement and the button profile without a headset.
|
||||||
|
|
||||||
## Settings in the headset
|
## Settings in the headset
|
||||||
@@ -428,7 +439,8 @@ the desktop's ImGui pass of the same frame is recorded.
|
|||||||
|
|
||||||
The panel is shown as a compositor quad layer of its own, submitted over the scene's projection or
|
The panel is shown as a compositor quad layer of its own, submitted over the scene's projection or
|
||||||
menu quad layer. The compositor samples the 1440 × 1080 canvas directly, so its text stays sharp
|
menu quad layer. The compositor samples the 1440 × 1080 canvas directly, so its text stays sharp
|
||||||
whatever `render_scale` gives the eyes. Every backend (D3D12, Windows Vulkan, Quest) makes the
|
whatever `render_scale` gives the eyes. Every backend (D3D12, Vulkan on Windows and Linux, Quest)
|
||||||
|
makes the
|
||||||
panel's swapchain pair the first time the panel opens (two 1440 × 1080 swapchains, plus two shared
|
panel's swapchain pair the first time the panel opens (two 1440 × 1080 swapchains, plus two shared
|
||||||
buffers on the Quest) and keeps it for the session. Until then nothing is allocated, and while the
|
buffers on the Quest) and keeps it for the session. Until then nothing is allocated, and while the
|
||||||
panel is closed nothing is copied or submitted. While it is open, each frame hands Aurora one more
|
panel is closed nothing is copied or submitted. While it is open, each frame hands Aurora one more
|
||||||
@@ -566,8 +578,8 @@ in first person, and karts, characters and course objects are simply missing unt
|
|||||||
camera catches up; the race intro's pan shows it too, since the other racers are culled from the
|
camera catches up; the race intro's pan shows it too, since the other racers are culled from the
|
||||||
intro camera's narrow view. `object_culling = false` (F10 > Camera > Object culling, also on the
|
intro camera's narrow view. `object_culling = false` (F10 > Camera > Object culling, also on the
|
||||||
headset settings panel's Camera tab) draws them anyway, and takes effect immediately. That is
|
headset settings panel's Camera tab) draws them anyway, and takes effect immediately. That is
|
||||||
the PC's default. The Quest defaults to `true`, the game's own culling, because every model
|
the PC's default. The Quest and the Steam Frame default to `true`, the game's own culling, because
|
||||||
drawn costs its GPU twice, once per eye.
|
every model drawn costs their mobile GPUs twice, once per eye.
|
||||||
|
|
||||||
Measured on a Quest 3 (base game, the first Grand Prix race at Luigi Circuit after the intro, player
|
Measured on a Quest 3 (base game, the first Grand Prix race at Luigi Circuit after the intro, player
|
||||||
idle, first-person cockpit, `render_scale = 0.8`, foveation medium, six interleaved rounds per
|
idle, first-person cockpit, `render_scale = 0.8`, foveation medium, six interleaved rounds per
|
||||||
@@ -678,13 +690,15 @@ holding grip no longer reaches the game (a shoulder on the gamepad; the Wii Remo
|
|||||||
leaves the grips unbound for this reason); the triggers, A and the right stick are unchanged. Releasing both grips gives steering back
|
leaves the grips unbound for this reason); the triggers, A and the right stick are unchanged. Releasing both grips gives steering back
|
||||||
to the stick. The settings panel withholds the wheel like any other input.
|
to the stick. The settings panel withholds the wheel like any other input.
|
||||||
|
|
||||||
**A USB wheel.** With a USB wheel and pedals set up (see the README), the wheel drives the race as
|
**A USB wheel.** With a USB wheel and pedals set up (see
|
||||||
|
[upstream's README](https://github.com/iChris4/Wiicompiled_VR)), the wheel drives the race as
|
||||||
player 1's GameCube controller. The cockpit's wheel follows its calibrated steering, at the same
|
player 1's GameCube controller. The cockpit's wheel follows its calibrated steering, at the same
|
||||||
full-lock angle as the stick (`wheel_kart_degrees`, `wheel_bike_degrees`), and hand steering steps
|
full-lock angle as the stick (`wheel_kart_degrees`, `wheel_bike_degrees`), and hand steering steps
|
||||||
aside while it drives.
|
aside while it drives.
|
||||||
|
|
||||||
**Tracked hands.** `hand_tracking` (Quest only for now, default off; the Quest launcher's
|
**Tracked hands.** `hand_tracking` (standalone headsets, default off, so far tried on the Quest only;
|
||||||
Settings > VR and the headset panel's Camera tab, under hand steering, which it needs) poses the
|
the Quest launcher's Settings > VR and the headset panel's Camera tab, under hand steering, which
|
||||||
|
it needs) poses the
|
||||||
cockpit hands from the headset's hand tracking instead of curling them with the grip. Two hand
|
cockpit hands from the headset's hand tracking instead of curling them with the grip. Two hand
|
||||||
trackers (`XR_EXT_hand_tracking`) are located every XR frame at the display time. While the
|
trackers (`XR_EXT_hand_tracking`) are located every XR frame at the display time. While the
|
||||||
controllers are held the Quest builds the joints from their touch sensors
|
controllers are held the Quest builds the joints from their touch sensors
|
||||||
@@ -810,7 +824,8 @@ short-lived immutable stereo packet. Each sealed GX frame and immersive packet c
|
|||||||
policy-generation tag; a mismatch is rendered in mono and the acquired XR frame is canceled, so an
|
policy-generation tag; a mismatch is rendered in mono and the acquired XR frame is canceled, so an
|
||||||
asynchronous menu/race transition cannot replay race transforms over unsafe content.
|
asynchronous menu/race transition cannot replay race transforms over unsafe content.
|
||||||
|
|
||||||
With interpolation off, PC (D3D12 and Windows Vulkan) and standalone (Android Vulkan) pace render-first:
|
With interpolation off, PC (D3D12 and Windows Vulkan), the Steam Frame (Linux Vulkan) and the Quest
|
||||||
|
(Android Vulkan) pace render-first:
|
||||||
the pacing thread locates views for an estimated display time (two periods past the last
|
the pacing thread locates views for an estimated display time (two periods past the last
|
||||||
prediction), hands Aurora a packet without leaving a compositor frame open, and waits for
|
prediction), hands Aurora a packet without leaving a compositor frame open, and waits for
|
||||||
rendering. A 50 ms stall repeats the retained layer; cancellation also advances a keep-alive
|
rendering. A 50 ms stall repeats the retained layer; cancellation also advances a keep-alive
|
||||||
@@ -819,7 +834,8 @@ xrBeginFrame, completes backend-specific copy/release work, and ends the frame u
|
|||||||
packet's original render poses with the current compositor display time.
|
packet's original render poses with the current compositor display time.
|
||||||
|
|
||||||
Android Vulkan renders into shared buffers and copies them into newly acquired XR images afterward.
|
Android Vulkan renders into shared buffers and copies them into newly acquired XR images afterward.
|
||||||
Both PC bindings acquire images from their non-retained swapchain pair before rendering; Aurora
|
The D3D12 and Vulkan bindings (Windows and Linux) acquire images from their non-retained swapchain
|
||||||
|
pair before rendering; Aurora
|
||||||
queues the copy on the session's queue before reporting completion. PC therefore needs no additional
|
queues the copy on the session's queue before reporting completion. PC therefore needs no additional
|
||||||
copy in the short compositor cycle. Pending images remain acquired and separate from the
|
copy in the short compositor cycle. Pending images remain acquired and separate from the
|
||||||
retained pair until completion or confirmed cancellation before encoding. GPU failure still
|
retained pair until completion or confirmed cancellation before encoding. GPU failure still
|
||||||
@@ -1030,7 +1046,8 @@ agreement with the HUD's placement, an eye turned away or beyond the window, a s
|
|||||||
|
|
||||||
## Foveated rendering
|
## Foveated rendering
|
||||||
|
|
||||||
On the Quest, `foveation` shades the edges of the immersive race view in 2x2, then 4x4 pixel
|
On the Quest and the Steam Frame, `foveation` shades the edges of the immersive race view in 2x2,
|
||||||
|
then 4x4 pixel
|
||||||
blocks, where the headset's lenses blur the picture anyway, and gives the GPU time back for a
|
blocks, where the headset's lenses blur the picture anyway, and gives the GPU time back for a
|
||||||
higher `render_scale` or a steadier frame rate. Each eye's render pass runs under a fragment
|
higher `render_scale` or a steadier frame rate. Each eye's render pass runs under a fragment
|
||||||
density map (`VK_EXT_fragment_density_map`, attached through dynamic rendering). The map is centred
|
density map (`VK_EXT_fragment_density_map`, attached through dynamic rendering). The map is centred
|
||||||
@@ -1051,13 +1068,17 @@ anything drawn outside an immersive race are never foveated.
|
|||||||
`XR_FB_foveation`, the extension DolphinXR uses by default, cannot help here. The runtime's density
|
`XR_FB_foveation`, the extension DolphinXR uses by default, cannot help here. The runtime's density
|
||||||
maps only shape render passes that draw into its swapchain images, and on the Quest Dawn draws each
|
maps only shape render passes that draw into its swapchain images, and on the Quest Dawn draws each
|
||||||
eye on its own device and hands it to the OpenXR device, which copies it into the swapchain. So the
|
eye on its own device and hands it to the OpenXR device, which copies it into the swapchain. So the
|
||||||
map has to go into Dawn's own eye passes. The stock Dawn package has no such feature, so the Quest
|
map has to go into Dawn's own eye passes. (On the Steam Frame Dawn does render on the runtime's
|
||||||
build links a Dawn built with Aurora's patches (`aurora-main/patches/dawn`, built by
|
device, but its eyes are copied into the swapchain afterwards, so the same holds.) The stock Dawn
|
||||||
`android/Build-QuestDawn.ps1`, see `docs/quest-port.md`). The patch enables the extension only when
|
package has no such feature, so both link a Dawn built with Aurora's patches
|
||||||
|
(`aurora-main/patches/dawn`, built by `android/Build-QuestDawn.ps1` for the Quest, see
|
||||||
|
`docs/quest-port.md`, and by `Launcher/build-dawn-linux.sh` for the Frame).
|
||||||
|
The patch enables the extension only when
|
||||||
Aurora asks for it at device creation, and every render pipeline then carries the density-map
|
Aurora asks for it at device creation, and every render pipeline then carries the density-map
|
||||||
pipeline flag. That is why the launch decides.
|
pipeline flag. That is why the launch decides.
|
||||||
|
|
||||||
A density map forces Adreno into binned rendering, where every extra render pass in an eye stores
|
A density map forces Adreno (the Quest's and the Frame's GPU) into binned rendering, where every
|
||||||
|
extra render pass in an eye stores
|
||||||
and reloads the whole eye. DolphinXR measured foveation as a net loss on Mario Kart Wii for exactly
|
and reloads the whole eye. DolphinXR measured foveation as a net loss on Mario Kart Wii for exactly
|
||||||
that reason (its bloom chain splits the frame about 20 times). An eye is therefore foveated only
|
that reason (its bloom chain splits the frame about 20 times). An eye is therefore foveated only
|
||||||
when it is drawn in a single render pass, as every eye is by default; an eye that a partial clear still
|
when it is drawn in a single render pass, as every eye is by default; an eye that a partial clear still
|
||||||
@@ -1091,14 +1112,16 @@ did (39 to 41.5 FPS).
|
|||||||
### Eye-tracked foveation
|
### Eye-tracked foveation
|
||||||
|
|
||||||
With `eye_tracked_foveation`, a runtime that offers `XR_EXT_eye_gaze_interaction` and reports an eye
|
With `eye_tracked_foveation`, a runtime that offers `XR_EXT_eye_gaze_interaction` and reports an eye
|
||||||
tracker (the Steam Frame's SteamVR) has its gaze pose located for each packet's display time and
|
tracker (SteamVR on the Steam Frame) has its gaze pose located for each packet's display time and
|
||||||
turned into tangents of each eye's view (`vr/eye_gaze.h`), which `AuroraStereoFrame` carries as
|
turned into tangents of each eye's view (`vr/eye_gaze.h`), which `AuroraStereoFrame` carries as
|
||||||
`gaze`/`gazeValid`. Aurora centres the level's rings, each widened by 8 degrees to cover the lag
|
`gaze`/`gazeValid`. Aurora centres the level's rings, each widened by 8 degrees to cover the lag
|
||||||
and error of tracking, on the gaze snapped to a cell of two map texels (about 3 degrees), keeping up
|
and error of tracking, on the gaze snapped to a cell of two map texels (about 3 degrees), keeping up
|
||||||
to 128 maps per eye, one per cell looked at, and binds a new one once
|
to 128 maps per eye, one per cell looked at, and binds a new one once
|
||||||
its upload completes, the previous map staying bound meanwhile. Without a tracked gaze (a blink, no
|
its upload completes, the previous map staying bound meanwhile. Without a tracked gaze (a blink, no
|
||||||
tracker, the setting off) the map is the forward one above, unchanged. The README's How it works
|
tracker, the setting off) the map is the forward one above, unchanged. Each map has a memory
|
||||||
covers the Steam Frame.
|
block of its own: the Frame's driver (Turnip) reads a map through a host mapping, and Dawn's buffer
|
||||||
|
uploads unmap the shared blocks they sub-allocate from, which crashed the game on a race restart.
|
||||||
|
The [README](README.md#how-it-works)'s How it works covers the Steam Frame.
|
||||||
|
|
||||||
## Diagnostics
|
## Diagnostics
|
||||||
|
|
||||||
@@ -1270,6 +1293,14 @@ the VkQueue only inside `xrBeginFrame`, `xrEndFrame`, `xrAcquireSwapchainImage`
|
|||||||
`xrReleaseSwapchainImage`, so `OpenXRRuntime::LockGraphicsQueue` holds Dawn's device guard around
|
`xrReleaseSwapchainImage`, so `OpenXRRuntime::LockGraphicsQueue` holds Dawn's device guard around
|
||||||
exactly those four calls and never across `xrWaitFrame` or `xrWaitSwapchainImage`.
|
exactly those four calls and never across `xrWaitFrame` or `xrWaitSwapchainImage`.
|
||||||
|
|
||||||
|
**Linux (the Steam Frame).** The same file is the Linux backend; only its `_WIN32` parts differ.
|
||||||
|
Dawn links statically there, so `Launcher/build-dawn-linux.sh` builds the pinned Dawn with the same
|
||||||
|
patches into a package whose `aurora-dawn.json` declares the Vulkan hook and density map ABIs, and
|
||||||
|
`Launcher/local-build.sh --openxr --dawn-package <dir>` builds against it. Without those hooks the
|
||||||
|
backend fails with *"Linux Vulkan OpenXR requires a Dawn built with Aurora's patches"*. Time
|
||||||
|
conversion uses `XR_KHR_convert_timespec_time`, and the extensions the Frame adds (its controller
|
||||||
|
profile, `XR_FB_display_refresh_rate`, `XR_EXT_eye_gaze_interaction`) are optional as everywhere.
|
||||||
|
|
||||||
**Tests.** `mkw_openxr_vulkan_replay_tests` compiles the real backend against the deterministic
|
**Tests.** `mkw_openxr_vulkan_replay_tests` compiles the real backend against the deterministic
|
||||||
compositor of the D3D12 replay tests, including the queue-guard requirement on acquire and release.
|
compositor of the D3D12 replay tests, including the queue-guard requirement on acquire and release.
|
||||||
`vulkan_native_bridge_smoke` (aurora, `AURORA_GPU_SMOKE_TESTS=ON`, real GPU, no headset) drives the
|
`vulkan_native_bridge_smoke` (aurora, `AURORA_GPU_SMOKE_TESTS=ON`, real GPU, no headset) drives the
|
||||||
@@ -1286,7 +1317,7 @@ custom DLL's ABI through three borrowed-image copy/readback cycles; run it with
|
|||||||
| Linux Vulkan (Steam Frame, SteamOS) | Implemented and played on a Steam Frame (beta): the Windows Vulkan design compiled for Linux, so the runtime creates Dawn's own instance and device and the eyes are copied on Dawn's queue with no sharing. Adds the Frame controller profile, 120 Hz and gaze-centred foveation. Needs a Dawn built with Aurora's patches (`Launcher/build-dawn-linux.sh`), then `Launcher/local-build.sh --openxr --dawn-package <dir> --headset steam_frame`. See the README, Quick start. |
|
| Linux Vulkan (Steam Frame, SteamOS) | Implemented and played on a Steam Frame (beta): the Windows Vulkan design compiled for Linux, so the runtime creates Dawn's own instance and device and the eyes are copied on Dawn's queue with no sharing. Adds the Frame controller profile, 120 Hz and gaze-centred foveation. Needs a Dawn built with Aurora's patches (`Launcher/build-dawn-linux.sh`), then `Launcher/local-build.sh --openxr --dawn-package <dir> --headset steam_frame`. See the README, Quick start. |
|
||||||
| Other platforms | Not wired yet. |
|
| Other platforms | Not wired yet. |
|
||||||
|
|
||||||
Both bindings share `openxr_integration.cpp`: the pacing thread, policy evaluation, the
|
All backends share `openxr_integration.cpp`: the pacing thread, policy evaluation, the
|
||||||
retained-layer protocol and the head-pose maths are compiled once against the neutral types in
|
retained-layer protocol and the head-pose maths are compiled once against the neutral types in
|
||||||
`vr/openxr_backend.h`, and only the backend class differs per platform.
|
`vr/openxr_backend.h`, and only the backend class differs per platform.
|
||||||
|
|
||||||
@@ -1366,7 +1397,8 @@ ends, including mid-frame flushes, so live setting changes cannot invalidate pen
|
|||||||
|
|
||||||
- Only the project's supported PAL `RMCP01` translation has race instrumentation addresses.
|
- Only the project's supported PAL `RMCP01` translation has race instrumentation addresses.
|
||||||
- The tracked controllers are always Player 1's Wii Remote; there is no left-handed swap, and only
|
- The tracked controllers are always Player 1's Wii Remote; there is no left-handed swap, and only
|
||||||
the Touch and simple controller profiles have suggested bindings. The Wii Remote presentation
|
the Touch, simple controller and Steam Frame profiles have suggested bindings. The Wii Remote
|
||||||
|
presentation
|
||||||
still needs headset validation: cursor direction and roll, trick/wheelie motion, rumble strength
|
still needs headset validation: cursor direction and roll, trick/wheelie motion, rumble strength
|
||||||
and the HOME Menu.
|
and the HOME Menu.
|
||||||
- The Quest build (`android/`, `docs/quest-port.md`) runs on a Quest 3 through menus and races.
|
- The Quest build (`android/`, `docs/quest-port.md`) runs on a Quest 3 through menus and races.
|
||||||
@@ -1384,6 +1416,6 @@ ends, including mid-frame flushes, so live setting changes cannot invalidate pen
|
|||||||
immersive race costs. Hands and a separate VR wheel are seen only through the window.
|
immersive race costs. Hands and a separate VR wheel are seen only through the window.
|
||||||
- The desktop window remains available as a mirror/fallback.
|
- The desktop window remains available as a mirror/fallback.
|
||||||
|
|
||||||
OpenXR diagnostics are written to the normal run log under
|
OpenXR diagnostics are written to the normal run log under `%LOCALAPPDATA%\WiiCompiled\Logs` on
|
||||||
`%LOCALAPPDATA%\WiiCompiled\Logs`. Search for `OpenXR` when reporting a startup or submission
|
Windows and `~/.local/share/WiiCompiled/Logs` on Linux (the Steam Frame); the Quest's are covered in
|
||||||
failure.
|
`docs/quest-port.md`. Search for `OpenXR` when reporting a startup or submission failure.
|
||||||
@@ -96,7 +96,8 @@ curl -fsSL https://raw.githubusercontent.com/mitch030504/Wiicompiled_VR_Frame/op
|
|||||||
### 3. Play
|
### 3. Play
|
||||||
|
|
||||||
Start **WiiCompiled** from the library in the headset. Open the settings panel with the left
|
Start **WiiCompiled** from the library in the headset. Open the settings panel with the left
|
||||||
shoulder button, go to the **VR** tab and set the [recommended settings](#recommended-settings).
|
shoulder button (with the controllers as a gamepad: both sticks clicked together), go to the **VR**
|
||||||
|
tab and set the [recommended settings](#recommended-settings).
|
||||||
|
|
||||||
### Updating
|
### Updating
|
||||||
|
|
||||||
@@ -107,17 +108,19 @@ so), so an update usually takes minutes. `--release <tag>` builds a given releas
|
|||||||
|
|
||||||
## Recommended settings
|
## Recommended settings
|
||||||
|
|
||||||
All of these are in the headset's settings panel (left shoulder button, **VR** tab) and in
|
All of these are in the headset's settings panel (**VR** tab) and in
|
||||||
`~/.local/share/WiiCompiled/Config.toml`. Quit the game before editing the file; it writes its
|
`~/.local/share/WiiCompiled/Config.toml`. Quit the game before editing the file; it writes its
|
||||||
settings back when it closes.
|
settings back when it closes.
|
||||||
|
|
||||||
| Setting | Value | Why |
|
| Setting | Value | Default | Why |
|
||||||
| --- | --- | --- |
|
| --- | --- | --- | --- |
|
||||||
| `[vr] render_scale` | `1.25` | Scales SteamVR's recommended eye size, 1728x1728 on the Frame: 1.25 is the panels' native 2160x2160, which the Frame renders in 9 to 11 ms a frame with medium foveation. |
|
| `[vr] render_scale` | `1.25` | `0.8` | Scales SteamVR's recommended eye size, 1728x1728 on the Frame: 1.25 is the panels' native 2160x2160, which the Frame renders in 9 to 11 ms a frame with medium foveation. |
|
||||||
| `[vr] foveation` | `medium` | `off` shades every pixel and costs the most. See [Known issues](#known-issues) if images double. |
|
| `[vr] foveation` | `medium` | `medium` | `off` shades every pixel and costs the most. See [Known issues](#known-issues) if images double. |
|
||||||
| `[vr] repeat_frames` | `true` (default) | Without it SteamVR halves the game's rate and fills refreshes itself. |
|
| `[vr] eye_tracked_foveation` | `true` | `true` | Centres the sharp region on your gaze instead of the middle of each eye. |
|
||||||
| `[vr] frame_interpolation_fps` | `0` | Rendering in-between frames needs 120 eye pairs a second, which made things worse on the Frame. |
|
| `[vr] repeat_frames` | `true` | `true` | Without it SteamVR halves the game's rate and fills refreshes itself. |
|
||||||
| `[video] resolution_multiplier` | `2` | The game's own frame, which the eyes are made from. 4x is far too heavy for the Frame's GPU. |
|
| `[vr] refresh_rate` | `120` | `120` | Two refreshes per game frame. SteamVR must be set to 120 Hz as well. |
|
||||||
|
| `[vr] frame_interpolation_fps` | `0` | `0` | Rendering in-between frames needs 120 eye pairs a second, which made things worse on the Frame. |
|
||||||
|
| `[video] resolution_multiplier` | `2` | `1` | The game's own frame, which the eyes are made from. 4x is far too heavy for the Frame's GPU. |
|
||||||
|
|
||||||
Keep SteamVR's refresh rate at 120 Hz. Motion Smoothing makes no difference to this game.
|
Keep SteamVR's refresh rate at 120 Hz. Motion Smoothing makes no difference to this game.
|
||||||
|
|
||||||
@@ -138,6 +141,9 @@ The Frame's controllers are bound through their own profile, so the left D-pad w
|
|||||||
| Grips, stick clicks, motion, aim | as on Quest Touch ([`OPENXR.md`](OPENXR.md), Controllers) | as on Touch |
|
| Grips, stick clicks, motion, aim | as on Quest Touch ([`OPENXR.md`](OPENXR.md), Controllers) | as on Touch |
|
||||||
| Right X, Y, menu and shoulder | unbound | unbound |
|
| Right X, Y, menu and shoulder | unbound | unbound |
|
||||||
|
|
||||||
|
In gamepad mode (`[vr] controller_mode = "gamepad"`) the left shoulder is the GameCube Y button, so
|
||||||
|
the settings panel opens with both sticks clicked together instead.
|
||||||
|
|
||||||
## Known issues
|
## Known issues
|
||||||
|
|
||||||
- **Doubled images** in races and on the HUD, worst while racing, sometimes in the right eye only.
|
- **Doubled images** in races and on the HUD, worst while racing, sometimes in the right eye only.
|
||||||
@@ -195,11 +201,11 @@ emulation as in [Quick start](#quick-start) step 1 first.
|
|||||||
### 1. Download the release and extract your disc
|
### 1. Download the release and extract your disc
|
||||||
|
|
||||||
Take the newest release from the [Releases](https://github.com/mitch030504/Wiicompiled_VR_Frame/releases)
|
Take the newest release from the [Releases](https://github.com/mitch030504/Wiicompiled_VR_Frame/releases)
|
||||||
page; the commands use `frame-beta-1`, so put the newest release's tag in its place:
|
page; the commands use `frame-beta-2`, so put the newest release's tag in its place:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
mkdir -p ~/wiicompiled/Wiicompiled_VR_Frame; cd ~/wiicompiled
|
mkdir -p ~/wiicompiled/Wiicompiled_VR_Frame; cd ~/wiicompiled
|
||||||
curl -fL https://github.com/mitch030504/Wiicompiled_VR_Frame/archive/refs/tags/frame-beta-1.tar.gz \
|
curl -fL https://github.com/mitch030504/Wiicompiled_VR_Frame/archive/refs/tags/frame-beta-2.tar.gz \
|
||||||
| tar -xz --strip-components=1 -C Wiicompiled_VR_Frame
|
| tar -xz --strip-components=1 -C Wiicompiled_VR_Frame
|
||||||
curl -fL -o nodtool https://github.com/encounter/nod/releases/download/v2.0.0-alpha.10/nodtool-linux-x86_64
|
curl -fL -o nodtool https://github.com/encounter/nod/releases/download/v2.0.0-alpha.10/nodtool-linux-x86_64
|
||||||
chmod +x nodtool
|
chmod +x nodtool
|
||||||
@@ -270,12 +276,12 @@ the executable. `rsync -c` copies just the files whose content changed and stamp
|
|||||||
current time, so the build recompiles exactly those. Unpacking over the source would restore each
|
current time, so the build recompiles exactly those. Unpacking over the source would restore each
|
||||||
file's commit date, which can be older than the last build, and changes would be skipped. Your
|
file's commit date, which can be older than the last build, and changes would be skipped. Your
|
||||||
`Assets/` and build folders stay. Install `rsync` if your system lacks it, and put the new release's
|
`Assets/` and build folders stay. Install `rsync` if your system lacks it, and put the new release's
|
||||||
tag in place of `frame-beta-2`:
|
tag in place of `frame-beta-3`:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
cd ~/wiicompiled
|
cd ~/wiicompiled
|
||||||
mkdir -p release-new
|
mkdir -p release-new
|
||||||
curl -fL https://github.com/mitch030504/Wiicompiled_VR_Frame/archive/refs/tags/frame-beta-2.tar.gz \
|
curl -fL https://github.com/mitch030504/Wiicompiled_VR_Frame/archive/refs/tags/frame-beta-3.tar.gz \
|
||||||
| tar -xz --strip-components=1 -C release-new
|
| tar -xz --strip-components=1 -C release-new
|
||||||
rsync -rcE release-new/ Wiicompiled_VR_Frame/
|
rsync -rcE release-new/ Wiicompiled_VR_Frame/
|
||||||
rm -rf release-new
|
rm -rf release-new
|
||||||
@@ -426,8 +432,10 @@ Leave out `--headset steam_frame` and pass `--cpu` for your CPU to get a generic
|
|||||||
it needs an OpenXR runtime with `XR_KHR_vulkan_enable2`. Untested.
|
it needs an OpenXR runtime with `XR_KHR_vulkan_enable2`. Untested.
|
||||||
|
|
||||||
## AI usage
|
## AI usage
|
||||||
AI coding tools were used during development of this project.
|
|
||||||
All translated output is verified against real hardware behavior and most importantly, physics accuracy is proven synced across Wii, Dolphin, and WiiCompiled (see FAQ).
|
AI coding tools were used during development of this project. Translated output is checked against
|
||||||
|
real hardware behaviour and, most importantly, the physics are proven identical across Wii, Dolphin
|
||||||
|
and WiiCompiled by ghosts that stay in sync (see [From upstream](#from-upstream)).
|
||||||
|
|
||||||
## Credits
|
## Credits
|
||||||
- **inkwreck** - making the logo
|
- **inkwreck** - making the logo
|
||||||
@@ -459,7 +467,6 @@ All translated output is verified against real hardware behavior and most import
|
|||||||
Bundled third-party components and their licenses live in
|
Bundled third-party components and their licenses live in
|
||||||
[`THIRD-PARTY-NOTICES.md`](THIRD-PARTY-NOTICES.md).
|
[`THIRD-PARTY-NOTICES.md`](THIRD-PARTY-NOTICES.md).
|
||||||
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
WiiCompiled is free software: you can redistribute it and/or modify it under the terms of the
|
WiiCompiled is free software: you can redistribute it and/or modify it under the terms of the
|
||||||
|
|||||||
@@ -1,5 +1,8 @@
|
|||||||
# WheelWizard VR integration validation
|
# WheelWizard VR integration validation
|
||||||
|
|
||||||
|
This is upstream's record of validating its Windows release candidates, kept for reference. It does
|
||||||
|
not cover this fork's Steam Frame releases (see [`DISTRIBUTION.md`](DISTRIBUTION.md)).
|
||||||
|
|
||||||
Validated locally on Windows x64 on 2026-09-09. These are release candidates; public release
|
Validated locally on Windows x64 on 2026-09-09. These are release candidates; public release
|
||||||
acceptance is not complete.
|
acceptance is not complete.
|
||||||
|
|
||||||
|
|||||||
@@ -122,7 +122,8 @@ Copyright byuu and the higan team.
|
|||||||
Non-Windows builds use libco's symmetric stackful coroutines in place of Win32 Fibers for guest
|
Non-Windows builds use libco's symmetric stackful coroutines in place of Win32 Fibers for guest
|
||||||
OSThread scheduling (`runtime/src/fiber_manager.cpp`). Vendored in full (all non-Windows
|
OSThread scheduling (`runtime/src/fiber_manager.cpp`). Vendored in full (all non-Windows
|
||||||
CPU-architecture backends - amd64, x86, arm, aarch64, ppc, ppc64v2, plus the portable sjlj
|
CPU-architecture backends - amd64, x86, arm, aarch64, ppc, ppc64v2, plus the portable sjlj
|
||||||
fallback - though this project's x86_64-only target only ever compiles amd64.c) in
|
fallback; x86_64 builds compile amd64.c, and the ARM64 builds for the Quest and the Steam Frame
|
||||||
|
aarch64.c) in
|
||||||
`runtime/third_party/libco` from commit `e18e09d634d612a01781168ad4d76be10a7e3bad`.
|
`runtime/third_party/libco` from commit `e18e09d634d612a01781168ad4d76be10a7e3bad`.
|
||||||
Source: <https://github.com/higan-emu/libco>. Full license text:
|
Source: <https://github.com/higan-emu/libco>. Full license text:
|
||||||
`runtime/third_party/libco/LICENSE`.
|
`runtime/third_party/libco/LICENSE`.
|
||||||
@@ -139,7 +140,7 @@ trees themselves (fetched by `Launcher/Prepare-Dependencies.ps1`) so end-user bu
|
|||||||
|
|
||||||
| Component | Version | License | Upstream |
|
| Component | Version | License | Upstream |
|
||||||
| --- | --- | --- | --- |
|
| --- | --- | --- | --- |
|
||||||
| Dawn (WebGPU) | `v20260603.191052` prebuilt | BSD-3-Clause | <https://dawn.googlesource.com/dawn> |
|
| Dawn (WebGPU) | `v20260603.191052` prebuilt; the Quest and Steam Frame builds compile the same revision from source with `aurora-main/patches/dawn` | BSD-3-Clause | <https://dawn.googlesource.com/dawn> |
|
||||||
| Tint (part of Dawn) | with Dawn | BSD-3-Clause | <https://dawn.googlesource.com/dawn> |
|
| Tint (part of Dawn) | with Dawn | BSD-3-Clause | <https://dawn.googlesource.com/dawn> |
|
||||||
| DirectXShaderCompiler (`dxcompiler.dll`) | with Dawn | NCSA / University of Illinois Open Source | <https://github.com/microsoft/DirectXShaderCompiler> |
|
| DirectXShaderCompiler (`dxcompiler.dll`) | with Dawn | NCSA / University of Illinois Open Source | <https://github.com/microsoft/DirectXShaderCompiler> |
|
||||||
| SDL | 3.4.4 | zlib | <https://github.com/libsdl-org/SDL> |
|
| SDL | 3.4.4 | zlib | <https://github.com/libsdl-org/SDL> |
|
||||||
@@ -230,6 +231,7 @@ unmodified, with their license texts, in the installer's `licenses/` folder.
|
|||||||
|
|
||||||
| Component | License | Upstream |
|
| Component | License | Upstream |
|
||||||
| --- | --- | --- |
|
| --- | --- | --- |
|
||||||
|
| Steam Frame build tools, fetched by `Launcher/steam-frame-install.sh` and the scripts it runs: the Debian trixie container image and its packages, LLVM 22 (clang, lld; `Launcher/prepare-portable-tools.sh`), CMake, Ninja, the .NET 8 SDK, Dawn's source and its dependencies (`Launcher/build-dawn-linux.sh`), and nodtool | Each its own (Apache-2.0 WITH LLVM-exception, BSD-3-Clause, Apache-2.0, MIT, Debian's per-package licenses, ...) | Pinned in those scripts |
|
||||||
| Android NDK r29 for Windows (clang, lld, sysroot), fetched by `--build-quest` from Google with a pinned SHA-1 | Android Software Development Kit License Agreement | <https://developer.android.com/studio/terms> |
|
| Android NDK r29 for Windows (clang, lld, sysroot), fetched by `--build-quest` from Google with a pinned SHA-1 | Android Software Development Kit License Agreement | <https://developer.android.com/studio/terms> |
|
||||||
| Android NDK r29 aarch64 sysroot, compiler-rt builtins, libunwind and libatomic, fetched by the Quest app's Build on this Quest from Google's Linux NDK zip with pinned SHA-256s | Android Software Development Kit License Agreement | <https://developer.android.com/studio/terms> |
|
| Android NDK r29 aarch64 sysroot, compiler-rt builtins, libunwind and libatomic, fetched by the Quest app's Build on this Quest from Google's Linux NDK zip with pinned SHA-256s | Android Software Development Kit License Agreement | <https://developer.android.com/studio/terms> |
|
||||||
|
|
||||||
|
|||||||
+9
-7
@@ -1,12 +1,14 @@
|
|||||||
# WiiCompiled VR for Meta Quest (Android)
|
# WiiCompiled VR for Meta Quest (Android)
|
||||||
|
|
||||||
Standalone Android/OpenXR build of the Mario Kart Wii recompilation for Quest 1,
|
Standalone Android/OpenXR build of the Mario Kart Wii recompilation for Quest 1, Quest 2,
|
||||||
Quest 2, Quest 3, Quest 3S and Quest Pro, and, as the `steamFrame` flavour, for Valve's Steam
|
Quest 3, Quest 3S and Quest Pro. A `steamFrame` flavour targets Valve's Steam Frame under Lepton,
|
||||||
Frame under Lepton (the [README](../README.md#the-android-flavour); the Frame is played with the native SteamOS build). The full design, build
|
but cannot show a picture there; the Frame is played with the native SteamOS build (the
|
||||||
walkthrough and current status live in [docs/quest-port.md](../docs/quest-port.md); this directory only
|
[README](../README.md#the-android-flavour)).
|
||||||
holds the Gradle project, its helper scripts, the game kit tooling
|
|
||||||
(`QuestGameKit.psm1`, `Build-QuestGame.ps1`), the on-headset build toolchain
|
The full design, build walkthrough and current status live in
|
||||||
(`Prepare-QuestToolchain.ps1`, `toolchain/`) and `nod-jni`.
|
[docs/quest-port.md](../docs/quest-port.md). This directory only holds the Gradle project, its
|
||||||
|
helper scripts, the game kit tooling (`QuestGameKit.psm1`, `Build-QuestGame.ps1`), the on-headset
|
||||||
|
build toolchain (`Prepare-QuestToolchain.ps1`, `toolchain/`) and `nod-jni`.
|
||||||
|
|
||||||
```powershell
|
```powershell
|
||||||
powershell -ExecutionPolicy Bypass -File android/Prepare-QuestDependencies.ps1 # stages the SDL3 3.4.4 AAR once
|
powershell -ExecutionPolicy Bypass -File android/Prepare-QuestDependencies.ps1 # stages the SDL3 3.4.4 AAR once
|
||||||
|
|||||||
@@ -35,8 +35,6 @@ The GX compatibility layer is built on top of [WebGPU](https://www.w3.org/TR/web
|
|||||||
abstraction layer. WebGPU allows targeting all major platforms simultaneously with minimal overhead. The WebGPU
|
abstraction layer. WebGPU allows targeting all major platforms simultaneously with minimal overhead. The WebGPU
|
||||||
implementation used is Chromium's [Dawn](https://dawn.googlesource.com/dawn/).
|
implementation used is Chromium's [Dawn](https://dawn.googlesource.com/dawn/).
|
||||||
|
|
||||||

|
|
||||||
|
|
||||||
### Building
|
### Building
|
||||||
|
|
||||||
See [docs/building.md](docs/building.md) for build instructions, CMake integration, and configuration options.
|
See [docs/building.md](docs/building.md) for build instructions, CMake integration, and configuration options.
|
||||||
|
|||||||
@@ -2,6 +2,9 @@
|
|||||||
|
|
||||||
This guide covers building **WiiCompiled** (base game) and **Retro Rewind** from source on macOS for Apple Silicon (`arm64`). Follow these instructions to compile the native executables directly.
|
This guide covers building **WiiCompiled** (base game) and **Retro Rewind** from source on macOS for Apple Silicon (`arm64`). Follow these instructions to compile the native executables directly.
|
||||||
|
|
||||||
|
This is upstream's desktop build and has no VR: OpenXR is not wired for macOS. To play on the Steam
|
||||||
|
Frame, follow the [README](../README.md#quick-start) instead.
|
||||||
|
|
||||||
> [!NOTE]
|
> [!NOTE]
|
||||||
> If you only want to build the base game (**WiiCompiled**), look for sections marked **`(Skip if only building WiiCompiled)`** to bypass Retro Rewind and online payload steps.
|
> If you only want to build the base game (**WiiCompiled**), look for sections marked **`(Skip if only building WiiCompiled)`** to bypass Retro Rewind and online payload steps.
|
||||||
|
|
||||||
|
|||||||
+25
-28
@@ -3,9 +3,10 @@
|
|||||||
This document is the design and build reference for the native Quest build. It
|
This document is the design and build reference for the native Quest build. It
|
||||||
complements `OPENXR.md`, which remains the specification for the presentation
|
complements `OPENXR.md`, which remains the specification for the presentation
|
||||||
policy, the virtual screen, the first-person camera and frame interpolation:
|
policy, the virtual screen, the first-person camera and frame interpolation:
|
||||||
all of that is shared, unchanged, between the Windows D3D12 product and the
|
all of that is shared, unchanged, between the PC products (Windows D3D12 and
|
||||||
Quest Vulkan product. What differs is everything below the stereo replay: the
|
Vulkan), the Steam Frame's native SteamOS product and the Quest Vulkan product.
|
||||||
graphics binding, the app shell and the platform glue.
|
What differs is everything below the stereo replay: the graphics binding, the
|
||||||
|
app shell and the platform glue.
|
||||||
|
|
||||||
## Sources of the design
|
## Sources of the design
|
||||||
|
|
||||||
@@ -1160,28 +1161,24 @@ or `EndAccess` errors); a black mirror too points at Aurora itself.
|
|||||||
|
|
||||||
## Known gaps and next steps
|
## Known gaps and next steps
|
||||||
|
|
||||||
- **Device bring-up.** Run on a Quest 3, capture logcat, fix what the runtime
|
- **Not yet verified on a headset:** stereo comfort and scale, the lifecycle (the Quest menu,
|
||||||
rejects. Likely first candidates: the exact `XR_KHR_vulkan_enable2` device
|
guardian and sleep pause the session through the ordinary `STOPPING`/`READY` events, and SDL's
|
||||||
extension negotiation, Dawn's begin/end layout reporting for AHardwareBuffer
|
surface loss goes through Aurora's existing Android paths, but neither has been exercised), and
|
||||||
imports, and swapchain format choice (`R8G8B8A8_SRGB` is expected).
|
a full race to the finish.
|
||||||
- **Performance.** The desktop product targets x86-64-v3; nothing has been
|
- **Performance.** Heavy tracks are still GPU-bound on a Quest 3 (Retro Rewind's SNES Ghost Valley 2
|
||||||
profiled on the XR2. The first run compiles every bundled pipeline recipe
|
at about 40 FPS at `render_scale` 1.0). `render_scale` defaults to 0.8 here (1.0 on PC); lower it
|
||||||
(about half a minute); later runs load Dawn's pipeline cache from `Cache/`
|
further if the compositor reports missed frames, live from the headset panel (VR → Render
|
||||||
next to `DATA`. `render_scale` defaults to 0.8 here (1.0 on
|
resolution). Foveation defaults to `medium`: at 0.8 it saves nothing measurable, above that 8 to
|
||||||
PC); lower it further if the compositor reports missed frames. It can be
|
22% of the eyes' GPU time ([Foveated rendering](#foveated-rendering)). The first run compiles
|
||||||
changed during a race from the headset panel (VR → Render resolution).
|
every bundled pipeline recipe (about half a minute); later runs load Dawn's pipeline cache from
|
||||||
Foveated rendering (above) is off by default: at `render_scale` 0.8 it saves
|
`Cache/` next to `DATA`.
|
||||||
nothing measurable, above that 8 to 22% of the eyes' GPU time.
|
- **Input.** Touch controllers have no D-pad, so the Wii Remote's D-pad is unbound on the Quest
|
||||||
- **Lifecycle.** Backgrounding (the Quest menu, guardian) pauses the session
|
(the Steam Frame's controller profile binds its left D-pad); remap in `Config.toml` if a mod needs
|
||||||
through the ordinary `STOPPING`/`READY` events; SDL's Android surface loss is
|
it.
|
||||||
handled by Aurora's existing Android paths. Neither has been exercised.
|
- **Retro Rewind on the headset.** The launcher downloads and updates the pack (**Download Retro
|
||||||
- **Input.** D-pad (trick inputs) is not bound; remap in `Config.toml` or bind
|
Rewind** on Home) and can build the mod on the headset with the pack in place. Copying a pack by
|
||||||
the thumbstick directions in a follow-up. Haptics are wired but nothing calls
|
hand instead needs care: `adb push` cannot create directories inside an app's external files
|
||||||
them yet.
|
directory (`secure_mkdirs failed`), so push it to `Download` and copy it over on the device, then
|
||||||
- **Retro Rewind on the headset** runs from a kit-built library (below), but its game must be built
|
`chmod -R a+rX` it.
|
||||||
on a PC and its pack copied next to `DATA` by hand. `adb push` cannot create directories inside
|
- **Release signing and store packaging** are out of scope; `Build-Quest.ps1` produces debug-signed
|
||||||
an app's external files directory (`secure_mkdirs failed`), so push the pack to `Download` and
|
APKs for sideloading.
|
||||||
copy it over on the device, then `chmod -R a+rX` it. The launcher does not fetch or update the
|
|
||||||
pack, and cannot build the mod on the headset.
|
|
||||||
- **Release signing and store packaging** are out of scope; `Build-Quest.ps1`
|
|
||||||
produces debug-signed APKs for sideloading.
|
|
||||||
+26
-29
@@ -13,17 +13,14 @@ A project manifest (YAML) names the input DOL and pins its layout; everything el
|
|||||||
|
|
||||||
Translation is four commands:
|
Translation is four commands:
|
||||||
|
|
||||||
1. **`translate-recursive <entry-point> --project <manifest>`** - walks the call graph from the
|
1. **`translate-recursive <entry-point> --project <manifest>`** walks the call graph from the
|
||||||
entry point, decodes every reachable function, and emits C++ (plus JSON metadata describing
|
entry point, decodes every reachable function, and emits C++ (plus JSON metadata describing
|
||||||
what was emitted).
|
what was emitted).
|
||||||
|
2. **`generate-data-init --project <manifest>`** writes the embedded `.data`/`.rodata`/`.sdata`
|
||||||
2. **`generate-data-init --project <manifest>`** - writes the embedded `.data`/`.rodata`/`.sdata`
|
section initializer and `RuntimeConfig.h`.
|
||||||
section initializer and `RuntimeConfig.h`.
|
3. **`emit-build-shards --project <manifest>`** emits the CMake build graph (`shards.cmake`)
|
||||||
|
covering both generated sources and `runtime/src`.
|
||||||
3. **`emit-build-shards --project <manifest>`** - emits the CMake build graph (`shards.cmake`)
|
4. **CMake + Ninja with Clang** compiles `runtime/` plus the generated output into one executable.
|
||||||
covering both generated sources and `runtime/src`.
|
|
||||||
|
|
||||||
4. **CMake + Ninja with Clang** compiles `runtime/` plus the generated output into one executable.
|
|
||||||
|
|
||||||
Discovery is purely recursive from the entry point unless the manifest provides an optional
|
Discovery is purely recursive from the entry point unless the manifest provides an optional
|
||||||
`function_map` (one `hexaddr name` per line) that seeds additional function boundaries. Unsupported
|
`function_map` (one `hexaddr name` per line) that seeds additional function boundaries. Unsupported
|
||||||
@@ -37,7 +34,7 @@ See `projects/examples/generic-dol.yml` for a minimal manifest driven by `RECOMP
|
|||||||
| --- | --- |
|
| --- | --- |
|
||||||
| .NET 8 SDK | Builds and runs the translator. |
|
| .NET 8 SDK | Builds and runs the translator. |
|
||||||
| CMake ≥ 3.16 and Ninja | Configures and drives the native build. |
|
| CMake ≥ 3.16 and Ninja | Configures and drives the native build. |
|
||||||
| Clang / LLVM | The shipped build uses LLVM-MinGW targeting `x86-64-v3`. MSVC is not the tested path. |
|
| Clang / LLVM | The Windows build uses LLVM-MinGW targeting `x86-64-v3`; the Steam Frame build uses LLVM 22 for ARM64 (`Launcher/prepare-portable-tools.sh`). MSVC is not the tested path. |
|
||||||
|
|
||||||
Build the CLI once and invoke the assembly directly:
|
Build the CLI once and invoke the assembly directly:
|
||||||
|
|
||||||
@@ -48,28 +45,28 @@ $translator = 'translator/src/Translator.Cli/bin/Release/net8.0/Translator.Cli.d
|
|||||||
|
|
||||||
## Manifest essentials
|
## Manifest essentials
|
||||||
|
|
||||||
- `inputs.dol.path` - the DOL to translate; optional SHA-256 pinning rejects wrong revisions.
|
- `inputs.dol.path` - the DOL to translate; optional SHA-256 pinning rejects wrong revisions.
|
||||||
- `memory.base` / `size` - guest address space.
|
- `memory.base` / `size` - guest address space.
|
||||||
- `memory.sda_base` / `sda2_base` - the r13/r2 Small Data Area bases your DOL's boot code installs
|
- `memory.sda_base` / `sda2_base` - the r13/r2 Small Data Area bases your DOL's boot code installs
|
||||||
(`lis`/`ori` pairs in `__init_registers`). Required by any command that writes `RuntimeConfig.h`;
|
(`lis`/`ori` pairs in `__init_registers`). Required by any command that writes `RuntimeConfig.h`;
|
||||||
the translator does not guess them.
|
the translator does not guess them.
|
||||||
- `translation.function_map.path` - optional symbol map used as the discovery oracle.
|
- `translation.function_map.path` - optional symbol map used as the discovery oracle.
|
||||||
- `translation.allow_unsupported_instructions` - off by default; enabling it emits runtime traps
|
- `translation.allow_unsupported_instructions` - off by default; enabling it emits runtime traps
|
||||||
instead of failing, and such a build can never ship.
|
instead of failing, and such a build can never ship.
|
||||||
- `translation.entry_observer` - optional header, C symbol, and entry-point list for a read-only
|
- `translation.entry_observer` - optional header, C symbol, and entry-point list for a read-only
|
||||||
host observer. Its callback must accept `(uint32_t, const CpuContext*)`; the translator materializes
|
host observer. Its callback must accept `(uint32_t, const CpuContext*)`; the translator
|
||||||
the complete guest context before every direct or transitive path that can reach it.
|
materializes the complete guest context before every direct or transitive path that can reach it.
|
||||||
|
|
||||||
Relative paths resolve from `workspace_root`, which itself resolves from the manifest directory.
|
Relative paths resolve from `workspace_root`, which itself resolves from the manifest directory.
|
||||||
|
|
||||||
## Commands
|
## Commands
|
||||||
|
|
||||||
- `info [--project path]`
|
- `info [--project path]`
|
||||||
- `translate-recursive <address> --project path`
|
- `translate-recursive <address> --project path`
|
||||||
- `generate-data-init --project path`
|
- `generate-data-init --project path`
|
||||||
- `emit-base-manifest --project path`
|
- `emit-base-manifest --project path`
|
||||||
- `emit-build-shards --project path`
|
- `emit-build-shards --project path`
|
||||||
- `translate-mod --project path [--profile name] ...` - static Kamek/Pulsar module translation
|
- `translate-mod --project path [--profile name] ...` - static Kamek/Pulsar module translation
|
||||||
|
|
||||||
Any command prints its own option list with `--help`.
|
Any command prints its own option list with `--help`.
|
||||||
|
|
||||||
|
|||||||
Reference in new issue
Block a user