engine: make Image_ComputeSize shared between renderer and imagelib

This commit is contained in:
Alibek Omarov
2025-12-14 00:00:19 +05:00
parent 44fb4fb594
commit 66ea91270b
5 changed files with 43 additions and 97 deletions

View File

@@ -1,9 +1,25 @@
/*
ref_common.c - RefAPI implementation
Copyright (C) 2025 Xash3D FWGS contributors
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 3 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.
*/
#include "common.h"
#include "client.h"
#include "library.h"
#include "cl_tent.h"
#include "platform/platform.h"
#include "vid_common.h"
#include "imagelib.h"
struct ref_state_s ref;
@@ -434,6 +450,7 @@ static const ref_api_t gEngfuncs =
FS_FreeImage,
Image_SetMDLPointer,
pfnImage_GetPFDesc,
Image_ComputeSize,
pfnDrawNormalTriangles,
pfnDrawTransparentTriangles,

View File

@@ -1464,16 +1464,25 @@ qboolean Image_Process( rgbdata_t **pix, int width, int height, uint flags, floa
return result;
}
// This codebase has too many copies of this function:
// - ref_gl has one
// - ref_vk has one
// - ref_soft has one
// - many more places probably have one too
// TODO figure out how to make it available for ref_*
/*
============
Image_ComputeSize
============
*/
size_t Image_ComputeSize( int type, int width, int height, int depth )
{
depth = Q_max( 1, depth );
switch( type )
{
case PF_LUMINANCE:
return ( width * height * depth );
case PF_BGR_24:
case PF_RGB_24:
return ( width * height * depth * 3 );
case PF_BGRA_32:
case PF_RGBA_32:
return ( width * height * depth * 4 );
case PF_DXT1:
case PF_BC4_SIGNED:
case PF_BC4_UNSIGNED:
@@ -1486,12 +1495,8 @@ size_t Image_ComputeSize( int type, int width, int height, int depth )
case PF_BC6H_SIGNED:
case PF_BC6H_UNSIGNED:
case PF_BC7_UNORM:
case PF_BC7_SRGB: return ((( width + 3 ) / 4 ) * (( height + 3 ) / 4 ) * depth * 16 );
case PF_LUMINANCE: return ( width * height * depth );
case PF_BGR_24:
case PF_RGB_24: return ( width * height * depth * 3 );
case PF_BGRA_32:
case PF_RGBA_32: return ( width * height * depth * 4 );
case PF_BC7_SRGB:
return ((( width + 3 ) / 4 ) * (( height + 3 ) / 4 ) * depth * 16 );
}
return 0;

View File

@@ -59,6 +59,7 @@ GNU General Public License for more details.
// Removed FillRGBABlend. Now FillRGBA accepts rendermode parameter.
// 10. Added R_GetWindowHandle to retrieve platform-specific window object.
// 11. Added size argument to Mod_ProcessRenderData
// 12. Added Image_CalcImageSize
#define REF_API_VERSION 11
#define TF_SKY (TF_SKYSIDE|TF_NOMIPMAP|TF_ALLOW_NEAREST)
@@ -483,6 +484,7 @@ typedef struct ref_api_s
void (*FS_FreeImage)( rgbdata_t *pack );
void (*Image_SetMDLPointer)( byte *p );
const struct bpc_desc_s *(*Image_GetPFDesc)( int idx );
size_t (*Image_CalcImageSize)( int type, int width, int height, int depth );
// client exports
void (*pfnDrawNormalTriangles)( void );

View File

@@ -302,48 +302,6 @@ static int GL_CalcTextureSamples( int flags )
return FBitSet( flags, IMAGE_HAS_ALPHA ) ? 2 : 1;
}
/*
==================
GL_CalcImageSize
==================
*/
static size_t GL_CalcImageSize( pixformat_t format, int width, int height, int depth )
{
size_t size = 0;
// check the depth error
depth = Q_max( 1, depth );
switch( format )
{
case PF_LUMINANCE:
size = width * height * depth;
break;
case PF_RGB_24:
case PF_BGR_24:
size = width * height * depth * 3;
break;
case PF_BGRA_32:
case PF_RGBA_32:
size = width * height * depth * 4;
break;
case PF_DXT1:
size = (((width + 3) >> 2) * ((height + 3) >> 2) * 8) * depth;
break;
case PF_DXT3:
case PF_DXT5:
case PF_BC6H_SIGNED:
case PF_BC6H_UNSIGNED:
case PF_BC7_UNORM:
case PF_BC7_SRGB:
case PF_ATI2:
size = (((width + 3) >> 2) * ((height + 3) >> 2) * 16) * depth;
break;
}
return size;
}
/*
==================
GL_CalcTextureSize
@@ -1173,7 +1131,7 @@ static qboolean GL_UploadTexture( gl_texture_t *tex, rgbdata_t *pic )
buf = pic->buffer;
bufend = pic->buffer + pic->size; // total image size include all the layers, cube sides, mipmaps
offset = GL_CalcImageSize( pic->type, pic->width, pic->height, pic->depth );
offset = gEngfuncs.Image_CalcImageSize( pic->type, pic->width, pic->height, pic->depth );
texsize = GL_CalcTextureSize( tex->format, tex->width, tex->height, tex->depth );
normalMap = FBitSet( tex->flags, TF_NORMALMAP ) ? true : false;
numSides = FBitSet( pic->flags, IMAGE_CUBEMAP ) ? 6 : 1;
@@ -1198,7 +1156,7 @@ static qboolean GL_UploadTexture( gl_texture_t *tex, rgbdata_t *pic )
height = Q_max( 1, ( tex->height >> j ));
depth = texture3d ? Q_max( 1, ( tex->depth >> j )) : tex->depth;
texsize = GL_CalcTextureSize( tex->format, width, height, depth );
size = GL_CalcImageSize( pic->type, width, height, depth );
size = gEngfuncs.Image_CalcImageSize( pic->type, width, height, depth );
GL_TextureImageCompressed( tex, i, j, width, height, depth, size, buf );
tex->size += texsize;
buf += size; // move pointer
@@ -1215,7 +1173,7 @@ static qboolean GL_UploadTexture( gl_texture_t *tex, rgbdata_t *pic )
height = Q_max( 1, ( tex->height >> j ));
depth = texture3d ? Q_max( 1, ( tex->depth >> j )) : tex->depth;
texsize = GL_CalcTextureSize( tex->format, width, height, depth );
size = GL_CalcImageSize( pic->type, width, height, depth );
size = gEngfuncs.Image_CalcImageSize( pic->type, width, height, depth );
GL_TextureImageRAW( tex, i, j, width, height, depth, pic->type, buf );
tex->size += texsize;
buf += size; // move pointer
@@ -1243,7 +1201,7 @@ static qboolean GL_UploadTexture( gl_texture_t *tex, rgbdata_t *pic )
width = Q_max( 1, ( tex->width >> j ));
height = Q_max( 1, ( tex->height >> j ));
texsize = GL_CalcTextureSize( tex->format, width, height, tex->depth );
size = GL_CalcImageSize( pic->type, width, height, tex->depth );
size = gEngfuncs.Image_CalcImageSize( pic->type, width, height, tex->depth );
GL_TextureImageRAW( tex, i, j, width, height, tex->depth, pic->type, data );
if( mipCount > 1 )
GL_BuildMipMap( data, width, height, tex->depth, tex->flags );
@@ -1255,7 +1213,7 @@ static qboolean GL_UploadTexture( gl_texture_t *tex, rgbdata_t *pic )
// move to next side
if( numSides > 1 && ( buf != NULL ))
buf += GL_CalcImageSize( pic->type, pic->width, pic->height, 1 );
buf += gEngfuncs.Image_CalcImageSize( pic->type, pic->width, pic->height, 1 );
}
}
@@ -1683,7 +1641,7 @@ int GL_LoadTextureArray( const char **names, int flags )
{
int width = Q_max( 1, ( pic->width >> j ));
int height = Q_max( 1, ( pic->height >> j ));
mipsize = GL_CalcImageSize( pic->type, width, height, 1 );
mipsize = gEngfuncs.Image_CalcImageSize( pic->type, width, height, 1 );
memcpy( pic->buffer + dstsize + mipsize * i, src->buffer + srcsize, mipsize );
dstsize += mipsize * numLayers;
srcsize += mipsize;

View File

@@ -119,42 +119,6 @@ void R_SetTextureParameters( void )
GL_UpdateTextureParams( i );
}
/*
==================
GL_CalcImageSize
==================
*/
static size_t GL_CalcImageSize( pixformat_t format, int width, int height, int depth )
{
size_t size = 0;
// check the depth error
depth = Q_max( 1, depth );
switch( format )
{
case PF_RGB_24:
case PF_BGR_24:
size = width * height * depth * 3;
break;
case PF_BGRA_32:
case PF_RGBA_32:
size = width * height * depth * 4;
break;
case PF_DXT1:
size = ((( width + 3 ) >> 2 ) * (( height + 3 ) >> 2 ) * 8 ) * depth;
break;
case PF_DXT3:
case PF_DXT5:
case PF_ATI2:
size = ((( width + 3 ) >> 2 ) * (( height + 3 ) >> 2 ) * 16 ) * depth;
break;
}
return size;
}
/*
==================
GL_CalcTextureSize
@@ -563,7 +527,7 @@ static qboolean GL_UploadTexture( image_t *tex, rgbdata_t *pic )
width = Q_max( 1, ( tex->width >> j ));
height = Q_max( 1, ( tex->height >> j ));
texsize = GL_CalcTextureSize( width, height, tex->depth );
size = GL_CalcImageSize( pic->type, width, height, tex->depth );
size = gEngfuncs.Image_CalcImageSize( pic->type, width, height, tex->depth );
// GL_TextureImageRAW( tex, i, j, width, height, tex->depth, pic->type, data );
// increase size to workaround triangle renderer bugs
// it seems to assume memory readable. maybe it was pointed to WAD?