From 0f10c44578c4500b770589e34cd8404bee4e8cba Mon Sep 17 00:00:00 2001 From: Jeffery Myers Date: Sun, 28 Feb 2021 14:31:25 -0800 Subject: [PATCH] Fixes gl state after HDR texture functions. (#1621) Updates skybox demo to show how to do both HDR and non HDR skyboxes Co-authored-by: Jeffery Myers --- examples/models/models_skybox.c | 71 +++++++++++++----- .../resources/shaders/glsl100/skybox.fs | 9 ++- .../resources/shaders/glsl330/skybox.fs | 9 ++- examples/models/resources/skybox.png | Bin 0 -> 10992 bytes src/rlgl.h | 6 +- 5 files changed, 67 insertions(+), 28 deletions(-) create mode 100644 examples/models/resources/skybox.png diff --git a/examples/models/models_skybox.c b/examples/models/models_skybox.c index f80fbf7a6..ad9c46c22 100644 --- a/examples/models/models_skybox.c +++ b/examples/models/models_skybox.c @@ -10,6 +10,9 @@ ********************************************************************************************/ #include "raylib.h" +#include "rlgl.h" + +bool useHDR = false; int main(void) { @@ -35,7 +38,8 @@ int main(void) skybox.materials[0].shader = LoadShader("resources/shaders/glsl100/skybox.vs", "resources/shaders/glsl100/skybox.fs"); #endif SetShaderValue(skybox.materials[0].shader, GetShaderLocation(skybox.materials[0].shader, "environmentMap"), (int[1]){ MAP_CUBEMAP }, UNIFORM_INT); - SetShaderValue(skybox.materials[0].shader, GetShaderLocation(skybox.materials[0].shader, "vflipped"), (int[1]){ 1 }, UNIFORM_INT); + SetShaderValue(skybox.materials[0].shader, GetShaderLocation(skybox.materials[0].shader, "doGamma"), (int[1]) { useHDR ? 1 : 0 }, UNIFORM_INT); + SetShaderValue(skybox.materials[0].shader, GetShaderLocation(skybox.materials[0].shader, "vflipped"), (int[1]){ useHDR ? 1 : 0 }, UNIFORM_INT); // Load cubemap shader and setup required shader locations #if defined(PLATFORM_DESKTOP) @@ -45,18 +49,29 @@ int main(void) #endif SetShaderValue(shdrCubemap, GetShaderLocation(shdrCubemap, "equirectangularMap"), (int[1]){ 0 }, UNIFORM_INT); - // Load HDR panorama (sphere) texture - char panoFileName[256] = { 0 }; - TextCopy(panoFileName, "resources/dresden_square_2k.hdr"); - Texture2D panorama = LoadTexture(panoFileName); + char skyboxFileName[256] = { 0 }; + + if (useHDR) + { + TextCopy(skyboxFileName, "resources/dresden_square_2k.hdr"); + + // Load HDR panorama (sphere) texture + Texture2D panorama = panorama = LoadTexture(skyboxFileName); - // Generate cubemap (texture with 6 quads-cube-mapping) from panorama HDR texture - // NOTE 1: New texture is generated rendering to texture, shader calculates the sphere->cube coordinates mapping - // NOTE 2: It seems on some Android devices WebGL, fbo does not properly support a FLOAT-based attachment, - // despite texture can be successfully created.. so using UNCOMPRESSED_R8G8B8A8 instead of UNCOMPRESSED_R32G32B32A32 - skybox.materials[0].maps[MAP_CUBEMAP].texture = GenTextureCubemap(shdrCubemap, panorama, 1024, UNCOMPRESSED_R8G8B8A8); + // Generate cubemap (texture with 6 quads-cube-mapping) from panorama HDR texture + // NOTE 1: New texture is generated rendering to texture, shader calculates the sphere->cube coordinates mapping + // NOTE 2: It seems on some Android devices WebGL, fbo does not properly support a FLOAT-based attachment, + // despite texture can be successfully created.. so using UNCOMPRESSED_R8G8B8A8 instead of UNCOMPRESSED_R32G32B32A32 + skybox.materials[0].maps[MAP_CUBEMAP].texture = GenTextureCubemap(shdrCubemap, panorama, 1024, UNCOMPRESSED_R8G8B8A8); - UnloadTexture(panorama); // Texture not required anymore, cubemap already generated + UnloadTexture(panorama); // Texture not required anymore, cubemap already generated + } + else + { + Image img = LoadImage("resources/skybox.png"); + skybox.materials[0].maps[MAP_CUBEMAP].texture = LoadTextureCubemap(img, CUBEMAP_AUTO_DETECT); + UnloadImage(img); + } SetCameraMode(camera, CAMERA_FIRST_PERSON); // Set a first person camera mode @@ -82,12 +97,22 @@ int main(void) { // Unload current cubemap texture and load new one UnloadTexture(skybox.materials[0].maps[MAP_CUBEMAP].texture); - panorama = LoadTexture(droppedFiles[0]); - TextCopy(panoFileName, droppedFiles[0]); - - // Generate cubemap from panorama texture - skybox.materials[0].maps[MAP_CUBEMAP].texture = GenTextureCubemap(shdrCubemap, panorama, 1024, UNCOMPRESSED_R8G8B8A8); - UnloadTexture(panorama); + if (useHDR) + { + Texture2D panorama = LoadTexture(droppedFiles[0]); + + // Generate cubemap from panorama texture + skybox.materials[0].maps[MAP_CUBEMAP].texture = GenTextureCubemap(shdrCubemap, panorama, 1024, UNCOMPRESSED_R8G8B8A8); + UnloadTexture(panorama); + } + else + { + Image img = LoadImage(droppedFiles[0]); + skybox.materials[0].maps[MAP_CUBEMAP].texture = LoadTextureCubemap(img, CUBEMAP_AUTO_DETECT); + UnloadImage(img); + } + + TextCopy(skyboxFileName, droppedFiles[0]); } } @@ -102,11 +127,19 @@ int main(void) ClearBackground(RAYWHITE); BeginMode3D(camera); - DrawModel(skybox, (Vector3){0, 0, 0}, 1.0f, WHITE); + rlDisableBackfaceCulling(); + rlDisableDepthMask(); + DrawModel(skybox, (Vector3){0, 0, 0}, 1.0f, WHITE); + rlEnableBackfaceCulling(); + rlEnableDepthMask(); DrawGrid(10, 1.0f); EndMode3D(); - DrawText(TextFormat("Panorama image from hdrihaven.com: %s", GetFileName(panoFileName)), 10, GetScreenHeight() - 20, 10, BLACK); + if (useHDR) + DrawText(TextFormat("Panorama image from hdrihaven.com: %s", GetFileName(skyboxFileName)), 10, GetScreenHeight() - 20, 10, BLACK); + else + DrawText(TextFormat(": %s", GetFileName(skyboxFileName)), 10, GetScreenHeight() - 20, 10, BLACK); + DrawFPS(10, 10); EndDrawing(); diff --git a/examples/models/resources/shaders/glsl100/skybox.fs b/examples/models/resources/shaders/glsl100/skybox.fs index 1269a96d9..4aa4ec9c0 100644 --- a/examples/models/resources/shaders/glsl100/skybox.fs +++ b/examples/models/resources/shaders/glsl100/skybox.fs @@ -8,6 +8,7 @@ varying vec3 fragPosition; // Input uniform values uniform samplerCube environmentMap; uniform bool vflipped; +uniform bool doGamma; void main() { @@ -19,9 +20,11 @@ void main() vec3 color = vec3(texelColor.x, texelColor.y, texelColor.z); - // Apply gamma correction - color = color/(color + vec3(1.0)); - color = pow(color, vec3(1.0/2.2)); + if (doGamma)// Apply gamma correction + { + color = color/(color + vec3(1.0)); + color = pow(color, vec3(1.0/2.2)); + } // Calculate final fragment color gl_FragColor = vec4(color, 1.0); diff --git a/examples/models/resources/shaders/glsl330/skybox.fs b/examples/models/resources/shaders/glsl330/skybox.fs index dd8078e09..800c1c6fc 100644 --- a/examples/models/resources/shaders/glsl330/skybox.fs +++ b/examples/models/resources/shaders/glsl330/skybox.fs @@ -16,6 +16,7 @@ in vec3 fragPosition; // Input uniform values uniform samplerCube environmentMap; uniform bool vflipped; +uniform bool doGamma; // Output fragment color out vec4 finalColor; @@ -28,9 +29,11 @@ void main() if (vflipped) color = texture(environmentMap, vec3(fragPosition.x, -fragPosition.y, fragPosition.z)).rgb; else color = texture(environmentMap, fragPosition).rgb; - // Apply gamma correction - color = color/(color + vec3(1.0)); - color = pow(color, vec3(1.0/2.2)); + if (doGamma)// Apply gamma correction + { + color = color/(color + vec3(1.0)); + color = pow(color, vec3(1.0/2.2)); + } // Calculate final fragment color finalColor = vec4(color, 1.0); diff --git a/examples/models/resources/skybox.png b/examples/models/resources/skybox.png new file mode 100644 index 0000000000000000000000000000000000000000..36a79b2de5bee79b932730011d25e1e5f6209d48 GIT binary patch literal 10992 zcmeHN3sh5A);@^>;tQ)I-~&Rd1uaED1XLcuM}1U5ejkG^U{DmSfI(4t1#T?upyg$y z77ztyoK~x&;SCBQ5hMr#0Z||zgc_O<2!s&wGB@|kjgFm}KGt8?{AztX3X957`Y~QwdHvlv6sv(#$4gYz%Wj_V~Aw=!ox)I!IT`I;K z(?d6SZvdbuV-|YQ0B>`Bckcawr+~akY(R;1Phvd^*sFlg6tE93O4zT2k0-FU3G9&! zYaGYwq}ao8taSqGkYinw*fRy*AA2ChI8v-dhCP*Id?kD$$G8(%(>T_rzm#}cfhjai|-rT-0y@3|b+9%iR{ zt*_GLD~q&8^cyEEzy^W&e@F$rSGUaf2zt& z3>y_4GBaY=#br{)m4Pnj>{p3{Z)HX~cg5wO%Eqo`jvc#LFO zHGOW9jQfQyw5l2TV|fB_uT<~JH#za5Q9WDYD9B%=<+|j+=5Q5=sr*paH&`Ou-tEUB zyD9TW9U+f5Oo)^YTey*g{pvLm8$muv%k9jDXt)gQ7blY|UeIXP$_p~?m%7j$%}9EA zG+25&3t?EKaqIgXv5$&jc(R83xN|PO#IdgIO6o37jUyI|KmA<8?I@p1Piy91_0l$} zLz}RYIYROt|Mg%jjc{kAL#FAr<&gc9`F0NQZci&=yfK^q!rgDuay7;)hC8`vXqc@L z``Z`Ng}Y`mkyNBcLe6x8njQ{eTw~sE9pia}8H~!y3gONcG&Fpc5j)ATDlJC4dVWT_ z^sehsdvll?u?z%&2q8JNg9Iqy11d5@m1A};n=HsLv71hxRe%ddyqGp{I5muTJ#Xnr zWh&BIJ`b#-yU6p)8cpae9$<34&6v?;S3!Q6cpBTFEd-OhCA*-!SSH*_8RIu+@+ zHUVZ{xf<@XCr0cZdr;KOQ*UhkQpW8aBn%LbI>DS=HRv8%=EYFO(7x-7Qx7;Z{&?cN z4DbKy{oUMQ5F?k$f+j#U0#B*PhH*4y-LgQkVq_)5942PJ|8fj0n{U^G8uj7Yt%)_% zF76zerkC$+;Ui$>9YO`m;)5=NNJ47H<{YSg=-G`D#>Y!!CPjAF8U9gzeTsq0DNJ-^ zC5PoFsDNR`&@UU&0yV8zl(1jeem$R7qfo}V*QgifrPTquyk}LGI_J@-fDJj1q#G{lSEuE1kzXE4VJGy4*TS9`D)x zd26zaQcBVfuMlSCzz>+yf>uR?IoB!a(y;fq9J6~HM#+R!cu{B0(y`pMNREc`*bRg% zr1Nvv5~XSOQJM0t)*6}%hMsl89w`r@N;sxRgzyeDBS}W=i&j0KXNm;zy_MH&M1rut z4a5{vgSVtY>nKZH;Sw#hl(V)Eg8inO-5eYHytbOq zk&*|5!VwX@vY#Uu;W2Hwy6TG^HUb9eeF3XJynzbIU+Gw9HT=Is0vbEvo!(NOA?=Ll z5n8XFo!q3RI(Oilngm1YVXWdLkTe-076NgKb7IHoi}BZlb!w_BSKr|vq#nd7qJZR~ zFfUU)v?>}ygE%GzJRqPP`Wokm#K!m>G%FJCP-QzHW(pi@w>GH0M!$GyVj_267mvN* zdU{w&D{pmtg4iBuNJY+nl+MTaYz$c;r#x>nq5J2V$2M3pu`J}w4@+n#A4x+!S&!rF z^K?VkY^C>-k`k>h$n2dOa4cawXcCG&TB;^El-PWFZ%Au%ozUU8PTs_|D*_#N~xD zd*?b_yNUGSYBON>U#EG3ROBu%4Yx5s z+&@NF@lihqmWJv8LeLd$y#a|lp-8}7uLE>v>zGBLc3W1O6ZS)h zE9PxTpA~d>T0bJE+((71BCz&j)hF}M2zOudUP4!KSJ5!}5$*>?e-dS3Nci_ZtVlx^ zmMnonBHN(wi=;kWsu7p^Gd`1^Bb6%yX-gk|mI0U?afDt*MPUrLm$K-G&}hdb8TCCp zyF{OG&{DDJ)yW#_a*#JB5RmQHdmw`PawjE6^q2j0&bxwTO^v7E!XPxdOfI8Z>t#;Q z)60}=HPm-NCoS!>@-(u?V7s?T@YP{5F%_BPW(l|G0sTqG#{o6m5wXsKZWY>FWM<#m z%0J%Ls7bN!q7@9;WgLoy(Fa`btGkK?GO87>JB+8&xk7~`1`9J{cX(i8?#`?HD($At z)P%(;#$yI+u(aM`b=O>A#^#K6V7X8jaT*&jWdD_$`$RER-)CugQoGhg)znR01ece) zVyE%c?QlMUhsg6eN+Bx*gsc81b7ezxrTvijVm^l%8`#|9h&6_Pf`;jdU#%^KLh@C+ z7K91fkUi@W`|dnu?ELdfMk2*Y`$<| za$#w@y=iY&sDR11lCZ8nw(*Ny!KdTSRA{sAtj5kq97Mwma4U!8xO?+^Ooc4&WFQzzHeg0Um^ED@=w)OiQ^XKWBrTjaUe>{ApnQBuCVlWkK=HsC zc5}?a8ScxD!|)}x>m=3Hhs0moW9!Fu74+STU5#}fOGUO?Tf!zhhP%Ivm9R9@rU!D0 zBRFuA*|#n}wr=8Tq8mrv^GMdek7VezZC7J~mrtU$dZM$=)IcF?&z@GK3{;M*Hwgy^YnN>}kgB>ZIqB73 zs}4P;lQB&3^*E=e758$$Z8E$>97rNN_f7~CuTc3Oo~opPYTEIGXi1q;?KcyThwzAC zoRgZ)Jop|Vat-G0G&ynWT1nMxSmv6=ozEc$kEA1)aFos6lX&<>m5-r*#=r#R6j6_( zg!Y*}eBJsXyHteJX@M&kAZ8bd@xh3~`!tMsfH)p`HEj{UR&CP7)4yCBV2cw&DlFMY zWH0kF=@Mtl>{4Om)jRWX$aQ74IAnrb;M<@kP~>SCa$L+HE`o2zSG(ieo#LIY# zwh2_b$DxC0YldAAH2@(M$hKbT)9*pfElD&C!rlt)GGMo-L_IZ=9c@O50%^=CWVY@d zGp`0`9RJ%Hrj!Kj@n<%o3{s+EygA8pM=GlYtH?ompEqT?U(N7;C(->l-vL{!<%eJq zvldXRmVzhU&_zyN08S7KUUtm|=N5nnC94JPo$hr794&znLcTS4KHV!|Po_Dsw6rzAiBRH8ijAzlK|?UgxVQIWY^z@vHd%T|z&=qq12A!=m46<25C1 z&$GOq+H+pPe9cioJ%fIelJ5Ug(*E6OsoL3BaqG=tE-4u9dUKc+UQek%f%&8JOEh9DplM1D*FBb*AAO?UQNnu)+{(_QN;0;Q35dlVcHaLneMMO}G zr!akWo;B#vSLqIfHhmR*hOavMs?|