diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index e62316f2138973c6dd31e4aaaf36f5e6678fae21..c4b6729b9999bea48df5b6e70880214b858f2cdf 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -339,6 +339,7 @@ if(${SRB2_CONFIG_HWRENDER}) ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_md2.c ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_trick.c ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_vertarray.c + ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_vertbuckets.c ) set (SRB2_HWRENDER_HEADERS @@ -352,6 +353,7 @@ if(${SRB2_CONFIG_HWRENDER}) ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_main.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_md2.h ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_vertarray.h + ${CMAKE_CURRENT_SOURCE_DIR}/hardware/hw_vertbuckets.h ) set(SRB2_R_OPENGL_SOURCES diff --git a/src/hardware/hw_cache.c b/src/hardware/hw_cache.c index 78fc31afccceb1397b08bc40bc3a17e247ff0d89..7b41ee42f30161e0d53d8b6760d22f7a9943d8cf 100644 --- a/src/hardware/hw_cache.c +++ b/src/hardware/hw_cache.c @@ -1105,4 +1105,9 @@ void HWR_GetFadeMask(lumpnum_t fademasklumpnum) Z_ChangeTag(grmip->grInfo.data, PU_HWRCACHE_UNLOCKED); } +int HWR_GetNumCacheTextures(void) +{ + return gr_numtextures; +} + #endif //HWRENDER diff --git a/src/hardware/hw_glob.h b/src/hardware/hw_glob.h index 88786bc112ae459eb8826fc14ab551d8f479ce98..2da80c64bf80e70869dabb2b04188febac1ff620 100644 --- a/src/hardware/hw_glob.h +++ b/src/hardware/hw_glob.h @@ -108,6 +108,9 @@ GLPatch_t *HWR_GetCachedGLPatchPwad(UINT16 wad, UINT16 lump); GLPatch_t *HWR_GetCachedGLPatch(lumpnum_t lumpnum); void HWR_GetFadeMask(lumpnum_t fademasklumpnum); +/** */ +int HWR_GetNumCacheTextures(void); + // -------- // hw_draw.c // -------- diff --git a/src/hardware/hw_vertbuckets.c b/src/hardware/hw_vertbuckets.c new file mode 100644 index 0000000000000000000000000000000000000000..10876bb76a86a9c368efcbb4ed46e77b23445145 --- /dev/null +++ b/src/hardware/hw_vertbuckets.c @@ -0,0 +1,94 @@ +// Emacs style mode select -*- C++ -*- +//----------------------------------------------------------------------------- +// +// Copyright (C) 2015 by Sonic Team Jr. +// +// This program is free software; you can redistribute it and/or +// modify it under the terms of the GNU General Public License +// as published by the Free Software Foundation; either version 2 +// of the License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +//----------------------------------------------------------------------------- +/// \file +/// \brief Vertex buckets mapping based on texture binding, implementation + +#include "hw_vertbuckets.h" + +#include "hw_glob.h" +#include "hw_drv.h" + +#include "../z_zone.h" + +// 6 because we assume at least a quad per texture. +#define INITIAL_BUCKET_SIZE 6 + +static FVertexArray * buckets = NULL; +static int numBuckets = 0; + +static int bucketsHaveBeenInitialized = 0; + +void HWR_ResetVertexBuckets(void) +{ + // Free all arrays if they've been initialized before. + if (bucketsHaveBeenInitialized) + { + int i = 0; + for (i = 0; i < numBuckets; i++) + { + HWR_FreeVertexArray(&buckets[i]); + } + Z_Free(buckets); + } + + // We will only have as many buckets as gr_numtextures + numBuckets = HWR_GetNumCacheTextures(); + buckets = Z_Malloc(numBuckets * sizeof(FVertexArray), PU_HWRCACHE, NULL); + + { + int i = 0; + for (i = 0; i < numBuckets; i++) + { + HWR_InitVertexArray(&buckets[i], INITIAL_BUCKET_SIZE); + } + } + bucketsHaveBeenInitialized = 1; +} + +FVertexArray * HWR_GetVertexArrayForTexture(int texNum) +{ + if (texNum >= numBuckets || texNum < 0) + { + I_Error("HWR_GetVertexArrayForTexture: texNum >= numBuckets"); + //return NULL; + } + return &buckets[texNum]; +} + +void HWR_DrawVertexBuckets(void) +{ + int i = 0; + for (i = 0; i < numBuckets; i++) + { + FSurfaceInfo surface; + FVertexArray * bucket = &buckets[i]; + + if (bucket->used == 0) + { + // We did not add any vertices with this texture, so we can skip binding and drawing. + continue; + } + + // Bind the texture. + + HWR_GetTexture(i); + // Draw the triangles. + // TODO handle polyflags and modulation for lighting/translucency? + HWD.pfnDrawPolygon(&surface, bucket->buffer, bucket->used, 0); + CONS_Printf("%d: %d tris\n", i, bucket->used); + } +} diff --git a/src/hardware/hw_vertbuckets.h b/src/hardware/hw_vertbuckets.h new file mode 100644 index 0000000000000000000000000000000000000000..c93f19d30172e283f562274cd6e3c5b06f22d463 --- /dev/null +++ b/src/hardware/hw_vertbuckets.h @@ -0,0 +1,42 @@ +// Emacs style mode select -*- C++ -*- +//----------------------------------------------------------------------------- +// +// Copyright (C) 2015 by Sonic Team Jr. +// +// This program is free software; you can redistribute it and/or +// modify it under the terms of the GNU General Public License +// as published by the Free Software Foundation; either version 2 +// of the License, or (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +//----------------------------------------------------------------------------- +/// \file +/// \brief Vertex buckets mapping based on texture binding + +#ifndef __HW_VERTBUCKETS_H__ +#define __HW_VERTBUCKETS_H__ + +#include "hw_vertarray.h" + +/* The vertex buckets are a mapping of runtime texture number to FVertexArray. + * BSP traversal, instead of sending DrawPolygon calls to the driver directly, + * will add vertices to these buckets based on the texture used. After BSP + * traversal, you should call HWR_DrawVertexBuckets in order to send DrawPolygon + * calls for each texture in the buckets. + */ + +/** Empty the vertex buckets to prepare for another BSP traversal. This function + * should be called before rendering any BSP node. */ +void HWR_ResetVertexBuckets(void); + +/** Get a pointer to the vertex array used for a given texture number. */ +FVertexArray * HWR_GetVertexArrayForTexture(int texNum); + +/** Send draw commands to the hardware driver to draw each of the buckets. */ +void HWR_DrawVertexBuckets(void); + +#endif //__HW_VERTBUCKETS_H__