Docs: shorter, consistent copy

README is a short overview that links to the install guide; repeated
sections are said once; Share working recipe everywhere; the setup
script names the real buttons; a shorter notice, the same as the site's.
This commit is contained in:
spoopyghosty0 committed 2026-10-10 16:34:19 -04:00
1 parent 2c1149815d
commit 35462324bb
19 files changed
+396 -516

No files matched your search

+7 -8
View File
@@ -1,31 +1,30 @@
name: Problem report
description: A game or FramePort doesn't work (FramePort → "Report a problem…" fills this in and saves a diagnostics zip).
description: A game or FramePort doesn't work (FramePort fills this in: "Report a problem…").
title: "[Problem] "
labels: ["bug"]
body:
- type: markdown
attributes:
value: |
Please attach the **diagnostics zip** FramePort saved (drag it into the "Diagnostics" box below). It contains
logs, the recipe and device details with personal data removed — no game files. Without the app, it can be
read with `frameport diag inspect <zip>`.
Please attach the **diagnostics zip** FramePort saved: drag it into the "Diagnostics" box below. It holds logs
and device details with personal data removed, and no game files.
- type: input
id: game
attributes:
label: Game
description: Title — package id (version, engine / XR API); empty for app problems
description: Title and package name; leave empty for problems with FramePort itself
- type: textarea
id: description
attributes:
label: What happens?
description: What you did, what you expected, what you saw (in the headset, if it started)
description: What you did, what you expected and what happened
validations:
required: true
- type: textarea
id: findings
attributes:
label: Launch test / triage
description: Filled in by FramePort from the last launch test
label: Launch test
description: Filled in by FramePort
- type: textarea
id: recipe
attributes:
+11 -11
View File
@@ -1,32 +1,32 @@
name: Working configuration
description: Submit a recipe that works on the Steam Frame (FramePort → game menu → "Share working config…" fills this in).
title: "[Working config] "
name: Working recipe
description: Share a recipe that works on the Steam Frame (FramePort fills this in: game menu → "Share working recipe…").
title: "[Working recipe] "
labels: ["working-config"]
body:
- type: markdown
attributes:
value: |
Thanks! A maintainer reviews the recipe; once it's labelled `catalog-accepted`, a pull request adding it to
`catalog/games/` is opened automatically. Please don't paste game files or links to them.
Thanks! Once a maintainer accepts the recipe, it becomes built-in for everyone. Please don't share game files
or links to them.
- type: input
id: game
attributes:
label: Game
description: Title — package id (platform, version, engine / XR API)
description: Title and package name (e.g. Lucky's Tale — com.playful.LuckysTale)
validations:
required: true
- type: input
id: result
attributes:
label: Result
description: works or issues (+ the last headless launch test)
description: works or issues
validations:
required: true
- type: textarea
id: recipe
attributes:
label: Recipe
description: The catalog entry (catalog/games/<package>.yaml). Don't edit the package line.
description: Filled in by FramePort. Don't edit the package line.
render: yaml
validations:
required: true
@@ -34,16 +34,16 @@ body:
id: environment
attributes:
label: Environment
description: FramePort, tool and SteamOS versions
description: FramePort and SteamOS versions
- type: textarea
id: notes
attributes:
label: Notes
description: What you checked in the headset, known issues, anything unusual
description: What you checked in the headset and any known issues
- type: checkboxes
id: confirm
attributes:
label: Confirmation
options:
- label: I played the game in the headset with this recipe (headless launch tests can't check the picture).
- label: I played the game in the headset with this recipe.
required: true
+1 -1
View File
@@ -1,5 +1,5 @@
name: catalog-from-issue
# A maintainer adds the label `catalog-accepted` to a "Working configuration" issue → this opens a PR adding the
# A maintainer adds the label `catalog-accepted` to a "Working recipe" issue → this opens a PR adding the
# recipe to catalog/games/. Never runs for unlabelled issues; the issue text is only read by the validating script
# (never interpolated into shell commands). Needs Settings → Actions → "Allow GitHub Actions to create pull requests".
on:
+77 -127
View File
@@ -7,176 +7,125 @@
![Platforms](https://img.shields.io/badge/platforms-Windows%20%7C%20macOS%20%7C%20Linux-blue)
![Steam Frame](https://img.shields.io/badge/Steam%20Frame-supported-1b2838?logo=steam&logoColor=white)
Install games that target the Meta Quest, Android, or general PCVR onto your **Valve Steam Frame**. FramePort handles everything from uploading game files, setting up your Frame, injecting compatibility patches, and adding shortcuts to your Steam library. FramePort aims to be as simple as possible by taking advantage of the fact that the Steam Frame runs on Linux.
Install Quest games, Android apps, Linux apps and PC VR games on the **Valve Steam Frame**. FramePort sets up the
Frame, patches each game so it runs there, uploads it and adds it to your Steam library with artwork.
[![FramePort: library, one-click install, play, monitor](docs/images/tour-teaser.webp)](docs/media/frameport-tour.mp4)
▶ [Watch the full tour](docs/media/frameport-tour.mp4) · New to FramePort? [Watch the install tutorial](docs/media/frameport-install.mp4)
(about 90 seconds each, MP4; also attached to every release)
(about 90 seconds each)
> **Notice:** FramePort explicitly does NOT download, share, or unlock games. You must provide legally obtained game
> executables. Core features of FramePort simply download and wrap other published tools (see [Built on](#built-on))
> with patches provided by FramePort adding a hardware compatibility layer. This enables users to use games/apps legally
> purchased on sites like [SideQuest](https://sidequestvr.com/).
> **Notice:** FramePort doesn't download, share or unlock games. Use games you got legally, e.g. from
> [SideQuest](https://sidequestvr.com/). FramePort downloads published open-source tools (see [Built on](#built-on))
> and adds its own patches so games run on the Frame.
>
> FramePort is a proof of concept.
## Features
![Library](docs/images/library.png)
- **Painless setup:** one short command on the Frame. No root, no `sudo`, no password.
[What it changes](docs/FRAME_SETUP.md).
- **Type on Frame:** use your computer's keyboard on the Frame: in VR apps, Android apps, Steam and the desktop.
[More](#type-on-frame).
- **One click per game:** convert, patch, sign, upload, add to Steam with artwork, launch test. Artwork that can't be found automatically can be picked from the stores or replaced with your own images.
- **Per-game recipes:** a tested catalog plus detection rules; every patch explained in plain words.
- **FrameBridge:** FramePort's OpenXR adapter emulates what the Frame natively lacks (passthrough, room, controller models,
curved and 360° layers); game settings as simple switches.
- **Beyond Quest:** Android apps as windows, PC VR via Proton or Revive, Windows (non-VR) games via Proton, a Files
tab with drag and drop.
- **Linux apps:** install Linux apps (AppImage, a folder, or a zip/tar archive) on the Frame with a Steam
shortcut; arm64 builds run natively on SteamOS, x86_64 builds through Valve's FEX translator.
- **Install links:** "Install with FrameDrop" buttons on web pages (the one-click protocol of the FrameDrop
sideloader) and pasted links open in FramePort, which asks, downloads, adds and installs the build.
- **Screenshots tab:** the screenshots you took in the headset, sorted by game (matched by play time) and day;
view them and download them to your computer.
- **Live view tab:** watch what the headset shows, with sound, in a browser window on your computer.
- **Monitor tab:** the running game's frame rate, the Frame's load, temperatures, power and battery live, and its
processes, which you can end. [More](#monitor).
- **Self-updating** releases, redacted diagnostics, one-click problem reports and working-config sharing.
- **Easy setup:** one line in the Frame's terminal. No root, no password. [What it changes](docs/FRAME_SETUP.md).
- **One click per game:** patch, upload, add to Steam with artwork and test that it starts.
- **Recipes:** tested patches and settings for 90+ games; other games get suggested patches, each explained in
plain words.
- **Game settings:** sharpness, refresh rate, controllers, 360° video and mixed reality as simple switches.
- **More than Quest games:** Android apps in a window, Linux apps, PC VR games and Windows programs.
- **Install links:** "Install with FrameDrop" buttons on websites open in FramePort.
- **Your Frame from your PC:** Type on Frame (your keyboard on the Frame), Files, Screenshots, Live view (what the
headset shows, in your browser) and Monitor (frame rate, temperatures, battery, processes).
- **Updates itself**, and reports problems without personal data.
## Quick start
1. [Download](https://github.com/spoopyghosty0/frameport/releases/latest) and unzip the build for Windows, macOS
(Apple Silicon) or Linux, then start FramePort.
2. **Connect the Frame** (once):
1. In FramePort click **Steam Frame → Start setup**. Keep FramePort open; the Frame and your computer must be on
the same Wi-Fi (or see the USB cable option in the app).
2. On the Frame open the **SteamVR dashboard → Launch a program → Desktop**: the Linux desktop opens on a virtual
screen.
3. Open the app menu (bottom-left corner of that desktop) → **System → Konsole** (or search for Konsole).
4. Run `curl -sL spoopyghosty0.github.io/frameport/s | bash` (the same for every Frame; or copy it from the
[setup page](https://spoopyghosty0.github.io/frameport/setup/) in the Frame's browser). It finds FramePort and
shows a 4-digit code: click **Allow** in FramePort when it shows the same one. It then runs this
[bash setup script](bootstrap/bootstrap.sh). FramePort's **Use the setup command** gives a line with your PC's
address instead, for networks that block the search.
5. After a few seconds the desktop closes by itself (Steam restarts once); that's expected. If
Steam asks to install **Lepton**, confirm it. FramePort shows the Frame as connected within a minute. No
password needed.
3. **Add games → Scan a folder** with your game backups (APK + OBB, or PC VR game folders).
4. Open a game → **Install on Frame**, then play it from the Frame's Steam library.
Full guide, firewalls and troubleshooting: [docs/INSTALL.md](docs/INSTALL.md). Questions (e.g. how to lay out games
with OBB files): [docs/FAQ.md](docs/FAQ.md).
## Type on Frame
Typing in VR is painful, so FramePort turns your computer's keyboard into a keyboard for the Frame. Open **Type on
Frame** (its own tab in the sidebar), select a text field in the headset and type: searches, logins, chat, in any
app, in Steam or on the desktop. Paste longer text to type it in one go. Nothing to install: FramePort adds a virtual
keyboard on the Frame while the tab is open, without root.
![Type on Frame](docs/images/type-on-frame.png)
Unity apps whose text fields close the moment you select them on the Frame (no system keyboard there) get a per-game
fix, so Steam's on-screen keyboard and Type on Frame work in them too.
[Details](docs/INSTALL.md#typing-on-the-frame).
## Screenshots
Screenshots you take in the headset show up in FramePort's **Screenshots** tab, grouped by day and matched to the game
you were playing. Open one full size, step through them, and download single shots, a selection or all of them to
your computer.
![Screenshots](docs/images/screenshots.png)
![Screenshot viewer](docs/images/screenshot-viewer.png)
## Live view
The **Live view** tab streams what the headset shows, with its sound, to your computer: click **Start live view** and
it opens in your default web browser (full screen with a double-click; click **Sound on** to hear it, as browsers start
videos muted). Pick 360p to 1080p, or the headset view's full size. The picture comes from SteamVR's built-in headset
view on the Frame and is encoded there while you watch (about one CPU core), so stop it when you're done. It's black
while the headset sleeps.
## Monitor
The **Monitor** tab shows what the Frame is doing while it's open: the running game with its frame rate against the
display's refresh rate, CPU, graphics chip, memory, the hottest temperature with the fan speed, power draw and battery
time left, each with a 2-minute chart. **Show details** adds every CPU core, all temperature sensors, where the power
goes and the network. Below, the game's processes (or Steam's, or all of them) with their CPU, GPU and memory use:
right-click one to end it, or end the whole game. Programs that Steam, SteamVR or the desktop need are marked and ask
again. The Frame sends the numbers itself (about 1 % of one CPU core) and stops when you leave the tab.
Details for each: [Install and first steps](docs/INSTALL.md).
![Monitor](docs/images/monitor.png)
![Screenshots](docs/images/screenshots.png)
## Quick start
1. [Download](https://github.com/spoopyghosty0/frameport/releases/latest) the build for Windows, macOS (Apple
Silicon) or Linux, unpack it and start FramePort.
2. In FramePort click **Steam Frame → Start setup**. The Frame and your PC must be on the same Wi-Fi (or use a USB
cable).
3. On the Frame open the **SteamVR dashboard → Launch a program → Desktop**, then the app menu → **System →
Konsole**, and run:
```
curl -sL frameport.app/s | bash
```
4. Click **Allow** in FramePort when it shows the same 4-digit code as the Frame. Steam restarts once; if it asks to
install **Lepton** (Valve's Android runtime), confirm it.
5. **Add games → Scan a folder…** with your games, open one and click **Install on Frame**. Play it from the Frame's
Steam library.
Full guide, firewalls and troubleshooting: [Install and first steps](docs/INSTALL.md). How to lay out game folders:
[FAQ](docs/FAQ.md).
## Compatibility
If a game has already been tested with FramePort, it will automatically use the optimal game config. Otherwise, FramePort
will attempt to guess key patches. If you find a new config that works for an app you are testing, please consider submitting it to the community!
**[List of tested games](docs/GAMES.md)**
**Tested something? Share it.** In FramePort open the game → **…** → **Share working recipe…** (it fills in the
recipe for you) or **Report a problem…** (attaches a diagnostics zip with personal data removed). Without the app:
[share a working config](https://github.com/spoopyghosty0/frameport/issues/new?template=working-config.yml) · [report a problem](https://github.com/spoopyghosty0/frameport/issues/new?template=bug-report.yml). Shared configs become built-in recipes for everyone.
Tested games use their recipe (the patches and settings that work for them) automatically; for other games FramePort
suggests patches. See the [list of tested games](docs/GAMES.md). Got a game working? Share its recipe from the game's
**…** menu: [how](docs/INSTALL.md#share-a-recipe-or-report-a-problem).
## Compared with other tools
FrameDrop and Valve's own tools install an app as it is. FramePort differs in four ways most people decide on:
FrameDrop and Valve's own tools install an app as it is. FramePort differs in four ways:
- **Free and open source** (GPL-3.0): read every line, build it yourself, change it, share it. FrameDrop is free
(donationware) without published source.
- **Quest games that don't run on the Frame as they are** get converted to OpenXR and patched, with a tested recipe
for 100+ games. The others install the APK as it is.
- **Free and open source** (GPL-3.0). FrameDrop is free (donationware) without published source.
- **Quest games that don't run on the Frame as they are** get converted and patched, with a tested recipe for 90+
games. The others install the game unchanged.
- **Windows, macOS and Linux.** FrameDrop is for Windows.
- **Wi-Fi or a USB cable**: your home Wi-Fi, the Frame's own hotspot, or a cable. No pairing screen.
- **Wi-Fi or a USB cable**, and no **Pair new host** step.
<details>
<summary>All differences</summary>
| | **FramePort** | **FrameDrop** | **By hand with Valve's tools** |
|---|---|---|---|
| What does it cost, and can I see the code? | Free, open source (GPL-3.0) | Free (donationware), source not published | Free, from Valve |
| Which computer can I use? | Windows, macOS, Linux | Windows | Depends on the tool |
| How do I connect the Frame the first time? | Type one command in the Frame's Konsole; it turns on Developer Mode itself. No password | Turn on Developer Mode, then Settings → Developer → Pair new host | Turn on Developer Mode and pair, or start Lepton Development and use adb |
| Wireless or cable? | Wi-Fi, the Frame's hotspot, or a USB cable | Same Wi-Fi network | Wi-Fi pairing, or adb |
| Will a Quest game that doesn't run on the Frame work? | Converted (OVRPort: Meta's VR runtime → OpenXR) and patched for the Frame | Not mentioned: the APK must meet Lepton's requirements as it is (arm64, minSdk 30 or lower) | Installs the APK as it is |
| Does it know which fixes a game needs? | A tested recipe for 100+ games, updated without an app update | Not stated | No |
| Will the game be in my Steam library? | Yes, with artwork and tags | As a "Devkit Game" shortcut | As "Devkit Game: &lt;title&gt;" (Devkit Client); not with adb |
| Android apps, Linux apps, Windows programs? | All three: Android apps in a window, Linux arm64 and x86_64, Windows programs through Proton (installed for you) | All three: Lepton Flatscreen, Linux arm64 zips, Windows .exe through Proton (install Proton first) | Through the Devkit Client; 2D Android apps need a marker file |
| PC VR (Rift) games? | On your PC through Revive; SteamVR and OpenXR ones on the Frame through Proton | Not supported | Not supported |
| Do "Install with …" buttons on websites work? | Its own and FrameDrop's | FrameDrop's (it defined them) | No |
| What if a game doesn't start? | A launch test reads the logs and names the likely fix | A log viewer pulls the headset log | No help |
| Can I see and use the Frame from my computer? | Live view, Monitor, Files, Screenshots, Type on Frame | Not stated | No |
| Cost and source code | Free, open source (GPL-3.0) | Free (donationware), source not published | Free, from Valve |
| Runs on | Windows, macOS, Linux | Windows | Depends on the tool |
| First connection | One line in the Frame's terminal; it turns on Developer Mode itself. No password | Turn on Developer Mode, then **Pair new host** | Turn on Developer Mode and pair, or use Android's debug tool (adb) |
| Wireless or cable | Wi-Fi, the Frame's hotspot or a USB cable | Same Wi-Fi network | Wi-Fi, or adb |
| Quest games that don't run as they are | Converted and patched for the Frame | Installed as they are | Installed as they are |
| Knows which patches a game needs | Tested recipes for 90+ games, updated without an app update | Not stated | No |
| In the Steam library | Yes, with artwork and tags | As a "Devkit Game" shortcut | As "Devkit Game: &lt;title&gt;"; not with adb |
| Android apps, Linux apps, Windows programs | All three; Proton (runs Windows programs) is installed for you | All three; install Proton first | Yes; 2D Android apps need an extra file |
| PC VR games | On your PC; some also on the Frame | Not supported | Not supported |
| "Install with …" buttons on websites | Its own and FrameDrop's | FrameDrop's (it defined them) | No |
| A game doesn't start | A launch test reads the logs and suggests a patch | A log viewer | No help |
| Use the Frame from your PC | Live view, Monitor, Files, Screenshots, Type on Frame | Not stated | No |
</details>
Other tools as described on their own pages, checked 2026-10-09:
[FrameDrop about](https://framedropvr.com/about) · [how-to](https://framedropvr.com/how-to) ·
[install buttons](https://framedropvr.com/docs) · [Valve: loading games on Steam Frame](https://partner.steamgames.com/doc/steamhardware/steamframe/loadgames).
Something out of date? [Open an issue](https://github.com/spoopyghosty0/frameport/issues/new).
Out of date? [Report a problem](https://github.com/spoopyghosty0/frameport/issues/new).
## Built on
Most of the work is done by these projects:
[OVRPort](https://github.com/Android-XR-Bridge/OVRPort) (Quest → OpenXR, originally
[ovrport/app](https://github.com/ovrport/app)) · Valve Lepton, Proton and SteamVR ·
[Revive](https://github.com/LibreVR/Revive) · Mesa (Zink) · [Khronos OpenXR SDK](https://github.com/KhronosGroup/OpenXR-SDK)
· Eclipse Temurin, Android apksigner and NDK · [Flet](https://flet.dev) · OculusDB and Steam store data.
What FramePort adds itself: [docs/ARCHITECTURE.md](docs/ARCHITECTURE.md).
What FramePort adds: [Architecture](docs/ARCHITECTURE.md).
## Documentation
| | |
|---|---|
| [INSTALL.md](docs/INSTALL.md) | Install, connect, update, PC VR, files, problem reports |
| [FRAME_SETUP.md](docs/FRAME_SETUP.md) | What setup changes on the Frame, networks and firewalls, undoing it |
| [COMPATIBILITY.md](docs/COMPATIBILITY.md) | What runs and how well |
| [GAMES.md](docs/GAMES.md) | Tested games and how well they run |
| [PLAYBOOK.md](docs/PLAYBOOK.md) | Symptoms and fixes per game |
| [FRAME_RUNTIME.md](docs/FRAME_RUNTIME.md) | Steam Frame runtime facts |
| [ARCHITECTURE.md](docs/ARCHITECTURE.md) | How the code is organised |
| [CONTRIBUTING.md](CONTRIBUTING.md) | Code, recipes, translations |
| [Install and first steps](docs/INSTALL.md) | Install, connect, update, PC VR games, files, problem reports |
| [What the setup changes](docs/FRAME_SETUP.md) | What setup changes on the Frame, networks and firewalls, undoing it |
| [Compatibility](docs/COMPATIBILITY.md) | What runs and how well |
| [Tested games](docs/GAMES.md) | Tested games and how well they run |
| [FAQ](docs/FAQ.md) | Game folders and common questions |
| [Porting playbook](docs/PLAYBOOK.md) | Symptoms and fixes per game |
| [Steam Frame runtime reference](docs/FRAME_RUNTIME.md) | Facts about the Frame's runtime |
| [Architecture](docs/ARCHITECTURE.md) | How the code is organized |
| [Contributing](CONTRIBUTING.md) | Code, recipes, translations |
## Development
@@ -187,8 +136,9 @@ uv run frameport --help # command line
uv run pytest # tests
```
## AI Usage Notice
While I would like to program everything manually, I no longer have much free time for personal projects. As a result I make use of AI tools to make it significantly quicker to debug compatibility issues.
## AI usage
I don't have much free time for this project, so I use AI tools to debug compatibility problems faster.
## License
+7 -8
View File
@@ -30,13 +30,13 @@ user_systemd() {
say "FramePort setup for $(hostname) ($(. /etc/os-release; echo "$NAME $VERSION_ID"))"
say "Authorizing the FramePort app's key"
say "Letting FramePort log in"
key=$(curl -fsS "$PC_URL/key?code=$PAIR_CODE")
[[ "$key" == ssh-ed25519\ * ]] || { echo "Could not fetch the app's key from $PC_URL (is the app still open?)"; exit 1; }
[[ "$key" == ssh-ed25519\ * ]] || { echo "Couldn't reach FramePort at $PC_URL. Is it still open?"; exit 1; }
mkdir -p ~/.ssh && chmod 700 ~/.ssh && touch ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys
grep -qxF "$key" ~/.ssh/authorized_keys || echo "$key" >> ~/.ssh/authorized_keys
say "Configuring podman for Lepton"
say "Setting up Lepton's containers"
# rootless podman leaks one kernel keyring per container start; ~200 game launches would exhaust the quota
mkdir -p ~/.config/containers
grep -qs '^ *keyring *=' ~/.config/containers/containers.conf || printf '[containers]\nkeyring = false\n' >> ~/.config/containers/containers.conf
@@ -117,7 +117,7 @@ JOB
if [[ -f /etc/steamos-devkit-enabled ]]; then
say "Developer Mode is on"
bash "$JOB" finish "$PC_URL" "$PAIR_CODE" "$STEAM_CONFIG" "$DEVKIT_HELPER" 2>&1 | tee "$LOG"
say "Done. Return to FramePort on your PC: this Frame should now appear as connected."
say "Done. FramePort on your PC shows this Frame as connected."
exit 0
fi
@@ -126,9 +126,8 @@ if [[ ! -x "$DEVKIT_HELPER" || ! -f "$STEAM_CONFIG" ]] || \
! user_systemd systemd-run --user --collect --quiet --unit="frameport-setup-$$" \
bash -c 'bash "$0" "$@" >"$HOME/.cache/frameport-setup.log" 2>&1' \
"$JOB" devmode "$PC_URL" "$PAIR_CODE" "$STEAM_CONFIG" "$DEVKIT_HELPER"; then
echo "Couldn't turn it on automatically. Turn it on in Settings > System > Developer, then run this command again."
echo "Couldn't turn it on. Turn it on in Settings → System → Enable Developer Mode, then run this again."
exit 1
fi
echo "Steam restarts to turn it on. That closes the desktop in a few seconds and the Frame returns to its"
echo "normal view; setup finishes on its own. If Steam asks to install Lepton, confirm it."
echo "Then return to FramePort on your PC: the Frame appears as connected within a minute."
echo "Steam restarts and the desktop closes. Confirm Lepton if asked."
echo "Then check FramePort on your PC."
+12 -12
View File
@@ -1,7 +1,7 @@
#!/usr/bin/env bash
# FramePort setup from the project page: the same for every Frame and every PC, nothing to copy from the PC. Run in
# the Frame's desktop terminal (SteamVR dashboard -> Launch a program -> Desktop, then System -> Konsole):
# curl -sL spoopyghosty0.github.io/frameport/s | bash
# curl -sL frameport.app/s | bash
# with FramePort open on your PC at Steam Frame -> Connect. Options: --pc <address[:port]> (skip the search).
#
# What it does:
@@ -26,7 +26,7 @@ while [[ $# -gt 0 ]]; do
esac
done
for tool in curl python3; do
command -v "$tool" >/dev/null || { echo "This needs $tool, which SteamOS normally has. Use the setup command FramePort shows instead."; exit 1; }
command -v "$tool" >/dev/null || { echo "This needs $tool, which SteamOS normally has. Run the setup command FramePort shows instead."; exit 1; }
done
# FramePort PCs, one per line: name<TAB>address:port<TAB>words. Stdlib Python: avahi isn't always answering on the
@@ -168,14 +168,14 @@ if [[ -n "$PC" ]]; then
[[ "$PC" == *:* ]] || PC="$PC:${PORTS%% *}"
WORDS=""
else
echo "Looking for FramePort on your network (open Steam Frame > Connect in FramePort on your PC)..."
echo "Looking for FramePort on your network (in FramePort on your PC: Steam Frame → Start setup)..."
mapfile -t pcs < <(find_pcs)
if [[ ${#pcs[@]} -eq 0 ]]; then
echo
echo "FramePort wasn't found. Check that:"
echo " - FramePort is open on your PC, at Steam Frame > Connect"
echo " - the Frame and the PC are on the same Wi-Fi (or the Frame is plugged into the PC with a USB cable)"
echo "Or run the setup command FramePort shows there; it includes your PC's address."
echo " - FramePort is open on your PC, at Steam Frame → Start setup"
echo " - the Frame and the PC are on the same Wi-Fi (or connected with a USB cable)"
echo "Or run the setup command FramePort shows there (Use the setup command)."
exit 1
fi
pick=0
@@ -202,12 +202,12 @@ fi
nonce=$(python3 -c 'import secrets; print(secrets.token_hex(12))')
digits=$(python3 -c 'import hashlib, sys; print(f"{int(hashlib.sha256(sys.argv[1].encode()).hexdigest()[:8], 16) % 10000:04d}")' "$nonce")
reply=$(curl -fsS -G --data-urlencode "host=$(hostname)" --data-urlencode "nonce=$nonce" "http://$PC/hello") || {
echo "FramePort at $PC didn't answer. Is it still open at Steam Frame > Connect?"; exit 1; }
echo "FramePort at $PC didn't answer. Is it still open at Steam Frame → Start setup?"; exit 1; }
id=$(python3 -c 'import json, sys; print(json.loads(sys.argv[1])["id"])' "$reply")
WORDS=$(python3 -c 'import json, sys; print(json.loads(sys.argv[1]).get("words", ""))' "$reply")
say "On your PC, FramePort asks whether to set up this Frame"
printf ' Click Allow there if it shows the code \033[1;33m%s\033[0m (this PC: %s)\n' "$digits" "${WORDS:-?}"
say "FramePort on your PC asks to set up this Frame"
printf ' Click Allow there if it shows \033[1;33m%s\033[0m (PC: %s)\n' "$digits" "${WORDS:-?}"
tmp=$(mktemp)
trap 'rm -f "$tmp"' EXIT
code=""
@@ -217,10 +217,10 @@ for _ in $(seq 12); do # up to about 20 minutes
200) code=$(python3 -c 'import json, sys; print(json.load(open(sys.argv[1]))["code"])' "$tmp"); break ;;
202) continue ;;
403) echo "Not allowed on the PC. Nothing was changed on this Frame."; exit 1 ;;
*) echo "Lost FramePort at $PC (HTTP $status). Run this again, or use the setup command FramePort shows."; exit 1 ;;
*) echo "Lost FramePort at $PC (HTTP $status). Run this again, or run the setup command FramePort shows."; exit 1 ;;
esac
done
[[ -n "$code" ]] || { echo "Nobody allowed it in time. Run this again when you're at the PC."; exit 1; }
[[ -n "$code" ]] || { echo "Not allowed in time. Run this again when you're at your PC."; exit 1; }
say "Allowed. Running FramePort's setup from $PC"
say "Allowed. Running the setup from $PC"
curl -fsS "http://$PC/$code" | bash
+11 -20
View File
@@ -1,30 +1,21 @@
# Compatibility
The built-in catalog has tested settings for games, each marked as working, working with known issues, or not
running on the Frame: see the [list of tested games](GAMES.md) (recipes in [catalog/games](../catalog/games)).
Other games get suggested patches from detection rules; each suggestion states its reason, and every patch can be
switched on or off under **Customize**: described in plain words, with **Show technical details** for the exact
effect of each patch.
FramePort's catalog has a tested recipe (the patches and settings that work) for many games, each marked as working,
working with issues or not running: see the [list of tested games](GAMES.md). Other games get suggested patches,
each with its reason. Every patch can be switched on or off under **Customize** on the game's page.
Tried an untested game? Its page asks how it runs; **Share working recipe…** opens a prefilled GitHub issue so your
recipe can join the built-in catalog for everyone.
Got a game working? [Share its recipe](INSTALL.md#share-a-recipe-or-report-a-problem).
![Patches](images/patches.png)
| Kind of app | On the Steam Frame |
| Kind of game | On the Steam Frame |
|---|---|
| Meta Quest games (APK) | Translated to OpenXR (OVRPort) and patched for the Frame; run in Valve's Android runtime (Lepton) |
| Other Android VR apps using OpenXR (e.g. Pico builds) | Translated the same way; the other headset's own extensions and store services aren't available |
| Ordinary Android apps and games (no VR) | Installed unchanged and shown as a flat window in the headset |
| PC VR games (Windows; OpenXR, SteamVR or Oculus) | Run through Proton on the Frame (experimental), or on a Windows PC with SteamVR and streamed to the Frame; Oculus-only games use Revive |
| Can't run | 32-bit-only or x86-only APKs, Pico/HTC Wave SDK apps, Android XR apps, and games that check an Oculus licence (they need the Oculus app on a PC) |
| Quest games | Converted to OpenXR (the VR standard the Frame uses) by OVRPort and patched; they run in Lepton, Valve's Android runtime |
| Other Android VR apps using OpenXR (e.g. Pico builds) | Converted the same way; the other headset's own features and store services aren't available |
| Android apps without VR | Installed unchanged and shown as a window in the headset |
| PC VR games | On the Frame through Proton (experimental), or on your PC and streamed to the Frame: see [PC VR games](INSTALL.md#pc-vr-games) |
| Can't run | 32-bit-only or x86-only Android apps, apps for Pico's or HTC's own VR system, Android XR apps, and games that check their license through the Oculus app |
Automated launch tests confirm that a game starts; visuals can only be checked in the headset.
Automatic launch tests show that a game starts; only the headset shows whether it looks right.
![Steam Frame](images/frame.png)
The **Files** tab manages files on the Frame: upload videos, documents, mods or saves from the computer (buttons or
drag-and-drop), download, rename and delete (one entry or a selection), in the shared folders every game sees or in
one game's own storage.
![Files](images/files.png)
+9 -13
View File
@@ -1,9 +1,9 @@
# FAQ
## How should I lay out a game that has OBB files (an APK plus a data folder)?
## How should I lay out a game that has OBB files?
Give every game its own folder, put the APK in it, and put the game's data next to the APK in a folder named
after the game's **package name** (the name the `.obb` files contain, e.g. `com.Armature.VR4`):
Some Quest games come as an APK (the app file) plus `.obb` files (the game's data). Give every game its own folder,
put the APK in it and put the data in a folder named after the game's **package name** (e.g. `com.Armature.VR4`):
```
Games/ ← scan this folder (Add games → Scan a folder)
@@ -16,16 +16,12 @@ Games/ ← scan this folder (Add games → Scan
└── com.beatgames.beatsaber.apk ← games without OBBs: just the APK
```
- **Data folder name:** the package name (`com.Armature.VR4` above), or `obb`. FramePort uses the first of the two
that exists and isn't empty.
- **Everything in that folder is copied** to the game's `Android/obb/<package>/` on the Frame, subfolders included.
So games that ship raw data files instead of `.obb` files work the same way.
- **One game per folder.** Several APKs in one folder count as one game; FramePort uses the first and keeps the others
as alternates.
- **Data folder name:** the package name (`com.Armature.VR4` above) or `obb`.
- **Everything in that folder is copied** to the Steam Frame, subfolders included, so other data files work too.
- **One game per folder.** Several APKs in one folder count as one game.
- **Scanning:** pick the folder that contains the game folders (`Games/` above) to add them all, or one game's folder
to add just that game. FramePort looks up to 5 levels deep.
- **A single game:** Add games → Add an APK… works with a lone APK too. Its data is found when the data folder sits next
to the APK, named as above.
- **A single game:** **Add games → Add an APK…** also finds the data folder next to the APK.
Not sure of the package name? Look at the OBB file names: `main.<version>.<package name>.obb`. Or add the APK
first: the game's page shows the package name under **Details**.
Not sure of the package name? It's in the OBB file names (`main.<version>.<package name>.obb`), and the game's page
shows it under **Details**.
+43 -37
View File
@@ -1,59 +1,65 @@
# Frame setup: what changes, networks, undoing it
# What the setup changes
For the steps themselves see [INSTALL.md](INSTALL.md#connecting-the-steam-frame).
For the setup steps see [Install and first steps](INSTALL.md#connecting-the-steam-frame). This page lists what the
setup changes on the Steam Frame, how to undo it and what your network needs.
## What the setup changes
## Changes on the Frame
The setup command runs [`bootstrap/bootstrap.sh`](../bootstrap/bootstrap.sh), served by the app over your
local network. Everything it changes:
The setup runs [`bootstrap/bootstrap.sh`](../bootstrap/bootstrap.sh), which FramePort sends from your PC. It changes:
| Change | Where | How to undo |
|---|---|---|
| Turns on **Developer Mode** (only if it's off). Steam restarts once, which closes Desktop Mode; the rest of the setup finishes on its own as a user service (log: `~/.cache/frameport-setup.log`). | `"DevModeEnabled" "1"` in `~/.local/share/Steam/config/config.vdf` (old file kept as `config.vdf.before-frameport`), then Valve's own `steamos-polkit-helpers/steamos-devkit-mode --enable`. That helper enables the SSH server (`sshd`), the devkit service that makes the Frame findable on the network, the remote-desktop and debug services, and system crash dumps. | Settings → System → Developer → Developer Mode off. Valve's helper switches all of those services off again. |
| Lets the app's SSH key in. | One line ending in `frameport` in `~/.ssh/authorized_keys`. The folder and file are created if missing. | Delete that line. |
| Configures podman for Lepton. Rootless podman leaks one kernel keyring per container start, and after about 200 game starts every game fails. | `[containers]` / `keyring = false` in `~/.config/containers/containers.conf`. | Remove those lines. |
| Asks Steam to install **Lepton** (Valve's Android runtime, Steam app 3029110) if it's missing. You confirm it in Steam. | Steam library | Uninstall it in Steam. |
| Turns on **Developer Mode** if it's off. Steam restarts once, which closes the desktop; the rest finishes on its own (log: `~/.cache/frameport-setup.log`). | `"DevModeEnabled" "1"` in `~/.local/share/Steam/config/config.vdf` (old copy kept as `config.vdf.before-frameport`), then Valve's own Developer Mode helper. | Settings → System → **Enable Developer Mode** off. |
| Lets FramePort log in. | One line ending in `frameport` in `~/.ssh/authorized_keys`. | Delete that line. |
| Stops game starts from failing after about 200 launches (a limit in podman, the tool Lepton runs games with). | `[containers]` / `keyring = false` in `~/.config/containers/containers.conf`. | Remove those lines. |
| Asks Steam to install **Lepton** (Valve's Android runtime) if it's missing. You confirm it in Steam. | Steam library | Uninstall it in Steam. |
The script runs as your user: no root, no `sudo`, no password. The only system-level change, Developer Mode, is
made by Valve's own helper, the same one the Settings switch uses. If Developer Mode can't be turned on
automatically, the script asks you to turn it on in Settings → System → Developer and run the command again.
Valve's Developer Mode helper is the same one the Settings switch uses. It turns on remote login (SSH), the service
that makes the Frame findable on your network, remote desktop, debugging and crash dumps; turning Developer Mode off
turns them all off again.
Nothing else on the system is touched: no packages, no read-only-filesystem changes, no polkit rules. The script
also leaves two files: `~/.cache/frameport-setup.sh` (the part that runs on its own) and its log.
The script runs as your user: no root, no `sudo`, no password. Nothing else on the system changes. It also leaves two
files: `~/.cache/frameport-setup.sh` (the part that finishes on its own) and its log.
**Later, the app adds** (all as your user, no root, no `sudo`):
- FramePort's helper in `~/.local/share/frameport/`;
If Developer Mode can't be turned on automatically, the script asks you to turn it on in Settings → System →
**Enable Developer Mode** and run the setup line again.
**Later, FramePort adds** (as your user):
- its helper in `~/.local/share/frameport/`;
- the games, each with a launcher and its data in `~/Applications/quest-frame/<package>/`;
- their Steam library entries and artwork (`shortcuts.vdf` + `config/grid/`);
- for PC VR games: an OpenXR layer (`~/.local/share/openxr/1/api_layers/explicit.d/XR_APILAYER_FRAMEPORT_timefix.json`)
and, when the first PC VR game is installed, Valve's ARM64 Proton and its Steam Linux Runtime (Steam downloads them;
Steam restarts once).
and Valve's ARM64 Proton with its Steam Linux Runtime (Steam downloads them and restarts once).
**Settings → Uninstall FramePort → Also remove from the Frame** deletes the games, their Steam entries, the helper
folder, the OpenXR layer and the setup script's files. Developer Mode, the SSH key line, the podman setting, Lepton
and Proton stay. Undo them as shown above or in Steam.
folder, the OpenXR layer and the setup files. Developer Mode, the login line, the podman setting, Lepton and Proton
stay: undo them as shown above.
## Network and firewalls
The setup is the only time the Frame connects to your computer: it downloads the script from FramePort on TCP port
8765 (8766/8767 if taken), only while the setup page is open and for at most 30 minutes. With the setup line from
the project page (`curl -sL spoopyghosty0.github.io/frameport/s | bash`, the script is
[bootstrap/setup.sh](../bootstrap/setup.sh)) the Frame first finds FramePort: FramePort announces itself over mDNS
(`_frameport-pair._tcp`, with this computer's name and two words, never the code) while that page is open; without
an answer the script tries the USB cable's address and the Frame's network on port 8765. It then asks FramePort, and
only after you click **Allow** (both sides show the same 4 digits) does FramePort hand over the one-time code, which
fetches the same setup script as the typed command. Everything
else goes from the computer to the Frame. If the command just says "timed out", the setup page shows what is likely
blocking it after about 45 seconds:
The setup is the only time the Frame connects to your PC. It downloads the setup script from FramePort on TCP port
8765 (8766 or 8767 if taken), only while the setup page is open and for at most 30 minutes. Everything else goes
from your PC to the Frame.
- **Windows:** allow FramePort (or Python, when running from source) when Windows asks. On a network Windows treats as
**Public** it stays blocked unless you allow public networks; set your home network to Private in Windows'
network settings instead.
How the setup line finds your PC:
1. FramePort announces itself on your network while the setup page is open (with your PC's name and two words, never
the code). If nothing answers, the setup line tries the USB cable's address and then scans the Frame's network.
2. Both sides show the same 4 digits. Nothing happens until you click **Allow** in FramePort.
3. FramePort then hands over the one-time code, and the Frame downloads the same setup script as the setup command.
The setup line's script is [bootstrap/setup.sh](../bootstrap/setup.sh). If the setup just says "timed out", the
setup page shows what is likely blocking it after about 45 seconds:
- **Windows:** allow FramePort when Windows asks. On a network Windows treats as **Public** it stays blocked; set
your home network to Private in Windows' network settings.
- **macOS:** with the firewall on (System Settings → Network → Firewall), allow incoming connections for FramePort
when asked.
- **Linux:** firewalld: `sudo firewall-cmd --add-port=8765/tcp` (until the next restart). ufw:
`sudo ufw allow 8765/tcp`, afterwards `sudo ufw delete allow 8765/tcp`.
- **WSL:** Windows' Hyper-V firewall blocks connections into WSL without asking. FramePort adds a temporary rule for
the setup ports (one admin prompt) and removes it again when setup is done or after 35 minutes. WSL must use
mirrored networking: `networkingMode=mirrored` under `[wsl2]` in `%UserProfile%\.wslconfig`, then `wsl --shutdown`.
- Or skip the setup command and use the devkit pairing (see [INSTALL.md](INSTALL.md#connecting-the-steam-frame)): it needs no connection into your computer.
- **WSL** (FramePort's Linux version on Windows): Windows blocks connections into WSL without asking. FramePort
adds a temporary firewall rule (one admin prompt) and removes it when setup is done or after 35 minutes. WSL must
share Windows' network: `networkingMode=mirrored` under `[wsl2]` in `%UserProfile%\.wslconfig`, then
`wsl --shutdown`.
- Or skip the setup line and use **Pair new host** (see [Install and first steps](INSTALL.md#connecting-the-steam-frame)):
it needs no connection into your PC.
+2 -2
View File
@@ -1,7 +1,7 @@
# Tested games
Games tested on the Steam Frame with FramePort's recipes. Games not listed here may work too: FramePort suggests patches for them, and a working recipe can be shared from the app (**Share working recipe…**).
Tested a game? [Share a working config](https://github.com/spoopyghosty0/frameport/issues/new?template=working-config.yml) or [report a problem](https://github.com/spoopyghosty0/frameport/issues/new?template=bug-report.yml) (in the app: the game's **…** menu does both and fills in the details).
Games tested on the Steam Frame with FramePort. Games not listed may work too: FramePort suggests patches for them. Got one working? [Share its recipe](INSTALL.md#share-a-recipe-or-report-a-problem).
Generated from [catalog/games](../catalog/games) by `scripts/compat_list.py`.
| Game | Platform | Status | Notes |
+185 -238
View File
@@ -1,312 +1,259 @@
# Installing FramePort
# Install and first steps
▶ **[Watch the install tutorial](media/frameport-install.mp4)** (about 90 seconds, MP4; also attached to every
release as `FramePort-install.mp4`): from the download to the first game on the Frame.
▶ **[Watch the install tutorial](media/frameport-install.mp4)** (about 90 seconds): from the download to the first
game on the Steam Frame.
[![The install tutorial](media/frameport-install.jpg)](media/frameport-install.mp4)
Download the archive for your computer from the [latest release](https://github.com/spoopyghosty0/frameport/releases/latest)
and extract it anywhere. No installer or admin rights are needed. On first start FramePort downloads its Java
runtime, the OVRPort CLI and apksigner into its data folder (Settings → Tools shows them).
Download the file for your PC from the [latest release](https://github.com/spoopyghosty0/frameport/releases/latest)
and unpack it anywhere. No installer or admin rights are needed.
| Computer | Archive | Start |
| Your PC | Download | Start |
|---|---|---|
| Windows 10/11 (x64) | `FramePort-windows-x64.zip` | `FramePort.exe` |
| macOS (Apple Silicon) | `FramePort-macos-arm64.zip` | `FramePort.app` |
| Linux (x64, GTK 3; Ubuntu 22.04 or newer) | `FramePort-linux-x64.tar.gz` | `FramePort/FramePort` |
| Linux (ARM64, GTK 3; Ubuntu 22.04 or newer) | `FramePort-linux-arm64.tar.gz` | `FramePort/FramePort` |
| Command line only (Python 3.11+) | `frameport-<version>-py3-none-any.whl` | `frameport --help` |
| Linux (x64, Ubuntu 22.04 or newer) | `FramePort-linux-x64.tar.gz` | `FramePort/FramePort` |
| Linux (ARM64, Ubuntu 22.04 or newer) | `FramePort-linux-arm64.tar.gz` | `FramePort/FramePort` |
The command-line version installs from the wheel's release link with `uv tool install <link>` (or pipx / pip).
On first start FramePort downloads the tools it uses (Settings → Tools shows them).
## First launch
The builds are signed with a free self-signed certificate (Windows) and an ad-hoc signature (macOS), so the first
start shows a warning:
FramePort isn't signed with a paid certificate, so the first start shows a warning:
- **Windows:** "Windows protected your PC" → **More info** → **Run anyway**. Optional: import
`FramePort-selfsigned.cer` (attached to each release) into *Trusted Root Certification Authorities* (Current User) to
show FramePort as the publisher; the certificate can only sign code. Remove it with `certmgr.msc`.
- **macOS:** right-click `FramePort.app` → **Open** → **Open** (once), or `xattr -dr com.apple.quarantine FramePort.app`.
- **Linux:** `tar xzf FramePort-linux-x64.tar.gz && ./FramePort/FramePort` (ARM64: `FramePort-linux-arm64.tar.gz`).
- **Windows:** "Windows protected your PC" → **More info** → **Run anyway**.
- **macOS:** right-click `FramePort.app` → **Open** → **Open** (once).
- **Linux:** `tar xzf FramePort-linux-x64.tar.gz && ./FramePort/FramePort`.
## Connecting the Steam Frame
The Frame and the computer must be on the same network (or connected with a USB cable, below).
The Frame and your PC must be on the same network (or connected with a [USB cable](#with-a-usb-cable)).
1. In FramePort open **Steam Frame** and click **Start setup**. Keep that page open: FramePort announces itself on
your network while it is.
2. First time only, on the Frame:
1. Open the **SteamVR dashboard → Launch a program → Desktop**: the Linux desktop opens on a virtual screen.
2. Open the app menu (bottom-left corner of that desktop) → **System → Konsole** (or search for Konsole).
3. Run the same line on every Frame (on-screen keyboard or any USB/Bluetooth keyboard), then press **Enter**:
1. In FramePort open **Steam Frame** and click **Start setup**. Keep that page open.
2. On the Frame, first time only:
1. Open the **SteamVR dashboard → Launch a program → Desktop**. The Frame's desktop opens.
2. Open the app menu (bottom left) → **System → Konsole**, the Frame's terminal.
3. Type this setup line and press **Enter** (on-screen keyboard or any USB or Bluetooth keyboard):
```
curl -sL spoopyghosty0.github.io/frameport/s | bash
curl -sL frameport.app/s | bash
```
No keyboard at hand? Open [the setup page](https://spoopyghosty0.github.io/frameport/setup/) in Chromium on the
Frame (in Steam, the **+** on the taskbar installs it), tap **Copy**, then paste it into Konsole.
4. The terminal finds FramePort and shows a 4-digit code. FramePort shows the same code with **Allow**: click it.
Nothing changes on the Frame before that.
5. After a few seconds the desktop closes by itself (Steam restarts once); that's expected. If
Steam asks to install **Lepton** (Valve's Android runtime), confirm it.
No keyboard? Open [the setup page](https://frameport.app/setup/) in Chromium on the Frame,
tap **Copy** and paste it into Konsole.
4. Konsole shows a 4-digit code. When FramePort shows the same code, click **Allow**. Nothing changes on the Frame
before that.
5. Steam restarts once and the desktop closes. If Steam asks to install **Lepton** (Valve's Android runtime),
confirm it.
FramePort connects by itself within a minute. No password is needed. The command lets FramePort in and turns on
**Developer Mode** (which includes SSH); everything it changes is listed in [FRAME_SETUP.md](FRAME_SETUP.md).
3. Later starts: a Frame in Developer Mode appears in the list and FramePort connects to it automatically. (If you
turn Developer Mode off in Settings → System → Developer, turn it on again there.)
FramePort connects within a minute. No password is needed. The setup turns on **Developer Mode**;
[What the setup changes](FRAME_SETUP.md) lists everything.
**The setup command (no search):** **Use the setup command** shows a line with your computer's address and a one-time
code instead, such as `curl -fsS 192.168.1.20:8765/1a2b3c4d | bash`. It needs neither the project page nor the
network search (for networks that block mDNS); it runs the same setup.
Later, FramePort connects to the Frame by itself. If you turn Developer Mode off (Settings → System → **Enable
Developer Mode**), turn it on again there.
**Without Konsole, without a click on the PC:** turn on Developer Mode yourself (Settings → System → Developer),
then open Settings → Developer → **Pair new host** on the Frame. FramePort, open on your PC, notices the Frame by
itself and sends its pairing request; approve FramePort in the headset and it connects (Valve's own devkit pairing; it
only sends this computer's key to the Frame). Switch it off on the Steam Frame page (**Pair Frames in Developer Mode
automatically**) if you don't want FramePort to ask Frames on your network. Install
Lepton from the Steam Frame page afterwards if it's missing.
**Setup command:** if your network blocks FramePort's search, click **Use the setup command**. It shows a line with
your PC's address and a one-time code, e.g. `curl -fsS 192.168.1.20:8765/1a2b3c4d | bash`. Run it in Konsole instead.
**Without Konsole:** turn on Developer Mode yourself (Settings → System → **Enable Developer Mode**), then open
Settings → Developer → **Pair new host** on the Frame. FramePort finds the Frame and asks to connect; approve it in the
headset. Install Lepton from FramePort's Steam Frame page afterwards if it's missing.
### With a USB cable
For networks that block the setup (guest Wi-Fi, firewalls, discovery not working), and for faster uploads:
A cable works on networks that block the setup, and uploads are faster (about 37 MB/s, three times typical Wi-Fi).
1. On the Frame, turn on **Developer Mode** (Settings → System → Developer Mode). The Frame's USB network only exists
in Developer Mode.
2. Connect the Frame's USB-C port to the computer.
3. In FramePort: **Steam Frame → Set up with a USB cable**. FramePort detects the cable and shows the setup command,
which reaches the computer over the cable. Already set up? It connects over the cable right away.
1. On the Frame, turn on Developer Mode (Settings → System → **Enable Developer Mode**). The cable only works in
Developer Mode.
2. Connect the Frame's USB-C port to your PC. No driver is needed.
3. In FramePort click **Steam Frame → Set up with a USB cable** and follow the steps.
The cable needs no driver on Windows 10/11, macOS or Linux, and the computer gets an address from the Frame
automatically. Uploads use the cable whenever it's plugged in (about 37 MB/s, ~3× typical Wi-Fi), even when FramePort
connected over Wi-Fi. Unplug it any time: FramePort finds the Frame on Wi-Fi again by itself.
Uploads use the cable whenever it's plugged in. Unplug it any time: FramePort finds the Frame on Wi-Fi again.
### Firewalls
If the setup command only says "timed out", a firewall on your computer blocks the Frame; the setup page
says which after about 45 seconds. Details per system: [FRAME_SETUP.md](FRAME_SETUP.md#network-and-firewalls).
If the setup only says "timed out", a firewall on your PC blocks the Frame. After about 45 seconds the setup page
says which. Details: [Network and firewalls](FRAME_SETUP.md#network-and-firewalls).
## Running FramePort on the Frame (experimental)
FramePort can run on the Steam Frame itself, without a PC: in **Desktop Mode**, download
`FramePort-linux-arm64.tar.gz`, unpack it (`tar xzf FramePort-linux-arm64.tar.gz`) and start `FramePort/FramePort`.
Turn on **Developer Mode** first (Steam → Settings → System); FramePort then manages "This Frame" directly, with
no pairing. Games are added to the Steam library when you go back to **Gaming Mode** (Steam has to restart for it,
which would end Desktop Mode). This is new: please report anything odd with **Report a problem**.
FramePort can run on the Frame itself, without a PC:
1. Turn on Developer Mode (Settings → System → **Enable Developer Mode**).
2. In Desktop Mode, download `FramePort-linux-arm64.tar.gz`, unpack it (`tar xzf FramePort-linux-arm64.tar.gz`) and
start `FramePort/FramePort`.
Games appear in the Steam library when you go back to Gaming Mode. Please report anything odd with **Report a
problem…**.
## Installing games
- **Install on Frame** on a game's page (or select several in the Library and install them together). Installs run
one after another in the background; **Activity** shows the current one at the top.
- **Update all** reinstalls every game whose build changed (e.g. after a FramePort update). Questions that need an
answer (e.g. Oculus games that can't run on the Frame) are asked once, for all games.
- If the Frame goes to sleep, turns off or leaves the Wi-Fi, the queue **waits** and continues once it's back; uploads
pick up where they stopped. While installs run, FramePort keeps the Frame from going to sleep. Before a large batch
it checks the Frame has enough free space.
- **microSD card / other drives:** the **Steam Frame** page's **Storage** section lists the Frame's drives and sets
where new games go (**Install new games to**). Games go into a `FramePort` folder on the card. To move a game that's
installed already, right-click it → **Move to…** (the game must be closed; saves, settings and the Steam entry stay).
A game on the card only starts while the card is inserted (FramePort then says "SD Card not inserted"). Cards
formatted as FAT, exFAT or NTFS can't hold games: format the card in SteamOS first.
- Your own game files are never changed. The converted copy is temporary: it's removed once the game is on the Frame
(Settings → Installing: keep them, or remove all now).
- **Game settings…** (game menu or the Steam Frame page): sharpness, refresh rate, controllers, menus, 360° video and
mixed-reality options in plain words, only those that matter for the game. Changes are kept with the game and,
when it's installed, used the next time it starts.
- Ordinary Android apps (no VR) are installed unchanged and shown as a flat window in the headset. Android's
back/home/recents buttons are hidden by default (patch **Hide Android's navigation bar**). If FramePort guesses
wrong (a phone app shows nothing in the headset, or a VR app opens as a flat window), choose **VR** or **Flat
window** under **Show as VR or as a flat window** in the game's **Customize** section, then **Update on Frame**.
- **Add games → Add a Windows program…** adds a single Windows program; the Frame runs it through Proton (as a
window unless it is a VR game). A program sitting in Downloads, the home folder or a drive root is copied on its
own first, so the install doesn't upload everything next to it.
- In the packaged app you can also **drag files onto the Library**: APKs, Linux apps (AppImage, `.zip`/`.tar.gz`),
Windows programs (`.exe`), folders, or a FrameDrop manifest (`.json`).
### Install links ("Install with FrameDrop" buttons)
Some developers put an **Install with FrameDrop** button on their site (the one-click protocol of the FrameDrop
sideloader, documented at framedropvr.com/docs). FramePort understands the same links:
- **Clicking a button** opens FramePort (or the window that's already open) on Windows and Linux. FramePort shows
the title, the files, their size and whether a checksum is given, and asks before it downloads anything. Then it
downloads the build, adds it to your library and starts the usual install on the Frame. If no Frame is connected,
the game is added now and installs once the Frame is back.
- **Add games → Add from a link…** takes the button's address (right-click → Copy link), a `framedrop://` or
`frameport://` link, a manifest (`.json`) or a direct link to an APK, a Linux build or a Windows program. Use it on
macOS, where web pages can't hand links to FramePort yet.
- **Settings → Install links** has one switch for `framedrop://` links (the buttons) and one for FramePort's own
`frameport://` links. Both are on by default. If FrameDrop is installed too and already opens `framedrop://`
links, FramePort leaves them to it; **Use FramePort for these links** takes them over (turn the switch off to give
them back).
- **For developers:** a FrameDrop manifest works as it is
(`{"schema": "framedrop.install/v1", "name": "…", "files": [{"url": "https://…", "sha256": "…"}]}`). FramePort
also reads an optional `"frameport": {"description": "…", "icon": "https://….png"}` object (FrameDrop ignores
it): the install question then shows the icon and description, and they become the game's icon and "About this
game" text when no store has them. For your page there's an "Install with FramePort" button:
[INSTALL_BUTTON.md](INSTALL_BUTTON.md). Without a manifest (a bare file link) FramePort guesses the title from the
file name and replaces it with the app's own name once it's downloaded.
- Only `https://` links to public servers are used (plain `http://` only on this PC, for testing); links with a
user name or password, or pointing into your local network, are refused. Only install from sites you trust.
![Game page](images/game.png)
Each game has **Game settings** in plain words (sharpness, refresh rate, controllers, menus, 360° video, mixed
reality), showing only what matters for that game. Changes are kept with the game and reach the Frame right away.
- **Install on Frame** on a game's page, or select several games in the Library and install them together. Installs
run in the background; **Activity** shows the current one.
- **Update all** updates every game whose build changed, e.g. after a FramePort update.
- If the Frame sleeps or leaves the Wi-Fi, installs wait and continue when it's back. While installs run, the Frame
stays awake.
- Your own game files are never changed. The patched copy is deleted once the game is on the Frame (Settings →
Installing).
- In the downloaded app you can also **drag files onto the Library**: games, Linux apps, Windows programs or folders.
**Game settings…** (in the game's menu) shows the settings that matter for that game in plain words: sharpness,
refresh rate, controllers, menus, 360° video and mixed reality. Changes are used the next time the game starts.
![Game settings](images/game-settings.png)
### microSD cards and other drives
- The **Steam Frame** page's **Storage** section sets where new games go (**Install new games to**).
- To move an installed game, right-click it → **Move to…**. The game must be closed; saves and the Steam entry stay.
- A game on a card only starts while the card is inserted.
- Cards formatted as FAT, exFAT or NTFS can't hold games: format the card in SteamOS first.
### Android apps and Windows programs
- Android apps without VR are installed unchanged and shown as a window in the headset. If one shows nothing (or a
VR app opens as a window), open **Customize** on the game's page, set **Show as VR or as a flat window** and click
**Update on Frame**.
- **Add games → Add a Windows program…** adds a single Windows program. The Frame runs it as a window through Proton
(Valve's tool for running Windows programs).
### Install links ("Install with FrameDrop" buttons)
Some websites have an **Install with FrameDrop** button. FramePort understands these buttons too:
- **Click a button** on Windows or Linux: FramePort opens, shows what it would download and asks first. Then it adds
the game and installs it on the Frame.
- **Add games → Add from a link…** takes a button's address (right-click → Copy link) or a direct download link. Use
it on macOS, where buttons can't open FramePort yet.
- **Settings → Install links** turns the buttons on or off. If FrameDrop is installed too, it keeps its buttons until
you click **Use FramePort for these links**.
- Only `https://` links to public servers are used. Only install from sites you trust.
Website owners: see [Install button](INSTALL_BUTTON.md).
## Typing on the Frame
- **Type on Frame** (its own tab in the sidebar; also on the Steam Frame page): while the tab is
open, this computer's keyboard works as a keyboard plugged into the Frame. Select a text field in the headset (in
an app, Steam or the desktop) and type; Esc and shortcuts go to the Frame too. Paste longer text into the box to
type it in one go (US keyboard layout). Opening another tab disconnects the keyboard.
- **Steam's on-screen keyboard** opens for text fields of apps shown as a window (2D apps, and VR apps with
**Show the app's Android window**). Steam lists that window as **Gamescope** (the Frame's display compositor);
leave it open: it's what receives the typing, the VR view isn't affected.
- **Unity apps whose text fields close at once** (a caret flashes, nothing can be typed): FramePort suggests
**Make Unity text fields work** for them. The first time, it downloads Cpp2IL (a tool that finds the right spot in the
game's code, ~17 MB). Games added before this version: open the game's menu → **Analyze again**, then reinstall.
- **Type on Frame** (in the sidebar): while this tab is open, your PC's keyboard types on the Frame. Select a text
field in the headset and type, or paste longer text into the box.
- **Steam's on-screen keyboard** works in apps shown as a window. Steam lists that window as **Gamescope**: leave it
open.
- **Unity games whose text fields close at once:** FramePort suggests the patch **Make Unity text fields work**.
Games added before this patch existed: open the game's menu → **Analyze again**, then reinstall.
## Watching the Frame (Monitor)
![Type on Frame](images/type-on-frame.png)
- **Monitor** (its own tab in the sidebar) shows live what the Frame is doing while the tab is open: the running game
with its frame rate (Quest games), CPU, graphics chip, memory, the hottest temperature with the fan speed, power
draw and battery time left, each with a 2-minute chart. **Show details** adds every CPU core, all temperature
sensors, where the power goes and the network.
- **Processes**: **Game** (default) lists the running game's processes, **Steam & SteamVR** and **All** show more.
Right-click a process (or use **⋯**) to end it, force-kill it or end its whole game; **End game** on the game card
closes the game the way Steam's Exit game does. A lock marks programs whose end would close Steam, SteamVR or the
desktop: FramePort asks again before ending those.
- The numbers come every second (or every 2/5 s) and cost the Frame about 1 % of one CPU core; nothing keeps
running on the Frame after you leave the tab.
## Watching the Frame
- **Monitor** (in the sidebar) shows the running game's frame rate, CPU, graphics, memory, temperature, power and
battery, each with a 2-minute chart. **Show details** shows more.
- Under **Processes**, right-click a process to end it. **End game** closes the game like Steam's Exit game. A lock
marks programs Steam or the desktop needs; FramePort asks again before ending those.
- **Live view** streams what the headset shows, with sound, to your browser. It uses about one CPU core of the Frame,
so stop it when you're done.
- **Screenshots** shows the screenshots you took in the headset, sorted by game and day, to view or download.
## Updating
**Game configs** (the tested recipes in the catalog) update by themselves: FramePort checks GitHub every 6 hours for
newly confirmed or fixed configs and uses them without a FramePort update; a game whose recipe changed then shows
**Update on Frame**. Configs that need a newer FramePort are skipped until you update. Settings → Data shows the last
check (**Check now**) and turns this off.
FramePort checks for a new version at start and every 6 hours. When there is one, the Library shows **Update now**:
FramePort downloads it, checks it, restarts and keeps your games and settings. **Later** skips that version.
FramePort checks for a new release at start and every 6 hours (it only downloads the release information). When one
exists, the Library shows **Update now**: FramePort downloads the new version, verifies it against the release's
`SHA256SUMS.txt` (on Windows also the signature), restarts and opens as the new version. Games, settings, signing keys
and the Frame connection are kept. Running installs finish first. **Later** skips that version.
Settings → **Updates**: turn the check off, or turn on **Install updates automatically** (downloads in the background,
installs at the next start). If FramePort's folder isn't writable, **Update now** opens the release page instead. The
update log is `logs/update.log` in the data folder.
**Dev builds:** when you're asked to test a fix before it's released, use Settings → Updates → **Install the latest
dev build…**. It shows what to test, then installs like an update (same checks). Dev builds are less tested; the next
release is offered to you as a normal update.
Command line: `frameport update` (`--check` only checks, exit code 10 = update available; `--yes` doesn't ask).
`FRAMEPORT_NO_UPDATE_CHECK=1` turns all checks off.
- Settings → **Updates** turns the check off or turns on **Install updates automatically**.
- **Recipes** (the tested patches and settings for each game) update by themselves. A game whose recipe changed shows
**Update on Frame**.
- **Dev builds:** if you're asked to test a change before its release, use Settings → Updates → **Install the latest
dev build…**. The next release then arrives as a normal update.
## PC VR games
PC VR games are Windows VR games (OpenXR, SteamVR or Oculus). Scan a folder of them (one folder per game) or use
**Add games → Add a PC game folder…**. FramePort finds the game's program and asks when there is more than one
candidate. **Already patched** on a game page installs a copy unchanged. Oculus-only games need Revive: FramePort uses
an installed Revive, or downloads a portable copy.
PC VR games are Windows VR games. Scan a folder of them (one folder per game) or use **Add games → Add a PC game
folder…**. FramePort asks which program starts the game if it finds more than one.
- **Play from this PC:** Windows with Steam and SteamVR. **Install on this PC** adds the game to Steam; stream it to the
Frame with Steam Link. If a game can't keep up with the refresh rate, FramePort lowers the rate and enables motion
smoothing in SteamVR's per-game settings the next time you press Play.
- **Play on the Frame (experimental):** Steam Frame → *PC VR games (Proton)* → **Install**, then **Install on Frame**
on the game page.
- Games that use the Oculus Platform SDK check the licence through the Oculus app, so they run on the PC only.
- **Play from this PC** (Windows with Steam and SteamVR): **Install on this PC** adds the game to Steam. Stream it to
the Frame with Steam Link.
- **Play on the Frame (experimental):** on the Steam Frame page, install *PC VR games (Proton)*, then click **Install
on Frame** on the game's page.
- **Oculus games** (made for Meta's Rift headset) need Revive, which FramePort downloads. Games that check their
license through the Oculus app only run on your PC.
**Windows games without VR:** **Add games → Add a PC game folder…** with the game's folder (pick the program that
starts it if asked). FramePort installs it on the Frame and Proton runs it as a window, like Steam's own Windows games;
it shows up in the Frame's Steam library tagged "Windows game on Frame". Whether a game runs depends on Proton on ARM
(x86 games run through emulation).
**Windows games without VR:** use **Add games → Add a PC game folder…** too. The Frame runs them as a window through
Proton, like Steam's own Windows games. Whether a game runs depends on Proton.
## Linux apps
The Frame runs SteamOS on an arm64 CPU, so native Linux apps built for **aarch64/arm64** run on it directly (no
Android container, no Proton). **Add games → Add a Linux app…** takes an AppImage or a `.zip`/`.tar.gz`/
`.tar.xz` archive; **Add a Linux app folder…** takes an unpacked app. FramePort finds the program that starts it (the
game page's **Change…** picks another one) and whether it's a VR (OpenXR) app. **Install on Frame** uploads it
unchanged and adds it to the Frame's Steam library, tagged "Linux app on Frame"; Play, launch tests and Uninstall
work like for other games.
**Add games → Add a Linux app…** takes an AppImage (a single-file Linux app) or a `.zip`/`.tar.gz`/`.tar.xz`
archive; **Add a Linux app folder…** takes an unpacked app. **Install on Frame** uploads it unchanged and adds it to
the Steam library.
- **x86_64 builds** run through **FEX**, Valve's x86 translator, with the x86 system libraries SteamOS ships for it
(the way Steam on the Frame runs x86 Linux games). The first install of one installs FEX on the Frame (Steam
restarts once and downloads it, a few MB). They run slower than arm64 builds: when an app offers both, FramePort picks the arm64 one. The game
page shows which CPU a build is for.
- The app must bring the libraries SteamOS doesn't have (checked for arm64 builds; x86_64 builds use FEX's x86
system, which has glibc and Mesa, and aren't checked ahead). If some are missing, the install reports them and the game
page lists them: look for a build that includes them.
- **Desktop Mode:** Linux apps also appear in Desktop Mode's application menu and as an icon on its desktop. Some
apps work better there, with a mouse and keyboard, than in Gaming Mode (where Steam Input turns the controllers into
a gamepad). Switch it off per app on the game page (**Desktop Mode**).
- From the command line: `frameport add-linux <AppImage, folder or archive> [--exe <program>]`.
- Apps built for **arm64** (the Frame's processor) run directly. Apps built for **x86_64** (most PCs) run through FEX,
a translator Steam installs on the Frame the first time; they run slower. The game page shows which kind you have.
- If the app needs libraries the Frame doesn't have, the game page lists them: look for a build that includes them.
- Linux apps also appear in **Desktop Mode**'s app menu. Turn this off on the game
page (**Desktop Mode**).
## Files on the Frame (videos, documents, mods, saves)
## Files on the Frame
The **Files** tab manages files on the Frame over the same connection as installs; no other transfer app is needed.
Pick a location, browse folders, and use **Upload files** / **Upload folder**, **New folder**, or the download, rename
and delete buttons on each entry. Right-click an entry (or the empty space) for the same actions in a menu. Tick
several entries (or the box above the list for all), or click and drag across them, to download or delete them
together; a right-click on one of them then acts on all. The **Screenshots** tab and the **Library** work the same
way: right-click for a menu, drag across cards to select several. In the downloaded app you can also drag files and folders from Explorer / Finder / your file manager onto
the list to upload them into the open folder. Uploads and downloads run in the Activity panel, resume after an interruption and
skip files that are already there.
The **Files** tab copies files between your PC and the Frame: videos, documents, mods and saves.
- **Videos**, **Downloads** and **Documents** appear inside every Quest game as `/sdcard/Movies`, `/sdcard/Download`
and `/sdcard/Documents`. Apps find files by browsing folders; Android's media index doesn't work on the Frame.
- Under **Game storage**, each installed game has its own `/sdcard` (mods, saves). A game's menu → **Add videos and
files…** opens it. Video players that list only their own folder (e.g. 4XVR's "Internal Storage" = `4XPlayer`) find
videos uploaded into that folder.
- **Home folder** shows everything in the Frame's home folder (hidden files with **Show hidden files**).
![Files](images/files.png)
Command line: `frameport frame send <files> --dest videos` (`frameport frame storage` lists the destinations).
- Use **Upload files**, **Upload folder** and **New folder**; right-click an entry to download, rename or delete
it. Drag across entries to select several.
- In the downloaded app you can drag files from your PC onto the list.
- **Videos**, **Downloads** and **Documents** are shared by every Quest game (inside the game: `/sdcard/Movies`,
`/sdcard/Download`, `/sdcard/Documents`).
- **Game storage** holds each game's own files. A game's menu → **Add videos and files…** opens it.
## Sharing a working game, reporting a problem
## Share a recipe or report a problem
- **Share working recipe…** (game menu): opens a prefilled GitHub issue with the game's patches and settings. Accepted
configs become built-in recipes. Untested games ask on their page once they've been installed or tested: **It
works**, **It has issues** or **It doesn't run**.
- **Report a problem…** (game menu, or Settings → Problems and feedback): saves a diagnostics zip to Documents (logs,
recipe, device details; IP addresses, user names, home folders and Steam ids replaced) and opens a prefilled GitHub
issue to attach it to. Command line: `frameport diag report <game>`, `frameport share-recipe <game>`.
- **Share working recipe…** (in the game's menu) opens a GitHub issue with the game's recipe filled in. Accepted
recipes become built-in for everyone. Untested games ask how they run after you install or test them.
- **Report a problem…** (in the game's menu, or Settings → Problems and feedback) saves a diagnostics zip with
personal data removed and opens a GitHub issue to attach it to.
## Command line
Everything the app does is also a `frameport` command (in a source checkout: `uv run frameport`); `frameport --help`
and `frameport <command> --help` describe every option. The main ones:
| Command | What it does |
|---|---|
| `scan <folder>` / `list` / `show <game>` | add games, list the library, show a game's analysis and patches |
| `add-linux <path>` | add a Linux app, arm64 or x86_64 (AppImage, folder or archive) |
| `recipe <game> --enable/--disable <patch>` | change a game's patches (`patches` lists them all) |
| `build <game>` / `install <game>` / `test <game>` | build, install on the Frame (`--to pc` for PC VR on this PC), launch test |
| `frame discover` / `frame connect` / `frame info` | find, pair with and describe the Frame |
| `frame send` / `frame storage` / `frame cleanup` | copy files to the Frame, show where they go, free space |
| `frame drives` / `frame move <game> --to <drive>` / `install --dest <drive>` | the Frame's drives (microSD), move a game, install to a drive |
| `tools status` / `tools install` | the tools FramePort downloads |
| `open-link "<link>"` | install from an "Install with FrameDrop" button's address or a manifest/APK/zip link (`--yes`, `--no-install`) |
| `diag report <game>` / `share-recipe <game>` | report a problem / share a working recipe |
| `update` | update FramePort |
Exit codes: 0 done, 1 something failed, 2 wrong usage, 10 (`update --check`) a newer version exists. Errors are
one line on stderr; `FRAMEPORT_DEBUG=1` shows the full traceback.
Without the app: [share a recipe](https://github.com/spoopyghosty0/frameport/issues/new?template=working-config.yml)
· [report a problem](https://github.com/spoopyghosty0/frameport/issues/new?template=bug-report.yml).
## Uninstalling
Settings → **Uninstall FramePort…** (or `frameport uninstall-app`) removes its data folder, the Steam shortcuts it
added on this computer and, optionally, its games on the Frame (saves can be kept). It first saves your signing keys
to Documents: game updates must be signed with the same key. Then delete the program folder.
Settings → **Uninstall FramePort…** removes FramePort's data and, if you choose, its games on the Frame (saves can be
kept). It first saves your signing keys to Documents: you need them to update your games later. Then delete the
FramePort folder.
## Verify a download
Each archive has a GitHub build attestation:
`gh attestation verify FramePort-windows-x64.zip -R spoopyghosty0/frameport`. `SHA256SUMS.txt` lists the checksums
(`sha256sum -c SHA256SUMS.txt`). Windows certificate SHA-256 fingerprint:
`SHA256SUMS.txt` in each release lists the files' checksums: `sha256sum -c SHA256SUMS.txt`. Each file also has a
GitHub build attestation (proof that GitHub built it from this repository):
`gh attestation verify FramePort-windows-x64.zip -R spoopyghosty0/frameport`.
Windows: to show FramePort as the publisher, import `FramePort-selfsigned.cer` (attached to each release) into
*Trusted Root Certification Authorities* (Current User). The certificate can only sign code; remove it with
`certmgr.msc`. Its SHA-256 fingerprint:
`4E:12:98:91:62:C0:E4:50:FB:65:1D:34:BB:73:00:09:7B:78:BE:88:5C:A7:6C:42:23:46:9B:92:A1:59:A7:6E`.
## For power users: the command line
The **command-line version** (Python 3.11 or newer) installs from the release's
`frameport-<version>-py3-none-any.whl` with `uv tool install <link>` (or pipx or pip).
Everything the app does is also a `frameport` command; `frameport --help` and `frameport <command> --help` list every
option. The main ones:
| Command | What it does |
|---|---|
| `scan <folder>` / `list` / `show <game>` | add games, list the library, show a game's patches |
| `add-linux <path> [--exe <program>]` | add a Linux app (AppImage, folder or archive) |
| `recipe <game> --enable/--disable <patch>` | change a game's patches (`patches` lists them all) |
| `build <game>` / `install <game>` / `test <game>` | build, install on the Frame (`--to pc` for this PC), launch test |
| `frame discover` / `frame connect` / `frame info` | find, connect to and describe the Frame |
| `frame send <files> --dest videos` / `frame storage` / `frame cleanup` | copy files to the Frame, list where they can go, free space |
| `frame drives` / `frame move <game> --to <drive>` / `install --dest <drive>` | list the Frame's drives, move a game, install to a drive |
| `tools status` / `tools install` | the tools FramePort downloads |
| `open-link "<link>"` | install from an install button's address or a download link (`--yes`, `--no-install`) |
| `diag report <game>` / `share-recipe <game>` | report a problem / share a working recipe |
| `update` | update FramePort (`--check` only checks: exit code 10 = update available) |
| `uninstall-app` | uninstall FramePort |
Exit codes: 0 done, 1 failed, 2 wrong usage. `FRAMEPORT_DEBUG=1` shows full error details;
`FRAMEPORT_NO_UPDATE_CHECK=1` turns update checks off.
+1 -1
View File
@@ -13,7 +13,7 @@ Short rules so every screen, help text, doc and web page sounds the same. Code s
- Tools by their names: OVRPort, Revive, Proton, Lepton, SteamVR.
- **Install** (first time), **Update** (a newer build), **Reinstall** (the same build again); **Play** starts a game.
- **Set up** = the one-time setup of a Frame; **connect** = linking FramePort to it. **Pair** only in Valve's own
**Pair new host**. The **setup line** is the fixed `curl -sL spoopyghosty0.github.io/frameport/s | bash`; the
**Pair new host**. The **setup line** is the fixed `curl -sL frameport.app/s | bash`; the
**setup command** is the one with this PC's address and a one-time code. FramePort's button is **Allow**.
- **Konsole** is the Frame's terminal. The way there is "SteamVR dashboard → Launch a program → Desktop, then app
menu → System → Konsole": say it in full once per page, then just "Konsole".
+7 -7
View File
@@ -1,6 +1,6 @@
# Themes
FramePort comes with three colour themes, all dark:
FramePort comes with three color themes, all dark:
| Theme | Look |
|---|---|
@@ -16,7 +16,7 @@ A theme is a small JSON file. To make one:
1. In **Settings → Appearance**, pick the theme closest to what you want and click **Copy this theme as a file**.
2. Paste it into a text editor and save it as `something.json`.
3. Change the name and the colours you want different. You can delete every colour you keep: missing colours come
3. Change the name and the colors you want different. You can delete every color you keep: missing colors come
from the `base` theme.
4. Back in **Settings → Appearance**, click **Install theme file…** and choose the file. FramePort checks it,
switches to it and keeps a copy in its data folder (`themes/`), so you can delete the original.
@@ -40,11 +40,11 @@ To remove an installed theme, click the bin icon on its card.
| Field | Meaning |
|---|---|
| `name` | Shown on the theme's card (up to 40 characters). |
| `base` | The built-in theme that fills in every colour the file leaves out: `portal` (default), `portal_oled` or `original`. |
| `dual` | `true`: two-colour touches like Portal's (blue-to-orange sidebar edge, two-colour "FramePort", the selected tab's fade, blue secondary buttons). `false`: one accent, like Original. Default: the base's. |
| `colors` | Any of the colours below, as `#RRGGBB` or `#RGB`. Names may be upper or lower case. |
| `base` | The built-in theme that fills in every color the file leaves out: `portal` (default), `portal_oled` or `original`. |
| `dual` | `true`: two-color touches like Portal's (blue-to-orange sidebar edge, two-color "FramePort", the selected tab's fade, blue secondary buttons). `false`: one accent, like Original. Default: the base's. |
| `colors` | Any of the colors below, as `#RRGGBB` or `#RGB`. Names may be upper or lower case. |
| Colour | Used for |
| Color | Used for |
|---|---|
| `BG` | Window background |
| `SIDEBAR` | Sidebar and activity panel |
@@ -57,5 +57,5 @@ To remove an installed theme, click the bin icon on its card.
| `PC` | PC VR games and "on this PC" |
FramePort refuses a theme file it can't show well, and says why: a light window background (FramePort is dark only),
text that's hard to read on cards, an unknown colour name or a value that isn't a colour. An example is in
text that's hard to read on cards, an unknown color name or a value that isn't a color. An example is in
[`themes/example-theme.json`](themes/example-theme.json).
+2 -2
View File
@@ -53,7 +53,7 @@ shots:
- wait_for: "Ready to play"
- name: files
docs: [docs/COMPATIBILITY.md]
docs: [docs/INSTALL.md]
steps:
- go: files
- wait_for: "Upload files…"
@@ -76,7 +76,7 @@ shots:
- wait_for: "Close"
- name: type-on-frame
docs: [README.md]
docs: [docs/INSTALL.md]
steps:
- hook: type_tab
- wait_for: "Keyboard connected"
+13 -13
View File
@@ -23,7 +23,7 @@ title:
seconds: 3.4
end:
heading: You're set
line: Your game is in the Frame's Steam library. More help in docs/INSTALL.md
line: Your game is in the Frame's Steam library. More help at frameport.app/docs/install/
footer: github.com/spoopyghosty0/frameport
seconds: 4.0
@@ -31,12 +31,12 @@ scenes:
- name: download
seconds: 7.5
card:
eyebrow: "Step 1 · On your computer"
eyebrow: "Step 1 · On your PC"
heading: Download FramePort
steps:
- "Open **github.com/spoopyghosty0/frameport** → **Releases** → the latest one"
- "Download the archive for your computer: **FramePort-windows-x64.zip**, **FramePort-macos-arm64.zip** or **FramePort-linux-x64.tar.gz**"
- "Extract it anywhere. There's no installer and no admin rights are needed"
- "Download the file for your PC: **FramePort-windows-x64.zip**, **FramePort-macos-arm64.zip** or **FramePort-linux-x64.tar.gz**"
- "Unpack it anywhere. No installer or admin rights needed"
- name: first-start
seconds: 7.5
@@ -47,10 +47,10 @@ scenes:
- "**Windows:** open **FramePort.exe**. At “Windows protected your PC” choose **More info** → **Run anyway**"
- "**macOS:** right-click **FramePort.app** → **Open** → **Open**"
- "**Linux:** run **FramePort/FramePort**"
note: "FramePort is signed with a free certificate, so your system asks once."
note: "FramePort isn't signed with a paid certificate, so your system asks once."
- name: welcome
caption: ["FramePort gets itself ready", "It downloads the tools it uses (Java, OVRPort, apksigner) by itself"]
caption: ["FramePort gets ready", "It downloads the tools it uses"]
hold: 1.0
steps:
- wait: 1.0
@@ -59,7 +59,7 @@ scenes:
- wait: 1.0
- name: connect
caption: ["Connect your Steam Frame", "Once: one line on the Frame, the same for everyone"]
caption: ["Connect your Steam Frame", "Once: one line on the Frame"]
hold: 1.5
steps:
- click: "Set up the Frame"
@@ -78,9 +78,9 @@ scenes:
steps:
- "In the SteamVR dashboard: **Launch a program** → **Desktop**"
- "Open the app menu (bottom left) → **System** → **Konsole**"
- "Type the line and press **Enter** (or open **spoopyghosty0.github.io/frameport/setup** in Chromium and paste it)"
code: "curl -sL spoopyghosty0.github.io/frameport/s | bash"
note: "It finds FramePort on your network and shows a 4-digit code. Nothing changes on the Frame until you allow it on the PC. Developer Mode already on? Just open **Settings → Developer → Pair new host** and approve FramePort in the headset."
- "Type the line and press **Enter** (or copy it from **frameport.app/setup** in Chromium)"
code: "curl -sL frameport.app/s | bash"
note: "Nothing changes on the Frame until you allow it on the PC."
- name: allow
caption: ["Allow it on your PC", "FramePort shows the same code as the Frame"]
@@ -100,8 +100,8 @@ scenes:
eyebrow: "On the Frame, by itself"
heading: The setup finishes on its own
steps:
- "FramePort's key is let in and **Developer Mode** turns on (no password)"
- "The desktop closes and Steam restarts once: that's expected"
- "**Developer Mode** turns on (no password)"
- "Steam restarts once and the desktop closes"
- "If Steam asks to install **Lepton**, confirm it"
- name: connected
@@ -127,7 +127,7 @@ scenes:
- wait: 1.0
- name: install
caption: ["Install a game", "FramePort patches it, installs it and adds it to the Frame's Steam library"]
caption: ["Install a game", "FramePort patches it and adds it to the Frame's Steam library"]
hold: 1.2
steps:
- click: {name: "Lucky's Tale", dy: 0.35} # (the title: the card's middle is its Install button)
+3 -3
View File
@@ -42,7 +42,7 @@ scenes:
- wait: 1.6
- name: game
caption: ["Every game gets its own recipe", "Known-good fixes from the catalog, or suggested from the game itself"]
caption: ["Every game gets its own recipe", "Tested patches, or patches suggested for the game"]
steps:
- click: {name: "Riven", dy: 0.35} # (the title: the card's middle is its Install button)
- wait: 1.8
@@ -54,7 +54,7 @@ scenes:
- wait: 0.5
- name: install
caption: ["One click to install", "Patched, signed, uploaded, added to Steam and launch-tested"]
caption: ["One click to install", "Patched, uploaded, added to Steam and tested"]
teaser: [0.6, 4.0]
hold: 1.2
steps:
@@ -108,7 +108,7 @@ scenes:
- wait: 0.4
- name: files
caption: ["Files on the Frame", "Videos, mods and saves: upload, download, select with a drag"]
caption: ["Files on the Frame", "Upload and download videos, mods and saves"]
steps:
- nav: "Files"
- wait: 1.6
+2 -6
View File
@@ -1,8 +1,4 @@
## Install
- **Windows:** unzip `FramePort-windows-x64.zip`, run `FramePort.exe` (warning → **More info → Run anyway**).
- **macOS:** unzip `FramePort-macos-arm64.zip`, right-click `FramePort.app` → **Open**.
- **Linux:** `tar xzf FramePort-linux-x64.tar.gz && ./FramePort/FramePort` (ARM64: `FramePort-linux-arm64.tar.gz`).
Full guide: [docs/INSTALL.md](https://github.com/spoopyghosty0/frameport/blob/main/docs/INSTALL.md) · checksums in
`SHA256SUMS.txt`.
Download the file for your PC, unpack it and start FramePort. Guide:
[Install and first steps](https://frameport.app/docs/install/).
+1 -1
View File
@@ -1,4 +1,4 @@
"""Turn a "Working configuration" issue (.github/ISSUE_TEMPLATE/working-config.yml) into catalog/games/<pkg>.yaml.
"""Turn a "Working recipe" issue (.github/ISSUE_TEMPLATE/working-config.yml) into catalog/games/<pkg>.yaml.
Used by .github/workflows/catalog-from-issue.yml after a maintainer labels the issue `catalog-accepted`; can also be
run by hand: gh issue view 12 --json body -q .body | python scripts/catalog_from_issue.py --issue 12
+2 -6
View File
@@ -13,8 +13,6 @@ from frameport.recommend import catalog # noqa: E402
STATUS = {"works": "✅ Works", "issues": "⚠️ Works with issues", "unsupported": "❌ Doesn't run"}
ORDER = {"works": 0, "issues": 1, "unsupported": 2}
ISSUES = "https://github.com/spoopyghosty0/frameport/issues/new?template="
SHARE, REPORT = ISSUES + "working-config.yml", ISSUES + "bug-report.yml"
def short(note: str) -> str:
@@ -34,10 +32,8 @@ def render() -> str:
note = "" if e.status == "works" else short(e.notes).replace("|", "/")
rows.append(f"| {e.title} | {platform} | {STATUS[e.status]} | {note} |")
return ("# Tested games\n\n"
"Games tested on the Steam Frame with FramePort's recipes. Games not listed here may work too: FramePort "
"suggests patches for them, and a working recipe can be shared from the app (**Share working recipe…**).\n"
f"Tested a game? [Share a working config]({SHARE}) or [report a problem]({REPORT}) (in the app: the game's "
"**…** menu does both and fills in the details).\n"
"Games tested on the Steam Frame with FramePort. Games not listed may work too: FramePort suggests "
"patches for them. Got one working? [Share its recipe](INSTALL.md#share-a-recipe-or-report-a-problem).\n\n"
"Generated from [catalog/games](../catalog/games) by `scripts/compat_list.py`.\n\n"
+ "\n".join(rows) + "\n")