nx_silhouette_quality.nx
buildroot/runtime/nx_silhouette_quality.nx
about
nx_silhouette_quality.nx -- horizon/skyline quality grader.
Per the honest audit 2026-05-16: heightmap statistical graders
(nx_world_quality_grader) can return S-class for terrain that
nonetheless produces a FLAT-LOOKING HORIZON. This primitive
grades the SILHOUETTE -- what you see when you look toward the
horizon -- on 5 axes designed to catch "high-stats, low-vista"
worlds.
Method: from a camera viewpoint, sample N azimuth rays (default
64) around the horizon. For each ray, march outward across the
heightmap and find the maximum ANGULAR ELEVATION (apparent height
above the camera, projected to a small-angle proxy:
elev_proxy = (max_h - cam_y) / dist
scaled to Q14). This produces a silhouette of N samples.
AXES (Q14 [0, Q]; higher = better skyline):
0. ELEVATION_RANGE: max - min angular elevation across silhouette.
Worlds with all peaks at the same apparent height = 0.
1. PEAK_COUNT: local-maxima count; target 3-8 distinct peaks per
half-horizon. Catches uniform-tooth-saw silhouettes.
2. SMOOTHNESS: penalty for too-jagged AND too-smooth. Mean abs
second-difference compared to target band.
3. ASPECT_DIVERSITY: stddev of peak-to-peak widths. Catches
repetitive tooth patterns.
4. SKY_BALANCE: fraction of view that is sky (above horizon proxy
threshold); target 0.3 - 0.7. Catches "all mountains" and "all
flatland".
EMITS LAYER_VERDICT (kind = NX_LAYER_KIND_READABILITY,
REFINE_HINT = REFINE_MORE_FEATURES).
genealogy_id: appleton_1996_landscape_aesthetics +
horizon_silhouette_canon
lineage_id: nx_silhouette_quality_5axis_v1
dependencies 4 imports · 0 importers
imports: nx_syscalls.nxnx_tier.nxnx_camera_q14.nxnx_layer_verdict.nx
imported by: nobody (leaf or entry point)
call flow from main pre-order; caps 40 nodes / depth 6 declared; ↻ = already shown
structs
| none |
consts
| 48 | const NX_MAGIC_36000: i64 = 36000 |
| 50 | const NX_SQ_Q: nx_int = 16384 |
| 53 | const NX_SQ_AXIS_RANGE: nx_int = 0 |
| 54 | const NX_SQ_AXIS_PEAK_COUNT: nx_int = 1 |
| 55 | const NX_SQ_AXIS_SMOOTHNESS: nx_int = 2 |
| 56 | const NX_SQ_AXIS_ASPECT_DIV: nx_int = 3 |
| 57 | const NX_SQ_AXIS_SKY_BALANCE: nx_int = 4 |
| 59 | const NX_SQ_AXIS_COUNT: nx_int = 5 |
functions
| 71 | func _sq_build_silhouette( called by 1: nx_silhouette_quality_grade calls 2: nx_camera_cos_q14_centidegnx_camera_sin_q14_centideg |
| 113 | func _sq_range_q14( called by 1: nx_silhouette_quality_grade |
| 138 | func _sq_peak_count_q14(silhouette: *i64, n_rays: nx_int) -> nx_int called by 1: nx_silhouette_quality_grade |
| 163 | func _sq_smoothness_q14(silhouette: *i64, n_rays: nx_int) -> nx_int called by 1: nx_silhouette_quality_grade |
| 191 | func _sq_aspect_div_q14(silhouette: *i64, n_rays: nx_int) -> nx_int |
| 246 | func _sq_sky_balance_q14(silhouette: *i64, n_rays: nx_int) -> nx_int called by 1: nx_silhouette_quality_grade |
| 276 | func nx_silhouette_quality_grade( |
| 303 | func main() -> i64 |