Skip to content

[FIX] Optimize spatial sector detection by skipping updates.#2110

Open
Neloreck wants to merge 1 commit into
OpenXRay:devfrom
xray-forge:dev-fix-raycast-condition
Open

[FIX] Optimize spatial sector detection by skipping updates.#2110
Neloreck wants to merge 1 commit into
OpenXRay:devfrom
xray-forge:dev-fix-raycast-condition

Conversation

@Neloreck

@Neloreck Neloreck commented Jul 3, 2026

Copy link
Copy Markdown
Contributor

Changes

  • Gates detect_sector() behind STYPEFLAG_INVALIDSECTOR in R_dsgraph_structure::build_subspace() (renderables) and CRender::Calculate() (near-camera lights); unmoved objects skip both ray casts.
  • SpatialBase::spatial_move() raises STYPEFLAG_INVALIDSECTOR only when the object moved more than 1m from its last detection point.
  • Adds SpatialBase::last_sector_point, recorded in spatial_updatesector_internal(), to drive the move threshold.

Notes

  • Bring back previous condition check + introduce spatial move invalidation from xray-monilith
  • Root cause. xrRender: detectSector moved into dsgraph #1311 (a8d9187, "xrRender: detectSector moved into dsgraph") moved the sector raycast out of the flag-guarded SpatialBase::spatial_updatesector_internal() and into the callers in R_dsgraph_structure::build_subspace() and CRender::Calculate(), where it now runs before the STYPEFLAG_INVALIDSECTOR check. The guard still exists but only skips storing an already-computed result — so every visible renderable and every near-camera light issues 2 CDB::COLLIDER::ray_query casts on every main pass, even when its sector has not changed. Before xrRender: detectSector moved into dsgraph #1311 the arg-less spatial_updatesector() bailed on the flag and never raycast for objects whose sector was still valid.
  • Fix. Restores the STYPEFLAG_INVALIDSECTOR gate at both call sites, and raises the flag in spatial_move() only when the object moved a meaningful distance, so static world geometry and stationary lights reuse their cached sector.
  • Profiling (in-game level scene). CDB::COLLIDER::ray_query drops from ~604 to ~129 calls/frame (−79%).
  • Behavioral tradeoff. An object that moves less than 1 m² between frames reuses its cached render sector for that frame. Sectors are room-sized, so this is imperceptible and matches the pre-xrRender: detectSector moved into dsgraph #1311 flag-gated behavior. The actor/view-entity shadow path in build_subspace() is intentionally left unconditional (single object, negligible cost, avoids any stale-sector risk on the player shadow).

Links

Fixes issue introduced in #1311

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

1 participant