From c3edd749ac26c6322eafa8303e592df3c32ffd25 Mon Sep 17 00:00:00 2001 From: divverent Date: Sun, 9 May 2010 10:28:26 +0000 Subject: [PATCH] screenshot: get rid of the 3*w*h+18 TGA buffer; instead however always capture as BGRA from the GPU; also cvar: r_drawworld (when 0, turns off world drawing), and scr_screenshot_alpha (try to save alpha channel with screenshot). Together, with this one can make nice alpha transparent screenshots of player models. git-svn-id: svn://svn.icculus.org/twilight/trunk/darkplaces@10180 d7cf8633-e32d-0410-b094-e92efae38249 --- cl_main.c | 2 +- cl_screen.c | 76 ++++++++++++++++++++++++++++++---------------------- clvm_cmds.c | 4 +-- fs.c | 17 +++++++++--- fs.h | 3 ++- gl_backend.h | 2 +- gl_rmain.c | 2 ++ image.c | 20 +++++++++----- image.h | 4 +-- image_png.c | 7 +++-- image_png.h | 2 +- render.h | 1 + 12 files changed, 87 insertions(+), 53 deletions(-) diff --git a/cl_main.c b/cl_main.c index 357250ec..b6c293c0 100644 --- a/cl_main.c +++ b/cl_main.c @@ -122,7 +122,7 @@ void CL_ClearState(void) cl.sensitivityscale = 1.0f; // enable rendering of the world and such - cl.csqc_vidvars.drawworld = true; + cl.csqc_vidvars.drawworld = r_drawworld.integer; cl.csqc_vidvars.drawenginesbar = true; cl.csqc_vidvars.drawcrosshair = true; diff --git a/cl_screen.c b/cl_screen.c index 9050ab0d..fe6f765d 100644 --- a/cl_screen.c +++ b/cl_screen.c @@ -37,6 +37,7 @@ cvar_t scr_screenshot_jpeg_quality = {CVAR_SAVE, "scr_screenshot_jpeg_quality"," cvar_t scr_screenshot_png = {CVAR_SAVE, "scr_screenshot_png","0", "save png instead of targa"}; cvar_t scr_screenshot_gammaboost = {CVAR_SAVE, "scr_screenshot_gammaboost","1", "gamma correction on saved screenshots and videos, 1.0 saves unmodified images"}; cvar_t scr_screenshot_hwgamma = {CVAR_SAVE, "scr_screenshot_hwgamma","1", "apply the video gamma ramp to saved screenshots and videos"}; +cvar_t scr_screenshot_alpha = {CVAR_SAVE, "scr_screenshot_alpha","0", "try to write an alpha channel to screenshots (debugging feature)"}; // scr_screenshot_name is defined in fs.c cvar_t cl_capturevideo = {0, "cl_capturevideo", "0", "enables saving of video to a .avi file using uncompressed I420 colorspace and PCM audio, note that scr_screenshot_gammaboost affects the brightness of the output)"}; cvar_t cl_capturevideo_printfps = {CVAR_SAVE, "cl_capturevideo_printfps", "1", "prints the frames per second captured in capturevideo (is only written to the log file, not to the console, as that would be visible on the video)"}; @@ -874,6 +875,7 @@ void CL_Screen_Init(void) Cvar_RegisterVariable (&scr_screenshot_gammaboost); Cvar_RegisterVariable (&scr_screenshot_hwgamma); Cvar_RegisterVariable (&scr_screenshot_name_in_mapdir); + Cvar_RegisterVariable (&scr_screenshot_alpha); Cvar_RegisterVariable (&cl_capturevideo); Cvar_RegisterVariable (&cl_capturevideo_printfps); Cvar_RegisterVariable (&cl_capturevideo_width); @@ -926,7 +928,6 @@ void SCR_ScreenShot_f (void) char mapname[MAX_QPATH]; unsigned char *buffer1; unsigned char *buffer2; - unsigned char *buffer3; qboolean jpeg = (scr_screenshot_jpeg.integer != 0); qboolean png = (scr_screenshot_png.integer != 0) && !jpeg; @@ -988,18 +989,17 @@ void SCR_ScreenShot_f (void) dpsnprintf(filename, sizeof(filename), "screenshots/%s%06d.%s", prefix_name, shotnumber, jpeg ? "jpg" : png ? "png" : "tga"); } - buffer1 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3); - buffer2 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3); - buffer3 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3 + 18); + buffer1 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 4); + buffer2 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * (scr_screenshot_alpha.integer ? 4 : 3)); - if (SCR_ScreenShot (filename, buffer1, buffer2, buffer3, 0, 0, vid.width, vid.height, false, false, false, jpeg, png, true)) + if (SCR_ScreenShot (filename, buffer1, buffer2, 0, 0, vid.width, vid.height, false, false, false, jpeg, png, true, scr_screenshot_alpha.integer)) Con_Printf("Wrote %s\n", filename); else { Con_Printf("Unable to write %s\n", filename); if(jpeg || png) { - if(SCR_ScreenShot (filename, buffer1, buffer2, buffer3, 0, 0, vid.width, vid.height, false, false, false, false, false, true)) + if(SCR_ScreenShot (filename, buffer1, buffer2, 0, 0, vid.width, vid.height, false, false, false, false, false, true, scr_screenshot_alpha.integer)) { strlcpy(filename + strlen(filename) - 3, "tga", 4); Con_Printf("Wrote %s\n", filename); @@ -1009,7 +1009,6 @@ void SCR_ScreenShot_f (void) Mem_Free (buffer1); Mem_Free (buffer2); - Mem_Free (buffer3); shotnumber++; } @@ -1216,7 +1215,6 @@ void SCR_CaptureVideo_VideoFrame(int newframestepframenum) return; CHECKGLERROR - //return SCR_ScreenShot(filename, cls.capturevideo.buffer, cls.capturevideo.buffer + vid.width * vid.height * 3, cls.capturevideo.buffer + vid.width * vid.height * 6, 0, 0, vid.width, vid.height, false, false, false, jpeg, true); // speed is critical here, so do saving as directly as possible qglReadPixels (x, y, vid.width, vid.height, GL_BGRA, GL_UNSIGNED_BYTE, cls.capturevideo.screenbuffer);CHECKGLERROR @@ -1327,7 +1325,6 @@ static void R_Envmap_f (void) char filename[MAX_QPATH], basename[MAX_QPATH]; unsigned char *buffer1; unsigned char *buffer2; - unsigned char *buffer3; if (Cmd_Argc() != 3) { @@ -1364,9 +1361,8 @@ static void R_Envmap_f (void) r_refdef.view.frustum_x = 1; // tan(45 * M_PI / 180.0); r_refdef.view.frustum_y = 1; // tan(45 * M_PI / 180.0); - buffer1 = (unsigned char *)Mem_Alloc(tempmempool, size * size * 3); + buffer1 = (unsigned char *)Mem_Alloc(tempmempool, size * size * 4); buffer2 = (unsigned char *)Mem_Alloc(tempmempool, size * size * 3); - buffer3 = (unsigned char *)Mem_Alloc(tempmempool, size * size * 3 + 18); for (j = 0;j < 12;j++) { @@ -1377,12 +1373,11 @@ static void R_Envmap_f (void) R_Mesh_Start(); R_RenderView(); R_Mesh_Finish(); - SCR_ScreenShot(filename, buffer1, buffer2, buffer3, 0, vid.height - (r_refdef.view.y + r_refdef.view.height), size, size, envmapinfo[j].flipx, envmapinfo[j].flipy, envmapinfo[j].flipdiagonaly, false, false, false); + SCR_ScreenShot(filename, buffer1, buffer2, 0, vid.height - (r_refdef.view.y + r_refdef.view.height), size, size, envmapinfo[j].flipx, envmapinfo[j].flipy, envmapinfo[j].flipdiagonaly, false, false, false, false); } Mem_Free (buffer1); Mem_Free (buffer2); - Mem_Free (buffer3); r_refdef.envmap = false; } @@ -1460,13 +1455,15 @@ void SHOWLMP_drawall(void) ============================================================================== */ -qboolean SCR_ScreenShot(char *filename, unsigned char *buffer1, unsigned char *buffer2, unsigned char *buffer3, int x, int y, int width, int height, qboolean flipx, qboolean flipy, qboolean flipdiagonal, qboolean jpeg, qboolean png, qboolean gammacorrect) +// buffer1: 4*w*h +// buffer2: 3*w*h (or 4*w*h if screenshotting alpha too) +qboolean SCR_ScreenShot(char *filename, unsigned char *buffer1, unsigned char *buffer2, int x, int y, int width, int height, qboolean flipx, qboolean flipy, qboolean flipdiagonal, qboolean jpeg, qboolean png, qboolean gammacorrect, qboolean keep_alpha) { - int indices[3] = {0,1,2}; + int indices[4] = {0,1,2,3}; // BGRA qboolean ret; CHECKGLERROR - qglReadPixels (x, y, width, height, jpeg ? GL_RGB : GL_BGR, GL_UNSIGNED_BYTE, buffer1);CHECKGLERROR + qglReadPixels (x, y, width, height, GL_BGRA, GL_UNSIGNED_BYTE, buffer1);CHECKGLERROR if(gammacorrect && (scr_screenshot_gammaboost.value != 1 || WANT_SCREENSHOT_HWGAMMA)) { @@ -1489,22 +1486,40 @@ qboolean SCR_ScreenShot(char *filename, unsigned char *buffer1, unsigned char *b for (i = 0;i < 256 * 3;i++) vidramp[i] = (unsigned short) (0.5 + pow(vidramp[i] * (1.0 / 65535.0), igamma) * 65535.0); } - for (i = 0;i < width*height*3;i += 3) + for (i = 0;i < width*height*4;i += 4) { - buffer1[i] = (unsigned char) (vidramp[buffer1[i]] * 255.0 / 65535.0 + 0.5); - buffer1[i+1] = (unsigned char) (vidramp[buffer1[i+1] + 256] * 255.0 / 65535.0 + 0.5); - buffer1[i+2] = (unsigned char) (vidramp[buffer1[i+2] + 512] * 255.0 / 65535.0 + 0.5); + buffer1[i] = (unsigned char) (vidramp[buffer1[i] + 512] * 255.0 / 65535.0 + 0.5); // B + buffer1[i+1] = (unsigned char) (vidramp[buffer1[i+1] + 256] * 255.0 / 65535.0 + 0.5); // G + buffer1[i+2] = (unsigned char) (vidramp[buffer1[i+2]] * 255.0 / 65535.0 + 0.5); // R + // A } } - Image_CopyMux (buffer2, buffer1, width, height, flipx, flipy, flipdiagonal, 3, 3, indices); - - if (jpeg) - ret = JPEG_SaveImage_preflipped (filename, width, height, buffer2); - else if (png) - ret = PNG_SaveImage_preflipped (filename, width, height, buffer2); + if(keep_alpha && !jpeg) + { + if(!png) + flipy = !flipy; // TGA: not preflipped + Image_CopyMux (buffer2, buffer1, width, height, flipx, flipy, flipdiagonal, 4, 4, indices); + if (png) + ret = PNG_SaveImage_preflipped (filename, width, height, true, buffer2); + else + ret = Image_WriteTGABGRA(filename, width, height, buffer2); + } else - ret = Image_WriteTGABGR_preflipped (filename, width, height, buffer2, buffer3); + { + if(jpeg) + { + indices[0] = 2; + indices[2] = 0; // RGB + } + Image_CopyMux (buffer2, buffer1, width, height, flipx, flipy, flipdiagonal, 3, 4, indices); + if (jpeg) + ret = JPEG_SaveImage_preflipped (filename, width, height, buffer2); + else if (png) + ret = PNG_SaveImage_preflipped (filename, width, height, false, buffer2); + else + ret = Image_WriteTGABGR_preflipped (filename, width, height, buffer2); + } return ret; } @@ -1666,15 +1681,12 @@ void SCR_DrawScreen (void) char filename[MAX_QPATH]; unsigned char *buffer1; unsigned char *buffer2; - unsigned char *buffer3; dpsnprintf(filename, sizeof(filename), "timedemoscreenshots/%s%06d.tga", cls.demoname, cls.td_frames); - buffer1 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3); + buffer1 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 4); buffer2 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3); - buffer3 = (unsigned char *)Mem_Alloc(tempmempool, vid.width * vid.height * 3 + 18); - SCR_ScreenShot(filename, buffer1, buffer2, buffer3, 0, 0, vid.width, vid.height, false, false, false, false, false, true); + SCR_ScreenShot(filename, buffer1, buffer2, 0, 0, vid.width, vid.height, false, false, false, false, false, true, false); Mem_Free(buffer1); Mem_Free(buffer2); - Mem_Free(buffer3); } } diff --git a/clvm_cmds.c b/clvm_cmds.c index 06d1d648..b1671460 100644 --- a/clvm_cmds.c +++ b/clvm_cmds.c @@ -724,7 +724,7 @@ void VM_CL_R_ClearScene (void) r_refdef.view.isoverlay = false; // FIXME: restore cl.csqc_origin // FIXME: restore cl.csqc_angles - cl.csqc_vidvars.drawworld = true; + cl.csqc_vidvars.drawworld = r_drawworld.integer; cl.csqc_vidvars.drawenginesbar = false; cl.csqc_vidvars.drawcrosshair = false; } @@ -858,7 +858,7 @@ void VM_CL_R_SetView (void) CSQC_R_RecalcView(); break; case VF_DRAWWORLD: - cl.csqc_vidvars.drawworld = k != 0; + cl.csqc_vidvars.drawworld = ((k != 0) && r_drawworld.integer); break; case VF_DRAWENGINESBAR: cl.csqc_vidvars.drawenginesbar = k != 0; diff --git a/fs.c b/fs.c index 01581988..a2f057c9 100644 --- a/fs.c +++ b/fs.c @@ -2920,9 +2920,11 @@ FS_WriteFile The filename will be prefixed by the current game directory ============ */ -qboolean FS_WriteFile (const char *filename, void *data, fs_offset_t len) +qboolean FS_WriteFileInBlocks (const char *filename, const void *const *data, const fs_offset_t *len, size_t count) { qfile_t *file; + size_t i; + fs_offset_t lentotal; file = FS_OpenRealFile(filename, "wb", false); if (!file) @@ -2931,12 +2933,21 @@ qboolean FS_WriteFile (const char *filename, void *data, fs_offset_t len) return false; } - Con_DPrintf("FS_WriteFile: %s (%u bytes)\n", filename, (unsigned int)len); - FS_Write (file, data, len); + lentotal = 0; + for(i = 0; i < count; ++i) + lentotal += len[i]; + Con_DPrintf("FS_WriteFile: %s (%u bytes)\n", filename, (unsigned int)lentotal); + for(i = 0; i < count; ++i) + FS_Write (file, data[i], len[i]); FS_Close (file); return true; } +qboolean FS_WriteFile (const char *filename, const void *data, fs_offset_t len) +{ + return FS_WriteFileInBlocks(filename, &data, &len, 1); +} + /* ============================================================================= diff --git a/fs.h b/fs.h index f8d813cb..42be6a7b 100644 --- a/fs.h +++ b/fs.h @@ -108,7 +108,8 @@ fssearch_t *FS_Search(const char *pattern, int caseinsensitive, int quiet); void FS_FreeSearch(fssearch_t *search); unsigned char *FS_LoadFile (const char *path, mempool_t *pool, qboolean quiet, fs_offset_t *filesizepointer); -qboolean FS_WriteFile (const char *filename, void *data, fs_offset_t len); +qboolean FS_WriteFileInBlocks (const char *filename, const void *const *data, const fs_offset_t *len, size_t count); +qboolean FS_WriteFile (const char *filename, const void *data, fs_offset_t len); // ------ Other functions ------ // diff --git a/gl_backend.h b/gl_backend.h index 2e93c89d..952cecd7 100644 --- a/gl_backend.h +++ b/gl_backend.h @@ -106,7 +106,7 @@ void R_Mesh_ResetTextureState(void); void R_Mesh_Draw(int firstvertex, int numvertices, int firsttriangle, int numtriangles, const int *element3i, const r_meshbuffer_t *element3i_indexbuffer, size_t element3i_bufferoffset, const unsigned short *element3s, const r_meshbuffer_t *element3s_indexbuffer, size_t element3s_bufferoffset); // saves a section of the rendered frame to a .tga or .jpg file -qboolean SCR_ScreenShot(char *filename, unsigned char *buffer1, unsigned char *buffer2, unsigned char *buffer3, int x, int y, int width, int height, qboolean flipx, qboolean flipy, qboolean flipdiagonal, qboolean jpeg, qboolean png, qboolean gammacorrect); +qboolean SCR_ScreenShot(char *filename, unsigned char *buffer1, unsigned char *buffer2, int x, int y, int width, int height, qboolean flipx, qboolean flipy, qboolean flipdiagonal, qboolean jpeg, qboolean png, qboolean gammacorrect, qboolean keep_alpha); // used by R_Envmap_f and internally in backend, clears the frame void R_ClearScreen(qboolean fogcolor); diff --git a/gl_rmain.c b/gl_rmain.c index 02e9e576..2ae129dc 100644 --- a/gl_rmain.c +++ b/gl_rmain.c @@ -76,6 +76,7 @@ cvar_t r_showcollisionbrushes_polygonoffset = {0, "r_showcollisionbrushes_polygo cvar_t r_showdisabledepthtest = {0, "r_showdisabledepthtest", "0", "disables depth testing on r_show* cvars, allowing you to see what hidden geometry the graphics card is processing"}; cvar_t r_drawportals = {0, "r_drawportals", "0", "shows portals (separating polygons) in world interior in quake1 maps"}; cvar_t r_drawentities = {0, "r_drawentities","1", "draw entities (doors, players, projectiles, etc)"}; +cvar_t r_drawworld = {0, "r_drawworld","1", "draw world (most static stuff)"}; cvar_t r_drawviewmodel = {0, "r_drawviewmodel","1", "draw your weapon model"}; cvar_t r_drawexteriormodel = {0, "r_drawexteriormodel","1", "draw your player model (e.g. in chase cam, reflections)"}; cvar_t r_cullentities_trace = {0, "r_cullentities_trace", "1", "probabistically cull invisible entities"}; @@ -6371,6 +6372,7 @@ void GL_Main_Init(void) Cvar_RegisterVariable(&r_showdisabledepthtest); Cvar_RegisterVariable(&r_drawportals); Cvar_RegisterVariable(&r_drawentities); + Cvar_RegisterVariable(&r_drawworld); Cvar_RegisterVariable(&r_cullentities_trace); Cvar_RegisterVariable(&r_cullentities_trace_samples); Cvar_RegisterVariable(&r_cullentities_trace_tempentitysamples); diff --git a/image.c b/image.c index 4fccb162..ccc59f2e 100644 --- a/image.c +++ b/image.c @@ -1142,9 +1142,12 @@ void Image_FixTransparentPixels_f(void) FS_FreeSearch(search); } -qboolean Image_WriteTGABGR_preflipped (const char *filename, int width, int height, const unsigned char *data, unsigned char *buffer) +qboolean Image_WriteTGABGR_preflipped (const char *filename, int width, int height, const unsigned char *data) { qboolean ret; + unsigned char buffer[18]; + const void *buffers[2]; + fs_offset_t sizes[2]; memset (buffer, 0, 18); buffer[2] = 2; // uncompressed type @@ -1154,18 +1157,21 @@ qboolean Image_WriteTGABGR_preflipped (const char *filename, int width, int heig buffer[15] = (height >> 8) & 0xFF; buffer[16] = 24; // pixel size - // swap rgb to bgr - memcpy(buffer + 18, data, width*height*3); - ret = FS_WriteFile (filename, buffer, width*height*3 + 18 ); + buffers[0] = buffer; + sizes[0] = 18; + buffers[1] = data; + sizes[1] = width*height*3; + ret = FS_WriteFileInBlocks(filename, buffers, sizes, 2); return ret; } -void Image_WriteTGABGRA (const char *filename, int width, int height, const unsigned char *data) +qboolean Image_WriteTGABGRA (const char *filename, int width, int height, const unsigned char *data) { int y; unsigned char *buffer, *out; const unsigned char *in, *end; + qboolean ret; buffer = (unsigned char *)Mem_Alloc(tempmempool, width*height*4 + 18); @@ -1214,9 +1220,11 @@ void Image_WriteTGABGRA (const char *filename, int width, int height, const unsi } } } - FS_WriteFile (filename, buffer, out - buffer); + ret = FS_WriteFile (filename, buffer, out - buffer); Mem_Free(buffer); + + return ret; } static void Image_Resample32LerpLine (const unsigned char *in, unsigned char *out, int inwidth, int outwidth) diff --git a/image.h b/image.h index 61bcc9c6..1309ffe4 100644 --- a/image.h +++ b/image.h @@ -32,10 +32,10 @@ qboolean LoadPCX_QWSkin(const unsigned char *f, int filesize, unsigned char *pix rtexture_t *loadtextureimage (rtexturepool_t *pool, const char *filename, qboolean complain, int flags, qboolean allowFixtrans, qboolean convertsRGB); // writes an upside down BGR image into a TGA -qboolean Image_WriteTGABGR_preflipped (const char *filename, int width, int height, const unsigned char *data, unsigned char *buffer); +qboolean Image_WriteTGABGR_preflipped (const char *filename, int width, int height, const unsigned char *data); // writes a BGRA image into a TGA file -void Image_WriteTGABGRA (const char *filename, int width, int height, const unsigned char *data); +qboolean Image_WriteTGABGRA (const char *filename, int width, int height, const unsigned char *data); // resizes the image (in can not be the same as out) void Image_Resample32(const void *indata, int inwidth, int inheight, int indepth, void *outdata, int outwidth, int outheight, int outdepth, int quality); diff --git a/image_png.c b/image_png.c index d1949315..b97e9c6d 100644 --- a/image_png.c +++ b/image_png.c @@ -443,7 +443,7 @@ PNG_SaveImage_preflipped Save a preflipped PNG image to a file ==================== */ -qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, unsigned char *data) +qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, qboolean has_alpha, unsigned char *data) { unsigned int offset, linesize; qfile_t* file = NULL; @@ -497,8 +497,7 @@ qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, //qpng_set_compression_level(png, Z_BEST_COMPRESSION); qpng_set_compression_level(png, Z_BEST_SPEED); - qpng_set_IHDR(png, pnginfo, width, height, 8, PNG_COLOR_TYPE_RGB, PNG_INTERLACE_ADAM7, PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT); - //qpng_set_IHDR(png, pnginfo, width, height, 8, PNG_COLOR_TYPE_RGB, PNG_INTERLACE_NONE, PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT); + qpng_set_IHDR(png, pnginfo, width, height, 8, has_alpha ? PNG_COLOR_TYPE_RGB_ALPHA : PNG_COLOR_TYPE_RGB, PNG_INTERLACE_ADAM7, PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT); qpng_set_filter(png, 0, PNG_NO_FILTERS); qpng_write_info(png, pnginfo); qpng_set_packing(png); @@ -506,7 +505,7 @@ qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, passes = qpng_set_interlace_handling(png); - linesize = width * 3; + linesize = width * (has_alpha ? 4 : 3); offset = linesize * (height - 1); for(i = 0; i < passes; ++i) for(j = 0; j < height; ++j) diff --git a/image_png.h b/image_png.h index c521afdc..e83d8cb7 100644 --- a/image_png.h +++ b/image_png.h @@ -27,7 +27,7 @@ qboolean PNG_OpenLibrary (void); void PNG_CloseLibrary (void); unsigned char* PNG_LoadImage_BGRA (const unsigned char *f, int filesize); -qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, unsigned char *data); +qboolean PNG_SaveImage_preflipped (const char *filename, int width, int height, qboolean has_alpha, unsigned char *data); #endif diff --git a/render.h b/render.h index 753fc92c..aa90252b 100644 --- a/render.h +++ b/render.h @@ -115,6 +115,7 @@ extern cvar_t r_showdisabledepthtest; // extern cvar_t r_drawentities; extern cvar_t r_drawviewmodel; +extern cvar_t r_drawworld; extern cvar_t r_speeds; extern cvar_t r_fullbright; extern cvar_t r_wateralpha; -- 2.39.2