diff --git a/tools/quake3/q3map2/decals.cpp b/tools/quake3/q3map2/decals.cpp index b2c1769b..cbee2c44 100644 --- a/tools/quake3/q3map2/decals.cpp +++ b/tools/quake3/q3map2/decals.cpp @@ -248,34 +248,29 @@ static bool MakeTextureMatrix( decalProjector_t& dp, const Plane3f& projection, note: non-normalized axes will screw up the plane transform */ -static void TransformDecalProjector( decalProjector_t *in, const Vector3 (&axis)[ 3 ], const Vector3& origin, decalProjector_t *out ){ +static void TransformDecalProjector( const decalProjector_t& in, const Vector3& origin, decalProjector_t& out ){ /* copy misc stuff */ - out->si = in->si; - out->numPlanes = in->numPlanes; + out.si = in.si; + out.numPlanes = in.numPlanes; /* translate bounding box and sphere (note: rotated projector bounding box will be invalid!) */ - out->minmax.mins = in->minmax.mins - origin; - out->minmax.maxs = in->minmax.maxs - origin; - out->center = in->center - origin; - out->radius = in->radius; - out->radius2 = in->radius2; + out.minmax.mins = in.minmax.mins - origin; + out.minmax.maxs = in.minmax.maxs - origin; + out.center = in.center - origin; + out.radius = in.radius; + out.radius2 = in.radius2; /* translate planes */ - for ( int i = 0; i < in->numPlanes; ++i ) + for ( int i = 0; i < in.numPlanes; ++i ) { - out->planes[ i ].a = vector3_dot( in->planes[ i ].normal(), axis[ 0 ] ); - out->planes[ i ].b = vector3_dot( in->planes[ i ].normal(), axis[ 1 ] ); - out->planes[ i ].c = vector3_dot( in->planes[ i ].normal(), axis[ 2 ] ); - out->planes[ i ].d = in->planes[ i ].dist() - vector3_dot( out->planes[ i ].normal(), origin ); + out.planes[ i ] = plane3_translated( in.planes[ i ], -origin ); } /* translate texture matrix */ for ( int i = 0; i < 2; ++i ) { - out->texMat[ i ][ 0 ] = vector3_dot( in->texMat[ i ].vec3(), axis[ 0 ] ); - out->texMat[ i ][ 1 ] = vector3_dot( in->texMat[ i ].vec3(), axis[ 1 ] ); - out->texMat[ i ][ 2 ] = vector3_dot( in->texMat[ i ].vec3(), axis[ 2 ] ); - out->texMat[ i ][ 3 ] = vector3_dot( out->texMat[ i ].vec3(), origin ) + in->texMat[ i ][ 3 ]; + out.texMat[ i ] = in.texMat[ i ]; + out.texMat[ i ].w() += vector3_dot( in.texMat[ i ].vec3(), origin ); } } @@ -403,10 +398,10 @@ void ProcessDecals(){ /* create projectors */ if ( distance > 0.125f ) { /* tesselate the patch */ - const mesh_t mesh = TessellatedMesh( p.mesh, IterationsForCurve( p.longestCurve, patchSubdivisions ) ); + mesh_t mesh = TessellatedMesh( p.mesh, IterationsForCurve( p.longestCurve, patchSubdivisions ) ); /* offset by projector origin */ - for ( bspDrawVert_t& vert : Span( mesh.verts, mesh.numVerts() ) ) + for ( bspDrawVert_t& vert : mesh ) vert.xyz += e.origin; /* iterate through the mesh quads */ @@ -447,7 +442,7 @@ void ProcessDecals(){ projects a decal onto a winding */ -static void ProjectDecalOntoWinding( decalProjector_t& dp, const mapDrawSurface_t& ds, winding_t& w ){ +static void ProjectDecalOntoWinding( const decalProjector_t& dp, const mapDrawSurface_t& ds, winding_t& w ){ /* dummy check */ if ( w.size() < 3 ) { return; @@ -538,7 +533,7 @@ static void ProjectDecalOntoWinding( decalProjector_t& dp, const mapDrawSurface_ projects a decal onto a brushface surface */ -static void ProjectDecalOntoFace( decalProjector_t& dp, const mapDrawSurface_t& ds ){ +static void ProjectDecalOntoFace( const decalProjector_t& dp, const mapDrawSurface_t& ds ){ /* dummy check */ if ( ds.sideRef == nullptr ) { return; @@ -563,7 +558,7 @@ static void ProjectDecalOntoFace( decalProjector_t& dp, const mapDrawSurface_t& projects a decal onto a patch surface */ -static void ProjectDecalOntoPatch( decalProjector_t& dp, mapDrawSurface_t& ds ){ +static void ProjectDecalOntoPatch( const decalProjector_t& dp, const mapDrawSurface_t& ds ){ /* backface check */ if ( ds.planar ) if ( vector3_dot( dp.planes[ 0 ].normal(), mapplanes[ ds.planeNum ].normal() ) < -0.0001f ) @@ -592,7 +587,7 @@ static void ProjectDecalOntoPatch( decalProjector_t& dp, mapDrawSurface_t& ds ){ projects a decal onto a triangle surface */ -static void ProjectDecalOntoTriangles( decalProjector_t& dp, const mapDrawSurface_t& ds ){ +static void ProjectDecalOntoTriangles( const decalProjector_t& dp, const mapDrawSurface_t& ds ){ /* triangle surfaces without shaders don't get marks by default */ if ( ds.type == ESurfaceType::Triangles && ds.shaderInfo->shaderText == nullptr ) { @@ -626,7 +621,6 @@ static void ProjectDecalOntoTriangles( decalProjector_t& dp, const mapDrawSurfac */ void MakeEntityDecals( const entity_t& e ){ - int i, j; decalProjector_t dp; @@ -641,19 +635,18 @@ void MakeEntityDecals( const entity_t& e ){ Timer timer; /* walk the list of decal projectors */ - for ( i = 0; i < numProjectors; ++i ) + for ( const decalProjector_t& projector : Span( projectors, numProjectors ) ) { /* print pacifier */ ++pacifier; /* get projector */ - TransformDecalProjector( &projectors[ i ], g_vector3_axes, e.origin, &dp ); + TransformDecalProjector( projector, e.origin, dp ); /* walk the list of surfaces in the entity */ - for ( j = e.firstDrawSurf; j < numMapDrawSurfs; ++j ) + for ( const mapDrawSurface_t& ds : Span( mapDrawSurfs + e.firstDrawSurf, mapDrawSurfs + numMapDrawSurfs ) ) { /* get surface */ - mapDrawSurface_t& ds = mapDrawSurfs[ j ]; if ( ds.verts.empty() ) { continue; } diff --git a/tools/quake3/q3map2/fog.cpp b/tools/quake3/q3map2/fog.cpp index 7e3e037e..a51f46a3 100644 --- a/tools/quake3/q3map2/fog.cpp +++ b/tools/quake3/q3map2/fog.cpp @@ -54,7 +54,7 @@ static std::pair, std::optional> SplitMeshByPlane( int frontAprox, backAprox; for ( i = 0; i < 2; ++i ) { - const bspDrawVert_t *dv = in.verts; + const bspDrawVert_t *dv = in.verts(); c_front = 0; c_back = 0; c_on = 0; @@ -196,8 +196,6 @@ static std::pair, std::optional> SplitMeshByPlane( return { std::move( f ), std::move( b ) }; else return { std::move( b ), std::move( f ) }; - - } @@ -210,7 +208,7 @@ static bool ChopPatchSurfaceByBrush( mapDrawSurface_t& ds, const brush_t *b ){ mesh_t outside[MAX_BRUSH_SIDES]; int numOutside = 0; - mesh_t m( mesh_view_t ( ds.patchWidth, ds.patchHeight, ds.verts.data() ) ); + mesh_t m( ds.patchWidth, ds.patchHeight, ds.verts.data() ); // only split by the top and bottom planes to avoid // some messy patch clipping issues @@ -224,13 +222,13 @@ static bool ChopPatchSurfaceByBrush( mapDrawSurface_t& ds, const brush_t *b ){ // nothing actually contained inside return false; } - m.swap( *back ); + m = std::move( *back ); if ( front ) { if ( numOutside == MAX_BRUSH_SIDES ) { Error( "MAX_BRUSH_SIDES" ); } - outside[ numOutside ].swap( *front ); + outside[ numOutside ] = std::move( *front ); numOutside++; } } @@ -246,9 +244,9 @@ static bool ChopPatchSurfaceByBrush( mapDrawSurface_t& ds, const brush_t *b ){ /* ydnar: do this the hacky right way */ mapDrawSurface_t& newds = AllocDrawSurface( ESurfaceType::Patch ); newds = ds; - newds.patchWidth = outside[ i ].width; + newds.patchWidth = outside[ i ].width; newds.patchHeight = outside[ i ].height; - newds.verts.assign( outside[ i ].verts, outside[ i ].verts + outside[ i ].numVerts() ); + newds.verts.assign( outside[ i ].begin(), outside[ i ].end() ); } /* only rejigger this patch if it was chopped */ @@ -259,9 +257,9 @@ static bool ChopPatchSurfaceByBrush( mapDrawSurface_t& ds, const brush_t *b ){ InvertMesh( m ); /* replace ds with m */ - ds.patchWidth = m.width; + ds.patchWidth = m.width; ds.patchHeight = m.height; - ds.verts.assign( m.verts, m.verts + m.numVerts() ); + ds.verts.assign( m.begin(), m.end() ); } return true; diff --git a/tools/quake3/q3map2/light_bounce.cpp b/tools/quake3/q3map2/light_bounce.cpp index 927067f9..6f3abc82 100644 --- a/tools/quake3/q3map2/light_bounce.cpp +++ b/tools/quake3/q3map2/light_bounce.cpp @@ -648,9 +648,9 @@ void RadLightForPatch( int num, int lightmapNum, const rawLightmap_t *lm, const /* construct a bogus vert list with color index stuffed into color[ 0 ] */ mesh_t bogus( ds.patchWidth, ds.patchHeight ); - std::copy_n( &yDrawVerts[ ds.firstVert ], ds.numVerts, bogus.verts ); + std::copy_n( &yDrawVerts[ ds.firstVert ], ds.numVerts, bogus.verts() ); for ( int i = 0; i < ds.numVerts; ++i ) - bogus.verts[ i ].color[ 0 ][ 0 ] = i; + bogus.verts()[ i ].color[ 0 ][ 0 ] = i; /* build a subdivided mesh identical to shadow facets for this patch */ /* this MUST MATCH FacetsForPatch() identically! */ @@ -659,7 +659,7 @@ void RadLightForPatch( int num, int lightmapNum, const rawLightmap_t *lm, const /* FIXME: build interpolation table into color[ 1 ] */ /* fix up color indexes */ - for ( bspDrawVert_t& vert : Span( mesh.verts, mesh.numVerts() ) ) + for ( bspDrawVert_t& vert : mesh ) { if ( vert.color[ 0 ][ 0 ] >= ds.numVerts ) { vert.color[ 0 ][ 0 ] = ds.numVerts - 1; diff --git a/tools/quake3/q3map2/map.cpp b/tools/quake3/q3map2/map.cpp index 89941349..fb682e54 100644 --- a/tools/quake3/q3map2/map.cpp +++ b/tools/quake3/q3map2/map.cpp @@ -1234,7 +1234,7 @@ static void AdjustBrushesForOrigin( entity_t& ent, const Vector3& offset ){ /* walk patch list */ for ( parseMesh_t& p : ent.patches ) { - for ( bspDrawVert_t& vert : Span( p.mesh.verts, p.mesh.numVerts() ) ) + for ( bspDrawVert_t& vert : p.mesh ) vert.xyz += offset; } } @@ -1295,7 +1295,7 @@ static void SetEntityBounds( entity_t& e ){ } for ( const parseMesh_t& p : e.patches ) { - for ( const bspDrawVert_t& vert : Span( p.mesh.verts, p.mesh.numVerts() ) ) + for ( const bspDrawVert_t& vert : p.mesh ) minmax.extend( vert.xyz ); } diff --git a/tools/quake3/q3map2/mesh.cpp b/tools/quake3/q3map2/mesh.cpp index cfa5a091..dc3148c4 100644 --- a/tools/quake3/q3map2/mesh.cpp +++ b/tools/quake3/q3map2/mesh.cpp @@ -115,11 +115,11 @@ void TransposeMesh( mesh_t& m ) { for ( int h = 0; h < m.height; ++h ) { for ( int w = 0; w < m.width; ++w ) { - out.verts[ w * m.height + h ] = m.verts[ h * m.width + w ]; + out.verts()[ w * m.height + h ] = m.verts()[ h * m.width + w ]; } } - m.swap( out ); + m = std::move( out ); } void InvertMesh( mesh_t& m ) { @@ -206,7 +206,7 @@ void MakeMeshNormals( mesh_t& in ){ if ( x < 0 || x >= in.width || y < 0 || y >= in.height ) { break; // edge of patch } - Vector3 temp = in.verts[y * in.width + x].xyz - base; + Vector3 temp = in[y][x].xyz - base; if ( VectorNormalize( temp ) == 0 ) { continue; // degenerate edge, get more dist } @@ -275,16 +275,17 @@ void PutMeshOnCurve( mesh_t& in ) { */ mesh_t SubdivideMesh( const mesh_view_t in, float maxError, float minLength ){ bspDrawVert_t expand[MAX_EXPANDED_AXIS][MAX_EXPANDED_AXIS]; - mesh_view_t out( in.width, in.height, expand[0] ); + int width = in.width; + int height = in.height; /* copy each row */ for ( int h = 0; h < in.height; ++h ) std::copy_n( in[h], in.width, expand[h] ); // horizontal subdivisions - for ( int i, j = 0; j + 2 < out.width; j += 2 ) { + for ( int i, j = 0; j + 2 < width; j += 2 ) { // check subdivided midpoints against control points - for ( i = 0; i < out.height; ++i ) { + for ( i = 0; i < height; ++i ) { const Vector3 prevxyz = expand[i][j + 1].xyz - expand[i][j].xyz; const Vector3 nextxyz = expand[i][j + 2].xyz - expand[i][j + 1].xyz; const Vector3 midxyz = ( expand[i][j].xyz + expand[i][j + 1].xyz * 2 + expand[i][j + 2].xyz ) * 0.25; @@ -301,19 +302,19 @@ mesh_t SubdivideMesh( const mesh_view_t in, float maxError, float minLength ){ } } - if ( out.width + 2 >= MAX_EXPANDED_AXIS ) { + if ( width + 2 >= MAX_EXPANDED_AXIS ) { break; // can't subdivide any more } - if ( i == out.height ) { + if ( i == height ) { continue; // didn't need subdivision } // insert two columns and replace the peak - out.width += 2; + width += 2; - for ( i = 0; i < out.height; ++i ) { - for ( int k = out.width - 1; k > j + 3; --k ) { + for ( i = 0; i < height; ++i ) { + for ( int k = width - 1; k > j + 3; --k ) { expand[i][k] = expand[i][k - 2]; } expand[i][j + 3] = LerpDrawVert( expand[i][j + 1], expand[i][j + 2] ); @@ -326,9 +327,9 @@ mesh_t SubdivideMesh( const mesh_view_t in, float maxError, float minLength ){ } // vertical subdivisions - for ( int i, j = 0; j + 2 < out.height; j += 2 ) { + for ( int i, j = 0; j + 2 < height; j += 2 ) { // check subdivided midpoints against control points - for ( i = 0; i < out.width; ++i ) { + for ( i = 0; i < width; ++i ) { const Vector3 prevxyz = expand[j + 1][i].xyz - expand[j][i].xyz; const Vector3 nextxyz = expand[j + 2][i].xyz - expand[j + 1][i].xyz; const Vector3 midxyz = ( expand[j][i].xyz + expand[j + 1][i].xyz * 2 + expand[j + 2][i].xyz ) * 0.25; @@ -344,19 +345,19 @@ mesh_t SubdivideMesh( const mesh_view_t in, float maxError, float minLength ){ } } - if ( out.height + 2 >= MAX_EXPANDED_AXIS ) { + if ( height + 2 >= MAX_EXPANDED_AXIS ) { break; // can't subdivide any more } - if ( i == out.width ) { + if ( i == width ) { continue; // didn't need subdivision } // insert two columns and replace the peak - out.height += 2; + height += 2; - for ( i = 0; i < out.width; ++i ) { - for ( int k = out.height - 1; k > j + 3; --k ) { + for ( i = 0; i < width; ++i ) { + for ( int k = height - 1; k > j + 3; --k ) { expand[k][i] = expand[k - 2][i]; } expand[j + 3][i] = LerpDrawVert( expand[j + 1][i], expand[j + 2][i] ); @@ -370,11 +371,11 @@ mesh_t SubdivideMesh( const mesh_view_t in, float maxError, float minLength ){ // collapse the verts - for ( int i = 1; i < out.height; ++i ) { - memmove( out[i], expand[i], out.width * sizeof( bspDrawVert_t ) ); + for ( int i = 1; i < height; ++i ) { + memmove( expand[0] + width * i, expand[i], width * sizeof( bspDrawVert_t ) ); } - return mesh_t( out ); + return mesh_t( width, height, expand[0] ); } @@ -410,7 +411,8 @@ int IterationsForCurve( float len, int subdivisions ){ mesh_t SubdivideMesh2( const mesh_view_t in, int iterations ){ bspDrawVert_t expand[ MAX_EXPANDED_AXIS ][ MAX_EXPANDED_AXIS ]; - mesh_view_t out( in.width, in.height, expand[0] ); + int width = in.width; + int height = in.height; /* copy each row */ for ( int h = 0; h < in.height; ++h ) @@ -420,18 +422,18 @@ mesh_t SubdivideMesh2( const mesh_view_t in, int iterations ){ for ( ; iterations > 0; --iterations ) { /* horizontal subdivisions */ - for ( int j = 0; j + 2 < out.width; j += 4 ) + for ( int j = 0; j + 2 < width; j += 4 ) { /* check size limit */ - if ( out.width + 2 >= MAX_EXPANDED_AXIS ) { + if ( width + 2 >= MAX_EXPANDED_AXIS ) { break; } /* insert two columns and replace the peak */ - out.width += 2; - for ( int i = 0; i < out.height; ++i ) + width += 2; + for ( int i = 0; i < height; ++i ) { - for ( int k = out.width - 1; k > j + 3; --k ) + for ( int k = width - 1; k > j + 3; --k ) expand [ i ][ k ] = expand[ i ][ k - 2 ]; expand[ i ][ j + 3 ] = LerpDrawVert( expand[ i ][ j + 1 ], expand[ i ][ j + 2 ] ); @@ -441,18 +443,18 @@ mesh_t SubdivideMesh2( const mesh_view_t in, int iterations ){ } /* vertical subdivisions */ - for ( int j = 0; j + 2 < out.height; j += 4 ) + for ( int j = 0; j + 2 < height; j += 4 ) { /* check size limit */ - if ( out.height + 2 >= MAX_EXPANDED_AXIS ) { + if ( height + 2 >= MAX_EXPANDED_AXIS ) { break; } /* insert two columns and replace the peak */ - out.height += 2; - for ( int i = 0; i < out.width; ++i ) + height += 2; + for ( int i = 0; i < width; ++i ) { - for ( int k = out.height - 1; k > j + 3; --k ) + for ( int k = height - 1; k > j + 3; --k ) expand[ k ][ i ] = expand[ k - 2 ][ i ]; expand[ j + 3 ][ i ] = LerpDrawVert( expand[ j + 1 ][ i ], expand[ j + 2 ][ i ] ); @@ -463,11 +465,11 @@ mesh_t SubdivideMesh2( const mesh_view_t in, int iterations ){ } /* collapse the verts */ - for ( int i = 1; i < out.height; ++i ) - memmove( out[ i ], expand[ i ], out.width * sizeof( bspDrawVert_t ) ); + for ( int i = 1; i < height; ++i ) + memmove( expand[0] + width * i, expand[ i ], width * sizeof( bspDrawVert_t ) ); /* return to sender */ - return mesh_t( out ); + return mesh_t( width, height, expand[0] ); } @@ -495,36 +497,37 @@ inline Vector3 ProjectPointOntoVector( const Vector3& point, const Vector3& vSta */ mesh_t RemoveLinearMeshColumnsRows( const mesh_t& in ) { bspDrawVert_t expand[MAX_EXPANDED_AXIS][MAX_EXPANDED_AXIS]; - mesh_view_t out( in.width, in.height, expand[0] ); + int width = in.width; + int height = in.height; /* copy each row */ for ( int h = 0; h < in.height; ++h ) std::copy_n( in[h], in.width, expand[h] ); - for ( int j = 1; j < out.width - 1; ++j ) { + for ( int j = 1; j < width - 1; ++j ) { double maxLength = 0; - for ( int i = 0; i < out.height; ++i ) { + for ( int i = 0; i < height; ++i ) { value_maximize( maxLength, vector3_length( expand[i][j].xyz - ProjectPointOntoVector( expand[i][j].xyz, expand[i][j - 1].xyz, expand[i][j + 1].xyz ) ) ); } if ( maxLength < 0.1 ) { - out.width--; - for ( int i = 0; i < out.height; ++i ) { - for ( int k = j; k < out.width; ++k ) { + width--; + for ( int i = 0; i < height; ++i ) { + for ( int k = j; k < width; ++k ) { expand[i][k] = expand[i][k + 1]; } } j--; } } - for ( int j = 1; j < out.height - 1; ++j ) { + for ( int j = 1; j < height - 1; ++j ) { double maxLength = 0; - for ( int i = 0; i < out.width; ++i ) { + for ( int i = 0; i < width; ++i ) { value_maximize( maxLength, vector3_length( expand[j][i].xyz - ProjectPointOntoVector( expand[j][i].xyz, expand[j - 1][i].xyz, expand[j + 1][i].xyz ) ) ); } if ( maxLength < 0.1 ) { - out.height--; - for ( int i = 0; i < out.width; ++i ) { - for ( int k = j; k < out.height; ++k ) { + height--; + for ( int i = 0; i < width; ++i ) { + for ( int k = j; k < height; ++k ) { expand[k][i] = expand[k + 1][i]; } } @@ -532,11 +535,11 @@ mesh_t RemoveLinearMeshColumnsRows( const mesh_t& in ) { } } // collapse the verts - for ( int i = 1; i < out.height; ++i ) { - memmove( out[i], expand[i], out.width * sizeof( bspDrawVert_t ) ); + for ( int i = 1; i < height; ++i ) { + memmove( expand[0] + width * i, expand[i], width * sizeof( bspDrawVert_t ) ); } - return mesh_t( out ); + return mesh_t( width, height, expand[0] ); } @@ -561,7 +564,8 @@ mesh_t TessellatedMesh( const mesh_view_t in, int iterations ){ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int maxsize, int *widthtable, int *heighttable ){ int i, j, k, w, h, maxsubdivisions, subdivisions; bspDrawVert_t expand[MAX_EXPANDED_AXIS][MAX_EXPANDED_AXIS]; - mesh_view_t out( in.width, in.height, expand[0] ); + int width = in.width; + int height = in.height; /* copy each row */ for ( int h = 0; h < in.height; ++h ) @@ -577,7 +581,7 @@ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int max for ( w = 0, j = 0; w < in.width - 1; ++w, j += subdivisions + 1 ) { double maxLength = 0; - for ( i = 0; i < out.height; ++i ) { + for ( i = 0; i < height; ++i ) { value_maximize( maxLength, vector3_length( expand[i][j + 1].xyz - expand[i][j].xyz ) ); } @@ -588,10 +592,10 @@ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int max continue; } - out.width += subdivisions; + width += subdivisions; - for ( i = 0; i < out.height; ++i ) { - for ( k = out.width - 1; k > j + subdivisions; --k ) { + for ( i = 0; i < height; ++i ) { + for ( k = width - 1; k > j + subdivisions; --k ) { expand[i][k] = expand[i][k - subdivisions]; } for ( k = 1; k <= subdivisions; ++k ) @@ -606,7 +610,7 @@ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int max for ( h = 0, j = 0; h < in.height - 1; ++h, j += subdivisions + 1 ) { double maxLength = 0; - for ( i = 0; i < out.width; ++i ) { + for ( i = 0; i < width; ++i ) { value_maximize( maxLength, vector3_length( expand[j + 1][i].xyz - expand[j][i].xyz ) ); } @@ -617,10 +621,10 @@ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int max continue; } - out.height += subdivisions; + height += subdivisions; - for ( i = 0; i < out.width; ++i ) { - for ( k = out.height - 1; k > j + subdivisions; --k ) { + for ( i = 0; i < width; ++i ) { + for ( k = height - 1; k > j + subdivisions; --k ) { expand[k][i] = expand[k - subdivisions][i]; } for ( k = 1; k <= subdivisions; ++k ) @@ -632,9 +636,9 @@ static mesh_t SubdivideMeshQuads( const mesh_view_t in, float minLength, int max } // collapse the verts - for ( i = 1; i < out.height; ++i ) { - memmove( out[i], expand[i], out.width * sizeof( bspDrawVert_t ) ); + for ( i = 1; i < height; ++i ) { + memmove( expand[0] + width * i, expand[i], width * sizeof( bspDrawVert_t ) ); } - return mesh_t( out ); + return mesh_t( width, height, expand[0] ); } diff --git a/tools/quake3/q3map2/patch.cpp b/tools/quake3/q3map2/patch.cpp index 780724f1..29666e0b 100644 --- a/tools/quake3/q3map2/patch.cpp +++ b/tools/quake3/q3map2/patch.cpp @@ -258,7 +258,7 @@ void ParsePatch( bool onlyLights, entity_t& mapEnt, int mapPrimitiveNum ){ /* find first valid vector */ for ( int i = 1; i < numVerts && delta[ 3 ] == 0; ++i ) { - delta.vec3() = m.verts[ 0 ].xyz - m.verts[ i ].xyz; + delta.vec3() = m.verts()[ 0 ].xyz - m.verts()[ i ].xyz; delta[ 3 ] = VectorNormalize( delta.vec3() ); } @@ -271,7 +271,7 @@ void ParsePatch( bool onlyLights, entity_t& mapEnt, int mapPrimitiveNum ){ /* if all vectors match this or are zero, then this is a degenerate patch */ for ( int i = 1; i < numVerts && degenerate; ++i ) { - Vector4 delta2( m.verts[ 0 ].xyz - m.verts[ i ].xyz, 0 ); + Vector4 delta2( m.verts()[ 0 ].xyz - m.verts()[ i ].xyz, 0 ); delta2[ 3 ] = VectorNormalize( delta2.vec3() ); if ( delta2[ 3 ] != 0 ) { /* create inverse vector */ @@ -317,7 +317,7 @@ void ParsePatch( bool onlyLights, entity_t& mapEnt, int mapPrimitiveNum ){ pm.shaderInfo = &ShaderInfoForShader( shader ); /* set mesh */ - pm.mesh.swap( m ); + pm.mesh = std::move( m ); /* set longest curve */ pm.longestCurve = longestCurve; @@ -396,8 +396,8 @@ void PatchMapDrawSurfs( entity_t& e ){ meshes[m1].bordering[m2] = meshes[m2].bordering[m1] = - std::ranges::any_of( Span( mesh1.verts, mesh1.numVerts() ), [mesh2]( const bspDrawVert_t& v1 ){ - return std::ranges::any_of( Span( mesh2.verts, mesh2.numVerts() ), [v1]( const bspDrawVert_t& v2 ){ + std::ranges::any_of( mesh1, [mesh2]( const bspDrawVert_t& v1 ){ + return std::ranges::any_of( mesh2, [v1]( const bspDrawVert_t& v2 ){ return vector3_equal_epsilon( v1.xyz, v2.xyz, 1.f ); } ); } ); @@ -424,8 +424,8 @@ void PatchMapDrawSurfs( entity_t& e ){ { if ( m.group ) { m.grouped = true; - for( const bspDrawVert_t& v : Span( m.mesh.mesh.verts, m.mesh.mesh.numVerts() ) ) - bounds.extend( v.xyz );; + for( const bspDrawVert_t& v : m.mesh.mesh ) + bounds.extend( v.xyz ); } } diff --git a/tools/quake3/q3map2/q3map2.h b/tools/quake3/q3map2/q3map2.h index 8936871d..862020e6 100644 --- a/tools/quake3/q3map2/q3map2.h +++ b/tools/quake3/q3map2/q3map2.h @@ -760,46 +760,58 @@ struct fog_t struct mesh_view_t { - int width, height; - bspDrawVert_t *verts; + const int width, height; + const bspDrawVert_t * const verts; - mesh_view_t( int width, int height, bspDrawVert_t *verts ) : width( width ), height( height ), verts( verts ){ + mesh_view_t( int width, int height, const bspDrawVert_t *verts ) : width( width ), height( height ), verts( verts ){ } - size_t numVerts() const { - return width * height; - } - bspDrawVert_t* operator[]( int h ){ - return verts + width * h; - } - const bspDrawVert_t* operator[]( int h ) const { - return verts + width * h; + const bspDrawVert_t* operator[]( int row ) const { + return verts + width * row; } }; -struct mesh_t : public mesh_view_t +struct mesh_t { - mesh_t() : mesh_view_t( 0, 0, nullptr ) { + const int width, height; +private: + bspDrawVert_t *m_verts; +public: + mesh_t() : width( 0 ), height( 0 ), m_verts( nullptr ) { } - mesh_t( int width, int height ) : mesh_view_t( width, height, new bspDrawVert_t[ width * height ] ){ + mesh_t( int width, int height ) : width( width ), height( height ), m_verts( new bspDrawVert_t[ width * height ] ) { } - explicit mesh_t( const mesh_view_t& view ) : mesh_view_t( view.width, view.height, new bspDrawVert_t[ view.width * view.height ] ) { - std::copy_n( view.verts, numVerts(), verts ); + mesh_t( int width, int height, const bspDrawVert_t *verts ) : mesh_t( width, height ) { + std::copy_n( verts, numVerts(), m_verts ); } - explicit mesh_t( const mesh_t& other ) : mesh_view_t( other.width, other.height, new bspDrawVert_t[ other.width * other.height ] ) { - std::copy_n( other.verts, numVerts(), verts ); + explicit mesh_t( const mesh_view_t& view ) : mesh_t( view.width, view.height, view.verts ) { } - mesh_t( mesh_t&& other ) noexcept : mesh_view_t( other.width, other.height, std::exchange( other.verts, nullptr ) ) { + operator mesh_view_t() const { + return { width, height, m_verts }; + } + explicit mesh_t( const mesh_t& other ) : mesh_t( other.width, other.height, other.m_verts ) { + } + mesh_t( mesh_t&& other ) noexcept : width( other.width ), height( other.height ), m_verts( std::exchange( other.m_verts, nullptr ) ) { } mesh_t& operator=( const mesh_t& ) = delete; - mesh_t& operator=( mesh_t&& ) noexcept = delete; + mesh_t& operator=( mesh_t&& other ) noexcept { + std::destroy_at( this ); + std::construct_at( this, std::move( other ) ); + return *this; + }; ~mesh_t(){ - delete[] verts; + delete[] m_verts; } - void swap( mesh_t& other ){ - std::swap( width, other.width ); - std::swap( height, other.height ); - std::swap( verts, other.verts ); + int numVerts() const { + return width * height; } + const bspDrawVert_t* operator[]( int row ) const { return m_verts + width * row; } + bspDrawVert_t* operator[]( int row ) { return m_verts + width * row; } + const bspDrawVert_t* verts() const { return m_verts; } + bspDrawVert_t* verts() { return m_verts; } + const bspDrawVert_t* begin() const { return m_verts; } + bspDrawVert_t* begin() { return m_verts; } + const bspDrawVert_t* end() const { return m_verts + numVerts(); } + bspDrawVert_t* end() { return m_verts + numVerts(); } }; @@ -1728,7 +1740,7 @@ void Fur( mapDrawSurface_t& src ); /* surface_foliage.c */ -void Foliage( mapDrawSurface_t& src, entity_t& entity ); +void Foliage( const mapDrawSurface_t& src, entity_t& entity ); /* ydnar: surface_meta.c */ diff --git a/tools/quake3/q3map2/surface.cpp b/tools/quake3/q3map2/surface.cpp index a5a5dabf..265558df 100644 --- a/tools/quake3/q3map2/surface.cpp +++ b/tools/quake3/q3map2/surface.cpp @@ -797,7 +797,7 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ /* store off the original (potentially bad) normals */ MakeMeshNormals( copy ); for ( int i = 0; i < numVerts; ++i ) - mesh.verts[ i ].normal = copy.verts[ i ].normal; + mesh.verts()[ i ].normal = copy.verts()[ i ].normal; /* put the mesh on the curve */ PutMeshOnCurve( copy ); @@ -807,8 +807,8 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ for ( int i = 0; i < numVerts; ++i ) { /* ydnar: only copy normals that are significantly different from the originals */ - if ( vector3_dot( copy.verts[ i ].normal, mesh.verts[ i ].normal ) < 0.75f ) { - mesh.verts[ i ].normal = copy.verts[ i ].normal; + if ( vector3_dot( copy.verts()[ i ].normal, mesh.verts()[ i ].normal ) < 0.75f ) { + mesh.verts()[ i ].normal = copy.verts()[ i ].normal; } } @@ -818,7 +818,7 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ /* get shader indexes for each point */ for ( int i = 0; i < numVerts; ++i ) { - shaderIndexes[ i ] = GetShaderIndexForPoint( *p.im, p.eMinmax, mesh.verts[ i ].xyz ); + shaderIndexes[ i ] = GetShaderIndexForPoint( *p.im, p.eMinmax, mesh.verts()[ i ].xyz ); offsets[ i ] = p.im->offsets[ shaderIndexes[ i ] ]; } @@ -830,27 +830,27 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ /* ydnar: gs mods */ mapDrawSurface_t& ds = AllocDrawSurface( ESurfaceType::Patch ); - ds.entityNum = p.entityNum; - ds.castShadows = p.castShadows; - ds.recvShadows = p.recvShadows; + ds.entityNum = p.entityNum; + ds.castShadows = p.castShadows; + ds.recvShadows = p.recvShadows; ds.shaderInfo = si; - ds.sampleSize = p.lightmapSampleSize; + ds.sampleSize = p.lightmapSampleSize; ds.lightmapScale = p.lightmapScale; /* ydnar */ - ds.ambientColor = p.ambientColor; - ds.patchWidth = mesh.width; + ds.ambientColor = p.ambientColor; + ds.patchWidth = mesh.width; ds.patchHeight = mesh.height; - ds.verts.assign( mesh.verts, mesh.verts + numVerts ); + ds.verts.assign( mesh.begin(), mesh.end() ); ds.fogNum = FOG_INVALID; ds.planeNum = -1; - ds.longestCurve = p.longestCurve; + ds.longestCurve = p.longestCurve; ds.maxIterations = p.maxIterations; /* construct a plane from the first vert */ - plane.normal() = mesh.verts[ 0 ].normal; - plane.dist() = vector3_dot( mesh.verts[ 0 ].xyz, plane.normal() ); + plane.normal() = mesh.verts()[ 0 ].normal; + plane.dist() = vector3_dot( mesh.verts()[ 0 ].xyz, plane.normal() ); /* spew forth errors */ if ( vector3_length( plane.normal() ) < 0.001f ) { @@ -858,7 +858,7 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ } /* test each vert */ - const bool planar = std::ranges::none_of( Span( mesh.verts, numVerts ), [&plane]( const bspDrawVert_t& vert ){ + const bool planar = std::ranges::none_of( mesh, [&plane]( const bspDrawVert_t& vert ){ /* normal test */ return !VectorCompare( plane.normal(), vert.normal ) /* point-plane test */ @@ -868,7 +868,7 @@ mapDrawSurface_t *DrawSurfaceForMesh( const entity_t& e, parseMesh_t& p ){ /* add a map plane */ if ( planar ) { /* make a map plane */ - ds.planeNum = FindFloatPlane( plane, Span( &mesh.verts[ 0 ].xyz, 1 ) ); + ds.planeNum = FindFloatPlane( plane, Span( &mesh.verts()[ 0 ].xyz, 1 ) ); ds.lightmapVecs[ 2 ] = plane.normal(); /* push this normal to all verts (ydnar 2003-02-14: bad idea, small patches get screwed up) */ @@ -2641,7 +2641,7 @@ static void BiasSurfaceTextures( mapDrawSurface_t& ds ){ adds models to a specified triangle, returns the number of models added */ -static int AddSurfaceModelsToTriangle_r( mapDrawSurface_t& ds, const surfaceModel_t& model, const TriRef& tri, entity_t& entity ){ +static int AddSurfaceModelsToTriangle_r( const mapDrawSurface_t& ds, const surfaceModel_t& model, const TriRef& tri, entity_t& entity ){ int max, n, localNumSurfaceModels; @@ -2779,7 +2779,7 @@ static int AddSurfaceModelsToTriangle_r( mapDrawSurface_t& ds, const surfaceMode adds a surface's shader models to the surface */ -static int AddSurfaceModels( mapDrawSurface_t& ds, entity_t& entity ){ +static int AddSurfaceModels( const mapDrawSurface_t& ds, entity_t& entity ){ /* dummy check */ if ( ds.shaderInfo == nullptr || ds.shaderInfo->surfaceModels.empty() ) { return 0; diff --git a/tools/quake3/q3map2/surface_foliage.cpp b/tools/quake3/q3map2/surface_foliage.cpp index 019e3b93..01d22eb0 100644 --- a/tools/quake3/q3map2/surface_foliage.cpp +++ b/tools/quake3/q3map2/surface_foliage.cpp @@ -154,7 +154,7 @@ static void SubdivideFoliageTriangle_r( const foliage_t& foliage, const TriRef& generates a foliage file for a bsp */ -void Foliage( mapDrawSurface_t& src, entity_t& entity ){ +void Foliage( const mapDrawSurface_t& src, entity_t& entity ){ /* get shader */ shaderInfo_t *si = src.shaderInfo; if ( si == nullptr || si->foliage.empty() ) { diff --git a/tools/quake3/q3map2/surface_meta.cpp b/tools/quake3/q3map2/surface_meta.cpp index 871b8b60..f269cf0d 100644 --- a/tools/quake3/q3map2/surface_meta.cpp +++ b/tools/quake3/q3map2/surface_meta.cpp @@ -372,7 +372,7 @@ static void TriangulatePatchSurface( const entity_t& e, mapDrawSurface_t& ds ){ dsNew.indexes.reserve( ( mesh.width - 1 ) * ( mesh.height - 1 ) * 6 ); /* copy the verts in */ - dsNew.verts.assign( mesh.verts, mesh.verts + mesh.numVerts() ); + dsNew.verts.assign( mesh.begin(), mesh.end() ); /* iterate through the mesh quads */ for( MeshQuadIterator it( mesh ); it; ++it ){ diff --git a/tools/quake3/q3map2/writebsp.cpp b/tools/quake3/q3map2/writebsp.cpp index 0e5b469e..9f1bc67b 100644 --- a/tools/quake3/q3map2/writebsp.cpp +++ b/tools/quake3/q3map2/writebsp.cpp @@ -484,7 +484,7 @@ void BeginModel( const entity_t& e ){ /* bound patches */ for ( const parseMesh_t& p : e.patches ) { - for ( const bspDrawVert_t& vert : Span( p.mesh.verts, p.mesh.numVerts() ) ) + for ( const bspDrawVert_t& vert : p.mesh ) minmax.extend( vert.xyz ); }