Commit Graph
411 Commits
Author SHA1 Message Date
MrBruh ff76b33f0b Merge pull request #337 from innerhat-dev/nav-marker-before-draw
Classify a nav marker before drawing it
2026-10-20 00:07:31 +13:00
MrBruh 69ec31a49d Merge pull request #328 from GiovanH/fix/split-screen-start-now
Port: Allow split-screen play in PC menus
2026-10-20 00:07:31 +13:00
MrBruh 54a9c8f0e6 Merge pull request #385 from arimwilson/bumper-jumper
Add the Master Chief Collection's Bumper Jumper button layout
2026-10-20 00:07:30 +13:00
MrBruh 5aafe7af9e Mark the second batch's changes to the game's sources as the port's
Several of the fixes taken from the forks changed source/ without the
port: comment that marks a change from the original (the second copy's
datagram ports, the downloaded maps' refusals, the main menu's clock,
the one-magazine HUD states, the render lists' sizes and others), and a
comment still named a function of that fork's. Each change now says so.
2026-10-19 23:06:19 +13:00
xshxdex98 04a63d9094 The main menu's scene keeps running behind every menu
A tick waits for an input update with an action for each player, and the
menus change who the local players are (signing profiles in and out, a
lobby's network game owning the queues). In a lobby, or once a client's
clock waited for a game, the main menu's scene stopped ticking; and a
screen flagged to pause game time (Mods, the map and gametype screens of
setting up a game) paused the clock that runs the scene, which then
started again from its beginning as the screen closed.

The main menu's scene now always ticks on this machine's clock
(game_time_menu_scene), its players idle where the queues have no input
for them, and at the main menu those screens no longer pause it. The
distributed netcode's per-tick work is not done for the scene: a lobby's
machines do not share it.

(cherry picked from commits 8444785804f8cfb413020da5a03fc5dd65f918e9, 6267d199117f87e56a3f41fc8932966a39a3feb2
and 3a4097bb48f34245b750028a5c0ae28e03bae037, made again on OpenCE's game_time_update,
which has no separate clock connection for the scene)
2026-10-19 23:02:57 +13:00
MrBruh 34002780ce Draw a HUD message's high-res button before looking for the map's picture
The high-res HUD draws a message's controller button by its place among
the HUD globals' button icons, but only once the map's message icons
bitmap had a picture at the button's sequence. Halo PC's message icons
have 13 sequences to the Xbox's 24, so on a Custom Edition map a prompt's
button past them was not drawn at all, and the rest only because the map
had some other picture there ("Hold [rocket launcher] to swap" on
coldsnap, with the high-res HUD off). The high-res button is now tried
first. With display.high_res_hud off, a Custom Edition map still draws
its own pictures.

Found in commit 4c3e74cf29341ff344aca09febc0fab7e1d19919, which instead
reads the Xbox's button pictures out of ui.map for every Custom Edition
map; that is not taken.
2026-10-19 23:00:31 +13:00
xshxdex98 74649ec993 Server browser: pings coloured by how good they are
The Join Game server browser shows each ping coloured: green under 80 ms,
yellow under 160, red above. A text colour hook of the menus'
(pc_menu_text_color) gives the ping its colour; the rest keep their own.

(cherry picked from commit 335c6522e9fb7aa33762e3f2cf27c518ac0e48ce, without that fork's
Online Games screen, the thresholds and colours kept in menu_functions.c)
2026-10-19 22:48:05 +13:00
xshxdex98 336dc0d262 Server browsers: a game selected in yellow, as Custom Edition's
In Join Game's server browser a click selects a game, its row in the
yellow-outlined picture Custom Edition draws for it, and a click on the
selected game, a double click, A, Enter or JOIN joins it; one click
joined it before. The keys move the selection.

(cherry picked from commit 472d232246568ed2e3ee56bc93d97a3530feea54, without that fork's
Online Games screen; OpenCE's rows already take the focus only from a
click, not from the pointer passing over them)
2026-10-19 22:45:37 +13:00
Milenko 329d311c16 Campaign: new profiles start at the beginning, as on the Xbox
The debug build this port comes from unlocked every campaign level on
every difficulty for each new profile. Retail Xbox Halo does not: a new
profile starts at The Pillar of Autumn and each level opens when the one
before it is finished. New profiles now start that way.

- game.unlock_all_levels (off by default) keeps the old behavior for new
  profiles, for those who want it.
- profile_reset_campaign in the console clears the current profile's
  finished levels and last played level, after a confirmation
  ("profile_reset_campaign yes"). Profiles made by earlier versions had
  every level open and cannot be told apart from a real full clear, so
  nothing is changed automatically.

(cherry picked from commit 224d9a757575509efb0dedab094bd0d34df59e96, without its top README
table, which OpenCE does not have)
2026-10-19 22:42:30 +13:00
xshxdex98 7b447b1065 Weapon HUD: no secondary warnings for one-magazine weapons
A one-magazine weapon's second magazine, read as empty, still set off the
secondary states: the secondary trigger ready, flash, reload and "no ammo
for reload" crosshair states, and the draw states of its total and loaded
ammunition (flashing, disabled), which coldsnap's and hugeass's master HUD
draws as NO FUEL beside the weapon's own NO AMMO. These now apply only to a
weapon with a second magazine.

(cherry picked from commit 488bd83eafaabf26a7e392eaf8b240b1319e07c3; OpenCE already cleared
the state first, kept the overlays off and checked two of the crosshair
states, so only the rest is taken, and no CHANGELOG.md)
2026-10-19 22:31:57 +13:00
xshxdex98 fc51992a7e Menus: a failing event function names its widget
"event handler function failed" said nothing of which: the gametype
editor logged it fifteen times. It names the function's number and the
widget's tag, taken before the function runs (it may delete the widget).

(cherry picked from commit 5f4494f42b1919dc1e38c6f8e168b646768e74f1)
2026-10-19 21:57:31 +13:00
Milenko a321e98fd0 PC menus: the mouse wheel leaves a screen's button bar
A screen's button bar (SELECT and BACK under a list) steps sideways, so
once the wheel scrolled past a list's last row onto the bar it went back
and forth between the two buttons until a row was chosen again with the
mouse. A touch drag already left the bar with up and down, as the d-pad
does; the wheel now does the same.

(cherry picked from commit 2ddad079fa5435a70a383d757de16b960c421505)
2026-10-19 21:49:02 +13:00
Milenko 3f06bf815f No shield damage sound while an overshield drains
On a network client the overshield's drain arrives with the host's updates
after the HUD has taken its last shield value for the tick, so every frame
the shield looked a step lower than the HUD remembered and the shield
damage sound played for the whole overshield. The Xbox plays nothing.

The meter's flash already told the drain from a hit (a step of 0.05 or
less from past full); the sound now uses the same test, so a drain is
silent on host and client while a real hit on an overshield still flashes
and sounds.

(cherry picked from commit fd9c918313076ecc686209a0f4c75a6ef23340c4)
2026-10-19 21:48:24 +13:00
xshxdex98 88b0290186 Progress bar: a depth buffer released only if there is one
OpenCE's leak fix releases the surfaces the capture took; the device's
depth buffer may be none (D3DDevice_GetDepthStencilSurface's NOTFOUND),
and D3DResource_Release reads the resource it is given.

(cherry picked from commit ff654a774061c74d30f31ce986d7ebdefcafad74)
2026-10-19 21:47:44 +13:00
Milenko 572c674e43 Change Name in a game no longer crashes
The virtual keyboard kept its keyboard tag from the main menu's map after
that map was unloaded, so Change Name in Settings from a game's pause
menu opened it on a stale tag and the game stopped. The keyboard is now
let go with the old map's interface, as its tags are; at the main menu it
is set up again, and in a game Change Name does nothing.

(cherry picked from commit 4c05c5b3237330669f55c2bdb123b7cde4e4e056)
2026-10-19 21:47:44 +13:00
MrBruh d490fd8bd4 Undo the map list's own return to the main menu after a match (#329)
The Xbox's postgame map select wrappers already carry
main_menu_if_no_history, with which the stock event code calls
main_goto_main_menu() when Back closes the last screen. The PC menus'
connected_map_select_wrapper, which menu_tags.c opens in their place,
was given the same flag by tools/port_settings.py in 4301ca88d, so the
hard-coded names and the network_game_abort() call in
widget_instance_go_back_to_previous were not needed, and they changed
stock split-screen behaviour (a split-screen game is a local server).
widget_instance_go_back_to_previous is as it was before 7d128e1bd.

Checked: the harness and touch menu tests (491 passed), test_web_build
(11 passed), ui_widget.c compiled for Linux and the Android guest.
2026-10-19 21:40:27 +13:00
MrBruh 7270ddc069 Merge pull request #329 from innerhat-dev/postgame-menu-begin-random
Allow a full begin_random list and return to the main menu after a match
2026-10-19 21:16:09 +13:00
MrBruh 0110c16001 Merge bnunu/halo-1 main into testing, keeping OpenCE's code where both changed it and leaving out its matching tooling and logs 2026-10-18 22:31:23 +13:00
MrBruh 8488a161eb Fix the text chat's review findings: no | in lines, case-blind mutes, wrapped lines, per-view and hidden chat, stream-only host messages, no chat in browser-joined public games (#399) 2026-10-18 19:33:08 +13:00
Jonas VolmanandClaude Opus 5.5 da38822634 Re-land the in-game text chat (revert #397)
This reverts 4ac609f0, the revert of #395, so the chat is back as it was
merged: T, Y and Tab, team and vehicle lines, the host's /mute, the
VOICE AND TEXT CHAT settings page and the Android placement.

The one conflict is source/text/draw_string.c, where #395's streamer mode
and testing's (90dd65ca, text_filter.c) both hook the drawn text; testing's
hook is kept. #395's own filter (chat_filter.c, game.streamer_mode) is left
in place, unhooked, for the next commit to take out.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-17 19:44:03 -07:00
MrBruh 90dd65cab4 Add a streamer mode that hides slurs, swearing and insults in text from other players, maps and mods 2026-10-18 15:16:12 +13:00
MrBruh 4ac609f0df Revert "Add an in-game text chat for network games" 2026-10-18 15:03:39 +13:00
Jonas VolmanandClaude Opus 5.5 75b2393ccf Merge testing into ingame-chat
testing's SOUND PROCESSING page and the chat's VOICE AND TEXT CHAT page
both split rows off Audio Setup in tools/port_settings.py. Both are kept,
as two category rows, sound processing first. The settings screens and
menus.json are regenerated from it, so they match testing's apart from the
chat's page, its row on Audio Setup and Controls Setup's COMMUNICATION
group.

Checked after the merge: the Linux debug build, the network format check,
the CI Linux test step (467 passed, 6 skipped), and the three-machine
system-link chat test, /mute and /unmute included.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-17 18:37:12 -07:00
Jonas VolmanandClaude Opus 5.5 3efe79a38d Add a text chat to network games
Network games had voice chat but no way to type to the other players, as
the PC version's chat did. T (controls.chat) types a line to everyone and
Y (controls.team_chat) one to the team; Enter sends it, Escape cancels it.
The lines are drawn above the motion sensor with the HUD's font: the
player's name in their team's colour (blue without teams), then the text
in a pale blue, and fade after ten seconds (port/linux/game/network_chat.c).

A client sends its line to the host (_distributed_message_chat_up), which
takes it only from the client's own stream and one of that machine's
players, five at once and one each 1.5 seconds after, its text cut to 63
characters of printable ASCII, and sends it on to the machines that hear
it (_distributed_message_chat_down): all, or a team's line those with a
player of the team. Older builds drop both kinds as unknown, so the
network version stays 29, as for the vote kick; network_format.txt
records the two kinds.

While a line is typed the keyboard drives no player, as with the console
(xinput_sdl.c), nor voice chat's push to talk or the debug keys. Controls
Setup gets a COMMUNICATION group with PUSH TO TALK, CHAT and TEAM CHAT
(the controls screen's spinner strings changed by hand to what
port_settings.py writes: ce_menus.py needs the PC version's tags).

Checked: tools/harness/tests/test_chat_logic.py (the text's cleaning, the
host's rate, who hears a team's line, the fade, with negative controls);
the CI Linux test step; three machines on system link with
debug.network_test_chat (new), every machine showing the lines to all in
one order and a team's line only on its team's machines; and a host drawn
on Xvfb with lines typed on its keyboard through xdotool (sent on Enter,
not on Escape, the player still while typing).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-17 18:02:07 -07:00
MrBruh 7059096e1b Merge main into testing, bringing in the pause menu and HUD fixes of #378 2026-10-17 17:43:40 +13:00
MrBruh dd16971b6c Add client-side mods with a Mods menu, load order and incompatibility checks 2026-10-17 16:19:49 +13:00
bnunu 25697bbaa1 Merge pull request #378 from chestahh/opence-ui-fixes
Fix regression in pause menu & The Maw timer, restoring legacy Xbox behaviour. Fix incorrect Edit Gametypes positioning
2026-10-16 17:49:30 -04:00
Ari WilsonandClaude Opus 5.5 a22dd332f7 Add the Master Chief Collection's Bumper Jumper button layout
Settings > Gamepads > Button Layout gets a sixth choice, Bumper Jumper as
the Master Chief Collection has it for Halo: Combat Evolved: jump on the
left bumper (the Duke's white), melee on the right (its black), switching
grenades on A, action and reload on B and the flashlight on X; the
triggers, stick clicks, Back and Start are the default layout's. The Edit
Profile picture, which shows the Xbox's pictures of its five layouts,
keeps the row's own picture for this one, of which the Xbox has none.

A layout the build does not know (a later build's) now gets the standard
buttons. With no case for it, every control was on A, start and back
with it, and input_abstraction_update_local_player_preferences' assertion
stopped the game, release builds too. Builds before this one still stop
when they load a profile saved with Bumper Jumper.

The buttons are mapped on each machine before its players' actions are
sent, and profiles are not sent (only names and colours), so
HALO_PORT_NETWORK_VERSION is unchanged.

Checked: tools/harness/tests/test_button_presets.py (every layout keeps
start and back and gives each control a button of its own, Bumper
Jumper's mapping, an unknown layout is the standard one, and three
negative controls), built 64-bit on macOS; the settings screens written
again with port_settings.settings_files(), which changed only Gamepads,
and test_web_build.py's and test_linux_port.py's menu checks; the units
that include player_profile.h and menu_functions.c compiled for i686
Linux against the portable system root. Not yet played with a controller,
and not built for Windows, Android or the web.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-16 14:23:35 -07:00
chestahh f8b3eecb37 Complete the high-resolution Xbox HUD
Upscale the original vehicle/passenger labels, warnings, reload dots and
messaging sheets without changing their glyph layout or sprite coordinates.
Use the existing Xbox controller redraws for A/B/X/Y/Black/White prompts;
other controller symbols retain the original Xbox art through upscaling.
Match the existing high-resolution vehicle meter contour to remove the
double wrench. Restore the rounded diamond sniper reticle, contain the
flashlight fill and assign discrete thresholds to whole ammunition bullets.

The HUD module owns interpolation and tag selection. A narrow texture-cache
hook is needed to obtain decoded original pixels and invalidate generated
textures with their source; the messaging hook selects the existing button
art. Both respect the High-Res HUD setting. MCC's separate draw/texture
paths remain intact. No MCC bitmap data is embedded; label interpolation
was retained at the user's request, with its limited sharpness acknowledged.

Validated Windows portable release build; 246 focused HUD tests; 15,360
real GPU ammunition checks; hidden Xbox HUD captures enabled/disabled;
Xbox/MCC/Xbox transitions at 30 and 120 FPS with no exceptions. Player health
and sniper zoom-label pixels outside the targeted regions are unchanged.
Android/web targets are unavailable in this Windows build configuration;
Custom Edition gameplay data is unavailable, so that path was inspected.
No simulation or network format changes; network version stays unchanged.

(cherry picked from commit 5398553e4a95d7d68376acf023e6ca671066a614)
2026-10-16 16:07:49 +01:00
chestahh 5e228ea9db Restore pause menu artwork, timer digits and multiplayer menu spacing
Restore the pause header and footer bands while retaining Settings, the
campaign body gradient, and the Xbox footer alpha of 191/255. Initialize
the scripted timer scaling flags so stack data cannot shrink its digits.
Move Edit Gametypes and its divider inside the connected panel.

This implementation-only upstream contribution excludes MCC, regression
tests, documentation, optional regeneration commands and workflows. The
complete fixes and tests remain on GulchCE testing and the local validation
branch. Original cherry-picked changes below were combined and scoped to
OpenCE; authorship is retained.

Validated: portable release Windows builds on both bases; 25 upstream
art/timer tests and 52 GulchCE tests before upstream test exclusion; hidden
Xbox and MCC pause captures, both timer HUD settings, and multiplayer menu
captures. Final generator matches all committed pause SVGs. Android/web
targets are unavailable in this Windows configuration; online co-op was
not replayed.

(cherry picked from commit a0c20572f8bfa6af0d2f94c57abef32357750bf0)
(cherry picked from commit c76a3a596f7dbe8ced581b2e6c759aae0baababb)
(cherry picked from commit f0804e1e5c857db6dc84ff16c72d3f8b8abf95a2)
(cherry picked from commit bff920f6a5ec614caf98ff5e8555a0320b0a29f1)
(cherry picked from commit b1b59eb7237d901dba10aa0b5187b184f3f44a7b)
2026-10-16 04:43:57 +01:00
justinfilip 36ea3fb80c Classify a nav marker before drawing it. 2026-10-13 08:06:03 -05:00
justinfilip 7d128e1bde Return to the main menu from the map list after a match. 2026-10-12 20:50:57 -05:00
Gio aa51dfccc6 Port: Allow split-screen play in PC menus
On the "pc" menu style, a LAN game whose players were all on the host's
computer could not start a local splitscreen game. This patch fixes that
check.

START NOW only starts a countdown for a game that takes no remote connections, has two machines, or
is "alone" (server_alone). server_alone only passed if there was literally one player, making splitscreen play impossible.
Note the "xbox" menu style did not have this bug since its splitscreen
didn't accept remote connections at all.

server_alone becomes server_players_on_one_machine: TRUE if there is at
least one player and every player is on the same machine.
One player still qualifies. Machines that have joined without a player are not
counted, so a lone host's countdown is not stopped when one connects (the
per-tick server_ok_to_countdown check).

The countdown is fully controlled by the host machine, so there is no
change to the network protocol.

There's an existing test failure on test_elevator_prediction which also
exists on main, ignore.
2026-10-12 20:13:42 -05:00
MrBruh 6d64abdb42 Fix map sharing restart overflow and harden map validation 2026-10-13 07:43:41 +13:00
MrBruh 065d7f2b1d Merge pull request #263 from addisonbair/pregame-lobby 2026-10-12 20:34:15 +13:00
MrBruh 5a7c655a60 Testing branch review fixes
Network version 28: the host now holds a downloading machine's players out
of the game, and keeps a multiplayer map's first scripted BSP. Dynamic lights
and the flashlight stay on past the Xbox limits, and a second weapon picked
up while firing is readied. Machines of version 27 would disagree on these.

- A large co-op game's respawn fallback no longer picks a teammate who is in
  the air, outside the BSP, or riding an AI vehicle.
- A machine still downloading the map times out when it goes silent.
- Held players join through the late-join queue, so they get the same checks.
  A machine with no held players is started instead of being refused.
- The co-op teleport uses world positions, which are right for seated players.
- Overshield drain no longer cuts off a hit's flash, and hits over 0.02 flash.
- The menu XML is the generator's (Custom Edition's layout) again.
- port: markers on two new declarations.

Checked: ninja linux, android and web build; tools/harness,
test_touch_menu and test_web_build pass.
2026-10-12 20:01:49 +13:00
justinfilip 2598dbe8b6 An overshield's drain is not a shield hit, and a second weapon is readied. 2026-10-11 18:34:17 -05:00
MrBruh a2aad18f65 Custom Edition map sharing
Hosts send players who join without the game's Custom Edition map the map
and the resource maps it needs; the other players help, torrent-style.
Network version 27: new map sharing messages, and players of an internet
game now reach each other.
2026-10-12 08:07:14 +13:00
Addison Bair 59a74b0c4b The pregame screen opened through the port's menus everywhere
Fast setup and the network test's join opened ui.map's pregame screen by name, where ui_widget.c opens the port's lobby; a ui.map of only the menus' tags hosts and joins with both.
2026-10-11 14:08:51 +00:00
MrBruh 095973133e Shield color on the first-person arms too (#244) 2026-10-11 12:25:51 +13:00
MrBruh d03f6e2777 Merge pull request #248 from jcompto95-tech/viewmodel-shield
Energy shield effects visible on view models (on a toggle)
2026-10-11 10:45:31 +13:00
justinfilip a3c139ec53 A custom HUD digit that is its own bitmap no longer trips the check that every digit shares one bitmap. 2026-10-10 15:33:11 -05:00
jcompto95-techandClaude Opus 5.5 8ee3806792 The energy shield's flare on the first-person arms (display.viewmodel_shield)
Video Setup > FOV and Viewmodels > Arm Shields, off by default. The stock
game draws a unit's shield flare (its modifier shader, the cyborg's shield
plasma, as its shield is hit, charges and falls) on the body only; the
first-person arms never showed it. With Arm Shields on, the hands model is
drawn with the unit's own modifier shader and the unit's own function values
and change colors, as render_object_list draws the body: the same flare, on
the arms. The first-person weapon is drawn without it.

The flare is a first-person transparent group, so it is drawn in the
viewmodel's projection (display.viewmodel_fov) and lines up with the arms.
The setting is read in view_fov.c with the other viewmodel settings.

Only the drawing changes. Checked by compiling the changed units.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_015jtk9vPUKbWd48oBMzXuzd
2026-10-10 10:30:18 -04:00
MrBruh 775015e879 The buttons' letters placed where the map's are, and their settings read again (#56)
The map's letters do not sit alike on every icon: on the message icons'
sheet, X's and Y's are about 1.7 texels lower on their ovals than the
redraws put them. tools/button_assets.py layout now moves each icon's
letter (and Y's shadow, given the id "shadow") to where it best matches
the map's, and buttons.json keeps the move; the menus' large buttons move
by under 0.03 texels, the message icons' by up to 1.7. The PNGs are drawn
again, the sheet with all 256 levels of alpha rather than 32.

hud_hires_sprites_drawable read display.high_res_hud and high_res_text
only once, and hud_hires_sprite_bitmap kept its answer for the bitmap's
address, so turning either setting off or on left the message icons as
they were: both check again when the settings change, as
hud_hires_override_find does. ui_widget.c declares hud_hires_sprite_bitmap
with the port's other functions instead of in the block that calls it.
AUTHORS.md credits saulob for the redraws.

Checked with button_assets.py check against ui.map and side by side with
the map's icons; ninja linux and ninja android build, and the harness and
test_linux_port pass.
2026-10-10 20:03:40 +13:00
MrBruh 1a0045edda Merge pull request #56 from saulob/feature/high-res-ui-buttons
Add high-res UI controller buttons
2026-10-10 19:17:43 +13:00
MrBruh c44930abbe Single-player SETTINGS: placed by REVERT TO SAVED's tag, main's centring kept (#67)
SETTINGS goes before REVERT TO SAVED found by its tag
(restart_at_save_point_button: it opens its confirmation, so no function
names it), not at the second row, so that a map whose list has it elsewhere
gets it in its place, and one that has it not is left alone. The rows are
spaced over their own span only when the list grew for it, and the list
then keeps its height; a list with room keeps the centring pause_list_patch
now gives it.

Gamepads' OK no longer copies the changed bytes into the player's profile
itself: saving the profile makes it the player's (#227). The edited
profile's index has its comment, and the README says what the list does.
2026-10-10 17:13:14 +13:00
MrBruh 9a264e9230 Merge pull request #67 from saulob/feature/in-game-settings-menu
Add in-game Settings menu

Conflicts resolved: the campaign's pause menu goes before main's
menus_pc_chosen, which the early return keeps using (display.menus in any
case), and pause_campaign_patch passes pause_list_patch the growth it now
returns.
2026-10-10 16:46:51 +13:00
MrBruh b1a71709ef FOV and viewmodel settings: one unit, port marks, the lens flare cull (#234)
render_fov.c, viewmodel_fov.c and viewmodel_visibility.c are one unit,
port/linux/game/view_fov.c, with a header comment as the others have, real
for float, _pi for its own pi, the rasterizer's target by name, and no
isfinite shim in math.h (the angles' range test already refuses NaN). The
game code's hooks are marked "port:", their include at the end of each
block, and rasterizer_lights.c's loops declare before they act (C89).

The first-person weapon's lens flares are not culled by the world's
frustum (main's new off-screen cull): they are
drawn at the weapon's own projection, which display.viewmodel_fov can make
wider than the world's.

HALO_VIEWMODEL_VIS is HALO_VIEWMODEL_VISIBLE; the settings' descriptions and
help lines say "stock" view and fit their boxes; Video Setup's XML is
written again by ce_menus.py; the README's field of view text is a section
of its own.
2026-10-10 16:24:04 +13:00
MrBruh a8178af24a Merge pull request #234 from innerhat-dev/fov-viewmodel-controls
Add opt-in FOV and viewmodel controls to Video Setup
2026-10-10 15:52:26 +13:00
MrBruh b5a4870d05 Saved profile's controls: the comment wrapped as the file's (#227) 2026-10-10 15:23:16 +13:00