c4da5c9867
Give the prefiltered environment map a texture unit of its own
Hirek1932026-10-17 02:16:58 +02:00
97112b143b
Draw the depth of the whole scene before its colour
Hirek1932026-10-17 02:15:50 +02:00
f352718e4a
Stream model data through persistently mapped buffers
Hirek1932026-10-17 01:24:33 +02:00
8dd80c4d2e
Even out the fog cells with their neighbours and stagger the points next to lamps
Hirek1932026-10-17 00:37:58 +02:00
d07204db5c
Take the light of a lamp in the fog along four rays in the cells next to it
Hirek1932026-10-17 00:31:59 +02:00
f1c12ca651
Spread the light of a lamp in the fog over the size of a cell next to the lamp
Hirek1932026-10-17 00:27:28 +02:00
e31a49f917
Sample the fog cells across their whole size and take their lamps from fixed clusters
Hirek1932026-10-17 00:22:29 +02:00
e8dbaf70a9
Sample the fog cells in their middle across the view and dither the output
Hirek1932026-10-17 00:11:27 +02:00
aa522d7376
Integrate the light of lamps across the fog cells instead of one point sample
Hirek1932026-10-16 23:52:17 +02:00
0662df23a7
Copy the Python runtime next to the executable only when the Python install has changed
Hirek1932026-10-16 23:37:27 +02:00
6ee628aaa5
Steady the volumetric fog and add a switch for the old headlight beams
Hirek1932026-10-16 23:23:51 +02:00
8b929fc1da
Give the volumetric clouds lumps, sky and ground light and a fog colour by the angle from the sun
Hirek1932026-10-16 22:25:11 +02:00
2be85410ce
Draw volumetric clouds, their shadows, a volumetric fog and catalogue stars from a new weather system in the GL 4.6 renderer
Hirek1932026-10-16 21:44:47 +02:00
2e02cf8137
Lay the light cluster tiles over the window when the post processing is skippe; Bind the light cluster buffers when a viewport is created
Hirek1932026-10-15 20:26:23 +02:00
624c7f4f0b
Do not cap the reach of a light at 1 km in the cluster culling
Hirek1932026-10-15 20:25:51 +02:00
54990f41a6
fix(ai): release what the AI was holding when the player takes over
jerrrrycho
2026-10-15 19:39:35 +02:00
f47172f34d
Migration cleanup and renderer documentation
Hirek1932026-10-15 19:05:35 +02:00
b400255dae
Test/physics unit tests (#213)
jerrrrycho
2026-10-15 17:56:41 +02:00
c77151979a
Bind an empty shadow map instead of unbinding the shadow map unit
Hirek1932026-10-15 17:11:31 +02:00
9f2ae071a6
Use clustered light lists in forward shading
Hirek1932026-10-15 16:16:53 +02:00
6aa6e505e8
Cull lights into clusters in a compute pass
Hirek1932026-10-15 15:21:21 +02:00
f85cf5fe52
Build view-space light cluster grid in a compute pass
Hirek1932026-10-15 14:16:55 +02:00
c0f45184b8
Move light data from UBO to std430 SSBO
Hirek1932026-10-15 13:20:59 +02:00
677a96c293
Add SSBO and compute shader support to gl wrappers
Hirek1932026-10-15 12:13:44 +02:00
adf1b1736f
fix(tools): metalness is checked on a nearest sample of the B channel instead of a box-averaged one, so thin metal strips with B only 0 or 255 are no longer reported as half metal because downscaling averages their edges with the paint around them
build-fix-cab-lighting
fix/cab-lighting
maj00r
2026-10-14 23:42:43 +02:00
7b77e4cef8
test: test vehicle definitions load with GCC and Clang
jerrrrycho
2026-10-14 22:53:22 +02:00
e448489853
fix(tools): a skin material without a suffix is reported as unused when its ,1 ,2 versions exist, since the game loads those instead, so the 64 missing textures of the ELF were never missing in the game; param_specular in a shader without a sun highlight changes nothing and is only reported as information
maj00r
2026-10-14 22:39:06 +02:00
94c3eacb72
fix(tools): water keeps its large param_specular as the glint of the sun on its fixed mirror and is only reported as information; the norm says which files are checked, that textures without a material go on their diffuse alone, and that diffuse, specgloss and normal maps all become BC7 made from the TGA
maj00r
2026-10-14 22:28:52 +02:00
a717c8a0c1
docs(tools): the material norm is written for the shaders of the branch it lives on, with ambient occlusion, parallax mapping and the lighting fixes, and names master as the one that still lights the old way
maj00r
2026-10-14 22:11:34 +02:00
e27e9a3639
docs(tools): a dark metal is reported as one the shaders light as a painted surface, with the choice of a brighter diffuse for a real metal or B = 0 for paint, a metal reflects at least at half strength whatever its normal map alpha, and the source textures are TGA from which BC7 replaces the DDS
maj00r
2026-10-14 22:10:55 +02:00
47716b50ff
docs(tools): the material norm names the shaders it is written for, fix/cab-lighting from 2ecf589d with the sun highlight weighted by its cosine, headlights with their own highlight and param_glossiness as a Phong exponent, and how master differs; the validator reads both versions from the shader sources, its options, output levels and requirements are documented with the order in which to fix a vehicle
maj00r
2026-10-14 21:44:34 +02:00
0436ea2f2b
feat(tools): a material norm for the current shaders and a validator that checks .mat files and their textures against it, reading what each shader does with specgloss, glossiness, specular and reflection from the shader sources, so dielectrics with sun highlights far above the 0.06 of a real F0, mirror-like glossiness, half-metal or speckled metalness, metals with a dark albedo or no reflections, headlight-boosting param_specular, noisy maps, unknown shaders and missing textures are reported per material
maj00r
2026-10-14 20:57:16 +02:00
101ab5be5f
fix(shaders): a surface marked as metal in specgloss but with an albedo darker than any real metal is lit as the painted or dirty dielectric it stands for, with its diffuse back and its highlight held to 0.06, instead of going black without a diffuse term, and a metal reflects its surroundings at least at half strength whatever the alpha of its normal map says, since its reflection is all of its colour; materials without specgloss stay as they were
maj00r
2026-10-14 22:09:13 +02:00
8df87d42cf
fix(shaders): the highlight of the sun is multiplied by the cosine of its light, so surfaces no longer glare milky white under a low sun; headlights light a surface with 1.35 of its diffuse colour and add a GGX highlight of their own scaled by specgloss and param_specular instead of multiplying the whole light by one plus param_specular; normalmap, parallax, detail, shadowless, sunless and default_detail materials read param_glossiness as a Phong exponent, roughness = (2 / (n + 2))^1/4, instead of 1 - 1/n or a fixed mirror
maj00r
2026-10-14 21:42:33 +02:00
806dde70bf
feat(render): ambient occlusion with bent normals darkens only the light of the surroundings instead of the whole image, so the sun and headlights keep their full strength; the occlusion and the bent normal of the previous frame are reprojected into the lighting of the scene, with the motion of the camera and of every vehicle and cab taken into account and with depth checks against disocclusion, the ambient light follows how much of the sky the bent normal sees, and reflections of the environment are occluded where the cone of visible directions around the bent normal cuts off the reflected lobe, only where the occlusion is clear enough that open flat panels and windows keep their grazing reflections
maj00r
2026-10-14 18:02:35 +02:00
a24f9fae3f
feat(render): ground truth ambient occlusion darkens creases, recesses and the space under desks and frames, computed at half resolution from the reversed depth buffer with a depth-aware blur and multiplied into the image before motion blur, so it works with the default settings; thin parts in front of a surface, such as a steering wheel, shade it only from close by, and gfx.postfx.gtao.enabled, radius, intensity, directions and steps set it from the ini
maj00r
2026-10-14 16:56:38 +02:00
000b8656cc
fix(render): dark parts of a cab and of the running gear are no longer crushed to black, as the AgX look raises its contrast power from 1.0 in the shadows up to 1.6 only from the middle tones on, which keeps the bright tones, the outside view and the night as they were but leaves black knobs, levers and lettering visible on a black desk; the light of a cab can be scaled with gfx.cab.ambient, 1.0 by default
maj00r
2026-10-14 16:55:43 +02:00
60b0a335b0
test: stub basic_node::radius_() for GCC and Clang
jerrrrycho
2026-10-14 21:58:30 +02:00
3365d42c3a
test: unit tests of the simulation core, run as part of the build
jerrrrycho
2026-10-14 16:36:40 +02:00
6c7aea19c2
build: the simulation core as a library the game links
jerrrrycho
2026-10-14 19:22:09 +02:00
02bb352caf
refactor(physics): read vehicle definitions from text as well as files
jerrrrycho
2026-10-14 16:36:39 +02:00
fac4eb0547
build: doctest 2.4.11 in ref/
jerrrrycho
2026-10-14 15:20:46 +02:00
20cf81b362
fix(shaders): parallax mapping reads its depth from a mip about four texels per pixel coarser, filtered bicubically where the hit is refined, so the relief no longer breaks into stalactites and the edges of stones no longer step along the texel grid of the compressed depth; it takes 16 to 64 layers by the angle of view and six steps of refinement, casts the shadows of the relief from the sun over the sun light and darkens the hollows deeper than the mean depth of the texture while lightening the tops, so the mean brightness of a surface stays the same
maj00r
2026-10-14 15:02:14 +02:00
3d6a465570
fix(shaders): parallax mapping of the opengl33 materials is shared by the four parallax shaders in parallax.glsl and samples its depth with the gradients of the surface instead of letting a loop of varying length pick the mip level, picks the number of layers by the angle of view alone and refines the hit with a binary search instead of one linear step, so stones near the camera no longer show combs of layer slices; it fades out between 60 and 100 m instead of stopping at a hard line and fades out at grazing angles, and the simple offset without extra effects no longer divides by an unbounded cosine of the view
maj00r
2026-10-14 14:23:52 +02:00
d93d51894d
feat(track): frogs, crossings, guard rails with their castings and spacers, check rails and shared running surfaces for every rail profile again, not only for tracks without a profile, default, s60, uic60 and s39; grooved profiles keep their shared grooves without check rails
build-feat-rail-crossings
feat/rail-crossings
maj00r
2026-10-14 14:01:15 +02:00
c4772823b3
feat(track): a check rail is held to its running rail by spacer blocks every 0.5 m along its straight part, laid in the same way as the spacers of a guard rail at a wide crossing, below the head from the web of the running rail to the face of the check rail, so the flangeway stays open above them; a check rail replaced by a wing rail gets none; the spacing of spacers and castings is shared by guard rails and check rails
maj00r
2026-10-14 14:01:08 +02:00
55abd24ead
fix(track): at a crossing at nearly a right angle the tip of a guard rail under the wheels of the other track takes their rolling surface on its top, bright under a used track and rusty under an unused one, with the sides staying matte, instead of the whole tip going matte because the plain span of the tread was laid as a band between two lines it does not have; plain spans of treads are painted in the debug colour of EU07_EDITOR_TREADS too
maj00r
2026-10-14 13:09:44 +02:00
1fa7dee5d6
fix(track): at a crossing at a wide angle the floor of the flangeway between a running rail and its guard rail is laid only where real crossings have it, as the cast floor of each corner up to 0.3 m past the rail of the other track and as separate spacer blocks every 0.5 m along the rest of the guard, and the floor takes its texture across its width at the scale of the head instead of one stretched column; the wheels of the other track roll over a guard rail across their whole tread instead of only over the head of their rail; and when the tracks cross at nearly a right angle the treads of the other track are laid as plain spans along the rail instead of lines running almost straight across it, which left fins standing up at every edge of a tread
maj00r
2026-10-14 12:43:36 +02:00
c177581d8f
fix(track): a point of a rail profile clamped to a cut edge of a lofted span is never moved past its own place nor raised past its own height, and the edges at a station are read from the side of the span being laid, so the rings at a step of an edge or at a bent mitred end no longer stretch points out of the profile and stand them up to 18 mm above the head as thin fins at the corners of wide crossings, and points of other cut rails sit exactly on the profile instead of up to a millimetre off it
maj00r
2026-10-14 12:25:57 +02:00
434923dae6
fix(track): the part of a guard rail under the running rail of the other track at a wide crossing takes the rail material of the other track, whose wheels alone roll there, instead of the brighter of the two, so a guard of a used track under an unused rail stays rusty, and it ends at the head of that rail without a tinted fade, since the guard itself is never rolled on
maj00r
2026-10-14 11:41:35 +02:00
2a5dda1509
feat(track): at a crossing at a wide angle the tread of the other track is laid where its wheels roll over the mitred corners: the part of a guard rail under the running rail of the other track becomes a running surface in the shared tread material instead of matte, and running rails of different materials share the tread over the rolled band of the other track instead of over a square span; wide_tread draws the edges of the band from the crossing itself, since the gauge lines meet in one point at right angles, and a tread gives its own fade, widened for bands lying across the rail; treaded keeps the matte parts of a guard rail matte, lay_treads splits guard rails at their treads, and a piece of no triangles is not inserted
maj00r
2026-10-14 11:25:34 +02:00
572ee569dc
feat(track): at a crossing at a wide angle every head of one track meets every head of the other in a mitre from the corner of their flangeways to the far corner of the heads, the way the corners of a cast diamond look, so the running rails and guard rails of both tracks form closed corners and only the flangeways stay open, instead of the rails of one track going through and the other ones glued to their sides; corner_cut gives the mitres, as bends of the running rails and as miters of the guard rails; the fit of a loft end to the profile of another rail and the field and gauge outlines of the rail profile are gone with the gluing
maj00r
2026-10-14 11:08:02 +02:00
f27ed682c0
feat(track): the guard rails of a crossing at a wide angle reach a metre past the rails of the other track instead of 0.3 m and open their flangeway over 0.6 m at the ends, the way the guard arms of the corners of a diamond run out on real crossings, the reach and the flare are the constants guard_reach and guard_flare shared by the plan and the layer
maj00r
2026-10-14 10:53:28 +02:00
701d82d1bd
refactor(track): the cap of a lofted rail end takes its texture from cap_texture and its triangles from ear_clip instead of computing both inside cap_loft
maj00r
2026-10-14 09:57:04 +02:00
74ae36e33a
refactor(track): the plates, fillers and check rails of a rail drawing are made from one box_profile and one helper for both sides, and the colour of a tread is sampled by sample_dds and sample_image into one colour_mean, a block of a DXT texture decoded by add_dxt_block, instead of one function
maj00r
2026-10-14 09:55:24 +02:00
474e1f3104
refactor(track): the crossings of the rails are found in steps, the tracks nearby, the meeting of two rails with its refined place and the crossing made of it, and the crossings of the neighbours mapped on this track, and the check rails are planned, merged, kept clear of blocks and cut in separate functions instead of two long functions; path_count and path_neighbour replace the repeated choice of the paths and the ends of a switch or a plain track
maj00r
2026-10-14 09:52:19 +02:00
47d67b2b1f
refactor(track): the rails are planned by the class TTrack::rail_planner instead of one function: each crossing is added by its kind (grooved, wide, acute, obtuse), the acute frog of a crossing and of a switch is one acute_frog and the vee of grooved rails one add_vee, the switch frog is described as a rail_crossing, the corners of crossings at a middle angle are kept as rail_crossing instead of a copy of its fields and framed by frame_guard, wide() takes the crossing and a wide_cut value instead of ten arguments, and the knots are sorted by knots::sort
maj00r
2026-10-14 09:48:12 +02:00
c9e492bb3e
refactor(track): a rail is laid by the class TTrack::rail_layer instead of one function of lambdas sharing a current material and the bends and fits of the ends; a piece of rail is a rail_piece value with its material, the ends of a run are passed as piece_ends, the bands across the top of the head of a running and of a shared tread are laid from one table each by lay_top, the guard and check rails take their flared offsets from one helper, and the grooved profile is split by split_grooved and cut by top_cuts
maj00r
2026-10-14 09:40:28 +02:00
278fb88bb3
refactor(track): the rail code is split by concern into gauge lines, crossings and check rails, rail materials, rail profile measuring, planning the cuts and laying the geometry, instead of one TrackRails.cpp; rail_offset reuses nearest_distance and lateral; TTrack::rail_dimensions measures the profile through track_rails::measure_rail
maj00r
2026-10-14 09:24:52 +02:00
0138635358
refactor(track): the rail layout value types (crossings, sizes, check and guard rails, cuts, bands, fills, treads, layout) and the wheel and rail constants live in world/RailLayout.h in track_rails instead of inside TTrack
maj00r
2026-10-14 09:21:19 +02:00
347d9035e0
refactor(track): a lofted rail span is described by one loft_span value instead of twenty arguments, and the knot line helpers (sample, bound, meetings, middle, shifted) live once in world/Knots.h instead of in lambdas of the segment and of lay_rail
maj00r
2026-10-14 09:16:37 +02:00
9a8cc08494
test(editor): geomhash also logs an exact hash of the bits of every vertex value, the userdata and the names of the tread materials, so a refactor can be checked to change nothing
maj00r
2026-10-14 09:08:55 +02:00
23975654a4
feat(track): at a crossing at a wide angle the rails and guard rails ending against the side of another rail or guard rail are glued to it, their ends fitted to its profile height by height instead of square ends with caps and a gap of 5 mm, so the corners of the crossing are closed; the ends at the flangeways stay open for the flanges; a loft span can shift its first and last cross-section along the track by a fit given per height of the profile, and the rail profile gives the outlines of its field and gauge sides
maj00r
2026-10-14 03:09:08 +02:00
2cb2ecfe0f
revert(track): no filler block at obtuse crossings, the flangeway between the point rail and the knuckle rail stays open as before
maj00r
2026-10-14 02:22:48 +02:00
481b76cea9
fix(track): the filler block of an obtuse crossing ends where the head of the point rail reaches its full width, so it only closes the flangeway and no longer shows as a plate in the widening vee between the point and the knuckle rail
maj00r
2026-10-14 02:21:54 +02:00
a0958cd44e
feat(track): at a crossing at a wide angle each guard rail is glued to its running rail by a filler block between their webs along its whole length, so the flangeways and the gaps cut for the wheels of the other track have a floor instead of showing the ballast; the filler of the track not going through lies a millimetre lower where both overlap
maj00r
2026-10-14 02:16:52 +02:00
3a43871f42
feat(track): at an obtuse crossing the flangeway between the point rail and the knuckle rail is closed below by a filler block at the height of the webs, from the meeting point to where the point reaches its full profile, so the ballast no longer shows through the gap; the rail profile gives the middle of its web and the height where its head starts above it
maj00r
2026-10-14 02:05:17 +02:00
a87148a96c
fix(track): at an obtuse crossing the rail ending at the meeting point and the rail going on from it are joined by a mitre on the bisector of the bend, like one bent knuckle rail, instead of two square ends overlapping in a wedge, and the check rails of the two tracks meet there the same way instead of overlapping each other by 3 cm; a loft span can turn its first and last cross-section about the gauge line for such joints
maj00r
2026-10-14 01:49:24 +02:00
a84e30670f
fix(track): the legs of an acute nose are cut along the line halfway between the gauge lines of the two rails, followed every 10 cm from the tip to where the full profiles part, instead of a straight bisector, so the nose of a switch frog with a curved diverging path has no seam opening along its middle
maj00r
2026-10-14 01:17:28 +02:00
2b554183ed
fix(track): a loft cut along its length keeps its surface where the cut crosses a point of the profile: each span between stations sorts the points as clamped or open by its middle, so the ring at a station where a point lies right on the edge does not drop the next point to its own height and leave a dark groove along the top of the rail; clamped points that are not on the edge are kept between the heights of the edge on both sides of the run, so they never stand above the surface
maj00r
2026-10-14 00:47:39 +02:00
1797484809
fix(track): the pieces of the top of a rail head are laid only where they have width on the head between its cut edges, split where the edges of the wheel treads cross those cut edges, and the shared spans reach 2 cm further for the fade, so no inverted piece is drawn inside the neighbouring rail and no fin stands out of the head; EU07_EDITOR_TREADS paints the pieces in plain colours: blue shared, green and red the fades, yellow the edge of the rolled band, magenta the matte part out of reach of the wheels
maj00r
2026-10-14 00:47:39 +02:00
5122c2ccb4
fix(track): the treads of the wheels reach from the gauge line as far as a wheel 140 mm wide with the back faces 1360 mm apart does, 820 mm from the axis of a standard gauge track, instead of a flat 100 mm
maj00r
2026-10-14 00:03:06 +02:00
a6e39ba77f
feat(track): frogs, crossings and shared running surfaces only for the rail profiles the sceneries of the package use: tracks without a profile, default, s60, uic60 and s39; rails of other profiles are laid whole again
maj00r
2026-10-14 00:03:06 +02:00
592d1687d5
feat(track): the texture of a shared running surface blends into the texture of the rail it lies on: 2 cm on each side of the boundary both are drawn in tinted variants of their materials that fade per vertex into the mean colour of the two treads, sampled from the texture files, so the edge of the wheels of the other track leaves a soft band instead of a line
maj00r
2026-10-14 00:01:20 +02:00