mirror of
https://github.com/id-Software/DOOM-3-BFG.git
synced 2025-03-15 07:00:58 +00:00
Merge branch '497-envprobe-rendertarget'
This commit is contained in:
commit
d9112cd381
34 changed files with 76043 additions and 506 deletions
10
base/def/env_probe.def
Normal file
10
base/def/env_probe.def
Normal file
|
@ -0,0 +1,10 @@
|
|||
entityDef env_probe
|
||||
{
|
||||
"editor_color" "0 0 1"
|
||||
"editor_mins" "-8 -8 -8"
|
||||
"editor_maxs" " 8 8 8"
|
||||
|
||||
"editor_usage" "Environment probe for Image Based Lighting"
|
||||
|
||||
"spawnclass" "EnvironmentProbe"
|
||||
}
|
169
base/def/misc.def
Normal file
169
base/def/misc.def
Normal file
|
@ -0,0 +1,169 @@
|
|||
/***********************************************************************
|
||||
|
||||
miscellaneous
|
||||
|
||||
***********************************************************************/
|
||||
|
||||
entityDef worldspawn {
|
||||
"editor_color" "0 0 0"
|
||||
"editor_mins" "?"
|
||||
"editor_maxs" "?"
|
||||
|
||||
"editor_usage" "Every map should have exactly one worldspawn."
|
||||
"editor_var music" "music wav file."
|
||||
"editor_var gravity" "gravity value for the level."
|
||||
"editor_var no_stamina" "disables stamina so the player can always run"
|
||||
"editor_var no_Weapons" "only fists and no melee attacks"
|
||||
"editor_var def_player" "player def to use when spawning this world"
|
||||
|
||||
"spawnclass" "idWorldspawn"
|
||||
"gravity" "1066"
|
||||
"name" "world"
|
||||
}
|
||||
|
||||
entityDef light {
|
||||
"editor_color" "0 1 0"
|
||||
"editor_mins" "-8 -8 -8"
|
||||
"editor_maxs" "8 8 8"
|
||||
"editor_rotatable" "1"
|
||||
|
||||
"editor_usage" "Light source. If health is set, light becomes breakable and turns off when shot."
|
||||
|
||||
"editor_material texture" "light shader to use."
|
||||
"editor_color color" "light color"
|
||||
"editor_var shaderParm3" "shaderParm 3"
|
||||
"editor_var shaderParm4" "shaderParm 4"
|
||||
"editor_var shaderParm5" "shaderParm 5"
|
||||
"editor_var shaderParm6" "shaderParm 6"
|
||||
"editor_var shaderParm7" "shaderParm 7"
|
||||
"editor_var count" "how many times light must be triggered to toggle."
|
||||
"editor_var break" "break when triggered."
|
||||
"editor_model model" "model to use."
|
||||
"editor_model broken" "model to use when the light is broken (defaults to model name with '_broken' appended to name)"
|
||||
"editor_var hideModelOnBreak" "hides the model when broken"
|
||||
"editor_var health" "amount of damage to recieve before becoming broken. 0 is nonbreakable."
|
||||
"editor_var target" "entities to trigger if shot."
|
||||
"editor_var levels" "the number of times a light must be triggered until it turns off. Each time it's triggered, it's dimmed to a lower level."
|
||||
"editor_var start_off" "causes the light to be off when the level starts."
|
||||
"editor_var snd_broken" "sound shader to use when broken"
|
||||
"editor_var mtr_broken" "material to use when broken"
|
||||
"editor_color color_demonic" "demonic color to use if in demonic mode."
|
||||
"editor_material mat_demonic" "demonic shader to use if in demonic mode."
|
||||
"editor_var leave_demonic_mat" "leaves the demonic shader when the effect expires.. color is still reverted back."
|
||||
|
||||
"spawnclass" "idLight"
|
||||
"health" "0"
|
||||
"levels" "1"
|
||||
"start_off" "0"
|
||||
"count" "1"
|
||||
"break" "0"
|
||||
|
||||
// jmarshall: Quake 1 light styles
|
||||
/*
|
||||
"style" "-1"
|
||||
|
||||
"ls_frametime" "100"
|
||||
|
||||
"num_styles" "12"
|
||||
|
||||
"light_style0" "m"
|
||||
"light_style1" "mmnmmommommnonmmonqnmmo"
|
||||
"light_style2" "abcdefghijklmnopqrstuvwxyzyxwvutsrqponmlkjihgfedcba"
|
||||
"light_style3" "mmmmmaaaaammmmmaaaaaabcdefgabcdefg"
|
||||
"light_style4" "mamamamamama"
|
||||
"light_style5" "jklmnopqrstuvwxyzyxwvutsrqponmlkj"
|
||||
"light_style6" "nmonqnmomnmomomno"
|
||||
"light_style7" "mmmaaaabcdefgmmmmaaaammmaamm"
|
||||
"light_style8" "mmmaaammmaaammmabcdefaaaammmmabcdefmmmaaaa"
|
||||
"light_style9" "aaaaaaaazzzzzzzz"
|
||||
"light_style10" "mmamammmmammamamaaamammma"
|
||||
"light_style11" "abcdefghijklmnopqrrqponmlkjihgfedcba"
|
||||
*/
|
||||
// jmarshall end
|
||||
}
|
||||
|
||||
entityDef speaker {
|
||||
"editor_color" "0 1 0"
|
||||
"editor_mins" "-8 -8 -8"
|
||||
"editor_maxs" "8 8 8"
|
||||
"editor_material" "textures/common/speaker"
|
||||
|
||||
|
||||
"editor_usage" ""
|
||||
|
||||
"editor_snd s_shader" "the sound shader or wavefile."
|
||||
"editor_snd snd_demonic" "demonic sound shader."
|
||||
"editor_var overlayDemonic" "set to 1 overlays the demonic sound instead of replacing it."
|
||||
"editor_var s_waitfortrigger" "play on load or play when triggered."
|
||||
"editor_var s_volume" "override shader volume level."
|
||||
"editor_var s_minDistance" "override shader minDistance."
|
||||
"editor_var s_maxDistance" "override shader maxDistance."
|
||||
"editor_var s_omni" "force omnidirectional"
|
||||
"editor_var s_looping" "force looping"
|
||||
"editor_var s_occlusion" "force no portal occlusion"
|
||||
"editor_var s_global" "force no falloff at all"
|
||||
"editor_var s_shakes" "this entity can make the screen shake when the sound is loud."
|
||||
"editor_var wait" "when set > 0, seconds between triggerings. time between sounds is wait + or - random"
|
||||
"editor_var random" "wait variance."
|
||||
|
||||
"spawnclass" "idSound"
|
||||
}
|
||||
|
||||
entityDef info_location {
|
||||
"editor_color" "1 1 0"
|
||||
"editor_mins" "-4 -4 -4"
|
||||
"editor_maxs" "4 4 4"
|
||||
|
||||
"editor_usage" "Place one of these in each door-separated area for naming the gameplay sections"
|
||||
"editor_var name" "location name for HUD. Cannot be the same as any other entity in the game."
|
||||
"editor_var location" "use this when you have two locations with the same name."
|
||||
|
||||
"spawnclass" "idLocationEntity"
|
||||
}
|
||||
|
||||
entityDef info_locationSeparator {
|
||||
"editor_color" "1 1 0"
|
||||
"editor_mins" "-16 -16 -16"
|
||||
"editor_maxs" "16 16 16"
|
||||
|
||||
"editor_usage" "Touch a vis-portal with this to break location name flood filling without using a door"
|
||||
|
||||
"spawnclass" "idLocationSeparatorEntity"
|
||||
}
|
||||
|
||||
entityDef info_vacuum {
|
||||
"editor_color" "1 1 0"
|
||||
"editor_mins" "-4 -4 -4"
|
||||
"editor_maxs" "4 4 4"
|
||||
|
||||
"editor_usage" "Place one of these in an outside area in each map for vacuum flooding"
|
||||
|
||||
"spawnclass" "idVacuumEntity"
|
||||
}
|
||||
|
||||
entityDef info_vacuumSeparator {
|
||||
"editor_color" "1 1 0"
|
||||
"editor_mins" "-16 -16 -16"
|
||||
"editor_maxs" "16 16 16"
|
||||
|
||||
"editor_usage" "Touch a vis-portal with this to break air/vacuum flood filling at windows. Trigger it to allow vacuum to flood through."
|
||||
|
||||
"spawnclass" "idVacuumSeparatorEntity"
|
||||
}
|
||||
|
||||
entityDef text {
|
||||
"editor_color" "1 1 0"
|
||||
"editor_mins" "-4 -4 -4"
|
||||
"editor_maxs" "4 4 4"
|
||||
"editor_showangle" "1"
|
||||
"editor_rotatable" "1"
|
||||
|
||||
"editor_usage" "Used to display debug text in a level"
|
||||
"editor_var text" "text to print"
|
||||
"editor_var force" "if set to 1 prints always otherwise only in developer mode"
|
||||
"editor_var playerOriented" "if set to 1 text always faces the player"
|
||||
|
||||
"spawnclass" "idTextEntity"
|
||||
}
|
||||
|
||||
|
16
base/devtools.cfg
Normal file
16
base/devtools.cfg
Normal file
|
@ -0,0 +1,16 @@
|
|||
|
||||
bind "I" "toggle r_showSurfaceInfo"
|
||||
bind "N" "noclip"
|
||||
bind "M" "spawn moveable_macbethchart"
|
||||
|
||||
bind "F1" "toggle r_showViewEnvprobes 1 2 0"
|
||||
bind "F2" "toggle r_showTris 1 2 3 0"
|
||||
bind "F3" "toggle r_forceAmbient 0.2 0.3 0.0001"
|
||||
bind "F4" "toggle r_skipInteractions"
|
||||
bind "F5" "savegame quick"
|
||||
bind "F6" "toggle r_hdrDebug"
|
||||
bind "F7" "toggle r_useSSAO"
|
||||
bind "F8" "toggle r_useFilmicPostProcessing"
|
||||
bind "F9" "loadgame quick"
|
||||
bind "F10" "toggle com_fixedTic"
|
||||
bind "F11" "toggle r_pbrDebug"
|
79
base/modelviewer.cfg
Normal file
79
base/modelviewer.cfg
Normal file
|
@ -0,0 +1,79 @@
|
|||
// model viewer
|
||||
bind kp_5 "toggle pm_thirdPerson;vstr a0;vstr r40;vstr h0"
|
||||
bind kp_uparrow "vstr closer"
|
||||
bind kp_downarrow "vstr farther"
|
||||
bind kp_leftarrow "vstr left"
|
||||
bind kp_rightarrow "vstr right"
|
||||
bind kp_pgdn "vstr lower"
|
||||
bind kp_pgup "vstr higher"
|
||||
|
||||
set a0 "pm_thirdPersonAngle 0;set left vstr a10;set right vstr a350"
|
||||
set a10 "pm_thirdPersonAngle 10;set left vstr a20;set right vstr a0"
|
||||
set a20 "pm_thirdPersonAngle 20;set left vstr a30;set right vstr a10"
|
||||
set a30 "pm_thirdPersonAngle 30;set left vstr a40;set right vstr a20"
|
||||
set a40 "pm_thirdPersonAngle 40;set left vstr a50;set right vstr a30"
|
||||
set a50 "pm_thirdPersonAngle 50;set left vstr a60;set right vstr a40"
|
||||
set a60 "pm_thirdPersonAngle 60;set left vstr a70;set right vstr a50"
|
||||
set a70 "pm_thirdPersonAngle 70;set left vstr a80;set right vstr a60"
|
||||
set a80 "pm_thirdPersonAngle 80;set left vstr a90;set right vstr a70"
|
||||
set a90 "pm_thirdPersonAngle 90;set left vstr a100;set right vstr a80"
|
||||
set a100 "pm_thirdPersonAngle 100;set left vstr a110;set right vstr a90"
|
||||
set a110 "pm_thirdPersonAngle 110;set left vstr a120;set right vstr a100"
|
||||
set a120 "pm_thirdPersonAngle 120;set left vstr a130;set right vstr a110"
|
||||
set a130 "pm_thirdPersonAngle 130;set left vstr a140;set right vstr a120"
|
||||
set a140 "pm_thirdPersonAngle 140;set left vstr a150;set right vstr a130"
|
||||
set a150 "pm_thirdPersonAngle 150;set left vstr a160;set right vstr a140"
|
||||
set a160 "pm_thirdPersonAngle 160;set left vstr a170;set right vstr a150"
|
||||
set a170 "pm_thirdPersonAngle 170;set left vstr a180;set right vstr a160"
|
||||
set a180 "pm_thirdPersonAngle 180;set left vstr a190;set right vstr a170"
|
||||
set a190 "pm_thirdPersonAngle 190;set left vstr a200;set right vstr a180"
|
||||
set a200 "pm_thirdPersonAngle 200;set left vstr a210;set right vstr a190"
|
||||
set a210 "pm_thirdPersonAngle 210;set left vstr a220;set right vstr a200"
|
||||
set a220 "pm_thirdPersonAngle 220;set left vstr a230;set right vstr a210"
|
||||
set a230 "pm_thirdPersonAngle 230;set left vstr a240;set right vstr a220"
|
||||
set a240 "pm_thirdPersonAngle 240;set left vstr a250;set right vstr a230"
|
||||
set a250 "pm_thirdPersonAngle 250;set left vstr a260;set right vstr a240"
|
||||
set a260 "pm_thirdPersonAngle 260;set left vstr a270;set right vstr a250"
|
||||
set a270 "pm_thirdPersonAngle 270;set left vstr a280;set right vstr a260"
|
||||
set a280 "pm_thirdPersonAngle 280;set left vstr a290;set right vstr a270"
|
||||
set a290 "pm_thirdPersonAngle 290;set left vstr a300;set right vstr a280"
|
||||
set a300 "pm_thirdPersonAngle 300;set left vstr a310;set right vstr a290"
|
||||
set a310 "pm_thirdPersonAngle 310;set left vstr a320;set right vstr a300"
|
||||
set a320 "pm_thirdPersonAngle 320;set left vstr a330;set right vstr a310"
|
||||
set a330 "pm_thirdPersonAngle 330;set left vstr a340;set right vstr a320"
|
||||
set a340 "pm_thirdPersonAngle 340;set left vstr a350;set right vstr a330"
|
||||
set a350 "pm_thirdPersonAngle 350;set left vstr a0;set right vstr a340"
|
||||
|
||||
set r5 "pm_thirdPersonRange 5;set farther vstr r10;set closer vstr r500"
|
||||
set r10 "pm_thirdPersonRange 10;set farther vstr r20;set closer vstr r5"
|
||||
set r20 "pm_thirdPersonRange 20;set farther vstr r30;set closer vstr r10"
|
||||
set r30 "pm_thirdPersonRange 30;set farther vstr r40;set closer vstr r20"
|
||||
set r40 "pm_thirdPersonRange 40;set farther vstr r50;set closer vstr r30"
|
||||
set r50 "pm_thirdPersonRange 50;set farther vstr r60;set closer vstr r40"
|
||||
set r60 "pm_thirdPersonRange 60;set farther vstr r70;set closer vstr r50"
|
||||
set r70 "pm_thirdPersonRange 70;set farther vstr r80;set closer vstr r60"
|
||||
set r80 "pm_thirdPersonRange 80;set farther vstr r90;set closer vstr r70"
|
||||
set r90 "pm_thirdPersonRange 90;set farther vstr r100;set closer vstr r80"
|
||||
set r100 "pm_thirdPersonRange 100;set farther vstr r120;set closer vstr r90"
|
||||
set r120 "pm_thirdPersonRange 120;set farther vstr r140;set closer vstr r100"
|
||||
set r140 "pm_thirdPersonRange 140;set farther vstr r160;set closer vstr r120"
|
||||
set r160 "pm_thirdPersonRange 160;set farther vstr r180;set closer vstr r140"
|
||||
set r180 "pm_thirdPersonRange 180;set farther vstr r200;set closer vstr r160"
|
||||
set r200 "pm_thirdPersonRange 200;set farther vstr r220;set closer vstr r180"
|
||||
set r220 "pm_thirdPersonRange 220;set farther vstr r240;set closer vstr r200"
|
||||
set r240 "pm_thirdPersonRange 240;set farther vstr r260;set closer vstr r220"
|
||||
set r260 "pm_thirdPersonRange 260;set farther vstr r280;set closer vstr r240"
|
||||
set r280 "pm_thirdPersonRange 280;set farther vstr r300;set closer vstr r260"
|
||||
set r300 "pm_thirdPersonRange 300;set farther vstr r350;set closer vstr r280"
|
||||
set r350 "pm_thirdPersonRange 350;set farther vstr r400;set closer vstr r300"
|
||||
set r400 "pm_thirdPersonRange 400;set farther vstr r500;set closer vstr r350"
|
||||
set r500 "pm_thirdPersonRange 500;set farther vstr r5;set closer vstr r400"
|
||||
|
||||
set h0 "pm_thirdPersonHeight 0;set lower vstr h10;set higher vstr h70"
|
||||
set h10 "pm_thirdPersonHeight -10;set lower vstr h20;set higher vstr h5"
|
||||
set h20 "pm_thirdPersonHeight -20;set lower vstr h30;set higher vstr h10"
|
||||
set h30 "pm_thirdPersonHeight -30;set lower vstr h40;set higher vstr h20"
|
||||
set h40 "pm_thirdPersonHeight -40;set lower vstr h50;set higher vstr h30"
|
||||
set h50 "pm_thirdPersonHeight -50;set lower vstr h60;set higher vstr h40"
|
||||
set h60 "pm_thirdPersonHeight -60;set lower vstr h70;set higher vstr h50"
|
||||
set h70 "pm_thirdPersonHeight -70;set lower vstr h0;set higher vstr h60"
|
|
@ -489,6 +489,12 @@ file(GLOB IRRXML_SOURCES libs/irrxml/src/*.cpp)
|
|||
file(GLOB IMGUI_INCLUDES libs/imgui/*.h)
|
||||
file(GLOB IMGUI_SOURCES libs/imgui/*.cpp)
|
||||
|
||||
file(GLOB STB_INCLUDES libs/stb/*.h)
|
||||
|
||||
file(GLOB MESA_INCLUDES libs/mesa/*.h)
|
||||
|
||||
file(GLOB TINYEXR_INCLUDES libs/tinyexr/*.h)
|
||||
|
||||
file(GLOB MIKKTSPACE_INCLUDES libs/mikktspace/*.h)
|
||||
file(GLOB MIKKTSPACE_SOURCES libs/mikktspace/*.c)
|
||||
|
||||
|
@ -708,7 +714,6 @@ file(GLOB UI_SOURCES ui/*.cpp)
|
|||
file(GLOB SWF_INCLUDES swf/*.h)
|
||||
file(GLOB SWF_SOURCES swf/*.cpp)
|
||||
|
||||
|
||||
set(GAMED3XP_INCLUDES
|
||||
d3xp/Achievements.h
|
||||
d3xp/Actor.h
|
||||
|
@ -1111,6 +1116,12 @@ source_group("libs\\irrxml" FILES ${IRRXML_SOURCES})
|
|||
source_group("libs\\imgui" FILES ${IMGUI_INCLUDES})
|
||||
source_group("libs\\imgui" FILES ${IMGUI_SOURCES})
|
||||
|
||||
source_group("libs\\stb" FILES ${STB_INCLUDES})
|
||||
|
||||
source_group("libs\\mesa" FILES ${MESA_INCLUDES})
|
||||
|
||||
source_group("libs\\tinyexr" FILES ${TINYEXR_INCLUDES})
|
||||
|
||||
source_group("libs\\mikktspace" FILES ${MIKKTSPACE_INCLUDES})
|
||||
source_group("libs\\mikktspace" FILES ${MIKKTSPACE_SOURCES})
|
||||
|
||||
|
@ -1300,6 +1311,9 @@ set(RBDOOM3_INCLUDES
|
|||
${IRRXML_INCLUDES}
|
||||
${FRAMEWORK_IMGUI_INCLUDES}
|
||||
${IMGUI_INCLUDES}
|
||||
${STB_INCLUDES}
|
||||
${MESA_INCLUDES}
|
||||
${TINYEXR_INCLUDES}
|
||||
${MIKKTSPACE_INCLUDES}
|
||||
${JPEG_INCLUDES}
|
||||
${PNG_INCLUDES}
|
||||
|
|
|
@ -4,6 +4,9 @@ astyle.exe -v --formatted --options=astyle-options.ini --exclude="libs" --exclud
|
|||
astyle.exe -v --formatted --options=astyle-options.ini --recursive libs/imgui/*.h
|
||||
astyle.exe -v --formatted --options=astyle-options.ini --recursive libs/imgui/*.cpp
|
||||
|
||||
astyle.exe -v --formatted --options=astyle-options.ini --recursive libs/stb/*.h
|
||||
astyle.exe -v --formatted --options=astyle-options.ini --recursive libs/tinyexr/*.h
|
||||
|
||||
astyle.exe -v -Q --options=astyle-options.ini --recursive ../base/renderprogs/*.hlsl
|
||||
|
||||
pause
|
|
@ -1266,7 +1266,7 @@ extern void Sys_CPUCount( int& logicalNum, int& coreNum, int& packageNum );
|
|||
// Hyperthreading is not dead yet. Intel's Core i7 Processor is quad-core with HT for 8 logicals.
|
||||
|
||||
// DOOM3: We don't have that many jobs, so just set this fairly low so we don't spin up a ton of idle threads
|
||||
#define MAX_JOB_THREADS 2
|
||||
#define MAX_JOB_THREADS 32
|
||||
#define NUM_JOB_THREADS "2"
|
||||
#define JOB_THREAD_CORES { CORE_ANY, CORE_ANY, CORE_ANY, CORE_ANY, \
|
||||
CORE_ANY, CORE_ANY, CORE_ANY, CORE_ANY, \
|
||||
|
|
277
neo/libs/mesa/format_r11g11b10f.h
Normal file
277
neo/libs/mesa/format_r11g11b10f.h
Normal file
|
@ -0,0 +1,277 @@
|
|||
/*
|
||||
* Copyright (C) 2011 Marek Olšák <maraeo@gmail.com>
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
||||
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
||||
* DEALINGS IN THE SOFTWARE.
|
||||
*/
|
||||
|
||||
/* Based on code from The OpenGL Programming Guide / 7th Edition, Appendix J.
|
||||
* Available here: http://www.opengl-redbook.com/appendices/
|
||||
* The algorithm in the book contains a bug though, which is fixed in the code
|
||||
* below.
|
||||
*/
|
||||
|
||||
#ifndef FORMAT_R11G11B10F_H
|
||||
#define FORMAT_R11G11B10F_H
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#define UF11(e, m) ((e << 6) | (m))
|
||||
#define UF11_EXPONENT_BIAS 15
|
||||
#define UF11_EXPONENT_BITS 0x1F
|
||||
#define UF11_EXPONENT_SHIFT 6
|
||||
#define UF11_MANTISSA_BITS 0x3F
|
||||
#define UF11_MANTISSA_SHIFT (23 - UF11_EXPONENT_SHIFT)
|
||||
#define UF11_MAX_EXPONENT (UF11_EXPONENT_BITS << UF11_EXPONENT_SHIFT)
|
||||
|
||||
#define UF10(e, m) ((e << 5) | (m))
|
||||
#define UF10_EXPONENT_BIAS 15
|
||||
#define UF10_EXPONENT_BITS 0x1F
|
||||
#define UF10_EXPONENT_SHIFT 5
|
||||
#define UF10_MANTISSA_BITS 0x1F
|
||||
#define UF10_MANTISSA_SHIFT (23 - UF10_EXPONENT_SHIFT)
|
||||
#define UF10_MAX_EXPONENT (UF10_EXPONENT_BITS << UF10_EXPONENT_SHIFT)
|
||||
|
||||
#define F32_INFINITY 0x7f800000
|
||||
|
||||
static inline uint32_t f32_to_uf11( float val )
|
||||
{
|
||||
union
|
||||
{
|
||||
float f;
|
||||
uint32_t ui;
|
||||
} f32 = {val};
|
||||
|
||||
uint16_t uf11 = 0;
|
||||
|
||||
/* Decode little-endian 32-bit floating-point value */
|
||||
int sign = ( f32.ui >> 16 ) & 0x8000;
|
||||
/* Map exponent to the range [-127,128] */
|
||||
int exponent = ( ( f32.ui >> 23 ) & 0xff ) - 127;
|
||||
int mantissa = f32.ui & 0x007fffff;
|
||||
|
||||
if( exponent == 128 ) /* Infinity or NaN */
|
||||
{
|
||||
/* From the GL_EXT_packed_float spec:
|
||||
*
|
||||
* "Additionally: negative infinity is converted to zero; positive
|
||||
* infinity is converted to positive infinity; and both positive and
|
||||
* negative NaN are converted to positive NaN."
|
||||
*/
|
||||
uf11 = UF11_MAX_EXPONENT;
|
||||
if( mantissa )
|
||||
{
|
||||
uf11 |= 1; /* NaN */
|
||||
}
|
||||
else
|
||||
{
|
||||
if( sign )
|
||||
{
|
||||
uf11 = 0; /* 0.0 */
|
||||
}
|
||||
}
|
||||
}
|
||||
else if( sign )
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else if( val > 65024.0f )
|
||||
{
|
||||
/* From the GL_EXT_packed_float spec:
|
||||
*
|
||||
* "Likewise, finite positive values greater than 65024 (the maximum
|
||||
* finite representable unsigned 11-bit floating-point value) are
|
||||
* converted to 65024."
|
||||
*/
|
||||
uf11 = UF11( 30, 63 );
|
||||
}
|
||||
else if( exponent > -15 ) /* Representable value */
|
||||
{
|
||||
exponent += UF11_EXPONENT_BIAS;
|
||||
mantissa >>= UF11_MANTISSA_SHIFT;
|
||||
uf11 = exponent << UF11_EXPONENT_SHIFT | mantissa;
|
||||
}
|
||||
|
||||
return uf11;
|
||||
}
|
||||
|
||||
static inline float uf11_to_f32( uint16_t val )
|
||||
{
|
||||
union
|
||||
{
|
||||
float f;
|
||||
uint32_t ui;
|
||||
} f32;
|
||||
|
||||
int exponent = ( val & 0x07c0 ) >> UF11_EXPONENT_SHIFT;
|
||||
int mantissa = ( val & 0x003f );
|
||||
|
||||
f32.f = 0.0;
|
||||
|
||||
if( exponent == 0 )
|
||||
{
|
||||
if( mantissa != 0 )
|
||||
{
|
||||
const float scale = 1.0 / ( 1 << 20 );
|
||||
f32.f = scale * mantissa;
|
||||
}
|
||||
}
|
||||
else if( exponent == 31 )
|
||||
{
|
||||
f32.ui = F32_INFINITY | mantissa;
|
||||
}
|
||||
else
|
||||
{
|
||||
float scale, decimal;
|
||||
exponent -= 15;
|
||||
if( exponent < 0 )
|
||||
{
|
||||
scale = 1.0f / ( 1 << -exponent );
|
||||
}
|
||||
else
|
||||
{
|
||||
scale = ( float )( 1 << exponent );
|
||||
}
|
||||
decimal = 1.0f + ( float ) mantissa / 64;
|
||||
f32.f = scale * decimal;
|
||||
}
|
||||
|
||||
return f32.f;
|
||||
}
|
||||
|
||||
static inline uint32_t f32_to_uf10( float val )
|
||||
{
|
||||
union
|
||||
{
|
||||
float f;
|
||||
uint32_t ui;
|
||||
} f32 = {val};
|
||||
|
||||
uint16_t uf10 = 0;
|
||||
|
||||
/* Decode little-endian 32-bit floating-point value */
|
||||
int sign = ( f32.ui >> 16 ) & 0x8000;
|
||||
/* Map exponent to the range [-127,128] */
|
||||
int exponent = ( ( f32.ui >> 23 ) & 0xff ) - 127;
|
||||
int mantissa = f32.ui & 0x007fffff;
|
||||
|
||||
if( exponent == 128 )
|
||||
{
|
||||
/* From the GL_EXT_packed_float spec:
|
||||
*
|
||||
* "Additionally: negative infinity is converted to zero; positive
|
||||
* infinity is converted to positive infinity; and both positive and
|
||||
* negative NaN are converted to positive NaN."
|
||||
*/
|
||||
uf10 = UF10_MAX_EXPONENT;
|
||||
if( mantissa )
|
||||
{
|
||||
uf10 |= 1; /* NaN */
|
||||
}
|
||||
else
|
||||
{
|
||||
if( sign )
|
||||
{
|
||||
uf10 = 0; /* 0.0 */
|
||||
}
|
||||
}
|
||||
}
|
||||
else if( sign )
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
else if( val > 64512.0f )
|
||||
{
|
||||
/* From the GL_EXT_packed_float spec:
|
||||
*
|
||||
* "Likewise, finite positive values greater than 64512 (the maximum
|
||||
* finite representable unsigned 10-bit floating-point value) are
|
||||
* converted to 64512."
|
||||
*/
|
||||
uf10 = UF10( 30, 31 );
|
||||
}
|
||||
else if( exponent > -15 ) /* Representable value */
|
||||
{
|
||||
exponent += UF10_EXPONENT_BIAS;
|
||||
mantissa >>= UF10_MANTISSA_SHIFT;
|
||||
uf10 = exponent << UF10_EXPONENT_SHIFT | mantissa;
|
||||
}
|
||||
|
||||
return uf10;
|
||||
}
|
||||
|
||||
static inline float uf10_to_f32( uint16_t val )
|
||||
{
|
||||
union
|
||||
{
|
||||
float f;
|
||||
uint32_t ui;
|
||||
} f32;
|
||||
|
||||
int exponent = ( val & 0x03e0 ) >> UF10_EXPONENT_SHIFT;
|
||||
int mantissa = ( val & 0x001f );
|
||||
|
||||
f32.f = 0.0;
|
||||
|
||||
if( exponent == 0 )
|
||||
{
|
||||
if( mantissa != 0 )
|
||||
{
|
||||
const float scale = 1.0 / ( 1 << 19 );
|
||||
f32.f = scale * mantissa;
|
||||
}
|
||||
}
|
||||
else if( exponent == 31 )
|
||||
{
|
||||
f32.ui = F32_INFINITY | mantissa;
|
||||
}
|
||||
else
|
||||
{
|
||||
float scale, decimal;
|
||||
exponent -= 15;
|
||||
if( exponent < 0 )
|
||||
{
|
||||
scale = 1.0f / ( 1 << -exponent );
|
||||
}
|
||||
else
|
||||
{
|
||||
scale = ( float )( 1 << exponent );
|
||||
}
|
||||
decimal = 1.0f + ( float ) mantissa / 32;
|
||||
f32.f = scale * decimal;
|
||||
}
|
||||
|
||||
return f32.f;
|
||||
}
|
||||
|
||||
static inline uint32_t float3_to_r11g11b10f( const float rgb[3] )
|
||||
{
|
||||
return ( f32_to_uf11( rgb[0] ) & 0x7ff ) |
|
||||
( ( f32_to_uf11( rgb[1] ) & 0x7ff ) << 11 ) |
|
||||
( ( f32_to_uf10( rgb[2] ) & 0x3ff ) << 22 );
|
||||
}
|
||||
|
||||
static inline void r11g11b10f_to_float3( uint32_t rgb, float retval[3] )
|
||||
{
|
||||
retval[0] = uf11_to_f32( rgb & 0x7ff );
|
||||
retval[1] = uf11_to_f32( ( rgb >> 11 ) & 0x7ff );
|
||||
retval[2] = uf10_to_f32( ( rgb >> 22 ) & 0x3ff );
|
||||
}
|
||||
|
||||
#endif /* FORMAT_R11G11B10F_H */
|
10242
neo/libs/stb/stb_image.h
Normal file
10242
neo/libs/stb/stb_image.h
Normal file
File diff suppressed because it is too large
Load diff
2863
neo/libs/stb/stb_image_resize.h
Normal file
2863
neo/libs/stb/stb_image_resize.h
Normal file
File diff suppressed because it is too large
Load diff
2010
neo/libs/stb/stb_image_write.h
Normal file
2010
neo/libs/stb/stb_image_write.h
Normal file
File diff suppressed because it is too large
Load diff
17730
neo/libs/tinyexr/tinyexr.h
Normal file
17730
neo/libs/tinyexr/tinyexr.h
Normal file
File diff suppressed because it is too large
Load diff
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2014-2016 Robert Beckebans
|
||||
Copyright (C) 2014-2021 Robert Beckebans
|
||||
Copyright (C) 2014-2016 Kot in Action Creative Artel
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
@ -43,6 +43,8 @@ If you have questions concerning this license or the applicable additional terms
|
|||
#include "DXT/DXTCodec.h"
|
||||
#include "Color/ColorSpace.h"
|
||||
|
||||
#include "../libs/mesa/format_r11g11b10f.h"
|
||||
|
||||
idCVar image_highQualityCompression( "image_highQualityCompression", "0", CVAR_BOOL, "Use high quality (slow) compression" );
|
||||
idCVar r_useHighQualitySky( "r_useHighQualitySky", "1", CVAR_BOOL | CVAR_ARCHIVE, "Use high quality skyboxes" );
|
||||
|
||||
|
@ -249,6 +251,15 @@ void idBinaryImage::Load2DFromMemory( int width, int height, const byte* pic_con
|
|||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_R11G11B10F )
|
||||
{
|
||||
// RB: copy it as it was a RGBA8 because of the same size
|
||||
img.Alloc( scaledWidth * scaledHeight * 4 );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_RGBA16F )
|
||||
{
|
||||
img.Alloc( scaledWidth * scaledHeight * 8 );
|
||||
|
@ -294,6 +305,319 @@ void idBinaryImage::Load2DFromMemory( int width, int height, const byte* pic_con
|
|||
Mem_Free( pic );
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
========================
|
||||
RB idBinaryImage::Load2DAtlasMipchainFromMemory
|
||||
========================
|
||||
*/
|
||||
void idBinaryImage::Load2DAtlasMipchainFromMemory( int width, int height, const byte* pic_const, int numLevels, textureFormat_t& textureFormat, textureColor_t& colorFormat )
|
||||
{
|
||||
int sourceWidth = width * ( 2.0f / 3.0f ); // RB
|
||||
|
||||
fileData.textureType = TT_2D;
|
||||
fileData.format = textureFormat;
|
||||
fileData.colorFormat = CFM_DEFAULT;
|
||||
fileData.width = sourceWidth;
|
||||
fileData.height = height;
|
||||
fileData.numLevels = numLevels;
|
||||
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d)", width, height ) );
|
||||
|
||||
byte* sourcePic = ( byte* )Mem_Alloc( width * height * 4, TAG_TEMP );
|
||||
memcpy( sourcePic, pic_const, width * height * 4 );
|
||||
|
||||
if( colorFormat == CFM_YCOCG_DXT5 )
|
||||
{
|
||||
// convert the image data to YCoCg and use the YCoCgDXT5 compressor
|
||||
idColorSpace::ConvertRGBToCoCg_Y( sourcePic, sourcePic, width, height );
|
||||
}
|
||||
else if( colorFormat == CFM_NORMAL_DXT5 )
|
||||
{
|
||||
// Blah, HQ swizzles automatically, Fast doesn't
|
||||
if( !image_highQualityCompression.GetBool() )
|
||||
{
|
||||
for( int i = 0; i < width * height; i++ )
|
||||
{
|
||||
sourcePic[i * 4 + 3] = sourcePic[i * 4 + 0];
|
||||
sourcePic[i * 4 + 0] = 0;
|
||||
sourcePic[i * 4 + 2] = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if( colorFormat == CFM_GREEN_ALPHA )
|
||||
{
|
||||
for( int i = 0; i < width * height; i++ )
|
||||
{
|
||||
sourcePic[i * 4 + 1] = sourcePic[i * 4 + 3];
|
||||
sourcePic[i * 4 + 0] = 0;
|
||||
sourcePic[i * 4 + 2] = 0;
|
||||
sourcePic[i * 4 + 3] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
images.SetNum( numLevels );
|
||||
|
||||
const int numColors = 5;
|
||||
static idVec4 colors[numColors] = { colorBlue, colorCyan, colorGreen, colorYellow, colorRed };
|
||||
|
||||
for( int level = 0; level < images.Num(); level++ )
|
||||
{
|
||||
idBinaryImageData& img = images[ level ];
|
||||
|
||||
// RB: create shrunk image which is a copy of the sub image in the atlas
|
||||
idVec4 rect = R_CalculateMipRect( sourceWidth, level );
|
||||
|
||||
int scaledWidth = rect.z;
|
||||
int scaledHeight = rect.w;
|
||||
|
||||
byte* pic = ( byte* )Mem_Alloc( scaledWidth * scaledHeight * 4, TAG_TEMP );
|
||||
|
||||
for( int x = rect.x; x < ( rect.x + rect.z ); x++ )
|
||||
//for( int x = 0; x < rect.z; x++ )
|
||||
{
|
||||
for( int y = rect.y; y < ( rect.y + rect.w ); y++ )
|
||||
//for( int y = 0; y < rect.w; y++ )
|
||||
{
|
||||
int sx = x - rect.x;
|
||||
int sy = y - rect.y;
|
||||
|
||||
#if 1
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 0] = sourcePic[( y * width + x ) * 4 + 0];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 1] = sourcePic[( y * width + x ) * 4 + 1];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 2] = sourcePic[( y * width + x ) * 4 + 2];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 3] = sourcePic[( y * width + x ) * 4 + 3];
|
||||
#else
|
||||
int colorIdx = level % numColors;
|
||||
float color[3];
|
||||
color[0] = colors[ colorIdx ].x;
|
||||
color[0] = colors[ colorIdx ].y;
|
||||
color[0] = colors[ colorIdx ].z;
|
||||
|
||||
uint32_t value = float3_to_r11g11b10f( color );
|
||||
|
||||
union
|
||||
{
|
||||
uint32 i;
|
||||
byte b[4];
|
||||
} tmp;
|
||||
|
||||
tmp.i = value;
|
||||
|
||||
//*( uint32_t* )pic[( sy * scaledWidth + sx ) * 3] = value;
|
||||
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 0] = tmp.b[0];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 1] = tmp.b[1];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 2] = tmp.b[2];
|
||||
pic[( sy * scaledWidth + sx ) * 4 + 3] = tmp.b[3];
|
||||
#endif
|
||||
}
|
||||
}
|
||||
// RB end
|
||||
|
||||
commonLocal.LoadPacifierBinarizeMiplevel( level + 1, numLevels );
|
||||
|
||||
// Images that are going to be DXT compressed and aren't multiples of 4 need to be
|
||||
// padded out before compressing.
|
||||
byte* dxtPic = pic;
|
||||
int dxtWidth = 0;
|
||||
int dxtHeight = 0;
|
||||
if( textureFormat == FMT_DXT5 || textureFormat == FMT_DXT1 )
|
||||
{
|
||||
if( ( scaledWidth & 3 ) || ( scaledHeight & 3 ) )
|
||||
{
|
||||
dxtWidth = ( scaledWidth + 3 ) & ~3;
|
||||
dxtHeight = ( scaledHeight + 3 ) & ~3;
|
||||
dxtPic = ( byte* )Mem_ClearedAlloc( dxtWidth * 4 * dxtHeight, TAG_IMAGE );
|
||||
for( int i = 0; i < scaledHeight; i++ )
|
||||
{
|
||||
memcpy( dxtPic + i * dxtWidth * 4, pic + i * scaledWidth * 4, scaledWidth * 4 );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
dxtPic = pic;
|
||||
dxtWidth = scaledWidth;
|
||||
dxtHeight = scaledHeight;
|
||||
}
|
||||
}
|
||||
|
||||
img.level = level;
|
||||
img.destZ = 0;
|
||||
img.width = scaledWidth;
|
||||
img.height = scaledHeight;
|
||||
|
||||
// compress data or convert floats as necessary
|
||||
if( textureFormat == FMT_DXT1 )
|
||||
{
|
||||
idDxtEncoder dxt;
|
||||
img.Alloc( dxtWidth * dxtHeight / 2 );
|
||||
if( image_highQualityCompression.GetBool() )
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - DXT1HQ", width, height ) );
|
||||
|
||||
dxt.CompressImageDXT1HQ( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
else
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - DXT1Fast", width, height ) );
|
||||
|
||||
dxt.CompressImageDXT1Fast( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_DXT5 )
|
||||
{
|
||||
idDxtEncoder dxt;
|
||||
img.Alloc( dxtWidth * dxtHeight );
|
||||
if( colorFormat == CFM_NORMAL_DXT5 )
|
||||
{
|
||||
if( image_highQualityCompression.GetBool() )
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - NormalMapDXT5HQ", width, height ) );
|
||||
|
||||
dxt.CompressNormalMapDXT5HQ( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
else
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - NormalMapDXT5Fast", width, height ) );
|
||||
|
||||
dxt.CompressNormalMapDXT5Fast( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
}
|
||||
else if( colorFormat == CFM_YCOCG_DXT5 )
|
||||
{
|
||||
if( image_highQualityCompression.GetBool() )
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - YCoCgDXT5HQ", width, height ) );
|
||||
|
||||
dxt.CompressYCoCgDXT5HQ( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
else
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - YCoCgDXT5Fast", width, height ) );
|
||||
|
||||
dxt.CompressYCoCgDXT5Fast( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
fileData.colorFormat = colorFormat = CFM_DEFAULT;
|
||||
if( image_highQualityCompression.GetBool() )
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - DXT5HQ", width, height ) );
|
||||
|
||||
dxt.CompressImageDXT5HQ( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
else
|
||||
{
|
||||
commonLocal.LoadPacifierBinarizeInfo( va( "(%d x %d) - DXT5Fast", width, height ) );
|
||||
|
||||
dxt.CompressImageDXT5Fast( dxtPic, img.data, dxtWidth, dxtHeight );
|
||||
}
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_LUM8 || textureFormat == FMT_INT8 )
|
||||
{
|
||||
// LUM8 and INT8 just read the red channel
|
||||
img.Alloc( scaledWidth * scaledHeight );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i * 4 ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_ALPHA )
|
||||
{
|
||||
// ALPHA reads the alpha channel
|
||||
img.Alloc( scaledWidth * scaledHeight );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i * 4 + 3 ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_L8A8 )
|
||||
{
|
||||
// L8A8 reads the alpha and red channels
|
||||
img.Alloc( scaledWidth * scaledHeight * 2 );
|
||||
for( int i = 0; i < img.dataSize / 2; i++ )
|
||||
{
|
||||
img.data[ i * 2 + 0 ] = pic[ i * 4 + 0 ];
|
||||
img.data[ i * 2 + 1 ] = pic[ i * 4 + 3 ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_RGB565 )
|
||||
{
|
||||
img.Alloc( scaledWidth * scaledHeight * 2 );
|
||||
for( int i = 0; i < img.dataSize / 2; i++ )
|
||||
{
|
||||
unsigned short color = ( ( pic[ i * 4 + 0 ] >> 3 ) << 11 ) | ( ( pic[ i * 4 + 1 ] >> 2 ) << 5 ) | ( pic[ i * 4 + 2 ] >> 3 );
|
||||
img.data[ i * 2 + 0 ] = ( color >> 8 ) & 0xFF;
|
||||
img.data[ i * 2 + 1 ] = color & 0xFF;
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_RG16F )
|
||||
{
|
||||
// RB: copy it as it was a RGBA8 because of the same size
|
||||
img.Alloc( scaledWidth * scaledHeight * 4 );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_R11G11B10F )
|
||||
{
|
||||
// RB: copy it as it was a RGBA8 because of the same size
|
||||
img.Alloc( scaledWidth * scaledHeight * 4 );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
else if( textureFormat == FMT_RGBA16F )
|
||||
{
|
||||
img.Alloc( scaledWidth * scaledHeight * 8 );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
fileData.format = textureFormat = FMT_RGBA8;
|
||||
img.Alloc( scaledWidth * scaledHeight * 4 );
|
||||
for( int i = 0; i < img.dataSize; i++ )
|
||||
{
|
||||
img.data[ i ] = pic[ i ];
|
||||
}
|
||||
}
|
||||
|
||||
// if we had to pad to quads, free the padded version
|
||||
if( pic != dxtPic )
|
||||
{
|
||||
Mem_Free( dxtPic );
|
||||
dxtPic = NULL;
|
||||
}
|
||||
|
||||
// downsample for the next level
|
||||
/*
|
||||
byte* shrunk = NULL;
|
||||
if( gammaMips )
|
||||
{
|
||||
shrunk = R_MipMapWithGamma( pic, scaledWidth, scaledHeight );
|
||||
}
|
||||
else
|
||||
{
|
||||
shrunk = R_MipMap( pic, scaledWidth, scaledHeight );
|
||||
}
|
||||
Mem_Free( pic );
|
||||
pic = shrunk;
|
||||
*/
|
||||
|
||||
Mem_Free( pic );
|
||||
}
|
||||
|
||||
Mem_Free( sourcePic );
|
||||
}
|
||||
|
||||
/*
|
||||
========================
|
||||
PadImageTo4x4
|
||||
|
|
|
@ -53,6 +53,7 @@ public:
|
|||
}
|
||||
|
||||
void Load2DFromMemory( int width, int height, const byte* pic_const, int numLevels, textureFormat_t& textureFormat, textureColor_t& colorFormat, bool gammaMips );
|
||||
void Load2DAtlasMipchainFromMemory( int width, int height, const byte* pic_const, int numLevels, textureFormat_t& textureFormat, textureColor_t& colorFormat );
|
||||
void LoadCubeFromMemory( int width, const byte* pics[6], int numLevels, textureFormat_t& textureFormat, bool gammaMips );
|
||||
|
||||
ID_TIME_T LoadFromGeneratedFile( ID_TIME_T sourceFileTime );
|
||||
|
|
|
@ -35,7 +35,7 @@ static const int MAX_SSAO_BUFFERS = 2;
|
|||
static const int MAX_HIERARCHICAL_ZBUFFERS = 6; // native resolution + 5 MIP LEVELS
|
||||
|
||||
static const int RADIANCE_CUBEMAP_SIZE = 256;
|
||||
static const int IRRADIANCE_CUBEMAP_SIZE = 32;
|
||||
static const int IRRADIANCE_CUBEMAP_SIZE = 128;
|
||||
|
||||
#if 1
|
||||
static int shadowMapResolutions[MAX_SHADOWMAP_RESOLUTIONS] = { 2048, 1024, 512, 512, 256 };
|
||||
|
@ -56,13 +56,11 @@ public:
|
|||
|
||||
static void CheckFramebuffers();
|
||||
|
||||
// deletes OpenGL object but leaves structure intact for reloading
|
||||
void PurgeFramebuffer();
|
||||
|
||||
void Bind();
|
||||
bool IsBound();
|
||||
static void Unbind();
|
||||
static bool IsDefaultFramebufferActive();
|
||||
static Framebuffer* GetActiveFramebuffer();
|
||||
|
||||
void AddColorBuffer( int format, int index, int multiSamples = 0 );
|
||||
void AddDepthBuffer( int format, int multiSamples = 0 );
|
||||
|
@ -132,6 +130,7 @@ struct globalFramebuffers_t
|
|||
#endif
|
||||
// Framebuffer* hdrQuarterFBO;
|
||||
Framebuffer* hdr64FBO;
|
||||
Framebuffer* envprobeFBO;
|
||||
Framebuffer* bloomRenderFBO[MAX_BLOOM_BUFFERS];
|
||||
Framebuffer* ambientOcclusionFBO[MAX_SSAO_BUFFERS];
|
||||
Framebuffer* csDepthFBO[MAX_HIERARCHICAL_ZBUFFERS];
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2013-2017 Robert Beckebans
|
||||
Copyright (C) 2013-2021 Robert Beckebans
|
||||
Copyright (C) 2016-2017 Dustin Land
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
@ -100,6 +100,7 @@ enum textureFormat_t
|
|||
FMT_RGBA16F, // 64 bpp
|
||||
FMT_RGBA32F, // 128 bpp
|
||||
FMT_R32F, // 32 bpp
|
||||
FMT_R11G11B10F, // 32 bpp
|
||||
// RB end
|
||||
};
|
||||
|
||||
|
@ -226,6 +227,7 @@ typedef enum
|
|||
TD_RGBA16F,
|
||||
TD_RGBA32F,
|
||||
TD_R32F,
|
||||
TD_R11G11B10F, // memory efficient HDR RGB format with only 32bpp
|
||||
// RB end
|
||||
} textureUsage_t;
|
||||
|
||||
|
@ -234,14 +236,17 @@ typedef enum
|
|||
CF_2D, // not a cube map
|
||||
CF_NATIVE, // _px, _nx, _py, etc, directly sent to GL
|
||||
CF_CAMERA, // _forward, _back, etc, rotated and flipped as needed before sending to GL
|
||||
CF_2D_ARRAY // not a cube map but not a single 2d texture either
|
||||
CF_PANORAMA, // TODO latlong encoded HDRI panorama typically used by Substance or Blender
|
||||
CF_2D_ARRAY, // not a cube map but not a single 2d texture either
|
||||
CF_2D_PACKED_MIPCHAIN // usually 2d but can be an octahedron, packed mipmaps into single 2d texture atlas and limited to dim^2
|
||||
} cubeFiles_t;
|
||||
|
||||
enum imageFileType_t
|
||||
{
|
||||
TGA,
|
||||
PNG,
|
||||
JPG
|
||||
JPG,
|
||||
EXR,
|
||||
};
|
||||
|
||||
#include "BinaryImage.h"
|
||||
|
@ -395,7 +400,7 @@ public:
|
|||
textureFilter_t filter,
|
||||
textureRepeat_t repeat,
|
||||
textureUsage_t usage,
|
||||
textureSamples_t samples = SAMPLE_1 );
|
||||
textureSamples_t samples = SAMPLE_1, cubeFiles_t cubeFiles = CF_2D );
|
||||
|
||||
void GenerateCubeImage( const byte* pic[6], int size,
|
||||
textureFilter_t filter, textureUsage_t usage );
|
||||
|
@ -573,6 +578,8 @@ public:
|
|||
idImage* currentRenderHDRImageQuarter;
|
||||
idImage* currentRenderHDRImage64;
|
||||
idImage* bloomRenderImage[2];
|
||||
idImage* envprobeHDRImage;
|
||||
idImage* envprobeDepthImage;
|
||||
idImage* heatmap5Image;
|
||||
idImage* heatmap7Image;
|
||||
idImage* smaaInputImage;
|
||||
|
@ -635,9 +642,13 @@ byte* R_MipMap( const byte* in, int width, int height );
|
|||
void R_BlendOverTexture( byte* data, int pixelCount, const byte blend[4] );
|
||||
void R_HorizontalFlip( byte* data, int width, int height );
|
||||
void R_VerticalFlip( byte* data, int width, int height );
|
||||
void R_VerticalFlipRGB16F( byte* data, int width, int height );
|
||||
void R_RotatePic( byte* data, int width );
|
||||
void R_ApplyCubeMapTransforms( int i, byte* data, int size );
|
||||
|
||||
idVec4 R_CalculateMipRect( uint dimensions, uint mip );
|
||||
int R_CalculateUsedAtlasPixels( int dimensions );
|
||||
|
||||
/*
|
||||
====================================================================
|
||||
|
||||
|
|
8203
neo/renderer/Image_env_UAC_lobby_amb.h
Normal file
8203
neo/renderer/Image_env_UAC_lobby_amb.h
Normal file
File diff suppressed because it is too large
Load diff
32779
neo/renderer/Image_env_UAC_lobby_spec.h
Normal file
32779
neo/renderer/Image_env_UAC_lobby_spec.h
Normal file
File diff suppressed because it is too large
Load diff
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2012-2020 Robert Beckebans
|
||||
Copyright (C) 2012-2021 Robert Beckebans
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
||||
|
@ -30,6 +30,18 @@ If you have questions concerning this license or the applicable additional terms
|
|||
#pragma hdrstop
|
||||
#include "precompiled.h"
|
||||
|
||||
#undef strncmp
|
||||
|
||||
#define STB_IMAGE_IMPLEMENTATION
|
||||
#include "../libs/stb/stb_image.h"
|
||||
|
||||
//#define STB_IMAGE_WRITE_IMPLEMENTATION
|
||||
//#include "../libs/stb/stb_image_write.h"
|
||||
|
||||
#define TINYEXR_IMPLEMENTATION
|
||||
#include "../libs/tinyexr/tinyexr.h"
|
||||
|
||||
#include "../libs/mesa/format_r11g11b10f.h"
|
||||
|
||||
#include "RenderCommon.h"
|
||||
|
||||
|
@ -755,7 +767,7 @@ static void LoadPNG( const char* filename, unsigned char** pic, int* width, int*
|
|||
|
||||
png_read_update_info( pngPtr, infoPtr );
|
||||
|
||||
byte* out = ( byte* )R_StaticAlloc( pngWidth * pngHeight * 4 );
|
||||
byte* out = ( byte* )R_StaticAlloc( pngWidth * pngHeight * 4, TAG_IMAGE );
|
||||
|
||||
*pic = out;
|
||||
*width = pngWidth;
|
||||
|
@ -878,6 +890,103 @@ void R_WritePNG( const char* filename, const byte* data, int bytesPerPixel, int
|
|||
Mem_Free( buffer );
|
||||
}
|
||||
|
||||
/*
|
||||
=========================================================
|
||||
|
||||
EXR LOADING
|
||||
|
||||
Interfaces with tinyexr
|
||||
=========================================================
|
||||
*/
|
||||
|
||||
/*
|
||||
=======================
|
||||
LoadEXR
|
||||
=======================
|
||||
*/
|
||||
static void LoadEXR( const char* filename, unsigned char** pic, int* width, int* height, ID_TIME_T* timestamp )
|
||||
{
|
||||
if( !pic )
|
||||
{
|
||||
fileSystem->ReadFile( filename, NULL, timestamp );
|
||||
return; // just getting timestamp
|
||||
}
|
||||
|
||||
*pic = NULL;
|
||||
|
||||
// load the file
|
||||
const byte* fbuffer = NULL;
|
||||
int fileSize = fileSystem->ReadFile( filename, ( void** )&fbuffer, timestamp );
|
||||
if( !fbuffer )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
float* rgba;
|
||||
const char* err;
|
||||
|
||||
{
|
||||
int ret = LoadEXRFromMemory( &rgba, width, height, fbuffer, fileSize, &err );
|
||||
if( ret != 0 )
|
||||
{
|
||||
common->Error( "LoadEXR( %s ): %s\n", filename, err );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
#if 0
|
||||
// dump file as .hdr for testing - this works
|
||||
{
|
||||
idStrStatic< MAX_OSPATH > hdrFileName = "test";
|
||||
//hdrFileName.AppendPath( filename );
|
||||
hdrFileName.SetFileExtension( ".hdr" );
|
||||
|
||||
int ret = stbi_write_hdr( hdrFileName.c_str(), *width, *height, 4, rgba );
|
||||
|
||||
if( ret == 0 )
|
||||
{
|
||||
return; // fail
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
if( rgba )
|
||||
{
|
||||
int32 pixelCount = *width * *height;
|
||||
byte* out = ( byte* )R_StaticAlloc( pixelCount * 4, TAG_IMAGE );
|
||||
|
||||
*pic = out;
|
||||
|
||||
// convert to packed R11G11B10F as uint32 for each pixel
|
||||
|
||||
const float* src = rgba;
|
||||
byte* dst = out;
|
||||
for( int i = 0; i < pixelCount; i++ )
|
||||
{
|
||||
// read 3 floats and ignore the alpha channel
|
||||
float p[3];
|
||||
|
||||
p[0] = src[0];
|
||||
p[1] = src[1];
|
||||
p[2] = src[2];
|
||||
|
||||
// convert
|
||||
uint32_t value = float3_to_r11g11b10f( p );
|
||||
*( uint32_t* )dst = value;
|
||||
|
||||
src += 4;
|
||||
dst += 4;
|
||||
}
|
||||
|
||||
free( rgba );
|
||||
}
|
||||
|
||||
// RB: EXR needs to be flipped to match the .tga behavior
|
||||
//R_VerticalFlip( *pic, *width, *height );
|
||||
|
||||
Mem_Free( ( void* )fbuffer );
|
||||
}
|
||||
|
||||
/*
|
||||
================
|
||||
R_WriteEXR
|
||||
|
@ -1034,6 +1143,85 @@ void R_WriteEXR( const char* filename, const void* rgba16f, int channelsPerPixel
|
|||
}
|
||||
// RB end
|
||||
|
||||
|
||||
/*
|
||||
=========================================================
|
||||
|
||||
HDR LOADING
|
||||
|
||||
Interfaces with stb_image
|
||||
=========================================================
|
||||
*/
|
||||
|
||||
|
||||
/*
|
||||
=======================
|
||||
LoadHDR
|
||||
|
||||
RB: load floating point data from memory and convert it into packed R11G11B10F data
|
||||
=======================
|
||||
*/
|
||||
static void LoadHDR( const char* filename, unsigned char** pic, int* width, int* height, ID_TIME_T* timestamp )
|
||||
{
|
||||
if( !pic )
|
||||
{
|
||||
fileSystem->ReadFile( filename, NULL, timestamp );
|
||||
return; // just getting timestamp
|
||||
}
|
||||
|
||||
*pic = NULL;
|
||||
|
||||
// load the file
|
||||
const byte* fbuffer = NULL;
|
||||
int fileSize = fileSystem->ReadFile( filename, ( void** )&fbuffer, timestamp );
|
||||
if( !fbuffer )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
int32 numChannels;
|
||||
|
||||
float* rgba = stbi_loadf_from_memory( ( stbi_uc const* ) fbuffer, fileSize, width, height, &numChannels, 0 );
|
||||
|
||||
if( numChannels != 3 )
|
||||
{
|
||||
common->Error( "LoadHDR( %s ): HDR has not 3 channels\n", filename );
|
||||
}
|
||||
|
||||
if( rgba )
|
||||
{
|
||||
int32 pixelCount = *width * *height;
|
||||
byte* out = ( byte* )R_StaticAlloc( pixelCount * 4, TAG_IMAGE );
|
||||
|
||||
*pic = out;
|
||||
|
||||
// convert to packed R11G11B10F as uint32 for each pixel
|
||||
|
||||
const float* src = rgba;
|
||||
byte* dst = out;
|
||||
for( int i = 0; i < pixelCount; i++ )
|
||||
{
|
||||
// read 3 floats and ignore the alpha channel
|
||||
float p[3];
|
||||
|
||||
p[0] = src[0];
|
||||
p[1] = src[1];
|
||||
p[2] = src[2];
|
||||
|
||||
// convert
|
||||
uint32_t value = float3_to_r11g11b10f( p );
|
||||
*( uint32_t* )dst = value;
|
||||
|
||||
src += 4;
|
||||
dst += 4;
|
||||
}
|
||||
|
||||
free( rgba );
|
||||
}
|
||||
|
||||
Mem_Free( ( void* )fbuffer );
|
||||
}
|
||||
|
||||
//===================================================================
|
||||
|
||||
|
||||
|
@ -1048,6 +1236,8 @@ static imageExtToLoader_t imageLoaders[] =
|
|||
{"png", LoadPNG},
|
||||
{"tga", LoadTGA},
|
||||
{"jpg", LoadJPG},
|
||||
{"exr", LoadEXR},
|
||||
{"hdr", LoadHDR},
|
||||
};
|
||||
|
||||
static const int numImageLoaders = sizeof( imageLoaders ) / sizeof( imageLoaders[0] );
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2013-2020 Robert Beckebans
|
||||
Copyright (C) 2013-2021 Robert Beckebans
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
||||
|
@ -39,6 +39,9 @@ If you have questions concerning this license or the applicable additional terms
|
|||
//#include "Image_blueNoiseVC_1M.h" // 256^2 R8 data
|
||||
#include "Image_blueNoiseVC_2.h" // 512^2 RGB8 data
|
||||
|
||||
#include "Image_env_UAC_lobby_amb.h"
|
||||
#include "Image_env_UAC_lobby_spec.h"
|
||||
|
||||
#define DEFAULT_SIZE 16
|
||||
|
||||
/*
|
||||
|
@ -262,6 +265,16 @@ static void R_HDR_RGBA16FImage_Res64( idImage* image )
|
|||
image->GenerateImage( NULL, 64, 64, TF_NEAREST, TR_CLAMP, TD_RGBA16F );
|
||||
}
|
||||
|
||||
static void R_EnvprobeImage_HDR( idImage* image )
|
||||
{
|
||||
image->GenerateImage( NULL, RADIANCE_CUBEMAP_SIZE, RADIANCE_CUBEMAP_SIZE, TF_NEAREST, TR_CLAMP, TD_RGBA16F );
|
||||
}
|
||||
|
||||
static void R_EnvprobeImage_Depth( idImage* image )
|
||||
{
|
||||
image->GenerateImage( NULL, RADIANCE_CUBEMAP_SIZE, RADIANCE_CUBEMAP_SIZE, TF_NEAREST, TR_CLAMP, TD_DEPTH );
|
||||
}
|
||||
|
||||
static void R_SMAAImage_ResNative( idImage* image )
|
||||
{
|
||||
image->GenerateImage( NULL, renderSystem->GetWidth(), renderSystem->GetHeight(), TF_LINEAR, TR_CLAMP, TD_LOOKUP_TABLE_RGBA );
|
||||
|
@ -929,31 +942,19 @@ static void R_CreateImGuiFontImage( idImage* image )
|
|||
|
||||
static void R_CreateBrdfLutImage( idImage* image )
|
||||
{
|
||||
#if 0
|
||||
static byte data[BRDFLUT_TEX_HEIGHT][BRDFLUT_TEX_WIDTH][4];
|
||||
|
||||
for( int x = 0; x < BRDFLUT_TEX_WIDTH; x++ )
|
||||
{
|
||||
for( int y = 0; y < BRDFLUT_TEX_HEIGHT; y++ )
|
||||
{
|
||||
#if 0
|
||||
data[AREATEX_HEIGHT - y][x][0] = areaTexBytes[ y * AREATEX_PITCH + x * 2 + 0 ];
|
||||
data[AREATEX_HEIGHT - y][x][1] = areaTexBytes[ y * AREATEX_PITCH + x * 2 + 1 ];
|
||||
data[AREATEX_HEIGHT - y][x][2] = 0;
|
||||
data[AREATEX_HEIGHT - y][x][3] = 1;
|
||||
#else
|
||||
data[y][x][0] = brfLutTexBytes[ y * BRDFLUT_TEX_PITCH + x * 2 + 0 ];
|
||||
data[y][x][1] = brfLutTexBytes[ y * BRDFLUT_TEX_PITCH + x * 2 + 1 ];
|
||||
data[y][x][2] = 0;
|
||||
data[y][x][3] = 1;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
image->GenerateImage( ( byte* )brfLutTexBytes, BRDFLUT_TEX_WIDTH, BRDFLUT_TEX_HEIGHT, TF_LINEAR, TR_CLAMP, TD_RG16F );
|
||||
}
|
||||
|
||||
static void R_CreateEnvprobeImage_UAC_lobby_irradiance( idImage* image )
|
||||
{
|
||||
image->GenerateImage( ( byte* )IMAGE_ENV_UAC_LOBBY_AMB_H_Bytes, IMAGE_ENV_UAC_LOBBY_AMB_H_TEX_WIDTH, IMAGE_ENV_UAC_LOBBY_AMB_H_TEX_HEIGHT, TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, SAMPLE_1, CF_2D_PACKED_MIPCHAIN );
|
||||
}
|
||||
|
||||
static void R_CreateEnvprobeImage_UAC_lobby_radiance( idImage* image )
|
||||
{
|
||||
image->GenerateImage( ( byte* )IMAGE_ENV_UAC_LOBBY_SPEC_H_Bytes, IMAGE_ENV_UAC_LOBBY_SPEC_H_TEX_WIDTH, IMAGE_ENV_UAC_LOBBY_SPEC_H_TEX_HEIGHT, TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, SAMPLE_1, CF_2D_PACKED_MIPCHAIN );
|
||||
}
|
||||
|
||||
// RB end
|
||||
|
||||
|
||||
|
@ -997,6 +998,9 @@ void idImageManager::CreateIntrinsicImages()
|
|||
currentRenderHDRImageQuarter = globalImages->ImageFromFunction( "_currentRenderHDRQuarter", R_HDR_RGBA16FImage_ResQuarter );
|
||||
currentRenderHDRImage64 = globalImages->ImageFromFunction( "_currentRenderHDR64", R_HDR_RGBA16FImage_Res64 );
|
||||
|
||||
envprobeHDRImage = globalImages->ImageFromFunction( "_envprobeHDR", R_EnvprobeImage_HDR );
|
||||
envprobeDepthImage = ImageFromFunction( "_envprobeDepth", R_EnvprobeImage_Depth );
|
||||
|
||||
bloomRenderImage[0] = globalImages->ImageFromFunction( "_bloomRender0", R_HDR_RGBA16FImage_ResQuarter_Linear );
|
||||
bloomRenderImage[1] = globalImages->ImageFromFunction( "_bloomRender1", R_HDR_RGBA16FImage_ResQuarter_Linear );
|
||||
|
||||
|
@ -1042,8 +1046,13 @@ void idImageManager::CreateIntrinsicImages()
|
|||
hellLoadingIconImage = ImageFromFile( "textures/loadingicon3", TF_DEFAULT, TR_CLAMP, TD_DEFAULT, CF_2D );
|
||||
|
||||
// RB begin
|
||||
defaultUACIrradianceCube = ImageFromFile( "env/UAC2_amb", TF_DEFAULT, TR_CLAMP, TD_LOOKUP_TABLE_RGB1, CF_2D );
|
||||
defaultUACRadianceCube = ImageFromFile( "env/UAC2_spec", TF_DEFAULT, TR_CLAMP, TD_LOOKUP_TABLE_RGB1, CF_2D );
|
||||
#if 0
|
||||
defaultUACIrradianceCube = ImageFromFile( "env/UAC5_amb", TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, CF_2D_PACKED_MIPCHAIN );
|
||||
defaultUACRadianceCube = ImageFromFile( "env/UAC5_spec", TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, CF_2D_PACKED_MIPCHAIN );
|
||||
#else
|
||||
defaultUACIrradianceCube = ImageFromFunction( "_defaultUACIrradiance", R_CreateEnvprobeImage_UAC_lobby_irradiance );
|
||||
defaultUACRadianceCube = ImageFromFunction( "_defaultUACRadiance", R_CreateEnvprobeImage_UAC_lobby_radiance );
|
||||
#endif
|
||||
// RB end
|
||||
|
||||
release_assert( loadingIconImage->referencedOutsideLevelLoad );
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2013-2020 Robert Beckebans
|
||||
Copyright (C) 2013-2021 Robert Beckebans
|
||||
Copyright (C) 2014-2016 Kot in Action Creative Artel
|
||||
Copyright (C) 2016-2017 Dustin Land
|
||||
|
||||
|
@ -77,6 +77,8 @@ int BitsForFormat( textureFormat_t format )
|
|||
return 128;
|
||||
case FMT_R32F:
|
||||
return 32;
|
||||
case FMT_R11G11B10F:
|
||||
return 8;
|
||||
// RB end
|
||||
case FMT_DEPTH:
|
||||
return 32;
|
||||
|
@ -132,6 +134,10 @@ ID_INLINE void idImage::DeriveOpts()
|
|||
opts.format = FMT_R32F;
|
||||
break;
|
||||
|
||||
case TD_R11G11B10F:
|
||||
opts.format = FMT_R11G11B10F;
|
||||
break;
|
||||
|
||||
case TD_DIFFUSE:
|
||||
// TD_DIFFUSE gets only set to when its a diffuse texture for an interaction
|
||||
opts.gammaMips = true;
|
||||
|
@ -313,7 +319,7 @@ void idImage::ActuallyLoadImage( bool fromBackEnd )
|
|||
{
|
||||
opts.textureType = TT_2D_ARRAY;
|
||||
}
|
||||
else if( cubeFiles != CF_2D )
|
||||
else if( cubeFiles == CF_NATIVE || cubeFiles == CF_CAMERA )
|
||||
{
|
||||
opts.textureType = TT_CUBIC;
|
||||
repeat = TR_CLAMP;
|
||||
|
@ -433,7 +439,7 @@ void idImage::ActuallyLoadImage( bool fromBackEnd )
|
|||
//else if( toolUsage )
|
||||
// binarizeReason = va( "binarize: tool usage '%s'", generatedName.c_str() );
|
||||
|
||||
if( cubeFiles != CF_2D )
|
||||
if( cubeFiles == CF_NATIVE || cubeFiles == CF_CAMERA )
|
||||
{
|
||||
int size;
|
||||
byte* pics[6];
|
||||
|
@ -514,6 +520,13 @@ void idImage::ActuallyLoadImage( bool fromBackEnd )
|
|||
opts.width = width;
|
||||
opts.height = height;
|
||||
opts.numLevels = 0;
|
||||
|
||||
// RB
|
||||
if( cubeFiles == CF_2D_PACKED_MIPCHAIN )
|
||||
{
|
||||
opts.width = width * ( 2.0f / 3.0f );
|
||||
}
|
||||
|
||||
DeriveOpts();
|
||||
|
||||
// foresthale 2014-05-30: give a nice progress display when binarizing
|
||||
|
@ -541,7 +554,14 @@ void idImage::ActuallyLoadImage( bool fromBackEnd )
|
|||
}
|
||||
|
||||
// RB: convert to compressed DXT or whatever choosen target format
|
||||
im.Load2DFromMemory( opts.width, opts.height, pic, opts.numLevels, opts.format, opts.colorFormat, opts.gammaMips );
|
||||
if( cubeFiles == CF_2D_PACKED_MIPCHAIN )
|
||||
{
|
||||
im.Load2DAtlasMipchainFromMemory( width, opts.height, pic, opts.numLevels, opts.format, opts.colorFormat );
|
||||
}
|
||||
else
|
||||
{
|
||||
im.Load2DFromMemory( opts.width, opts.height, pic, opts.numLevels, opts.format, opts.colorFormat, opts.gammaMips );
|
||||
}
|
||||
commonLocal.LoadPacifierBinarizeEnd();
|
||||
|
||||
Mem_Free( pic );
|
||||
|
@ -644,6 +664,7 @@ void idImage::Print() const
|
|||
NAME_FORMAT( RGBA16F );
|
||||
NAME_FORMAT( RGBA32F );
|
||||
NAME_FORMAT( R32F );
|
||||
NAME_FORMAT( R11G11B10F );
|
||||
// RB end
|
||||
NAME_FORMAT( DEPTH );
|
||||
NAME_FORMAT( X16 );
|
||||
|
@ -743,20 +764,27 @@ void idImage::Reload( bool force )
|
|||
GenerateImage
|
||||
================
|
||||
*/
|
||||
void idImage::GenerateImage( const byte* pic, int width, int height, textureFilter_t filterParm, textureRepeat_t repeatParm, textureUsage_t usageParm, textureSamples_t samples )
|
||||
void idImage::GenerateImage( const byte* pic, int width, int height, textureFilter_t filterParm, textureRepeat_t repeatParm, textureUsage_t usageParm, textureSamples_t samples, cubeFiles_t _cubeFiles )
|
||||
{
|
||||
PurgeImage();
|
||||
|
||||
filter = filterParm;
|
||||
repeat = repeatParm;
|
||||
usage = usageParm;
|
||||
cubeFiles = CF_2D;
|
||||
cubeFiles = _cubeFiles;
|
||||
|
||||
opts.textureType = ( samples > SAMPLE_1 ) ? TT_2D_MULTISAMPLE : TT_2D;
|
||||
opts.width = width;
|
||||
opts.height = height;
|
||||
opts.numLevels = 0;
|
||||
opts.samples = samples;
|
||||
|
||||
// RB
|
||||
if( cubeFiles == CF_2D_PACKED_MIPCHAIN )
|
||||
{
|
||||
opts.width = width * ( 2.0f / 3.0f );
|
||||
}
|
||||
|
||||
DeriveOpts();
|
||||
|
||||
// RB: allow pic == NULL for internal framebuffer images
|
||||
|
@ -779,7 +807,14 @@ void idImage::GenerateImage( const byte* pic, int width, int height, textureFilt
|
|||
commonLocal.LoadPacifierBinarizeProgressTotal( opts.width * opts.height );
|
||||
}
|
||||
|
||||
im.Load2DFromMemory( width, height, pic, opts.numLevels, opts.format, opts.colorFormat, opts.gammaMips );
|
||||
if( cubeFiles == CF_2D_PACKED_MIPCHAIN )
|
||||
{
|
||||
im.Load2DAtlasMipchainFromMemory( width, opts.height, pic, opts.numLevels, opts.format, opts.colorFormat );
|
||||
}
|
||||
else
|
||||
{
|
||||
im.Load2DFromMemory( width, height, pic, opts.numLevels, opts.format, opts.colorFormat, opts.gammaMips );
|
||||
}
|
||||
|
||||
commonLocal.LoadPacifierBinarizeEnd();
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2021 Robert Beckebans
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
||||
|
@ -527,6 +528,31 @@ void R_VerticalFlip( byte* data, int width, int height )
|
|||
}
|
||||
}
|
||||
|
||||
// RB: halfFloat_t helper
|
||||
struct ColorRGB16F
|
||||
{
|
||||
uint16 red;
|
||||
uint16 green;
|
||||
uint16 blue;
|
||||
};
|
||||
|
||||
void R_VerticalFlipRGB16F( byte* data, int width, int height )
|
||||
{
|
||||
int i, j;
|
||||
ColorRGB16F temp;
|
||||
|
||||
for( i = 0; i < width; i++ )
|
||||
{
|
||||
for( j = 0; j < height / 2; j++ )
|
||||
{
|
||||
temp = *( ( ColorRGB16F* )data + j * width + i );
|
||||
|
||||
*( ( ColorRGB16F* )data + j * width + i ) = *( ( ColorRGB16F* )data + ( height - 1 - j ) * width + i );
|
||||
*( ( ColorRGB16F* )data + ( height - 1 - j ) * width + i ) = temp;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void R_RotatePic( byte* data, int width )
|
||||
{
|
||||
int i, j;
|
||||
|
@ -570,3 +596,35 @@ void R_ApplyCubeMapTransforms( int iter, byte* data, int size )
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
// This is the most efficient way to atlas a mip chain to a 2d texture
|
||||
// https://twitter.com/SebAaltonen/status/1327188239451611139
|
||||
|
||||
idVec4 R_CalculateMipRect( uint dimensions, uint mip )
|
||||
{
|
||||
uint pixels_mip = dimensions >> mip;
|
||||
idVec4 uv_rect = idVec4( 0, 0, pixels_mip, pixels_mip );
|
||||
|
||||
if( mip > 0 )
|
||||
{
|
||||
uv_rect.x = dimensions;
|
||||
uv_rect.y = dimensions - pixels_mip * 2;
|
||||
}
|
||||
|
||||
return uv_rect;
|
||||
}
|
||||
|
||||
int R_CalculateUsedAtlasPixels( int dimensions )
|
||||
{
|
||||
int numPixels = 0;
|
||||
const int numMips = idMath::BitsForInteger( dimensions );
|
||||
|
||||
for( int mip = 0; mip < numMips; mip++ )
|
||||
{
|
||||
idVec4 dstRect = R_CalculateMipRect( dimensions, mip );
|
||||
|
||||
numPixels += ( dstRect.z * dstRect.w );
|
||||
}
|
||||
|
||||
return numPixels;
|
||||
}
|
||||
|
|
|
@ -133,6 +133,19 @@ void Framebuffer::Init()
|
|||
globalFramebuffers.hdrNonMSAAFBO->Check();
|
||||
#endif
|
||||
|
||||
// HDR CUBEMAP CAPTURE
|
||||
|
||||
globalFramebuffers.envprobeFBO = new Framebuffer( "_envprobeRender", RADIANCE_CUBEMAP_SIZE, RADIANCE_CUBEMAP_SIZE );
|
||||
globalFramebuffers.envprobeFBO->Bind();
|
||||
|
||||
globalFramebuffers.envprobeFBO->AddColorBuffer( GL_RGBA16F, 0 );
|
||||
globalFramebuffers.envprobeFBO->AddDepthBuffer( GL_DEPTH24_STENCIL8 );
|
||||
|
||||
globalFramebuffers.envprobeFBO->AttachImage2D( GL_TEXTURE_2D, globalImages->envprobeHDRImage, 0 );
|
||||
globalFramebuffers.envprobeFBO->AttachImageDepth( GL_TEXTURE_2D, globalImages->envprobeDepthImage );
|
||||
|
||||
globalFramebuffers.envprobeFBO->Check();
|
||||
|
||||
// HDR DOWNSCALE
|
||||
|
||||
globalFramebuffers.hdr64FBO = new Framebuffer( "_hdr64", 64, 64 );
|
||||
|
@ -365,6 +378,7 @@ void Framebuffer::Unbind()
|
|||
{
|
||||
glBindFramebuffer( GL_FRAMEBUFFER, 0 );
|
||||
glBindRenderbuffer( GL_RENDERBUFFER, 0 );
|
||||
|
||||
tr.backend.currentFramebuffer = NULL;
|
||||
}
|
||||
}
|
||||
|
@ -374,6 +388,11 @@ bool Framebuffer::IsDefaultFramebufferActive()
|
|||
return ( tr.backend.currentFramebuffer == NULL );
|
||||
}
|
||||
|
||||
Framebuffer* Framebuffer::GetActiveFramebuffer()
|
||||
{
|
||||
return tr.backend.currentFramebuffer;
|
||||
}
|
||||
|
||||
void Framebuffer::AddColorBuffer( int format, int index, int multiSamples )
|
||||
{
|
||||
if( index < 0 || index >= glConfig.maxColorAttachments )
|
||||
|
|
|
@ -725,6 +725,15 @@ void idImage::AllocImage()
|
|||
dataFormat = GL_LUMINANCE_ALPHA;
|
||||
dataType = GL_UNSIGNED_SHORT;
|
||||
break;
|
||||
|
||||
// see http://what-when-how.com/Tutorial/topic-615ll9ug/Praise-for-OpenGL-ES-30-Programming-Guide-291.html
|
||||
case FMT_R11G11B10F:
|
||||
internalFormat = GL_R11F_G11F_B10F;
|
||||
dataFormat = GL_RGB;
|
||||
dataType = GL_UNSIGNED_INT_10F_11F_11F_REV;
|
||||
//dataType = GL_FLOAT;
|
||||
break;
|
||||
|
||||
default:
|
||||
idLib::Error( "Unhandled image format %d in %s\n", opts.format, GetName() );
|
||||
}
|
||||
|
|
|
@ -1407,6 +1407,7 @@ void idRenderBackend::GL_Clear( bool color, bool depth, bool stencil, byte stenc
|
|||
glClear( clearFlags );
|
||||
|
||||
// RB begin
|
||||
/*
|
||||
if( r_useHDR.GetBool() && clearHDR && globalFramebuffers.hdrFBO != NULL )
|
||||
{
|
||||
bool isDefaultFramebufferActive = Framebuffer::IsDefaultFramebufferActive();
|
||||
|
@ -1419,6 +1420,28 @@ void idRenderBackend::GL_Clear( bool color, bool depth, bool stencil, byte stenc
|
|||
Framebuffer::Unbind();
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
if( r_useHDR.GetBool() && clearHDR )
|
||||
{
|
||||
bool isDefaultFramebufferActive = Framebuffer::IsDefaultFramebufferActive();
|
||||
|
||||
if( viewDef && viewDef->renderView.rdflags & RDF_IRRADIANCE )
|
||||
{
|
||||
globalFramebuffers.envprobeFBO->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
}
|
||||
|
||||
glClear( clearFlags );
|
||||
|
||||
if( isDefaultFramebufferActive )
|
||||
{
|
||||
Framebuffer::Unbind();
|
||||
}
|
||||
}
|
||||
// RB end
|
||||
}
|
||||
|
||||
|
|
|
@ -2078,7 +2078,7 @@ idRenderBackend::AmbientPass
|
|||
*/
|
||||
void idRenderBackend::AmbientPass( const drawSurf_t* const* drawSurfs, int numDrawSurfs, bool fillGbuffer )
|
||||
{
|
||||
const bool hdrIsActive = ( r_useHDR.GetBool() && globalFramebuffers.hdrFBO != NULL && globalFramebuffers.hdrFBO->IsBound() );
|
||||
Framebuffer* previousFramebuffer = Framebuffer::GetActiveFramebuffer();
|
||||
|
||||
if( numDrawSurfs == 0 )
|
||||
{
|
||||
|
@ -2096,6 +2096,11 @@ void idRenderBackend::AmbientPass( const drawSurf_t* const* drawSurfs, int numDr
|
|||
return;
|
||||
}
|
||||
|
||||
if( viewDef->renderView.rdflags & RDF_NOAMBIENT )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
#if defined( USE_VULKAN )
|
||||
if( fillGbuffer )
|
||||
{
|
||||
|
@ -2543,9 +2548,9 @@ void idRenderBackend::AmbientPass( const drawSurf_t* const* drawSurfs, int numDr
|
|||
if( fillGbuffer )
|
||||
{
|
||||
// go back to main render target
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -2945,6 +2950,11 @@ void idRenderBackend::ShadowMapPass( const drawSurf_t* drawSurfs, const viewLigh
|
|||
return;
|
||||
}
|
||||
|
||||
if( viewDef->renderView.rdflags & RDF_NOSHADOWS )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
RENDERLOG_PRINTF( "---------- RB_ShadowMapPass( side = %i ) ----------\n", side );
|
||||
|
||||
renderProgManager.BindShader_Depth();
|
||||
|
@ -3472,21 +3482,6 @@ void idRenderBackend::ShadowMapPass( const drawSurf_t* drawSurfs, const viewLigh
|
|||
DrawElementsWithCounters( drawSurf );
|
||||
}
|
||||
}
|
||||
|
||||
// cleanup the shadow specific rendering state
|
||||
if( r_useHDR.GetBool() ) //&& !backEnd.viewDef->is2Dgui )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
Framebuffer::Unbind();
|
||||
}
|
||||
renderProgManager.Unbind();
|
||||
|
||||
GL_State( GLS_DEFAULT );
|
||||
|
||||
SetFragmentParm( RENDERPARM_ALPHA_TEST, vec4_zero.ToFloatPtr() );
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -3515,6 +3510,8 @@ void idRenderBackend::DrawInteractions( const viewDef_t* _viewDef )
|
|||
|
||||
const bool useLightDepthBounds = r_useLightDepthBounds.GetBool() && !r_useShadowMapping.GetBool();
|
||||
|
||||
Framebuffer* previousFramebuffer = Framebuffer::GetActiveFramebuffer();
|
||||
|
||||
//
|
||||
// for each light, perform shadowing and adding
|
||||
//
|
||||
|
@ -3578,6 +3575,21 @@ void idRenderBackend::DrawInteractions( const viewDef_t* _viewDef )
|
|||
ShadowMapPass( vLight->globalShadows, vLight, side );
|
||||
}
|
||||
|
||||
// go back to main render target
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
Framebuffer::Unbind();
|
||||
}
|
||||
renderProgManager.Unbind();
|
||||
|
||||
GL_State( GLS_DEFAULT );
|
||||
|
||||
SetFragmentParm( RENDERPARM_ALPHA_TEST, vec4_zero.ToFloatPtr() );
|
||||
|
||||
// go back from light view to default camera view
|
||||
ResetViewportAndScissorToDefaultCamera( _viewDef );
|
||||
|
||||
|
@ -4676,7 +4688,7 @@ void idRenderBackend::Tonemap( const viewDef_t* _viewDef )
|
|||
|
||||
void idRenderBackend::Bloom( const viewDef_t* _viewDef )
|
||||
{
|
||||
if( _viewDef->is2Dgui || !r_useHDR.GetBool() )
|
||||
if( _viewDef->is2Dgui || !r_useHDR.GetBool() || ( _viewDef->renderView.rdflags & RDF_IRRADIANCE ) )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
@ -4822,13 +4834,18 @@ void idRenderBackend::DrawScreenSpaceAmbientOcclusion( const viewDef_t* _viewDef
|
|||
return;
|
||||
}
|
||||
|
||||
if( _viewDef->renderView.rdflags & RDF_NOAMBIENT )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
renderLog.OpenMainBlock( MRB_SSAO_PASS );
|
||||
renderLog.OpenBlock( "Render_SSAO", colorBlue );
|
||||
|
||||
currentSpace = &viewDef->worldSpace;
|
||||
RB_SetMVP( viewDef->worldSpace.mvp );
|
||||
|
||||
const bool hdrIsActive = ( r_useHDR.GetBool() && globalFramebuffers.hdrFBO != NULL && globalFramebuffers.hdrFBO->IsBound() );
|
||||
Framebuffer* previousFramebuffer = Framebuffer::GetActiveFramebuffer();
|
||||
|
||||
int screenWidth = renderSystem->GetWidth();
|
||||
int screenHeight = renderSystem->GetHeight();
|
||||
|
@ -4920,9 +4937,9 @@ void idRenderBackend::DrawScreenSpaceAmbientOcclusion( const viewDef_t* _viewDef
|
|||
GL_State( GLS_SRCBLEND_DST_COLOR | GLS_DSTBLEND_ZERO | GLS_ALPHAMASK | GLS_DEPTHMASK | GLS_DEPTHFUNC_ALWAYS );
|
||||
}
|
||||
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5049,9 +5066,9 @@ void idRenderBackend::DrawScreenSpaceAmbientOcclusion( const viewDef_t* _viewDef
|
|||
// AO blur Y
|
||||
if( downModulateScreen )
|
||||
{
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5086,9 +5103,9 @@ void idRenderBackend::DrawScreenSpaceAmbientOcclusion( const viewDef_t* _viewDef
|
|||
if( !downModulateScreen )
|
||||
{
|
||||
// go back to main scene render target
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5133,12 +5150,17 @@ void idRenderBackend::DrawScreenSpaceGlobalIllumination( const viewDef_t* _viewD
|
|||
return;
|
||||
}
|
||||
|
||||
if( _viewDef->renderView.rdflags & RDF_NOAMBIENT )
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
RENDERLOG_PRINTF( "---------- RB_SSGI() ----------\n" );
|
||||
|
||||
currentSpace = &viewDef->worldSpace;
|
||||
RB_SetMVP( viewDef->worldSpace.mvp );
|
||||
|
||||
const bool hdrIsActive = ( r_useHDR.GetBool() && globalFramebuffers.hdrFBO != NULL && globalFramebuffers.hdrFBO->IsBound() );
|
||||
Framebuffer* previousFramebuffer = Framebuffer::GetActiveFramebuffer();
|
||||
|
||||
int screenWidth = renderSystem->GetWidth();
|
||||
int screenHeight = renderSystem->GetHeight();
|
||||
|
@ -5147,7 +5169,8 @@ void idRenderBackend::DrawScreenSpaceGlobalIllumination( const viewDef_t* _viewD
|
|||
GL_Viewport( 0, 0, screenWidth, screenHeight );
|
||||
GL_Scissor( 0, 0, screenWidth, screenHeight );
|
||||
|
||||
if( !hdrIsActive )
|
||||
// TODO remove
|
||||
if( previousFramebuffer == NULL )
|
||||
{
|
||||
const idScreenRect& viewport = viewDef->viewport;
|
||||
globalImages->currentRenderImage->CopyFramebuffer( viewport.x1, viewport.y1, viewport.GetWidth(), viewport.GetHeight() );
|
||||
|
@ -5237,9 +5260,9 @@ void idRenderBackend::DrawScreenSpaceGlobalIllumination( const viewDef_t* _viewD
|
|||
GL_State( GLS_SRCBLEND_ONE | GLS_DSTBLEND_ONE | GLS_DEPTHMASK | GLS_DEPTHFUNC_ALWAYS );
|
||||
}
|
||||
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5301,9 +5324,9 @@ void idRenderBackend::DrawScreenSpaceGlobalIllumination( const viewDef_t* _viewD
|
|||
}
|
||||
|
||||
GL_SelectTexture( 2 );
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalImages->currentRenderHDRImage->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5336,9 +5359,9 @@ void idRenderBackend::DrawScreenSpaceGlobalIllumination( const viewDef_t* _viewD
|
|||
#endif
|
||||
|
||||
// AO blur Y
|
||||
if( hdrIsActive )
|
||||
if( previousFramebuffer != NULL )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
previousFramebuffer->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5539,7 +5562,14 @@ void idRenderBackend::DrawViewInternal( const viewDef_t* _viewDef, const int ste
|
|||
|
||||
if( useHDR )
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
if( _viewDef->renderView.rdflags & RDF_IRRADIANCE )
|
||||
{
|
||||
globalFramebuffers.envprobeFBO->Bind();
|
||||
}
|
||||
else
|
||||
{
|
||||
globalFramebuffers.hdrFBO->Bind();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -5710,8 +5740,9 @@ void idRenderBackend::DrawViewInternal( const viewDef_t* _viewDef, const int ste
|
|||
DBG_RenderDebugTools( drawSurfs, numDrawSurfs );
|
||||
|
||||
#if !defined(USE_VULKAN)
|
||||
|
||||
// RB: convert back from HDR to LDR range
|
||||
if( useHDR )
|
||||
if( useHDR && !( _viewDef->renderView.rdflags & RDF_IRRADIANCE ) )
|
||||
{
|
||||
/*
|
||||
int x = backEnd.viewDef->viewport.x1;
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
|
||||
Doom 3 BFG Edition GPL Source Code
|
||||
Copyright (C) 1993-2012 id Software LLC, a ZeniMax Media company.
|
||||
Copyright (C) 2012-2020 Robert Beckebans
|
||||
Copyright (C) 2012-2021 Robert Beckebans
|
||||
Copyright (C) 2014-2016 Kot in Action Creative Artel
|
||||
|
||||
This file is part of the Doom 3 BFG Edition GPL Source Code ("Doom 3 BFG Edition Source Code").
|
||||
|
@ -482,6 +482,22 @@ struct viewEnvprobe_t
|
|||
idImage* irradianceImage; // cubemap image used for diffuse IBL by backend
|
||||
idImage* radianceImage; // cubemap image used for specular IBL by backend
|
||||
};
|
||||
|
||||
struct calcEnvprobeParms_t
|
||||
{
|
||||
// input
|
||||
byte* buffers[6]; // HDR R11G11B11F standard OpenGL cubemap sides
|
||||
int samples;
|
||||
|
||||
int outWidth;
|
||||
int outHeight;
|
||||
|
||||
idStr filename;
|
||||
|
||||
// output
|
||||
halfFloat_t* outBuffer; // HDR R11G11B11F packed atlas
|
||||
int time; // execution time in milliseconds
|
||||
};
|
||||
// RB end
|
||||
|
||||
const int MAX_CLIP_PLANES = 1; // we may expand this to six for some subview issues
|
||||
|
@ -935,6 +951,10 @@ public:
|
|||
|
||||
idParallelJobList* frontEndJobList;
|
||||
|
||||
// RB irradiance and GGX background jobs
|
||||
idParallelJobList* envprobeJobList;
|
||||
idList<calcEnvprobeParms_t*> irradianceJobs;
|
||||
|
||||
idRenderBackend backend;
|
||||
|
||||
private:
|
||||
|
|
|
@ -304,7 +304,7 @@ idCVar r_showViewEnvprobes( "r_showViewEnvprobes", "0", CVAR_RENDERER | CVAR_INT
|
|||
idCVar r_exposure( "r_exposure", "0.5", CVAR_ARCHIVE | CVAR_RENDERER | CVAR_FLOAT, "HDR exposure or LDR brightness [0.0 .. 1.0]", 0.0f, 1.0f );
|
||||
// RB end
|
||||
|
||||
const char* fileExten[3] = { "tga", "png", "jpg" };
|
||||
const char* fileExten[4] = { "tga", "png", "jpg", "exr" };
|
||||
const char* envDirection[6] = { "_px", "_nx", "_py", "_ny", "_pz", "_nz" };
|
||||
const char* skyDirection[6] = { "_forward", "_back", "_left", "_right", "_up", "_down" };
|
||||
|
||||
|
@ -731,7 +731,17 @@ void R_ReadTiledPixels( int width, int height, byte* buffer, renderView_t* ref =
|
|||
// include extra space for OpenGL padding to word boundaries
|
||||
int sysWidth = renderSystem->GetWidth();
|
||||
int sysHeight = renderSystem->GetHeight();
|
||||
byte* temp = ( byte* )R_StaticAlloc( ( sysWidth + 3 ) * sysHeight * 3 );
|
||||
|
||||
byte* temp = NULL;
|
||||
if( ref && ref->rdflags & RDF_IRRADIANCE )
|
||||
{
|
||||
// * 2 = sizeof( half float )
|
||||
temp = ( byte* )R_StaticAlloc( RADIANCE_CUBEMAP_SIZE * RADIANCE_CUBEMAP_SIZE * 3 * 2 );
|
||||
}
|
||||
else
|
||||
{
|
||||
temp = ( byte* )R_StaticAlloc( ( sysWidth + 3 ) * sysHeight * 3 );
|
||||
}
|
||||
|
||||
// foresthale 2014-03-01: fixed custom screenshot resolution by doing a more direct render path
|
||||
#ifdef BUGFIXEDSCREENSHOTRESOLUTION
|
||||
|
@ -821,15 +831,29 @@ void R_ReadTiledPixels( int width, int height, byte* buffer, renderView_t* ref =
|
|||
h = height - yo;
|
||||
}
|
||||
|
||||
glReadBuffer( GL_FRONT );
|
||||
glReadPixels( 0, 0, w, h, GL_RGB, GL_UNSIGNED_BYTE, temp );
|
||||
|
||||
int row = ( w * 3 + 3 ) & ~3; // OpenGL pads to dword boundaries
|
||||
|
||||
for( int y = 0 ; y < h ; y++ )
|
||||
if( ref && ref->rdflags & RDF_IRRADIANCE )
|
||||
{
|
||||
memcpy( buffer + ( ( yo + y )* width + xo ) * 3,
|
||||
temp + y * row, w * 3 );
|
||||
globalFramebuffers.envprobeFBO->Bind();
|
||||
|
||||
glPixelStorei( GL_PACK_ROW_LENGTH, RADIANCE_CUBEMAP_SIZE );
|
||||
glReadPixels( 0, 0, w, h, GL_RGB, GL_HALF_FLOAT, buffer );
|
||||
|
||||
R_VerticalFlipRGB16F( buffer, w, h );
|
||||
|
||||
Framebuffer::Unbind();
|
||||
}
|
||||
else
|
||||
{
|
||||
glReadBuffer( GL_FRONT );
|
||||
glReadPixels( 0, 0, w, h, GL_RGB, GL_UNSIGNED_BYTE, temp );
|
||||
|
||||
int row = ( w * 3 + 3 ) & ~3; // OpenGL pads to dword boundaries
|
||||
|
||||
for( int y = 0 ; y < h ; y++ )
|
||||
{
|
||||
memcpy( buffer + ( ( yo + y )* width + xo ) * 3,
|
||||
temp + y * row, w * 3 );
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -874,7 +898,11 @@ void idRenderSystemLocal::TakeScreenshot( int width, int height, const char* fil
|
|||
int pix = width * height;
|
||||
const int bufferSize = pix * 3 + 18;
|
||||
|
||||
if( exten == PNG )
|
||||
if( exten == EXR )
|
||||
{
|
||||
buffer = ( byte* )R_StaticAlloc( pix * 3 * 2 );
|
||||
}
|
||||
else if( exten == PNG )
|
||||
{
|
||||
buffer = ( byte* )R_StaticAlloc( pix * 3 );
|
||||
}
|
||||
|
@ -886,7 +914,7 @@ void idRenderSystemLocal::TakeScreenshot( int width, int height, const char* fil
|
|||
|
||||
if( blends <= 1 )
|
||||
{
|
||||
if( exten == PNG )
|
||||
if( exten == PNG || exten == EXR )
|
||||
{
|
||||
R_ReadTiledPixels( width, height, buffer, ref );
|
||||
}
|
||||
|
@ -944,7 +972,12 @@ void idRenderSystemLocal::TakeScreenshot( int width, int height, const char* fil
|
|||
r_jitter.SetBool( false );
|
||||
}
|
||||
|
||||
if( exten == PNG )
|
||||
if( exten == EXR )
|
||||
{
|
||||
R_WriteEXR( finalFileName, buffer, 3, width, height, "fs_basepath" );
|
||||
//R_WritePNG( finalFileName, buffer, 3, width, height, false, "fs_basepath" );
|
||||
}
|
||||
else if( exten == PNG )
|
||||
{
|
||||
R_WritePNG( finalFileName, buffer, 3, width, height, false, "fs_basepath" );
|
||||
}
|
||||
|
@ -1685,6 +1718,10 @@ void idRenderSystemLocal::Clear()
|
|||
}
|
||||
|
||||
frontEndJobList = NULL;
|
||||
|
||||
// RB
|
||||
envprobeJobList = NULL;
|
||||
irradianceJobs.Clear();
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -2027,6 +2064,7 @@ void idRenderSystemLocal::Init()
|
|||
}
|
||||
|
||||
frontEndJobList = parallelJobManager->AllocJobList( JOBLIST_RENDERER_FRONTEND, JOBLIST_PRIORITY_MEDIUM, 2048, 0, NULL );
|
||||
envprobeJobList = parallelJobManager->AllocJobList( JOBLIST_UTILITY, JOBLIST_PRIORITY_MEDIUM, 2048, 0, NULL ); // RB
|
||||
|
||||
bInitialized = true;
|
||||
|
||||
|
|
|
@ -235,6 +235,13 @@ typedef struct
|
|||
} renderEnvironmentProbe_t;
|
||||
// RB end
|
||||
|
||||
|
||||
// RB: added back refdef flags from Quake 3
|
||||
const int RDF_NOSHADOWS = BIT( 0 ); // force renderer to use faster lighting only path
|
||||
const int RDF_NOAMBIENT = BIT( 1 ); // don't render indirect lighting
|
||||
const int RDF_IRRADIANCE = BIT( 2 ); // render into 256^2 HDR render target for irradiance/radiance GGX calculation
|
||||
const int RDF_UNDERWATER = BIT( 3 ); // TODO enable automatic underwater caustics and fog
|
||||
|
||||
typedef struct renderView_s
|
||||
{
|
||||
// player views will set this to a non-zero integer for model suppress / allow
|
||||
|
@ -258,6 +265,8 @@ typedef struct renderView_s
|
|||
// the viewEyeBuffer may be of a different polarity than stereoScreenSeparation if the eyes have been swapped
|
||||
int viewEyeBuffer; // -1 = left eye, 1 = right eye, 0 = monoscopic view or GUI
|
||||
float stereoScreenSeparation; // projection matrix horizontal offset, positive or negative based on camera eye
|
||||
|
||||
int rdflags; // RB: RDF_NOSHADOWS, etc
|
||||
} renderView_t;
|
||||
|
||||
|
||||
|
|
|
@ -769,10 +769,10 @@ void R_DeriveEnvprobeData( RenderEnvprobeLocal* probe )
|
|||
|
||||
// TODO get preconvolved cubemaps
|
||||
fullname.Format( "env/%s/envprobe%i_amb", basename.c_str(), probeIndex );
|
||||
probe->irradianceImage = globalImages->ImageFromFile( fullname, TF_DEFAULT, TR_CLAMP, TD_LOOKUP_TABLE_RGB1, CF_2D );
|
||||
probe->irradianceImage = globalImages->ImageFromFile( fullname, TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, CF_2D_PACKED_MIPCHAIN );
|
||||
|
||||
fullname.Format( "env/%s/envprobe%i_spec", basename.c_str(), probeIndex );
|
||||
probe->radianceImage = globalImages->ImageFromFile( fullname, TF_DEFAULT, TR_CLAMP, TD_LOOKUP_TABLE_RGB1, CF_2D );
|
||||
probe->radianceImage = globalImages->ImageFromFile( fullname, TF_DEFAULT, TR_CLAMP, TD_R11G11B10F, CF_2D_PACKED_MIPCHAIN );
|
||||
|
||||
// ------------------------------------
|
||||
// compute the light projection matrix
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -113,6 +113,5 @@ struct dynamicShadowVolumeParms_t
|
|||
|
||||
|
||||
void DynamicShadowVolumeJob( const dynamicShadowVolumeParms_t* parms );
|
||||
void DynamicShadowVolume_SetupSPURSHeader( CellSpursJob128* job, const dynamicShadowVolumeParms_t* parms );
|
||||
|
||||
#endif // !__DYNAMICSHADOWVOLUME_H__
|
||||
|
|
|
@ -80,6 +80,5 @@ struct preLightShadowVolumeParms_t
|
|||
|
||||
|
||||
void PreLightShadowVolumeJob( const preLightShadowVolumeParms_t* parms );
|
||||
void PreLightShadowVolume_SetupSPURSHeader( CellSpursJob128* job, const preLightShadowVolumeParms_t* parms );
|
||||
|
||||
#endif // !__PRELIGHTSHADOWVOLUME_H__
|
||||
|
|
|
@ -83,6 +83,5 @@ struct staticShadowVolumeParms_t
|
|||
|
||||
|
||||
void StaticShadowVolumeJob( const staticShadowVolumeParms_t* parms );
|
||||
void StaticShadowVolume_SetupSPURSHeader( CellSpursJob128* job, const staticShadowVolumeParms_t* parms );
|
||||
|
||||
#endif // !__STATICSHADOWVOLUME_H__
|
||||
|
|
Loading…
Reference in a new issue