2016-12-18 04:43:04 +00:00
/*
= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
Copyright ( C ) 1999 - 2005 Id Software , Inc .
This file is part of Quake III Arena source code .
Quake III Arena source code 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 .
Quake III Arena source code 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 .
You should have received a copy of the GNU General Public License
along with Quake III Arena source code ; if not , write to the Free Software
Foundation , Inc . , 51 Franklin St , Fifth Floor , Boston , MA 02110 - 1301 USA
= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =
*/
// tr_init.c -- functions that are not called every frame
# include "tr_local.h"
2017-10-03 17:11:10 +00:00
# include "tr_help.h"
2016-12-18 04:43:04 +00:00
glconfig_t glConfig ;
glinfo_t glInfo ;
2017-11-05 21:40:32 +00:00
screenshotCommand_t r_delayedScreenshot ;
qbool r_delayedScreenshotPending = qfalse ;
int r_delayedScreenshotFrame = 0 ;
2016-12-18 04:43:04 +00:00
cvar_t * r_displayRefresh ;
cvar_t * r_detailTextures ;
cvar_t * r_intensity ;
cvar_t * r_gamma ;
2017-08-18 14:02:02 +00:00
cvar_t * r_greyscale ;
2016-12-18 04:43:04 +00:00
cvar_t * r_measureOverdraw ;
cvar_t * r_fastsky ;
cvar_t * r_dynamiclight ;
cvar_t * r_lodbias ;
cvar_t * r_lodscale ;
cvar_t * r_norefresh ;
cvar_t * r_drawentities ;
cvar_t * r_drawworld ;
cvar_t * r_fullbright ;
2017-08-18 15:03:30 +00:00
cvar_t * r_lightmap ;
2020-01-12 21:52:02 +00:00
cvar_t * r_lightmapGreyscale ;
2022-04-23 21:38:06 +00:00
cvar_t * r_mapGreyscale ;
cvar_t * r_mapGreyscaleCTF ;
2023-07-03 01:44:06 +00:00
cvar_t * r_teleporterFlash ;
2022-12-28 19:49:18 +00:00
cvar_t * r_sleepThreshold ;
2023-08-03 00:38:29 +00:00
cvar_t * r_shadingRate ;
2023-08-28 22:43:26 +00:00
cvar_t * r_guiFont ;
2023-10-18 23:02:14 +00:00
cvar_t * r_guiFontFile ;
cvar_t * r_guiFontHeight ;
2016-12-18 04:43:04 +00:00
cvar_t * r_novis ;
cvar_t * r_nocull ;
cvar_t * r_nocurves ;
2020-04-26 14:32:51 +00:00
cvar_t * r_depthFade ;
2019-09-25 03:25:59 +00:00
cvar_t * r_dither ;
2019-09-25 03:31:55 +00:00
cvar_t * r_rtColorFormat ;
2022-10-23 00:58:20 +00:00
cvar_t * r_depthClamp ;
2022-12-28 19:49:18 +00:00
cvar_t * r_gpuPreference ;
2024-01-21 01:27:18 +00:00
cvar_t * r_gpuIndex ;
2019-09-25 03:25:59 +00:00
cvar_t * r_mipGenFilter ;
cvar_t * r_mipGenGamma ;
2020-04-28 15:04:43 +00:00
cvar_t * r_ditherStrength ;
2020-04-16 03:01:48 +00:00
cvar_t * r_transpSort ;
2016-12-18 04:43:04 +00:00
cvar_t * r_ext_max_anisotropy ;
2022-12-28 19:49:18 +00:00
cvar_t * r_smaa ;
2016-12-18 04:43:04 +00:00
2022-04-24 20:44:25 +00:00
cvar_t * r_ignoreShaderSortKey ;
2016-12-18 04:43:04 +00:00
cvar_t * r_vertexLight ;
cvar_t * r_uiFullScreen ;
cvar_t * r_mode ;
2017-11-22 17:26:26 +00:00
cvar_t * r_blitMode ;
2016-12-18 04:43:04 +00:00
cvar_t * r_singleShader ;
cvar_t * r_roundImagesDown ;
cvar_t * r_colorMipLevels ;
cvar_t * r_picmip ;
cvar_t * r_clear ;
2023-08-28 22:43:26 +00:00
cvar_t * r_vsync ;
2022-12-28 19:49:18 +00:00
cvar_t * r_lego ;
2024-01-13 21:40:13 +00:00
cvar_t * r_pipeline ;
2016-12-18 04:43:04 +00:00
cvar_t * r_lockpvs ;
cvar_t * r_noportals ;
cvar_t * r_portalOnly ;
cvar_t * r_subdivisions ;
cvar_t * r_lodCurveError ;
cvar_t * r_width ;
cvar_t * r_height ;
2017-11-22 17:59:51 +00:00
cvar_t * r_brightness ;
cvar_t * r_mapBrightness ;
2016-12-18 04:43:04 +00:00
cvar_t * r_debugSurface ;
cvar_t * r_ambientScale ;
cvar_t * r_directedScale ;
cvar_t * r_debugLight ;
cvar_t * r_debugSort ;
2022-12-28 19:49:18 +00:00
cvar_t * r_debugUI ;
cvar_t * r_debugInput ;
2016-12-18 04:43:04 +00:00
// these limits apply to the sum of all scenes in a frame:
// the main view, all the 3D icons, and even the console etc
# define DEFAULT_MAX_POLYS 8192
# define DEFAULT_MAX_POLYVERTS 32768
static cvar_t * r_maxpolys ;
static cvar_t * r_maxpolyverts ;
int max_polys ;
int max_polyverts ;
2017-11-22 17:26:26 +00:00
void R_ConfigureVideoMode ( int desktopWidth , int desktopHeight )
2016-12-18 04:43:04 +00:00
{
2017-11-22 17:26:26 +00:00
glInfo . winFullscreen = ! ! r_fullscreen - > integer ;
glInfo . vidFullscreen = r_fullscreen - > integer & & r_mode - > integer = = VIDEOMODE_CHANGE ;
if ( r_fullscreen - > integer & & r_mode - > integer = = VIDEOMODE_DESKTOPRES ) {
glConfig . vidWidth = desktopWidth ;
glConfig . vidHeight = desktopHeight ;
glConfig . windowAspect = ( float ) glConfig . vidWidth / ( float ) glConfig . vidHeight ;
glInfo . winWidth = desktopWidth ;
glInfo . winHeight = desktopHeight ;
return ;
}
2016-12-18 11:05:45 +00:00
2017-11-22 17:26:26 +00:00
if ( r_fullscreen - > integer & & r_mode - > integer = = VIDEOMODE_UPSCALE ) {
glConfig . vidWidth = r_width - > integer ;
glConfig . vidHeight = r_height - > integer ;
glConfig . windowAspect = ( float ) glConfig . vidWidth / ( float ) glConfig . vidHeight ;
glInfo . winWidth = desktopWidth ;
glInfo . winHeight = desktopHeight ;
return ;
}
glConfig . vidWidth = r_width - > integer ;
glConfig . vidHeight = r_height - > integer ;
glConfig . windowAspect = ( float ) glConfig . vidWidth / ( float ) glConfig . vidHeight ;
glInfo . winWidth = r_width - > integer ;
glInfo . winHeight = r_height - > integer ;
2016-12-18 04:43:04 +00:00
}
///////////////////////////////////////////////////////////////
2022-12-28 19:49:18 +00:00
static void RB_TakeScreenshotTGA ( int width , int height , const char * fileName )
2016-12-18 04:43:04 +00:00
{
int c = ( width * height * 3 ) ;
RI_AutoPtr p ( sizeof ( TargaHeader ) + c ) ;
TargaHeader * tga = p . Get < TargaHeader > ( ) ;
Com_Memset ( tga , 0 , sizeof ( TargaHeader ) ) ;
tga - > image_type = 2 ; // uncompressed BGR
tga - > width = LittleShort ( width ) ;
tga - > height = LittleShort ( height ) ;
tga - > pixel_size = 24 ;
2022-12-28 19:49:18 +00:00
renderPipeline - > ReadPixels ( width , height , 1 , CS_BGR , p + sizeof ( TargaHeader ) ) ;
2016-12-18 04:43:04 +00:00
ri . FS_WriteFile ( fileName , p , sizeof ( TargaHeader ) + c ) ;
}
2022-12-28 19:49:18 +00:00
static void RB_TakeScreenshotJPG ( int width , int height , const char * fileName )
2016-12-18 04:43:04 +00:00
{
RI_AutoPtr p ( width * height * 4 ) ;
2022-12-28 19:49:18 +00:00
renderPipeline - > ReadPixels ( width , height , 1 , CS_RGBA , p ) ;
2016-12-18 04:43:04 +00:00
RI_AutoPtr out ( width * height * 4 ) ;
int n = SaveJPGToBuffer ( out , 95 , width , height , p ) ;
ri . FS_WriteFile ( fileName , out , n ) ;
}
2023-11-23 18:59:39 +00:00
void RB_TakeScreenshotCmd ( const screenshotCommand_t * cmd )
2016-12-18 04:43:04 +00:00
{
switch ( cmd - > type ) {
case screenshotCommand_t : : SS_JPG :
2022-12-28 19:49:18 +00:00
RB_TakeScreenshotJPG ( cmd - > width , cmd - > height , cmd - > fileName ) ;
2018-01-06 23:03:42 +00:00
ri . Printf ( PRINT_ALL , " Wrote %s \n " , cmd - > fileName ) ;
2016-12-18 04:43:04 +00:00
break ;
case screenshotCommand_t : : SS_TGA :
2022-12-28 19:49:18 +00:00
RB_TakeScreenshotTGA ( cmd - > width , cmd - > height , cmd - > fileName ) ;
2018-01-06 23:03:42 +00:00
ri . Printf ( PRINT_ALL , " Wrote %s \n " , cmd - > fileName ) ;
2016-12-18 04:43:04 +00:00
break ;
}
2017-11-05 21:40:32 +00:00
if ( cmd - > conVis > 0.0f ) {
ri . SetConsoleVisibility ( cmd - > conVis ) ;
r_delayedScreenshotPending = qfalse ;
r_delayedScreenshotFrame = 0 ;
}
2016-12-18 04:43:04 +00:00
}
// screenshot filename is YYYY_MM_DD-HH_MM_SS-TTT
// so you can find the damn things and you never run out of them for movies :)
2017-11-05 21:40:32 +00:00
static void R_TakeScreenshot ( const char * ext , screenshotCommand_t : : ss_type type , qbool hideConsole )
2016-12-18 04:43:04 +00:00
{
2018-01-06 23:03:42 +00:00
static char s [ MAX_OSPATH ] ;
2016-12-18 04:43:04 +00:00
2017-11-05 21:40:32 +00:00
const float conVis = hideConsole ? ri . SetConsoleVisibility ( 0.0f ) : 0.0f ;
screenshotCommand_t * cmd ;
if ( conVis > 0.0f ) {
cmd = & r_delayedScreenshot ;
r_delayedScreenshotPending = qtrue ;
r_delayedScreenshotFrame = 0 ;
} else {
2023-11-23 18:59:39 +00:00
cmd = & backEndData - > readbackCommands . screenshot ;
if ( cmd - > requested )
2017-11-05 21:40:32 +00:00
return ;
}
2016-12-18 04:43:04 +00:00
if ( ri . Cmd_Argc ( ) = = 2 ) {
Com_sprintf ( s , sizeof ( s ) , " screenshots/%s.%s " , ri . Cmd_Argv ( 1 ) , ext ) ;
} else {
qtime_t t ;
Com_RealTime ( & t ) ;
int ms = min ( 999 , backEnd . refdef . time & 1023 ) ;
Com_sprintf ( s , sizeof ( s ) , " screenshots/%d_%02d_%02d-%02d_%02d_%02d-%03d.%s " ,
1900 + t . tm_year , 1 + t . tm_mon , t . tm_mday , t . tm_hour , t . tm_min , t . tm_sec , ms , ext ) ;
}
2023-11-23 18:59:39 +00:00
cmd - > requested = qtrue ;
2016-12-18 04:43:04 +00:00
cmd - > width = glConfig . vidWidth ;
cmd - > height = glConfig . vidHeight ;
cmd - > fileName = s ;
cmd - > type = type ;
2017-11-05 21:40:32 +00:00
cmd - > conVis = conVis ;
}
static void R_ScreenShotTGA_f ( )
{
R_TakeScreenshot ( " tga " , screenshotCommand_t : : SS_TGA , qfalse ) ;
}
static void R_ScreenShotJPG_f ( )
{
R_TakeScreenshot ( " jpg " , screenshotCommand_t : : SS_JPG , qfalse ) ;
2016-12-18 04:43:04 +00:00
}
2017-11-05 21:40:32 +00:00
static void R_ScreenShotNoConTGA_f ( )
2016-12-18 04:43:04 +00:00
{
2017-11-05 21:40:32 +00:00
R_TakeScreenshot ( " tga " , screenshotCommand_t : : SS_TGA , qtrue ) ;
2016-12-18 04:43:04 +00:00
}
2017-11-05 21:40:32 +00:00
static void R_ScreenShotNoConJPG_f ( )
2016-12-18 04:43:04 +00:00
{
2017-11-05 21:40:32 +00:00
R_TakeScreenshot ( " jpg " , screenshotCommand_t : : SS_JPG , qtrue ) ;
2016-12-18 04:43:04 +00:00
}
//============================================================================
2023-11-23 18:59:39 +00:00
void RB_TakeVideoFrameCmd ( const videoFrameCommand_t * cmd )
2016-12-18 04:43:04 +00:00
{
if ( cmd - > motionJpeg )
{
2022-12-28 19:49:18 +00:00
renderPipeline - > ReadPixels ( cmd - > width , cmd - > height , 1 , CS_RGBA , cmd - > captureBuffer ) ;
2019-09-25 03:25:59 +00:00
const int frameSize = SaveJPGToBuffer ( cmd - > encodeBuffer , 95 , cmd - > width , cmd - > height , cmd - > captureBuffer ) ;
2018-09-29 06:22:47 +00:00
ri . CL_WriteAVIVideoFrame ( cmd - > encodeBuffer , frameSize ) ;
2016-12-18 04:43:04 +00:00
}
else
{
2022-12-28 19:49:18 +00:00
renderPipeline - > ReadPixels ( cmd - > width , cmd - > height , 4 , CS_BGR , cmd - > captureBuffer ) ;
2019-09-25 03:25:59 +00:00
const int frameSize = PAD ( cmd - > width , 4 ) * cmd - > height * 3 ;
2018-09-29 06:22:47 +00:00
ri . CL_WriteAVIVideoFrame ( cmd - > captureBuffer , frameSize ) ;
2016-12-18 04:43:04 +00:00
}
}
///////////////////////////////////////////////////////////////
2023-11-11 20:38:02 +00:00
static void GfxInfo_f ( )
2016-12-18 04:43:04 +00:00
{
2023-11-11 20:38:02 +00:00
ri . Printf ( PRINT_ALL , " RHI: %s \n " , rhiInfo . name ) ;
ri . Printf ( PRINT_ALL , " Adapter: %s \n " , rhiInfo . adapter ) ;
ri . Printf ( PRINT_ALL , " Tearing support: %s \n " , rhiInfo . hasTearing ? " YES " : " NO " ) ;
ri . Printf ( PRINT_ALL , " Base VRS support: %s \n " , rhiInfo . hasBaseVRS ? " YES " : " NO " ) ;
ri . Printf ( PRINT_ALL , " Extended VRS support: %s \n " , rhiInfo . hasExtendedVRS ? " YES " : " NO " ) ;
ri . Printf ( PRINT_ALL , " UMA: %s \n " , rhiInfo . isUMA ? " YES " : " NO " ) ;
ri . Printf ( PRINT_ALL , " Cache coherent UMA: %s \n " , rhiInfo . isCacheCoherentUMA ? " YES " : " NO " ) ;
2016-12-18 04:43:04 +00:00
}
///////////////////////////////////////////////////////////////
2017-10-03 17:11:10 +00:00
static const cmdTableItem_t r_cmds [ ] =
{
{ " gfxinfo " , GfxInfo_f , NULL , " prints display mode info " } ,
{ " imagelist " , R_ImageList_f , NULL , " prints loaded images " } ,
2022-11-25 02:32:41 +00:00
{ " imageinfo " , R_ImageInfo_f , NULL , " prints info for a specific image " } ,
2017-10-03 17:11:10 +00:00
{ " shaderlist " , R_ShaderList_f , NULL , " prints loaded shaders " } ,
2022-05-28 14:50:42 +00:00
{ " shaderinfo " , R_ShaderInfo_f , R_CompleteShaderName_f , " prints info for a specific shader " } ,
2022-12-11 18:09:34 +00:00
{ " shadermixeduse " , R_ShaderMixedUse_f , NULL , " prints all mixed use issues " } ,
2017-10-03 17:11:10 +00:00
{ " skinlist " , R_SkinList_f , NULL , " prints loaded skins " } ,
{ " modellist " , R_Modellist_f , NULL , " prints loaded models " } ,
2024-01-21 01:27:18 +00:00
{ " gpulist " , RHI : : PrintGPUList , NULL , help_gpulist } ,
2017-10-03 17:11:10 +00:00
{ " screenshot " , R_ScreenShotTGA_f , NULL , " takes a TARGA (.tga) screenshot " } ,
2017-11-05 21:40:32 +00:00
{ " screenshotJPEG " , R_ScreenShotJPG_f , NULL , " takes a JPEG (.jpg) screenshot " } ,
{ " screenshotnc " , R_ScreenShotNoConTGA_f , NULL , " takes a TARGA screenshot w/o the console " } ,
{ " screenshotncJPEG " , R_ScreenShotNoConJPG_f , NULL , " takes a JPEG screenshot w/o the console " }
2016-12-18 04:43:04 +00:00
} ;
2017-10-03 17:11:10 +00:00
static const cvarTableItem_t r_cvars [ ] =
2016-12-18 04:43:04 +00:00
{
//
// latched and archived variables
//
2023-08-28 22:43:26 +00:00
{
& r_mipGenFilter , " r_mipGenFilter " , " L4 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_STRING , NULL , NULL , " mip-map generation filter " ,
" Mip-map filter " , CVARCAT_GRAPHICS , " Texture sharpness in the distance " , " " ,
CVAR_GUI_VALUE ( " L4 " , " Lanczos 4 " , " Very sharp, 4-pixel radius " )
CVAR_GUI_VALUE ( " L3 " , " Lanczos 3 " , " Very sharp, 3-pixel radius " )
CVAR_GUI_VALUE ( " BL " , " Bi-linear " , " Blurry, 1-pixel radius " )
CVAR_GUI_VALUE ( " MN2 " , " Mitchell-Netravali 2 " , " Balanced, 2-pixel radius " )
CVAR_GUI_VALUE ( " BH4 " , " 3-term Blackman-Harris 4 " , " Balanced, 4-pixel radius " )
CVAR_GUI_VALUE ( " BH3 " , " 3-term Blackman-Harris 3 " , " Balanced, 3-pixel radius " )
CVAR_GUI_VALUE ( " BH2 " , " 3-term Blackman-Harris 2 " , " Balanced, 2-pixel radius " )
CVAR_GUI_VALUE ( " T2 " , " Tent 2 (1/3 2/3) " , " Blurry, 2-pixel radius " )
} ,
{
& r_mipGenGamma , " r_mipGenGamma " , " 1.8 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 1.0 " , " 3.0 " , help_r_mipGenGamma ,
" Mip-map gamma " , CVARCAT_GRAPHICS , " Texture contrast in the distance " , " "
} ,
{
& r_ext_max_anisotropy , " r_ext_max_anisotropy " , " 16 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 0 " , " 16 " , help_r_ext_max_anisotropy ,
" Texture anisotropy " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Texture sharpness at oblique angles " , " "
} ,
{
& r_roundImagesDown , " r_roundImagesDown " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_roundImagesDown ,
" Low-resolution resampling " , CVARCAT_GRAPHICS , " Lowers the resolution of non-power of two textures "
} ,
{
& r_colorMipLevels , " r_colorMipLevels " , " 0 " , CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_colorMipLevels ,
" Colorize texture mips " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_detailTextures , " r_detailtextures " , " 1 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , " enables detail textures shader stages " ,
" Enable detail textures " , CVARCAT_GRAPHICS , " It also toggles decals on some maps " , " "
} ,
{
& r_mode , " r_mode " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 0 " , XSTRING ( VIDEOMODE_MAX ) , help_r_mode ,
" Full-screen video mode " , CVARCAT_DISPLAY , " " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Native res " , " Same resolution as on the desktop " )
CVAR_GUI_VALUE ( " 1 " , " Custom res/upscale " , " Custom resolution, upsampled by CNQ3 " )
CVAR_GUI_VALUE ( " 2 " , " Video mode change " , " Custom resolution, upsampled by the system \n \n "
" Only use this on monitors that can reach higher refresh rates at lower resolutions. \n "
" It makes alt-tabbing slow. " )
} ,
{
& r_brightness , " r_brightness " , " 2 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 0.25 " , " 32 " , " overall brightness " ,
" Screen brightness " , CVARCAT_GRAPHICS , " " , " "
} ,
{
// should be called r_lightmapBrightness
& r_mapBrightness , " r_mapBrightness " , " 2 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 0.25 " , " 32 " , " brightness of lightmap textures " ,
" Lightmap brightness " , CVARCAT_GRAPHICS , " Applies to lightmap textures only " , " "
} ,
{
// should be called r_textureBrightness
& r_intensity , " r_intensity " , " 1 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 1 " , " 32 " , " brightness of non-lightmap map textures " ,
" Texture brightness " , CVARCAT_GRAPHICS , " Applies to non-lightmap textures only " , " "
} ,
{
& r_fullscreen , " r_fullscreen " , " 1 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , " full-screen mode " ,
" Fullscreen " , CVARCAT_DISPLAY , " " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Windowed " , " " )
CVAR_GUI_VALUE ( " 1 " , " Fullscreen " , " " )
} ,
{
& r_width , " r_width " , " 1280 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 320 " , " 65535 " , " custom window/render width " ,
" Window/render width " , CVARCAT_DISPLAY , " Used in windowed mode and non-native full-screen " , " "
} ,
{
& r_height , " r_height " , " 720 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 240 " , " 65535 " , " custom window/render height " ,
" Window/render height " , CVARCAT_DISPLAY , " Used in windowed mode and non-native full-screen " , " "
} ,
{
& r_vertexLight , " r_vertexLight " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , " disables lightmap texture blending " ,
" Vertex lighting " , CVARCAT_GRAPHICS , " Uses per-vertex lighting data instead of lightmaps " , " "
} ,
{
// note that r_subdivisions > 64 will create rendering artefacts because you'll see the other side of a curved surface when against it
& r_subdivisions , " r_subdivisions " , " 1 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 1 " , " 64 " , help_r_subdivisions ,
" Patch tessellation step size " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Lower values produce smoother curves " , " "
} ,
{
& r_fullbright , " r_fullbright " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_fullbright ,
" Fullbright lighting " , CVARCAT_GRAPHICS , " Lightmap textures get replaced by white/grey images " , " "
} ,
{
& r_lightmap , " r_lightmap " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_lightmap ,
" Draw lightmaps " , CVARCAT_GRAPHICS , " Draws lightmap data only when available " , " "
} ,
{
& r_lightmapGreyscale , " r_lightmapGreyscale " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_FLOAT , " 0 " , " 1 " , " how desaturated the lightmap looks " ,
" Lightmap desaturation " , CVARCAT_GRAPHICS , " Desaturates the lightmap data " , " "
} ,
2023-09-16 23:56:35 +00:00
{
& r_depthFade , " r_depthFade " , " 1 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_depthFade ,
" Depth fade " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Prevents transparent surfaces from creating sharp edges when \" cutting \" through opaque geometry " , " "
} ,
2023-08-28 22:43:26 +00:00
{
& r_dither , " r_dither " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_dither ,
" Dither " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Adds noise to fight color banding artifacts " , " "
} ,
{
& r_rtColorFormat , " r_rtColorFormat " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 0 " , XSTRING ( RTCF_MAX ) , help_r_rtColorFormat ,
" Render target format " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Controls the number of bits per pixel for the RGBA channels " , " " ,
CVAR_GUI_VALUE ( " 0 " , " R8G8B8A8 " , " High perf, standard quality " )
CVAR_GUI_VALUE ( " 1 " , " R10G10B10A2 " , " High perf, better colors, worse alpha " )
CVAR_GUI_VALUE ( " 2 " , " R16G16B16A16 " , " Low perf, better colors and alpha " )
} ,
{
& r_depthClamp , " r_depthClamp " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , help_r_depthClamp ,
" Depth clamping " , CVARCAT_GRAPHICS , " Enable if you want a horizontal FOV larger than 130 " , " "
} ,
{
& r_gpuPreference , " r_gpuPreference " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 0 " , XSTRING ( GPUPREF_MAX ) , help_r_gpuPreference ,
2024-01-21 01:27:18 +00:00
" GPU preference " , CVARCAT_DISPLAY | CVARCAT_PERFORMANCE , " Choose between low-power and high-performance devices " , " " ,
2023-08-28 22:43:26 +00:00
CVAR_GUI_VALUE ( " 0 " , " High performance " , " " )
CVAR_GUI_VALUE ( " 1 " , " Low power " , " " )
CVAR_GUI_VALUE ( " 2 " , " None " , " " )
} ,
2024-01-21 01:27:18 +00:00
{
// GUI settings and data range are set by the RHI during init
& r_gpuIndex , " r_gpuIndex " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_INTEGER , " 0 " , NULL , help_r_gpuIndex
} ,
2023-08-28 22:43:26 +00:00
{
& r_vsync , " r_vsync " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL , " enables v-sync " ,
2024-01-13 21:40:13 +00:00
" V-Sync " , CVARCAT_DISPLAY | CVARCAT_PERFORMANCE , " Enabling locks the framerate to the monitor's refresh rate " , " " ,
2023-08-28 22:43:26 +00:00
CVAR_GUI_VALUE ( " 0 " , " Frame cap " , " The framerate is capped by CNQ3's own limiter " )
CVAR_GUI_VALUE ( " 1 " , " V-Sync " , " The framerate matches the monitor's refresh rate " )
} ,
2024-01-13 21:40:13 +00:00
{
2024-01-21 02:38:32 +00:00
& r_pipeline , " r_pipeline " , " 0 " , CVAR_ARCHIVE | CVAR_LATCH , CVART_BOOL , NULL , NULL ,
" rendering pipeline \n "
S_COLOR_VAL " 0 " S_COLOR_HELP " = Gameplay \n "
S_COLOR_VAL " 1 " S_COLOR_HELP " = Cinematic " ,
2024-01-13 21:40:13 +00:00
" Rendering pipeline " , CVARCAT_GRAPHICS , " " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Gameplay " , " Use to play the game " )
CVAR_GUI_VALUE ( " 1 " , " Cinematic " , " Use for screenshots and movies " )
} ,
2016-12-18 04:43:04 +00:00
//
2017-10-03 17:11:10 +00:00
// latched variables that can only change over a restart
2016-12-18 04:43:04 +00:00
//
2023-08-28 22:43:26 +00:00
{
& r_displayRefresh , " r_displayRefresh " , " 0 " , CVAR_LATCH , CVART_INTEGER , " 0 " , " 480 " , S_COLOR_VAL " 0 " S_COLOR_HELP " lets the driver decide " ,
" Refresh rate " , CVARCAT_DISPLAY , " 0 to let the driver decide " , " Only available in fullscreen with video mode change "
} ,
{
& r_singleShader , " r_singleShader " , " 0 " , CVAR_CHEAT | CVAR_LATCH , CVART_BOOL , NULL , NULL , " forces the default shader on all world surfaces except the sky " ,
" Force default shader " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " Forces it on all world surfaces except the sky " , " "
} ,
2016-12-18 04:43:04 +00:00
//
// archived variables that can change at any time
//
2023-08-28 22:43:26 +00:00
{
& r_smaa , " r_smaa " , " 0 " , CVAR_ARCHIVE , CVART_INTEGER , " 0 " , " 4 " , help_r_smaa ,
" SMAA " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Enhanced sub-pixel morphological anti-aliasing " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Disabled " , " " )
CVAR_GUI_VALUE ( " 1 " , " Low quality " , " " )
CVAR_GUI_VALUE ( " 2 " , " Medium quality " , " " )
CVAR_GUI_VALUE ( " 3 " , " High quality " , " " )
CVAR_GUI_VALUE ( " 4 " , " Ultra quality " , " " )
} ,
{
& r_picmip , " r_picmip " , " 0 " , CVAR_ARCHIVE , CVART_INTEGER , " 0 " , " 16 " , help_r_picmip ,
" Picmip " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Higher numbers make for blurrier textures " , " "
} ,
{
& r_blitMode , " r_blitMode " , " 0 " , CVAR_ARCHIVE , CVART_INTEGER , " 0 " , XSTRING ( BLITMODE_MAX ) , help_r_blitMode ,
" Fullscreen blit mode " , CVARCAT_DISPLAY , " Dictates how the image gets upsampled " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Scaled to fit " , " Preserves aspect ratio -> black bars " )
CVAR_GUI_VALUE ( " 1 " , " Centered " , " No scaling at all " )
CVAR_GUI_VALUE ( " 2 " , " Stretched " , " Takes the entire screen -> no black bars " )
} ,
{
& r_lodbias , " r_lodbias " , " -2 " , CVAR_ARCHIVE , CVART_INTEGER , " -2 " , " 2 " , help_r_lodbias ,
" MD3 LoD bias " , CVARCAT_GRAPHICS , " Applies to items and player models \n Lower means more detail " , " "
} ,
{
& r_ignoreShaderSortKey , " r_ignoreShaderSortKey " , " 0 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , help_r_ignoreShaderSortKey ,
" Ignore shader draw order " , CVARCAT_GRAPHICS , " All transparent surfaces are sorted by depth " , " "
} ,
{
& r_fastsky , " r_fastsky " , " 0 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , help_r_fastsky ,
" Fast sky " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Draws the sky and portal surfaces in black " , " "
} ,
{
& r_noportals , " r_noportals " , " 0 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , help_r_noportals ,
" Disable portal rendering " , CVARCAT_GRAPHICS , " Draws teleporter and mirror surfaces in black " , " "
} ,
{
& r_dynamiclight , " r_dynamiclight " , " 1 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , " enables dynamic lights " ,
2023-09-10 16:45:55 +00:00
" Enable dynamic lights " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " For power-ups, muzzle flashes, rockets, explosions, ... " , " "
2023-08-28 22:43:26 +00:00
} ,
{
& r_lego , " r_lego " , " 0 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , " LEGO(R) texture filtering " ,
" LEGO(R) textures " , CVARCAT_GRAPHICS , " Makes textures look blocky " , " Forces nearest neighbor texture filtering "
} ,
{
& r_gamma , " r_gamma " , " 1.2 " , CVAR_ARCHIVE , CVART_FLOAT , " 0.5 " , " 3 " , help_r_gamma ,
" Screen gamma " , CVARCAT_GRAPHICS , " " , " "
} ,
{
& r_greyscale , " r_greyscale " , " 0 " , CVAR_ARCHIVE , CVART_FLOAT , " 0 " , " 1 " , " how desaturated the final image looks " ,
" Screen desaturation " , CVARCAT_GRAPHICS , " " , " "
} ,
{
& r_ditherStrength , " r_ditherStrength " , " 1.0 " , CVAR_ARCHIVE , CVART_FLOAT , " 0.125 " , " 8.0 " , help_r_ditherStrength ,
" Dither strength " , CVARCAT_GRAPHICS , " Amount of noise added to fight color banding " , " "
} ,
{
& r_transpSort , " r_transpSort " , " 0 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , help_r_transpSort ,
" Transparent surface sorting " , CVARCAT_GRAPHICS , " " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Sort dynamic " , " " )
CVAR_GUI_VALUE ( " 1 " , " Sort all " , " " )
} ,
{
& r_lodCurveError , " r_lodCurveError " , " 2000 " , CVAR_ARCHIVE , CVART_FLOAT , " 250 " , " 10000 " , " curved surfaces LOD scale " ,
" Curve LoD scale " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Higher is more detailed " , " "
} ,
{
& r_mapGreyscale , " r_mapGreyscale " , " 0 " , CVAR_ARCHIVE , CVART_FLOAT , " 0 " , " 1 " , " how desaturated the map looks " ,
" Non-CTF map desaturation " , CVARCAT_GRAPHICS , " Desaturates non-CTF world surfaces " , " CTF surfaces are the red/blue base banners/markers "
} ,
{
& r_mapGreyscaleCTF , " r_mapGreyscaleCTF " , " 0 " , CVAR_ARCHIVE , CVART_FLOAT , " 0 " , " 1 " , help_r_mapGreyscaleCTF ,
" CTF map desaturation " , CVARCAT_GRAPHICS , " Desaturates CTF world surfaces " , " CTF surfaces are the red/blue base banners/markers "
} ,
{
& r_teleporterFlash , " r_teleporterFlash " , " 1 " , CVAR_ARCHIVE , CVART_BOOL , NULL , NULL , " draws bright colors when being teleported " ,
" Bright teleporter flash " , CVARCAT_GRAPHICS , " Draws bright colors while being teleported " , " "
} ,
{
& r_sleepThreshold , " r_sleepThreshold " , " 2500 " , CVAR_ARCHIVE , CVART_INTEGER , " 2000 " , " 4000 " , help_r_sleepThreshold ,
" Frame sleep threshold " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Higher means more consistent frame times but higher CPU usage " ,
" This is the time cushion (in microseconds) for frame sleep. \n "
" It's a trade-off between frame time consistency and CPU usage. \n "
" Set to 2000 if you have a struggling old/low-power CPU. \n "
" 2500 should be enough to deal with delayed thread wake-ups. \n "
" Use the frame graph to confirm that higher values help on your system. "
} ,
{
& r_shadingRate , " r_shadingRate " , " 0 " , CVAR_ARCHIVE , CVART_INTEGER , " 0 " , " 6 " , help_r_shadingRate ,
" Shading rate " , CVARCAT_GRAPHICS | CVARCAT_PERFORMANCE , " Variable-Rate Shading (VRS) mode " ,
" The numbers are the horizontal and vertical subsampling factors. \n "
" 1x1 is forced for the sky, nopicmipped sprites (e.g. simple items) \n "
" and nopicmipped alpha tested surfaces (e.g. grates). \n "
" If extended modes are not supported, 2x2 is used instead. \n "
" Prefer horizontal subsampling as many maps have textures \n "
" with thin horizontal lines, which become an aliased mess when \n "
" vertically subsampled. " ,
CVAR_GUI_VALUE ( " 0 " , " Off " , " 1x horizontal, 1x vertical " )
CVAR_GUI_VALUE ( " 1 " , " 2x1 " , " 2x horizontal, 1x vertical " )
CVAR_GUI_VALUE ( " 2 " , " 1x2 " , " 1x horizontal, 2x vertical " )
CVAR_GUI_VALUE ( " 3 " , " 2x2 " , " 2x horizontal, 2x vertical " )
CVAR_GUI_VALUE ( " 4 " , " 4x2 " , " 4x horizontal, 2x vertical " )
CVAR_GUI_VALUE ( " 5 " , " 2x4 " , " 2x horizontal, 4x vertical " )
CVAR_GUI_VALUE ( " 6 " , " 4x4 " , " 4x horizontal, 4x vertical " )
} ,
{
2023-10-18 23:02:14 +00:00
& r_guiFont , " r_guiFont " , " 0 " , CVAR_ARCHIVE , CVART_INTEGER , " 0 " , " 2 " , help_r_guiFont ,
2023-08-28 22:43:26 +00:00
" GUI font " , CVARCAT_GUI , " " , " " ,
CVAR_GUI_VALUE ( " 0 " , " Proggy Clean (13px) " , " " )
CVAR_GUI_VALUE ( " 1 " , " Sweet16 Mono (16px) " , " " )
2023-10-18 23:02:14 +00:00
CVAR_GUI_VALUE ( " 2 " , " Custom Font File " , " " )
} ,
{
& r_guiFontFile , " r_guiFontFile " , " " , CVAR_ARCHIVE , CVART_STRING , NULL , NULL , " custom font .ttf file " ,
" GUI font file " , CVARCAT_GUI , " Path of the custom .ttf font file " , " " , NULL
} ,
{
& r_guiFontHeight , " r_guiFontHeight " , " 24 " , CVAR_ARCHIVE , CVART_INTEGER , " 7 " , " 48 " , " custom font height " ,
" GUI font height " , CVARCAT_GUI , " Height of the custom font " , " " , NULL
2023-08-28 22:43:26 +00:00
} ,
2016-12-18 04:43:04 +00:00
//
// temporary variables that can change at any time
//
2023-08-28 22:43:26 +00:00
{
& r_ambientScale , " r_ambientScale " , " 0.6 " , CVAR_CHEAT , CVART_FLOAT , " 0 " , NULL , " entity ambient light scale " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_directedScale , " r_directedScale " , " 1 " , CVAR_CHEAT , CVART_FLOAT , " 0 " , NULL , " entity directed light scale " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
// keeping it around in case we enable other mods again
& r_uiFullScreen , " r_uifullscreen " , " 0 " , CVAR_TEMP , CVART_BOOL , NULL , NULL , NULL ,
" " , 0 , " " , " "
} ,
{
& r_debugLight , " r_debuglight " , " 0 " , CVAR_TEMP , CVART_BOOL , NULL , NULL , " prints entity light values " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_debugSort , " r_debugSort " , " 0 " , CVAR_CHEAT , CVART_FLOAT , " 0 " , NULL , " doesn't render shaders with a greater sort key " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_nocurves , " r_nocurves " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " doesn't render grid meshes " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_drawworld , " r_drawworld " , " 1 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " disables rendering of world surfaces " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_portalOnly , " r_portalOnly " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " only draws the mirrored plane " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_lodscale , " r_lodscale " , " 5 " , CVAR_CHEAT , CVART_FLOAT , " 1 " , " 20 " , " LOD scale for MD3 models " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_norefresh , " r_norefresh " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " disables 3D scene rendering " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_drawentities , " r_drawentities " , " 1 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " enables entity rendering " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_nocull , " r_nocull " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " disables frustum culling " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_novis , " r_novis " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " disables PVS usage " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_debugSurface , " r_debugSurface " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " draws collision models " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_clear , " r_clear " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " clears to violet instead of black " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_lockpvs , " r_lockpvs " , " 0 " , CVAR_CHEAT , CVART_BOOL , NULL , NULL , " helps visualize the current PVS' limits " ,
" " , CVARCAT_GRAPHICS | CVARCAT_DEBUGGING , " " , " "
} ,
{
& r_maxpolys , " r_maxpolys " , XSTRING ( DEFAULT_MAX_POLYS ) , 0 , CVART_INTEGER , XSTRING ( DEFAULT_MAX_POLYS ) , NULL , " maximum polygon count per frame " ,
" Max poly count " , 0 , " Maximum polygon count per frame " , " "
} ,
{
& r_maxpolyverts , " r_maxpolyverts " , XSTRING ( DEFAULT_MAX_POLYVERTS ) , 0 , CVART_INTEGER , XSTRING ( DEFAULT_MAX_POLYVERTS ) , NULL , " maximum polygon vertex count per frame " ,
" Max poly vertices " , 0 , " Maximum polygon vertex count per frame " , " "
} ,
{
& r_debugUI , " r_debugUI " , " 0 " , CVAR_TEMP , CVART_BOOL , NULL , NULL , " displays the debug/profile GUI " ,
" " , 0 , " " , " "
} ,
{
& r_debugInput , " r_debugInput " , " 0 " , CVAR_TEMP , CVART_BOOL , NULL , NULL , " routes input to the debug/profile GUI " ,
" " , 0 , " " , " "
}
2017-10-03 17:11:10 +00:00
} ;
static void R_Register ( )
{
ri . Cvar_RegisterTable ( r_cvars , ARRAY_LEN ( r_cvars ) ) ;
ri . Cmd_RegisterTable ( r_cmds , ARRAY_LEN ( r_cmds ) ) ;
2016-12-18 04:43:04 +00:00
}
2019-09-25 03:25:59 +00:00
static void R_InitMipFilter ( )
{
struct filter_t {
const char * cvarName ;
const char * fullName ;
float kernel [ 4 ] ;
} ;
// preferred option goes first
const filter_t filterArray [ ] = {
{ " L4 " , " Lanczos 4 " , - 0.0491683967f , - 0.0816986337f , 0.151636884f , 0.479230106f } ,
{ " L3 " , " Lanczos 3 " , 0.0f , - 0.0646646321f , 0.131493837f , 0.433170795f } ,
{ " BL " , " Bi-linear " , 0.0f , 0.0f , 0.0f , 0.5f } ,
{ " MN2 " , " Mitchell-Netravali 2 (B = 1/3, C = 1/3) " , 0.0f , 0.0f , 0.123327762f , 0.376672268f } ,
{ " BH4 " , " 3-term Blackman-Harris 4 " , 0.00106591149f , 0.0288433302f , 0.151539952f , 0.318550885f } ,
{ " BH3 " , " 3-term Blackman-Harris 3 " , 0.0f , 0.00302829780f , 0.101031370f , 0.395940334f } ,
{ " BH2 " , " 3-term Blackman-Harris 2 " , 0.0f , 0.0f , 0.0151469158f , 0.484853119f } ,
{ " T2 " , " Tent 2 (1/3 2/3) " , 0.0f , 0.0f , 1.0f / 6.0f , 2.0f / 6.0f } ,
// The results are so similar to Lanczos...
//{ "K4", "Kaiser 4", -0.0487834960f, -0.0811581835f, 0.151146635f, 0.478795081f },
//{ "K3", "Kaiser 3", 0.0f, -0.0642274171f, 0.131010026f, 0.433217406f }
} ;
int index = - 1 ;
for ( int i = 0 ; i < ARRAY_LEN ( filterArray ) ; + + i ) {
if ( ! Q_stricmp ( r_mipGenFilter - > string , filterArray [ i ] . cvarName ) ) {
index = i ;
break ;
}
}
if ( index < 0 ) {
index = 0 ;
ri . Printf ( PRINT_WARNING , " Invalid %s value, selecting the %s filter instead \n " , r_mipGenFilter - > name , filterArray [ index ] . fullName ) ;
}
memcpy ( tr . mipFilter , filterArray [ index ] . kernel , sizeof ( tr . mipFilter ) ) ;
}
2016-12-18 04:43:04 +00:00
void R_Init ( )
{
COMPILE_TIME_ASSERT ( sizeof ( glconfig_t ) = = 11332 ) ;
COMPILE_TIME_ASSERT ( sizeof ( TargaHeader ) = = 18 ) ;
QSUBSYSTEM_INIT_START ( " Renderer " ) ;
// clear all our internal state
Com_Memset ( & tr , 0 , sizeof ( tr ) ) ;
Com_Memset ( & backEnd , 0 , sizeof ( backEnd ) ) ;
Com_Memset ( & tess , 0 , sizeof ( tess ) ) ;
2017-01-11 13:24:58 +00:00
if ( ( intptr_t ) tess . xyz & 15 )
2016-12-18 04:43:04 +00:00
Com_Printf ( " WARNING: tess.xyz not 16 byte aligned \n " ) ;
R_NoiseInit ( ) ;
R_Register ( ) ;
max_polys = max ( r_maxpolys - > integer , DEFAULT_MAX_POLYS ) ;
max_polyverts = max ( r_maxpolyverts - > integer , DEFAULT_MAX_POLYVERTS ) ;
2017-11-03 18:34:32 +00:00
byte * ptr = ( byte * ) ri . Hunk_Alloc ( sizeof ( backEndData_t ) + sizeof ( srfPoly_t ) * max_polys + sizeof ( polyVert_t ) * max_polyverts , h_low ) ;
backEndData = ( backEndData_t * ) ptr ;
backEndData - > polys = ( srfPoly_t * ) ( ptr + sizeof ( backEndData_t ) ) ;
backEndData - > polyVerts = ( polyVert_t * ) ( ptr + sizeof ( backEndData_t ) + sizeof ( srfPoly_t ) * max_polys ) ;
2016-12-18 04:43:04 +00:00
2017-11-03 18:34:32 +00:00
R_ClearFrame ( ) ;
2016-12-18 04:43:04 +00:00
2019-09-25 03:25:59 +00:00
R_InitMipFilter ( ) ;
2024-01-13 21:40:13 +00:00
R_SelectRenderPipeline ( ) ;
2022-12-28 19:49:18 +00:00
renderPipeline - > Init ( ) ;
2016-12-18 04:43:04 +00:00
R_InitImages ( ) ;
R_InitShaders ( ) ;
R_InitSkins ( ) ;
R_ModelInit ( ) ;
QSUBSYSTEM_INIT_DONE ( " Renderer " ) ;
}
static void RE_Shutdown ( qbool destroyWindow )
{
2022-12-28 19:49:18 +00:00
ri . Printf ( PRINT_DEVELOPER , " RE_Shutdown( %i ) \n " , destroyWindow ) ;
2019-09-25 03:25:59 +00:00
2022-12-28 19:49:18 +00:00
R_ShutDownGUI ( ) ;
2016-12-18 04:43:04 +00:00
if ( tr . registered ) {
2017-10-03 22:35:26 +00:00
ri . Cmd_UnregisterModule ( ) ;
2024-01-13 21:40:13 +00:00
if ( ! destroyWindow & & r_pipeline - > latchedString ! = NULL ) {
destroyWindow = qtrue ;
}
2022-12-28 19:49:18 +00:00
renderPipeline - > ShutDown ( destroyWindow ) ;
2016-12-18 04:43:04 +00:00
}
2019-09-25 03:25:59 +00:00
// shut down platform-specific video stuff
2016-12-18 04:43:04 +00:00
if ( destroyWindow ) {
2019-09-25 03:25:59 +00:00
Sys_V_Shutdown ( ) ;
2017-11-03 18:33:54 +00:00
memset ( & glConfig , 0 , sizeof ( glConfig ) ) ;
2016-12-18 04:43:04 +00:00
}
tr . registered = qfalse ;
}
static void RE_BeginRegistration ( glconfig_t * glconfigOut )
{
R_Init ( ) ;
* glconfigOut = glConfig ;
tr . viewCluster = - 1 ; // force markleafs to regenerate
RE_ClearScene ( ) ;
tr . registered = qtrue ;
}
static void RE_EndRegistration ( )
{
}
2019-09-25 03:25:59 +00:00
static void RE_StretchRaw ( int x , int y , int w , int h , int cols , int rows , const byte * data , int client , qbool dirty )
2018-12-08 21:43:58 +00:00
{
2019-09-25 03:25:59 +00:00
if ( ! tr . registered )
return ;
2022-12-28 19:49:18 +00:00
//@TODO: gal.UpdateScratch( tr.scratchImage[client], cols, rows, data, dirty );
2019-09-25 03:25:59 +00:00
tr . scratchShader - > stages [ 0 ] - > bundle . image [ 0 ] = tr . scratchImage [ client ] ;
RE_StretchPic ( x , y , w , h , 0.5f / cols , 0.5f / rows , ( cols - 0.5f ) / cols , ( rows - 0.5f ) / rows , ( qhandle_t ) tr . scratchShader - > index ) ;
}
static qbool RE_Registered ( )
{
return tr . registered ;
}
static qbool RE_IsFrameSleepNeeded ( )
{
return ! Sys_V_IsVSynced ( ) ;
2018-12-08 21:43:58 +00:00
}
2022-10-23 00:58:20 +00:00
static qbool RE_IsDepthClampEnabled ( )
{
return r_depthClamp - > integer ! = 0 ;
}
2023-08-28 22:43:26 +00:00
static void RE_ComputeCursorPosition ( int * x , int * y )
{
if ( r_fullscreen - > integer ! = 1 | | r_mode - > integer ! = VIDEOMODE_UPSCALE ) {
return ;
}
if ( r_blitMode - > integer = = BLITMODE_CENTERED ) {
* x - = ( glInfo . winWidth - glConfig . vidWidth ) / 2 ;
* y - = ( glInfo . winHeight - glConfig . vidHeight ) / 2 ;
} else if ( r_blitMode - > integer = = BLITMODE_STRETCHED ) {
const float sx = ( float ) glConfig . vidWidth / ( float ) glInfo . winWidth ;
const float sy = ( float ) glConfig . vidHeight / ( float ) glInfo . winHeight ;
* x * = sx ;
* y * = sy ;
} else if ( r_blitMode - > integer = = BLITMODE_ASPECT ) {
const float art = ( float ) glConfig . vidWidth / ( float ) glConfig . vidHeight ;
const float arw = ( float ) glInfo . winWidth / ( float ) glInfo . winHeight ;
float wsx , wsy , s ;
if ( arw > art ) {
wsx = art / arw ;
wsy = 1.0f ;
s = ( float ) glConfig . vidHeight / ( float ) glInfo . winHeight ;
} else {
wsx = 1.0f ;
wsy = arw / art ;
s = ( float ) glConfig . vidWidth / ( float ) glInfo . winWidth ;
}
const int x0 = ( glInfo . winWidth - ( glInfo . winWidth * wsx ) ) * 0.5f ;
const int y0 = ( glInfo . winHeight - ( glInfo . winHeight * wsy ) ) * 0.5f ;
* x - = x0 ;
* y - = y0 ;
* x * = s ;
* y * = s ;
} else {
Q_assert ( ! " Invalid r_blitMode " ) ;
}
}
2016-12-18 04:43:04 +00:00
const refexport_t * GetRefAPI ( const refimport_t * rimp )
{
static refexport_t re ;
ri = * rimp ;
Com_Memset ( & re , 0 , sizeof ( re ) ) ;
// the RE_ functions are Renderer Entry points
re . Shutdown = RE_Shutdown ;
re . BeginRegistration = RE_BeginRegistration ;
re . RegisterModel = RE_RegisterModel ;
re . RegisterSkin = RE_RegisterSkin ;
re . RegisterShader = RE_RegisterShader ;
re . RegisterShaderNoMip = RE_RegisterShaderNoMip ;
re . LoadWorld = RE_LoadWorldMap ;
re . SetWorldVisData = RE_SetWorldVisData ;
re . EndRegistration = RE_EndRegistration ;
re . BeginFrame = RE_BeginFrame ;
re . EndFrame = RE_EndFrame ;
re . MarkFragments = R_MarkFragments ;
re . LerpTag = R_LerpTag ;
re . ModelBounds = R_ModelBounds ;
re . ClearScene = RE_ClearScene ;
re . AddRefEntityToScene = RE_AddRefEntityToScene ;
re . AddPolyToScene = RE_AddPolyToScene ;
re . LightForPoint = R_LightForPoint ;
re . AddLightToScene = RE_AddLightToScene ;
re . RenderScene = RE_RenderScene ;
re . SetColor = RE_SetColor ;
re . DrawStretchPic = RE_StretchPic ;
2017-12-27 04:13:33 +00:00
re . DrawTriangle = RE_DrawTriangle ;
2016-12-18 04:43:04 +00:00
re . DrawStretchRaw = RE_StretchRaw ;
re . GetEntityToken = R_GetEntityToken ;
re . inPVS = R_inPVS ;
re . TakeVideoFrame = RE_TakeVideoFrame ;
2019-09-25 03:25:59 +00:00
re . Registered = RE_Registered ;
re . ShouldSleep = RE_IsFrameSleepNeeded ;
2018-12-08 21:43:58 +00:00
2022-10-23 00:58:20 +00:00
re . DepthClamp = RE_IsDepthClampEnabled ;
2023-08-28 22:43:26 +00:00
re . ComputeCursorPosition = RE_ComputeCursorPosition ;
2016-12-18 04:43:04 +00:00
return & re ;
}