๐ฅ Halo CE in your browser: mobile touch controls, streamed maps, System Link, and WebAssembly absurdity.
C
1
4 commits
updated Sep 30, 2026
A mobile-first Halo CE web port with touch controls, controllers, browser saves, streamed maps, System Link play, and a real Play button at the top.
No installer. No native app package. Just WebAssembly doing something it absolutely should not be able to do.
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ ๐ฎ PLAY HALO CE FROM A BROWSER TAB โ โ ๐ฑ TOUCH. CONTROLLER. KEYBOARD. โ โ ๐ STREAM MAPS. KEEP SAVES. JOIN FRIENDS. โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
Halo Mobile takes the Halo: Combat Evolved decompilation and pushes it through a modern browser stack: WebAssembly, WebGL 2, OffscreenCanvas, OPFS, service workers, and a launcher built for phones.
The result is an installable browser game with direct Play controls, private on-device storage, custom touch layouts, controller support, and multiplayer System Link rooms. Yes, that is a campaign-capable Halo port. Yes, that is a browser tab. ๐คฏ
๐ง TL;DR: bring authorized game data, open the launcher, hit Play, and let the browser carry the absurdly large energy sword.
| โก | Mission | What happens |
|---|---|---|
| ๐ฑ | Play on Android | Run the WebAssembly build in current Chrome with touch controls. |
| ๐ | Install on iPhone or iPad | Add the PWA to the Home Screen for a full-screen app-like experience. |
| ๐ฎ | Use a controller | Pair Bluetooth or USB controllers and let touch controls step aside. |
| ๐น๏ธ | Use keyboard + mouse | Play on a desktop browser or a tablet with peripherals. |
| ๐พ | Keep saves locally | Store saves, settings, and shader caches in private browser storage. |
| ๐ฆ | Import private game data | Choose an authorized disc image or an extracted maps folder. |
| ๐ก | Stream maps on demand | Use a separately hosted byte-range map service instead of importing every map. |
| ๐ค | Play System Link | Create, join, share, and match into browser-based Halo rooms. |
| ๐งช | Try direct presentation | Use the experimental direct worker-canvas mode for reduced frame transport. |
| ๐ ๏ธ | Build the whole thing | Compile the web port with Emscripten and Ninja. |
The shortest path from clone to โwhy is Halo running in my browser?โ
# ๐ Get the source
git clone https://github.com/OMG-Guest/Halo-Mobile.git
cd Halo-Mobile
# ๐งฐ Install and activate Emscripten 6.0.10
git clone --depth 1 https://github.com/emscripten-core/emsdk.git ../emsdk
python3 ../emsdk/emsdk.py install 6.0.10
python3 ../emsdk/emsdk.py activate 6.0.10
source ../emsdk/emsdk_env.sh
# ๐ Build and test
python3 configure.py --release
ninja web
node --test port/web/tests/*.cjs
The browser app is written to build/web/site. Serve it locally:
# ๐ Launch a local server
python3 -m http.server --directory build/web/site 8081
Open http://localhost:8081. The service worker reloads once to establish browser isolation. Then you are flying. โ๏ธ
The code is here. The game data is not. Keep it that way.
This repository includes zero Halo maps, disc images, saves, credentials, or generated builds. Supply compatible Halo game data only from a source you are authorized to use.
| ๐ | Launcher route | Result |
|---|---|---|
| ๐ฟ | Choose disc image | Import an authorized ISO or XISO into private browser storage. |
| ๐ | Import maps folder | Select an extracted compatible maps directory. |
| ๐ก | Play streamed maps | Point the launcher at a separately hosted downloaded-maps manifest with HTTP byte ranges. |
Do not commit map files, disc images, browser saves, credentials, or build output. Ever.
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ฑ Browser launcher โ
โ Play โข Touch โข Controller โข Install โข System Link rooms โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโผโโโโโโโโโโโโโ
โ ๐ Service worker + PWA โ
โ COOP / COEP + offline โ
โโโโโโโโโโโโโโฌโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโ
โ โ๏ธ Emscripten + WebAssembly engine โ
โ WebGL 2 โข worker canvas โข audio โ
โโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโ
โ โ
โโโโโโโโโโโโโผโโโโโโโโโโ โโโโโโโโโผโโโโโโโโโโโโโ
โ ๐พ OPFS โ โ ๐ก Range map host โ
โ saves + local maps โ โ optional streaming โ
โโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโ
For Android USB development:
# ๐ฒ Make the desktop server appear as Android localhost
adb reverse tcp:8081 tcp:8081
Then open http://localhost:8081 in Android Chrome. Use HTTPSโnot insecure LAN HTTPโfor complete mobile browser capabilities.
Pixels have baggage. Pick your transport.
| ๐จ | Mode | Use it when |
|---|---|---|
| โก | Direct worker canvas | The launcher default: reduces per-frame pixel transport on compatible hardware. |
| ๐ก๏ธ | Bounded readback | Add ?present=readback when you need the fixed-buffer fallback. |
Direct worker-canvas presentation is the current default. Compare it with ?present=readback when diagnosing device-specific stability or performance.
๐ฆ Halo-Mobile
โโโ ๐ port/web/site/ Launcher, PWA shell, controls, service worker
โโโ ๐ port/web/src/ Browser and Emscripten platform bridge
โโโ ๐งช port/web/tests/ Launcher, presenter, and stream-map tests
โโโ ๐ง source/ Halo decompilation source
โโโ ๐ง tools/web_build.py Browser Ninja build graph
โโโ ๐ LICENSE.md License and notice material
| ๐ต Problem | ๐ ๏ธ Fix |
|---|---|
| Browser says required features are missing | Use a current supported browser and reload after the service worker starts. |
| Phone cannot use all capabilities on a LAN IP | Serve the app over HTTPS. Use localhost only for ADB reverse development. |
| Streamed maps do not start | Confirm the manifest and maps use same-origin byte-range endpoints. |
| Android cannot reach the desktop server | Run ADB reverse for port 8081, then use Android localhost. |
| Direct mode is unstable | Return to bounded readback. |
| Saves are missing | Browser origins are separate. Keep the same origin and export saves before moving. |
Fix browser bugs. Improve touch controls. Test weird devices. Make the build more reliable. Keep proprietary game data out of every commit.
Before opening a change:
# โ
Verify the browser port
node --test port/web/tests/*.cjs
If you believe browser games should be allowed to be ridiculous, smash that star button. โญ
Built from decompilation research, WebAssembly, and an unreasonable amount of browser ambition. ๐ฌ
The ring is a web app now. Deal with it. ๐
Halo Mobile builds on fucktrevor/HCE-Mobile, cybersecurity/halo-ce-universal, bnunu/halo-1, and punpckhdq/halo. Preserve their attribution and licenses. Read LICENSE.md.
C
80.1%
Python
15.9%
C++
2.4%
๐ฅ Halo CE in your browser: mobile touch controls, streamed maps, System Link, and WebAssembly absurdity.
C
1
4 commits
updated Sep 30, 2026
A mobile-first Halo CE web port with touch controls, controllers, browser saves, streamed maps, System Link play, and a real Play button at the top.
No installer. No native app package. Just WebAssembly doing something it absolutely should not be able to do.
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ โ ๐ฎ PLAY HALO CE FROM A BROWSER TAB โ โ ๐ฑ TOUCH. CONTROLLER. KEYBOARD. โ โ ๐ STREAM MAPS. KEEP SAVES. JOIN FRIENDS. โ โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
Halo Mobile takes the Halo: Combat Evolved decompilation and pushes it through a modern browser stack: WebAssembly, WebGL 2, OffscreenCanvas, OPFS, service workers, and a launcher built for phones.
The result is an installable browser game with direct Play controls, private on-device storage, custom touch layouts, controller support, and multiplayer System Link rooms. Yes, that is a campaign-capable Halo port. Yes, that is a browser tab. ๐คฏ
๐ง TL;DR: bring authorized game data, open the launcher, hit Play, and let the browser carry the absurdly large energy sword.
| โก | Mission | What happens |
|---|---|---|
| ๐ฑ | Play on Android | Run the WebAssembly build in current Chrome with touch controls. |
| ๐ | Install on iPhone or iPad | Add the PWA to the Home Screen for a full-screen app-like experience. |
| ๐ฎ | Use a controller | Pair Bluetooth or USB controllers and let touch controls step aside. |
| ๐น๏ธ | Use keyboard + mouse | Play on a desktop browser or a tablet with peripherals. |
| ๐พ | Keep saves locally | Store saves, settings, and shader caches in private browser storage. |
| ๐ฆ | Import private game data | Choose an authorized disc image or an extracted maps folder. |
| ๐ก | Stream maps on demand | Use a separately hosted byte-range map service instead of importing every map. |
| ๐ค | Play System Link | Create, join, share, and match into browser-based Halo rooms. |
| ๐งช | Try direct presentation | Use the experimental direct worker-canvas mode for reduced frame transport. |
| ๐ ๏ธ | Build the whole thing | Compile the web port with Emscripten and Ninja. |
The shortest path from clone to โwhy is Halo running in my browser?โ
# ๐ Get the source
git clone https://github.com/OMG-Guest/Halo-Mobile.git
cd Halo-Mobile
# ๐งฐ Install and activate Emscripten 6.0.10
git clone --depth 1 https://github.com/emscripten-core/emsdk.git ../emsdk
python3 ../emsdk/emsdk.py install 6.0.10
python3 ../emsdk/emsdk.py activate 6.0.10
source ../emsdk/emsdk_env.sh
# ๐ Build and test
python3 configure.py --release
ninja web
node --test port/web/tests/*.cjs
The browser app is written to build/web/site. Serve it locally:
# ๐ Launch a local server
python3 -m http.server --directory build/web/site 8081
Open http://localhost:8081. The service worker reloads once to establish browser isolation. Then you are flying. โ๏ธ
The code is here. The game data is not. Keep it that way.
This repository includes zero Halo maps, disc images, saves, credentials, or generated builds. Supply compatible Halo game data only from a source you are authorized to use.
| ๐ | Launcher route | Result |
|---|---|---|
| ๐ฟ | Choose disc image | Import an authorized ISO or XISO into private browser storage. |
| ๐ | Import maps folder | Select an extracted compatible maps directory. |
| ๐ก | Play streamed maps | Point the launcher at a separately hosted downloaded-maps manifest with HTTP byte ranges. |
Do not commit map files, disc images, browser saves, credentials, or build output. Ever.
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ ๐ฑ Browser launcher โ
โ Play โข Touch โข Controller โข Install โข System Link rooms โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโผโโโโโโโโโโโโโ
โ ๐ Service worker + PWA โ
โ COOP / COEP + offline โ
โโโโโโโโโโโโโโฌโโโโโโโโโโโโโ
โ
โโโโโโโโโโโโโโโโโโโโผโโโโโโโโโโโโโโโโโโโ
โ โ๏ธ Emscripten + WebAssembly engine โ
โ WebGL 2 โข worker canvas โข audio โ
โโโโโโโโโโฌโโโโโโโโโโโโโโโโโโโโฌโโโโโโโโโโ
โ โ
โโโโโโโโโโโโโผโโโโโโโโโโ โโโโโโโโโผโโโโโโโโโโโโโ
โ ๐พ OPFS โ โ ๐ก Range map host โ
โ saves + local maps โ โ optional streaming โ
โโโโโโโโโโโโโโโโโโโโโโโ โโโโโโโโโโโโโโโโโโโโโโ
For Android USB development:
# ๐ฒ Make the desktop server appear as Android localhost
adb reverse tcp:8081 tcp:8081
Then open http://localhost:8081 in Android Chrome. Use HTTPSโnot insecure LAN HTTPโfor complete mobile browser capabilities.
Pixels have baggage. Pick your transport.
| ๐จ | Mode | Use it when |
|---|---|---|
| โก | Direct worker canvas | The launcher default: reduces per-frame pixel transport on compatible hardware. |
| ๐ก๏ธ | Bounded readback | Add ?present=readback when you need the fixed-buffer fallback. |
Direct worker-canvas presentation is the current default. Compare it with ?present=readback when diagnosing device-specific stability or performance.
๐ฆ Halo-Mobile
โโโ ๐ port/web/site/ Launcher, PWA shell, controls, service worker
โโโ ๐ port/web/src/ Browser and Emscripten platform bridge
โโโ ๐งช port/web/tests/ Launcher, presenter, and stream-map tests
โโโ ๐ง source/ Halo decompilation source
โโโ ๐ง tools/web_build.py Browser Ninja build graph
โโโ ๐ LICENSE.md License and notice material
| ๐ต Problem | ๐ ๏ธ Fix |
|---|---|
| Browser says required features are missing | Use a current supported browser and reload after the service worker starts. |
| Phone cannot use all capabilities on a LAN IP | Serve the app over HTTPS. Use localhost only for ADB reverse development. |
| Streamed maps do not start | Confirm the manifest and maps use same-origin byte-range endpoints. |
| Android cannot reach the desktop server | Run ADB reverse for port 8081, then use Android localhost. |
| Direct mode is unstable | Return to bounded readback. |
| Saves are missing | Browser origins are separate. Keep the same origin and export saves before moving. |
Fix browser bugs. Improve touch controls. Test weird devices. Make the build more reliable. Keep proprietary game data out of every commit.
Before opening a change:
# โ
Verify the browser port
node --test port/web/tests/*.cjs
If you believe browser games should be allowed to be ridiculous, smash that star button. โญ
Built from decompilation research, WebAssembly, and an unreasonable amount of browser ambition. ๐ฌ
The ring is a web app now. Deal with it. ๐
Halo Mobile builds on fucktrevor/HCE-Mobile, cybersecurity/halo-ce-universal, bnunu/halo-1, and punpckhdq/halo. Preserve their attribution and licenses. Read LICENSE.md.
C
80.1%
Python
15.9%
C++
2.4%