fxaa.glsl 48 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174
  1. /*============================================================================
  2. NVIDIA FXAA 3.11 by TIMOTHY LOTTES
  3. ------------------------------------------------------------------------------
  4. COPYRIGHT (C) 2010, 2011 NVIDIA CORPORATION. ALL RIGHTS RESERVED.
  5. ------------------------------------------------------------------------------
  6. TO THE MAXIMUM EXTENT PERMITTED BY APPLICABLE LAW, THIS SOFTWARE IS PROVIDED
  7. *AS IS* AND NVIDIA AND ITS SUPPLIERS DISCLAIM ALL WARRANTIES, EITHER EXPRESS
  8. OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
  9. MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL NVIDIA
  10. OR ITS SUPPLIERS BE LIABLE FOR ANY SPECIAL, INCIDENTAL, INDIRECT, OR
  11. CONSEQUENTIAL DAMAGES WHATSOEVER (INCLUDING, WITHOUT LIMITATION, DAMAGES FOR
  12. LOSS OF BUSINESS PROFITS, BUSINESS INTERRUPTION, LOSS OF BUSINESS INFORMATION,
  13. OR ANY OTHER PECUNIARY LOSS) ARISING OUT OF THE USE OF OR INABILITY TO USE
  14. THIS SOFTWARE, EVEN IF NVIDIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
  15. DAMAGES.
  16. ------------------------------------------------------------------------------
  17. INTEGRATION CHECKLIST
  18. ------------------------------------------------------------------------------
  19. (1.)
  20. In the shader source, setup defines for the desired configuration.
  21. When providing multiple shaders (for different presets),
  22. simply setup the defines differently in multiple files.
  23. Example,
  24. #define FXAA_PC 1
  25. #define FXAA_HLSL_5 1
  26. #define FXAA_QUALITY__PRESET 12
  27. Or,
  28. #define FXAA_360 1
  29. Or,
  30. #define FXAA_PS3 1
  31. Etc.
  32. (2.)
  33. Then include this file,
  34. #include "Fxaa3_11.h"
  35. (3.)
  36. Then call the FXAA pixel shader from within your desired shader.
  37. Look at the FXAA Quality FxaaPixelShader() for docs on inputs.
  38. As for FXAA 3.11 all inputs for all shaders are the same
  39. to enable easy porting between platforms.
  40. return FxaaPixelShader(...);
  41. (4.)
  42. Insure pass prior to FXAA outputs RGBL (see next section).
  43. Or use,
  44. #define FXAA_GREEN_AS_LUMA 1
  45. (5.)
  46. Setup engine to provide the following constants
  47. which are used in the FxaaPixelShader() inputs,
  48. FxaaFloat2 fxaaQualityRcpFrame,
  49. FxaaFloat4 fxaaConsoleRcpFrameOpt,
  50. FxaaFloat4 fxaaConsoleRcpFrameOpt2,
  51. FxaaFloat4 fxaaConsole360RcpFrameOpt2,
  52. FxaaFloat fxaaQualitySubpix,
  53. FxaaFloat fxaaQualityEdgeThreshold,
  54. FxaaFloat fxaaQualityEdgeThresholdMin,
  55. FxaaFloat fxaaConsoleEdgeSharpness,
  56. FxaaFloat fxaaConsoleEdgeThreshold,
  57. FxaaFloat fxaaConsoleEdgeThresholdMin,
  58. FxaaFloat4 fxaaConsole360ConstDir
  59. Look at the FXAA Quality FxaaPixelShader() for docs on inputs.
  60. (6.)
  61. Have FXAA vertex shader run as a full screen triangle,
  62. and output "pos" and "fxaaConsolePosPos"
  63. such that inputs in the pixel shader provide,
  64. // {xy} = center of pixel
  65. FxaaFloat2 pos,
  66. // {xy__} = upper left of pixel
  67. // {__zw} = lower right of pixel
  68. FxaaFloat4 fxaaConsolePosPos,
  69. (7.)
  70. Insure the texture sampler(s) used by FXAA are set to bilinear filtering.
  71. ------------------------------------------------------------------------------
  72. INTEGRATION - RGBL AND COLORSPACE
  73. ------------------------------------------------------------------------------
  74. FXAA3 requires RGBL as input unless the following is set,
  75. #define FXAA_GREEN_AS_LUMA 1
  76. In which case the engine uses green in place of luma,
  77. and requires RGB input is in a non-linear colorspace.
  78. RGB should be LDR (low dynamic range).
  79. Specifically do FXAA after tonemapping.
  80. RGB data as returned by a texture fetch can be non-linear,
  81. or linear when FXAA_GREEN_AS_LUMA is not set.
  82. Note an "sRGB format" texture counts as linear,
  83. because the result of a texture fetch is linear data.
  84. Regular "RGBA8" textures in the sRGB colorspace are non-linear.
  85. If FXAA_GREEN_AS_LUMA is not set,
  86. luma must be stored in the alpha channel prior to running FXAA.
  87. This luma should be in a perceptual space (could be gamma 2.0).
  88. Example pass before FXAA where output is gamma 2.0 encoded,
  89. color.rgb = ToneMap(color.rgb); // linear color output
  90. color.rgb = sqrt(color.rgb); // gamma 2.0 color output
  91. return color;
  92. To use FXAA,
  93. color.rgb = ToneMap(color.rgb); // linear color output
  94. color.rgb = sqrt(color.rgb); // gamma 2.0 color output
  95. color.a = dot(color.rgb, FxaaFloat3(0.299, 0.587, 0.114)); // compute luma
  96. return color;
  97. Another example where output is linear encoded,
  98. say for instance writing to an sRGB formated render target,
  99. where the render target does the conversion back to sRGB after blending,
  100. color.rgb = ToneMap(color.rgb); // linear color output
  101. return color;
  102. To use FXAA,
  103. color.rgb = ToneMap(color.rgb); // linear color output
  104. color.a = sqrt(dot(color.rgb, FxaaFloat3(0.299, 0.587, 0.114))); // compute luma
  105. return color;
  106. Getting luma correct is required for the algorithm to work correctly.
  107. ------------------------------------------------------------------------------
  108. BEING LINEARLY CORRECT?
  109. ------------------------------------------------------------------------------
  110. Applying FXAA to a framebuffer with linear RGB color will look worse.
  111. This is very counter intuitive, but happends to be true in this case.
  112. The reason is because dithering artifacts will be more visiable
  113. in a linear colorspace.
  114. ------------------------------------------------------------------------------
  115. COMPLEX INTEGRATION
  116. ------------------------------------------------------------------------------
  117. Q. What if the engine is blending into RGB before wanting to run FXAA?
  118. A. In the last opaque pass prior to FXAA,
  119. have the pass write out luma into alpha.
  120. Then blend into RGB only.
  121. FXAA should be able to run ok
  122. assuming the blending pass did not any add aliasing.
  123. This should be the common case for particles and common blending passes.
  124. A. Or use FXAA_GREEN_AS_LUMA.
  125. ============================================================================*/
  126. #version 430 core
  127. layout(local_size_x = 16, local_size_y = 16) in;
  128. layout(rgba8, binding = 0) uniform image2D imgOutput;
  129. uniform sampler2D inputTexture;
  130. layout(location=0) uniform vec2 invResolution;
  131. #define FXAA_QUALITY__PRESET 12
  132. #define FXAA_GREEN_AS_LUMA 1
  133. #define FXAA_PC 1
  134. #define FXAA_GLSL_130 1
  135. /*============================================================================
  136. INTEGRATION KNOBS
  137. /*==========================================================================*/
  138. #ifndef FXAA_PC
  139. //
  140. // FXAA Quality
  141. // The high quality PC algorithm.
  142. //
  143. #define FXAA_PC 0
  144. #endif
  145. /*--------------------------------------------------------------------------*/
  146. #ifndef FXAA_GLSL_120
  147. #define FXAA_GLSL_120 0
  148. #endif
  149. /*--------------------------------------------------------------------------*/
  150. #ifndef FXAA_GLSL_130
  151. #define FXAA_GLSL_130 0
  152. #endif
  153. /*==========================================================================*/
  154. #ifndef FXAA_GREEN_AS_LUMA
  155. //
  156. // For those using non-linear color,
  157. // and either not able to get luma in alpha, or not wanting to,
  158. // this enables FXAA to run using green as a proxy for luma.
  159. // So with this enabled, no need to pack luma in alpha.
  160. //
  161. // This will turn off AA on anything which lacks some amount of green.
  162. // Pure red and blue or combination of only R and B, will get no AA.
  163. //
  164. // Might want to lower the settings for both,
  165. // fxaaConsoleEdgeThresholdMin
  166. // fxaaQualityEdgeThresholdMin
  167. // In order to insure AA does not get turned off on colors
  168. // which contain a minor amount of green.
  169. //
  170. // 1 = On.
  171. // 0 = Off.
  172. //
  173. #define FXAA_GREEN_AS_LUMA 0
  174. #endif
  175. /*--------------------------------------------------------------------------*/
  176. #ifndef FXAA_EARLY_EXIT
  177. //
  178. // Controls algorithm's early exit path.
  179. // On PS3 turning this ON adds 2 cycles to the shader.
  180. // On 360 turning this OFF adds 10ths of a millisecond to the shader.
  181. // Turning this off on console will result in a more blurry image.
  182. // So this defaults to on.
  183. //
  184. // 1 = On.
  185. // 0 = Off.
  186. //
  187. #define FXAA_EARLY_EXIT 1
  188. #endif
  189. /*--------------------------------------------------------------------------*/
  190. #ifndef FXAA_DISCARD
  191. //
  192. // Only valid for PC OpenGL currently.
  193. // Probably will not work when FXAA_GREEN_AS_LUMA = 1.
  194. //
  195. // 1 = Use discard on pixels which don't need AA.
  196. // For APIs which enable concurrent TEX+ROP from same surface.
  197. // 0 = Return unchanged color on pixels which don't need AA.
  198. //
  199. #define FXAA_DISCARD 0
  200. #endif
  201. /*--------------------------------------------------------------------------*/
  202. #ifndef FXAA_FAST_PIXEL_OFFSET
  203. //
  204. // Used for GLSL 120 only.
  205. //
  206. // 1 = GL API supports fast pixel offsets
  207. // 0 = do not use fast pixel offsets
  208. //
  209. #ifdef GL_EXT_gpu_shader4
  210. #define FXAA_FAST_PIXEL_OFFSET 1
  211. #endif
  212. #ifdef GL_NV_gpu_shader5
  213. #define FXAA_FAST_PIXEL_OFFSET 1
  214. #endif
  215. #ifdef GL_ARB_gpu_shader5
  216. #define FXAA_FAST_PIXEL_OFFSET 1
  217. #endif
  218. #ifndef FXAA_FAST_PIXEL_OFFSET
  219. #define FXAA_FAST_PIXEL_OFFSET 0
  220. #endif
  221. #endif
  222. /*--------------------------------------------------------------------------*/
  223. #ifndef FXAA_GATHER4_ALPHA
  224. //
  225. // 1 = API supports gather4 on alpha channel.
  226. // 0 = API does not support gather4 on alpha channel.
  227. //
  228. #if (FXAA_HLSL_5 == 1)
  229. #define FXAA_GATHER4_ALPHA 1
  230. #endif
  231. #ifdef GL_ARB_gpu_shader5
  232. #define FXAA_GATHER4_ALPHA 1
  233. #endif
  234. #ifdef GL_NV_gpu_shader5
  235. #define FXAA_GATHER4_ALPHA 1
  236. #endif
  237. #ifndef FXAA_GATHER4_ALPHA
  238. #define FXAA_GATHER4_ALPHA 0
  239. #endif
  240. #endif
  241. /*============================================================================
  242. FXAA QUALITY - TUNING KNOBS
  243. ------------------------------------------------------------------------------
  244. NOTE the other tuning knobs are now in the shader function inputs!
  245. ============================================================================*/
  246. #ifndef FXAA_QUALITY__PRESET
  247. //
  248. // Choose the quality preset.
  249. // This needs to be compiled into the shader as it effects code.
  250. // Best option to include multiple presets is to
  251. // in each shader define the preset, then include this file.
  252. //
  253. // OPTIONS
  254. // -----------------------------------------------------------------------
  255. // 10 to 15 - default medium dither (10=fastest, 15=highest quality)
  256. // 20 to 29 - less dither, more expensive (20=fastest, 29=highest quality)
  257. // 39 - no dither, very expensive
  258. //
  259. // NOTES
  260. // -----------------------------------------------------------------------
  261. // 12 = slightly faster then FXAA 3.9 and higher edge quality (default)
  262. // 13 = about same speed as FXAA 3.9 and better than 12
  263. // 23 = closest to FXAA 3.9 visually and performance wise
  264. // _ = the lowest digit is directly related to performance
  265. // _ = the highest digit is directly related to style
  266. //
  267. #define FXAA_QUALITY__PRESET 12
  268. #endif
  269. /*============================================================================
  270. FXAA QUALITY - PRESETS
  271. ============================================================================*/
  272. /*============================================================================
  273. FXAA QUALITY - MEDIUM DITHER PRESETS
  274. ============================================================================*/
  275. #if (FXAA_QUALITY__PRESET == 10)
  276. #define FXAA_QUALITY__PS 3
  277. #define FXAA_QUALITY__P0 1.5
  278. #define FXAA_QUALITY__P1 3.0
  279. #define FXAA_QUALITY__P2 12.0
  280. #endif
  281. /*--------------------------------------------------------------------------*/
  282. #if (FXAA_QUALITY__PRESET == 11)
  283. #define FXAA_QUALITY__PS 4
  284. #define FXAA_QUALITY__P0 1.0
  285. #define FXAA_QUALITY__P1 1.5
  286. #define FXAA_QUALITY__P2 3.0
  287. #define FXAA_QUALITY__P3 12.0
  288. #endif
  289. /*--------------------------------------------------------------------------*/
  290. #if (FXAA_QUALITY__PRESET == 12)
  291. #define FXAA_QUALITY__PS 5
  292. #define FXAA_QUALITY__P0 1.0
  293. #define FXAA_QUALITY__P1 1.5
  294. #define FXAA_QUALITY__P2 2.0
  295. #define FXAA_QUALITY__P3 4.0
  296. #define FXAA_QUALITY__P4 12.0
  297. #endif
  298. /*--------------------------------------------------------------------------*/
  299. #if (FXAA_QUALITY__PRESET == 13)
  300. #define FXAA_QUALITY__PS 6
  301. #define FXAA_QUALITY__P0 1.0
  302. #define FXAA_QUALITY__P1 1.5
  303. #define FXAA_QUALITY__P2 2.0
  304. #define FXAA_QUALITY__P3 2.0
  305. #define FXAA_QUALITY__P4 4.0
  306. #define FXAA_QUALITY__P5 12.0
  307. #endif
  308. /*--------------------------------------------------------------------------*/
  309. #if (FXAA_QUALITY__PRESET == 14)
  310. #define FXAA_QUALITY__PS 7
  311. #define FXAA_QUALITY__P0 1.0
  312. #define FXAA_QUALITY__P1 1.5
  313. #define FXAA_QUALITY__P2 2.0
  314. #define FXAA_QUALITY__P3 2.0
  315. #define FXAA_QUALITY__P4 2.0
  316. #define FXAA_QUALITY__P5 4.0
  317. #define FXAA_QUALITY__P6 12.0
  318. #endif
  319. /*--------------------------------------------------------------------------*/
  320. #if (FXAA_QUALITY__PRESET == 15)
  321. #define FXAA_QUALITY__PS 8
  322. #define FXAA_QUALITY__P0 1.0
  323. #define FXAA_QUALITY__P1 1.5
  324. #define FXAA_QUALITY__P2 2.0
  325. #define FXAA_QUALITY__P3 2.0
  326. #define FXAA_QUALITY__P4 2.0
  327. #define FXAA_QUALITY__P5 2.0
  328. #define FXAA_QUALITY__P6 4.0
  329. #define FXAA_QUALITY__P7 12.0
  330. #endif
  331. /*============================================================================
  332. FXAA QUALITY - LOW DITHER PRESETS
  333. ============================================================================*/
  334. #if (FXAA_QUALITY__PRESET == 20)
  335. #define FXAA_QUALITY__PS 3
  336. #define FXAA_QUALITY__P0 1.5
  337. #define FXAA_QUALITY__P1 2.0
  338. #define FXAA_QUALITY__P2 8.0
  339. #endif
  340. /*--------------------------------------------------------------------------*/
  341. #if (FXAA_QUALITY__PRESET == 21)
  342. #define FXAA_QUALITY__PS 4
  343. #define FXAA_QUALITY__P0 1.0
  344. #define FXAA_QUALITY__P1 1.5
  345. #define FXAA_QUALITY__P2 2.0
  346. #define FXAA_QUALITY__P3 8.0
  347. #endif
  348. /*--------------------------------------------------------------------------*/
  349. #if (FXAA_QUALITY__PRESET == 22)
  350. #define FXAA_QUALITY__PS 5
  351. #define FXAA_QUALITY__P0 1.0
  352. #define FXAA_QUALITY__P1 1.5
  353. #define FXAA_QUALITY__P2 2.0
  354. #define FXAA_QUALITY__P3 2.0
  355. #define FXAA_QUALITY__P4 8.0
  356. #endif
  357. /*--------------------------------------------------------------------------*/
  358. #if (FXAA_QUALITY__PRESET == 23)
  359. #define FXAA_QUALITY__PS 6
  360. #define FXAA_QUALITY__P0 1.0
  361. #define FXAA_QUALITY__P1 1.5
  362. #define FXAA_QUALITY__P2 2.0
  363. #define FXAA_QUALITY__P3 2.0
  364. #define FXAA_QUALITY__P4 2.0
  365. #define FXAA_QUALITY__P5 8.0
  366. #endif
  367. /*--------------------------------------------------------------------------*/
  368. #if (FXAA_QUALITY__PRESET == 24)
  369. #define FXAA_QUALITY__PS 7
  370. #define FXAA_QUALITY__P0 1.0
  371. #define FXAA_QUALITY__P1 1.5
  372. #define FXAA_QUALITY__P2 2.0
  373. #define FXAA_QUALITY__P3 2.0
  374. #define FXAA_QUALITY__P4 2.0
  375. #define FXAA_QUALITY__P5 3.0
  376. #define FXAA_QUALITY__P6 8.0
  377. #endif
  378. /*--------------------------------------------------------------------------*/
  379. #if (FXAA_QUALITY__PRESET == 25)
  380. #define FXAA_QUALITY__PS 8
  381. #define FXAA_QUALITY__P0 1.0
  382. #define FXAA_QUALITY__P1 1.5
  383. #define FXAA_QUALITY__P2 2.0
  384. #define FXAA_QUALITY__P3 2.0
  385. #define FXAA_QUALITY__P4 2.0
  386. #define FXAA_QUALITY__P5 2.0
  387. #define FXAA_QUALITY__P6 4.0
  388. #define FXAA_QUALITY__P7 8.0
  389. #endif
  390. /*--------------------------------------------------------------------------*/
  391. #if (FXAA_QUALITY__PRESET == 26)
  392. #define FXAA_QUALITY__PS 9
  393. #define FXAA_QUALITY__P0 1.0
  394. #define FXAA_QUALITY__P1 1.5
  395. #define FXAA_QUALITY__P2 2.0
  396. #define FXAA_QUALITY__P3 2.0
  397. #define FXAA_QUALITY__P4 2.0
  398. #define FXAA_QUALITY__P5 2.0
  399. #define FXAA_QUALITY__P6 2.0
  400. #define FXAA_QUALITY__P7 4.0
  401. #define FXAA_QUALITY__P8 8.0
  402. #endif
  403. /*--------------------------------------------------------------------------*/
  404. #if (FXAA_QUALITY__PRESET == 27)
  405. #define FXAA_QUALITY__PS 10
  406. #define FXAA_QUALITY__P0 1.0
  407. #define FXAA_QUALITY__P1 1.5
  408. #define FXAA_QUALITY__P2 2.0
  409. #define FXAA_QUALITY__P3 2.0
  410. #define FXAA_QUALITY__P4 2.0
  411. #define FXAA_QUALITY__P5 2.0
  412. #define FXAA_QUALITY__P6 2.0
  413. #define FXAA_QUALITY__P7 2.0
  414. #define FXAA_QUALITY__P8 4.0
  415. #define FXAA_QUALITY__P9 8.0
  416. #endif
  417. /*--------------------------------------------------------------------------*/
  418. #if (FXAA_QUALITY__PRESET == 28)
  419. #define FXAA_QUALITY__PS 11
  420. #define FXAA_QUALITY__P0 1.0
  421. #define FXAA_QUALITY__P1 1.5
  422. #define FXAA_QUALITY__P2 2.0
  423. #define FXAA_QUALITY__P3 2.0
  424. #define FXAA_QUALITY__P4 2.0
  425. #define FXAA_QUALITY__P5 2.0
  426. #define FXAA_QUALITY__P6 2.0
  427. #define FXAA_QUALITY__P7 2.0
  428. #define FXAA_QUALITY__P8 2.0
  429. #define FXAA_QUALITY__P9 4.0
  430. #define FXAA_QUALITY__P10 8.0
  431. #endif
  432. /*--------------------------------------------------------------------------*/
  433. #if (FXAA_QUALITY__PRESET == 29)
  434. #define FXAA_QUALITY__PS 12
  435. #define FXAA_QUALITY__P0 1.0
  436. #define FXAA_QUALITY__P1 1.5
  437. #define FXAA_QUALITY__P2 2.0
  438. #define FXAA_QUALITY__P3 2.0
  439. #define FXAA_QUALITY__P4 2.0
  440. #define FXAA_QUALITY__P5 2.0
  441. #define FXAA_QUALITY__P6 2.0
  442. #define FXAA_QUALITY__P7 2.0
  443. #define FXAA_QUALITY__P8 2.0
  444. #define FXAA_QUALITY__P9 2.0
  445. #define FXAA_QUALITY__P10 4.0
  446. #define FXAA_QUALITY__P11 8.0
  447. #endif
  448. /*============================================================================
  449. FXAA QUALITY - EXTREME QUALITY
  450. ============================================================================*/
  451. #if (FXAA_QUALITY__PRESET == 39)
  452. #define FXAA_QUALITY__PS 12
  453. #define FXAA_QUALITY__P0 1.0
  454. #define FXAA_QUALITY__P1 1.0
  455. #define FXAA_QUALITY__P2 1.0
  456. #define FXAA_QUALITY__P3 1.0
  457. #define FXAA_QUALITY__P4 1.0
  458. #define FXAA_QUALITY__P5 1.5
  459. #define FXAA_QUALITY__P6 2.0
  460. #define FXAA_QUALITY__P7 2.0
  461. #define FXAA_QUALITY__P8 2.0
  462. #define FXAA_QUALITY__P9 2.0
  463. #define FXAA_QUALITY__P10 4.0
  464. #define FXAA_QUALITY__P11 8.0
  465. #endif
  466. /*============================================================================
  467. API PORTING
  468. ============================================================================*/
  469. #if (FXAA_GLSL_120 == 1) || (FXAA_GLSL_130 == 1)
  470. #define FxaaBool bool
  471. #define FxaaDiscard discard
  472. #define FxaaFloat float
  473. #define FxaaFloat2 vec2
  474. #define FxaaFloat3 vec3
  475. #define FxaaFloat4 vec4
  476. #define FxaaHalf float
  477. #define FxaaHalf2 vec2
  478. #define FxaaHalf3 vec3
  479. #define FxaaHalf4 vec4
  480. #define FxaaInt2 ivec2
  481. #define FxaaSat(x) clamp(x, 0.0, 1.0)
  482. #define FxaaTex sampler2D
  483. #else
  484. #define FxaaBool bool
  485. #define FxaaDiscard clip(-1)
  486. #define FxaaFloat float
  487. #define FxaaFloat2 float2
  488. #define FxaaFloat3 float3
  489. #define FxaaFloat4 float4
  490. #define FxaaHalf half
  491. #define FxaaHalf2 half2
  492. #define FxaaHalf3 half3
  493. #define FxaaHalf4 half4
  494. #define FxaaSat(x) saturate(x)
  495. #endif
  496. /*--------------------------------------------------------------------------*/
  497. #if (FXAA_GLSL_120 == 1)
  498. // Requires,
  499. // #version 120
  500. // And at least,
  501. // #extension GL_EXT_gpu_shader4 : enable
  502. // (or set FXAA_FAST_PIXEL_OFFSET 1 to work like DX9)
  503. #define FxaaTexTop(t, p) texture2DLod(t, p, 0.0)
  504. #if (FXAA_FAST_PIXEL_OFFSET == 1)
  505. #define FxaaTexOff(t, p, o, r) texture2DLodOffset(t, p, 0.0, o)
  506. #else
  507. #define FxaaTexOff(t, p, o, r) texture2DLod(t, p + (o * r), 0.0)
  508. #endif
  509. #if (FXAA_GATHER4_ALPHA == 1)
  510. // use #extension GL_ARB_gpu_shader5 : enable
  511. #define FxaaTexAlpha4(t, p) textureGather(t, p, 3)
  512. #define FxaaTexOffAlpha4(t, p, o) textureGatherOffset(t, p, o, 3)
  513. #define FxaaTexGreen4(t, p) textureGather(t, p, 1)
  514. #define FxaaTexOffGreen4(t, p, o) textureGatherOffset(t, p, o, 1)
  515. #endif
  516. #endif
  517. /*--------------------------------------------------------------------------*/
  518. #if (FXAA_GLSL_130 == 1)
  519. // Requires "#version 130" or better
  520. #define FxaaTexTop(t, p) textureLod(t, p, 0.0)
  521. #define FxaaTexOff(t, p, o, r) textureLodOffset(t, p, 0.0, o)
  522. #if (FXAA_GATHER4_ALPHA == 1)
  523. // use #extension GL_ARB_gpu_shader5 : enable
  524. #define FxaaTexAlpha4(t, p) textureGather(t, p, 3)
  525. #define FxaaTexOffAlpha4(t, p, o) textureGatherOffset(t, p, o, 3)
  526. #define FxaaTexGreen4(t, p) textureGather(t, p, 1)
  527. #define FxaaTexOffGreen4(t, p, o) textureGatherOffset(t, p, o, 1)
  528. #endif
  529. #endif
  530. /*============================================================================
  531. GREEN AS LUMA OPTION SUPPORT FUNCTION
  532. ============================================================================*/
  533. #if (FXAA_GREEN_AS_LUMA == 0)
  534. FxaaFloat FxaaLuma(FxaaFloat4 rgba) { return rgba.w; }
  535. #else
  536. FxaaFloat FxaaLuma(FxaaFloat4 rgba) { return rgba.y; }
  537. #endif
  538. /*============================================================================
  539. FXAA3 QUALITY - PC
  540. ============================================================================*/
  541. #if (FXAA_PC == 1)
  542. /*--------------------------------------------------------------------------*/
  543. FxaaFloat4 FxaaPixelShader(
  544. //
  545. // Use noperspective interpolation here (turn off perspective interpolation).
  546. // {xy} = center of pixel
  547. FxaaFloat2 pos,
  548. //
  549. // Used only for FXAA Console, and not used on the 360 version.
  550. // Use noperspective interpolation here (turn off perspective interpolation).
  551. // {xy__} = upper left of pixel
  552. // {__zw} = lower right of pixel
  553. FxaaFloat4 fxaaConsolePosPos,
  554. //
  555. // Input color texture.
  556. // {rgb_} = color in linear or perceptual color space
  557. // if (FXAA_GREEN_AS_LUMA == 0)
  558. // {___a} = luma in perceptual color space (not linear)
  559. FxaaTex tex,
  560. //
  561. // Only used on the optimized 360 version of FXAA Console.
  562. // For everything but 360, just use the same input here as for "tex".
  563. // For 360, same texture, just alias with a 2nd sampler.
  564. // This sampler needs to have an exponent bias of -1.
  565. FxaaTex fxaaConsole360TexExpBiasNegOne,
  566. //
  567. // Only used on the optimized 360 version of FXAA Console.
  568. // For everything but 360, just use the same input here as for "tex".
  569. // For 360, same texture, just alias with a 3nd sampler.
  570. // This sampler needs to have an exponent bias of -2.
  571. FxaaTex fxaaConsole360TexExpBiasNegTwo,
  572. //
  573. // Only used on FXAA Quality.
  574. // This must be from a constant/uniform.
  575. // {x_} = 1.0/screenWidthInPixels
  576. // {_y} = 1.0/screenHeightInPixels
  577. FxaaFloat2 fxaaQualityRcpFrame,
  578. //
  579. // Only used on FXAA Console.
  580. // This must be from a constant/uniform.
  581. // This effects sub-pixel AA quality and inversely sharpness.
  582. // Where N ranges between,
  583. // N = 0.50 (default)
  584. // N = 0.33 (sharper)
  585. // {x___} = -N/screenWidthInPixels
  586. // {_y__} = -N/screenHeightInPixels
  587. // {__z_} = N/screenWidthInPixels
  588. // {___w} = N/screenHeightInPixels
  589. FxaaFloat4 fxaaConsoleRcpFrameOpt,
  590. //
  591. // Only used on FXAA Console.
  592. // Not used on 360, but used on PS3 and PC.
  593. // This must be from a constant/uniform.
  594. // {x___} = -2.0/screenWidthInPixels
  595. // {_y__} = -2.0/screenHeightInPixels
  596. // {__z_} = 2.0/screenWidthInPixels
  597. // {___w} = 2.0/screenHeightInPixels
  598. FxaaFloat4 fxaaConsoleRcpFrameOpt2,
  599. //
  600. // Only used on FXAA Console.
  601. // Only used on 360 in place of fxaaConsoleRcpFrameOpt2.
  602. // This must be from a constant/uniform.
  603. // {x___} = 8.0/screenWidthInPixels
  604. // {_y__} = 8.0/screenHeightInPixels
  605. // {__z_} = -4.0/screenWidthInPixels
  606. // {___w} = -4.0/screenHeightInPixels
  607. FxaaFloat4 fxaaConsole360RcpFrameOpt2,
  608. //
  609. // Only used on FXAA Quality.
  610. // This used to be the FXAA_QUALITY__SUBPIX define.
  611. // It is here now to allow easier tuning.
  612. // Choose the amount of sub-pixel aliasing removal.
  613. // This can effect sharpness.
  614. // 1.00 - upper limit (softer)
  615. // 0.75 - default amount of filtering
  616. // 0.50 - lower limit (sharper, less sub-pixel aliasing removal)
  617. // 0.25 - almost off
  618. // 0.00 - completely off
  619. FxaaFloat fxaaQualitySubpix,
  620. //
  621. // Only used on FXAA Quality.
  622. // This used to be the FXAA_QUALITY__EDGE_THRESHOLD define.
  623. // It is here now to allow easier tuning.
  624. // The minimum amount of local contrast required to apply algorithm.
  625. // 0.333 - too little (faster)
  626. // 0.250 - low quality
  627. // 0.166 - default
  628. // 0.125 - high quality
  629. // 0.063 - overkill (slower)
  630. FxaaFloat fxaaQualityEdgeThreshold,
  631. //
  632. // Only used on FXAA Quality.
  633. // This used to be the FXAA_QUALITY__EDGE_THRESHOLD_MIN define.
  634. // It is here now to allow easier tuning.
  635. // Trims the algorithm from processing darks.
  636. // 0.0833 - upper limit (default, the start of visible unfiltered edges)
  637. // 0.0625 - high quality (faster)
  638. // 0.0312 - visible limit (slower)
  639. // Special notes when using FXAA_GREEN_AS_LUMA,
  640. // Likely want to set this to zero.
  641. // As colors that are mostly not-green
  642. // will appear very dark in the green channel!
  643. // Tune by looking at mostly non-green content,
  644. // then start at zero and increase until aliasing is a problem.
  645. FxaaFloat fxaaQualityEdgeThresholdMin,
  646. //
  647. // Only used on FXAA Console.
  648. // This used to be the FXAA_CONSOLE__EDGE_SHARPNESS define.
  649. // It is here now to allow easier tuning.
  650. // This does not effect PS3, as this needs to be compiled in.
  651. // Use FXAA_CONSOLE__PS3_EDGE_SHARPNESS for PS3.
  652. // Due to the PS3 being ALU bound,
  653. // there are only three safe values here: 2 and 4 and 8.
  654. // These options use the shaders ability to a free *|/ by 2|4|8.
  655. // For all other platforms can be a non-power of two.
  656. // 8.0 is sharper (default!!!)
  657. // 4.0 is softer
  658. // 2.0 is really soft (good only for vector graphics inputs)
  659. FxaaFloat fxaaConsoleEdgeSharpness,
  660. //
  661. // Only used on FXAA Console.
  662. // This used to be the FXAA_CONSOLE__EDGE_THRESHOLD define.
  663. // It is here now to allow easier tuning.
  664. // This does not effect PS3, as this needs to be compiled in.
  665. // Use FXAA_CONSOLE__PS3_EDGE_THRESHOLD for PS3.
  666. // Due to the PS3 being ALU bound,
  667. // there are only two safe values here: 1/4 and 1/8.
  668. // These options use the shaders ability to a free *|/ by 2|4|8.
  669. // The console setting has a different mapping than the quality setting.
  670. // Other platforms can use other values.
  671. // 0.125 leaves less aliasing, but is softer (default!!!)
  672. // 0.25 leaves more aliasing, and is sharper
  673. FxaaFloat fxaaConsoleEdgeThreshold,
  674. //
  675. // Only used on FXAA Console.
  676. // This used to be the FXAA_CONSOLE__EDGE_THRESHOLD_MIN define.
  677. // It is here now to allow easier tuning.
  678. // Trims the algorithm from processing darks.
  679. // The console setting has a different mapping than the quality setting.
  680. // This only applies when FXAA_EARLY_EXIT is 1.
  681. // This does not apply to PS3,
  682. // PS3 was simplified to avoid more shader instructions.
  683. // 0.06 - faster but more aliasing in darks
  684. // 0.05 - default
  685. // 0.04 - slower and less aliasing in darks
  686. // Special notes when using FXAA_GREEN_AS_LUMA,
  687. // Likely want to set this to zero.
  688. // As colors that are mostly not-green
  689. // will appear very dark in the green channel!
  690. // Tune by looking at mostly non-green content,
  691. // then start at zero and increase until aliasing is a problem.
  692. FxaaFloat fxaaConsoleEdgeThresholdMin,
  693. //
  694. // Extra constants for 360 FXAA Console only.
  695. // Use zeros or anything else for other platforms.
  696. // These must be in physical constant registers and NOT immedates.
  697. // Immedates will result in compiler un-optimizing.
  698. // {xyzw} = float4(1.0, -1.0, 0.25, -0.25)
  699. FxaaFloat4 fxaaConsole360ConstDir
  700. ) {
  701. /*--------------------------------------------------------------------------*/
  702. FxaaFloat2 posM;
  703. posM.x = pos.x;
  704. posM.y = pos.y;
  705. #if (FXAA_GATHER4_ALPHA == 1)
  706. #if (FXAA_DISCARD == 0)
  707. FxaaFloat4 rgbyM = FxaaTexTop(tex, posM);
  708. #if (FXAA_GREEN_AS_LUMA == 0)
  709. #define lumaM rgbyM.w
  710. #else
  711. #define lumaM rgbyM.y
  712. #endif
  713. #endif
  714. #if (FXAA_GREEN_AS_LUMA == 0)
  715. FxaaFloat4 luma4A = FxaaTexAlpha4(tex, posM);
  716. FxaaFloat4 luma4B = FxaaTexOffAlpha4(tex, posM, FxaaInt2(-1, -1));
  717. #else
  718. FxaaFloat4 luma4A = FxaaTexGreen4(tex, posM);
  719. FxaaFloat4 luma4B = FxaaTexOffGreen4(tex, posM, FxaaInt2(-1, -1));
  720. #endif
  721. #if (FXAA_DISCARD == 1)
  722. #define lumaM luma4A.w
  723. #endif
  724. #define lumaE luma4A.z
  725. #define lumaS luma4A.x
  726. #define lumaSE luma4A.y
  727. #define lumaNW luma4B.w
  728. #define lumaN luma4B.z
  729. #define lumaW luma4B.x
  730. #else
  731. FxaaFloat4 rgbyM = FxaaTexTop(tex, posM);
  732. #if (FXAA_GREEN_AS_LUMA == 0)
  733. #define lumaM rgbyM.w
  734. #else
  735. #define lumaM rgbyM.y
  736. #endif
  737. FxaaFloat lumaS = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2( 0, 1), fxaaQualityRcpFrame.xy));
  738. FxaaFloat lumaE = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2( 1, 0), fxaaQualityRcpFrame.xy));
  739. FxaaFloat lumaN = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2( 0,-1), fxaaQualityRcpFrame.xy));
  740. FxaaFloat lumaW = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2(-1, 0), fxaaQualityRcpFrame.xy));
  741. #endif
  742. /*--------------------------------------------------------------------------*/
  743. FxaaFloat maxSM = max(lumaS, lumaM);
  744. FxaaFloat minSM = min(lumaS, lumaM);
  745. FxaaFloat maxESM = max(lumaE, maxSM);
  746. FxaaFloat minESM = min(lumaE, minSM);
  747. FxaaFloat maxWN = max(lumaN, lumaW);
  748. FxaaFloat minWN = min(lumaN, lumaW);
  749. FxaaFloat rangeMax = max(maxWN, maxESM);
  750. FxaaFloat rangeMin = min(minWN, minESM);
  751. FxaaFloat rangeMaxScaled = rangeMax * fxaaQualityEdgeThreshold;
  752. FxaaFloat range = rangeMax - rangeMin;
  753. FxaaFloat rangeMaxClamped = max(fxaaQualityEdgeThresholdMin, rangeMaxScaled);
  754. FxaaBool earlyExit = range < rangeMaxClamped;
  755. /*--------------------------------------------------------------------------*/
  756. if(earlyExit)
  757. #if (FXAA_DISCARD == 1)
  758. FxaaDiscard;
  759. #else
  760. return rgbyM;
  761. #endif
  762. /*--------------------------------------------------------------------------*/
  763. #if (FXAA_GATHER4_ALPHA == 0)
  764. FxaaFloat lumaNW = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2(-1,-1), fxaaQualityRcpFrame.xy));
  765. FxaaFloat lumaSE = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2( 1, 1), fxaaQualityRcpFrame.xy));
  766. FxaaFloat lumaNE = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2( 1,-1), fxaaQualityRcpFrame.xy));
  767. FxaaFloat lumaSW = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2(-1, 1), fxaaQualityRcpFrame.xy));
  768. #else
  769. FxaaFloat lumaNE = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2(1, -1), fxaaQualityRcpFrame.xy));
  770. FxaaFloat lumaSW = FxaaLuma(FxaaTexOff(tex, posM, FxaaInt2(-1, 1), fxaaQualityRcpFrame.xy));
  771. #endif
  772. /*--------------------------------------------------------------------------*/
  773. FxaaFloat lumaNS = lumaN + lumaS;
  774. FxaaFloat lumaWE = lumaW + lumaE;
  775. FxaaFloat subpixRcpRange = 1.0/range;
  776. FxaaFloat subpixNSWE = lumaNS + lumaWE;
  777. FxaaFloat edgeHorz1 = (-2.0 * lumaM) + lumaNS;
  778. FxaaFloat edgeVert1 = (-2.0 * lumaM) + lumaWE;
  779. /*--------------------------------------------------------------------------*/
  780. FxaaFloat lumaNESE = lumaNE + lumaSE;
  781. FxaaFloat lumaNWNE = lumaNW + lumaNE;
  782. FxaaFloat edgeHorz2 = (-2.0 * lumaE) + lumaNESE;
  783. FxaaFloat edgeVert2 = (-2.0 * lumaN) + lumaNWNE;
  784. /*--------------------------------------------------------------------------*/
  785. FxaaFloat lumaNWSW = lumaNW + lumaSW;
  786. FxaaFloat lumaSWSE = lumaSW + lumaSE;
  787. FxaaFloat edgeHorz4 = (abs(edgeHorz1) * 2.0) + abs(edgeHorz2);
  788. FxaaFloat edgeVert4 = (abs(edgeVert1) * 2.0) + abs(edgeVert2);
  789. FxaaFloat edgeHorz3 = (-2.0 * lumaW) + lumaNWSW;
  790. FxaaFloat edgeVert3 = (-2.0 * lumaS) + lumaSWSE;
  791. FxaaFloat edgeHorz = abs(edgeHorz3) + edgeHorz4;
  792. FxaaFloat edgeVert = abs(edgeVert3) + edgeVert4;
  793. /*--------------------------------------------------------------------------*/
  794. FxaaFloat subpixNWSWNESE = lumaNWSW + lumaNESE;
  795. FxaaFloat lengthSign = fxaaQualityRcpFrame.x;
  796. FxaaBool horzSpan = edgeHorz >= edgeVert;
  797. FxaaFloat subpixA = subpixNSWE * 2.0 + subpixNWSWNESE;
  798. /*--------------------------------------------------------------------------*/
  799. if(!horzSpan) lumaN = lumaW;
  800. if(!horzSpan) lumaS = lumaE;
  801. if(horzSpan) lengthSign = fxaaQualityRcpFrame.y;
  802. FxaaFloat subpixB = (subpixA * (1.0/12.0)) - lumaM;
  803. /*--------------------------------------------------------------------------*/
  804. FxaaFloat gradientN = lumaN - lumaM;
  805. FxaaFloat gradientS = lumaS - lumaM;
  806. FxaaFloat lumaNN = lumaN + lumaM;
  807. FxaaFloat lumaSS = lumaS + lumaM;
  808. FxaaBool pairN = abs(gradientN) >= abs(gradientS);
  809. FxaaFloat gradient = max(abs(gradientN), abs(gradientS));
  810. if(pairN) lengthSign = -lengthSign;
  811. FxaaFloat subpixC = FxaaSat(abs(subpixB) * subpixRcpRange);
  812. /*--------------------------------------------------------------------------*/
  813. FxaaFloat2 posB;
  814. posB.x = posM.x;
  815. posB.y = posM.y;
  816. FxaaFloat2 offNP;
  817. offNP.x = (!horzSpan) ? 0.0 : fxaaQualityRcpFrame.x;
  818. offNP.y = ( horzSpan) ? 0.0 : fxaaQualityRcpFrame.y;
  819. if(!horzSpan) posB.x += lengthSign * 0.5;
  820. if( horzSpan) posB.y += lengthSign * 0.5;
  821. /*--------------------------------------------------------------------------*/
  822. FxaaFloat2 posN;
  823. posN.x = posB.x - offNP.x * FXAA_QUALITY__P0;
  824. posN.y = posB.y - offNP.y * FXAA_QUALITY__P0;
  825. FxaaFloat2 posP;
  826. posP.x = posB.x + offNP.x * FXAA_QUALITY__P0;
  827. posP.y = posB.y + offNP.y * FXAA_QUALITY__P0;
  828. FxaaFloat subpixD = ((-2.0)*subpixC) + 3.0;
  829. FxaaFloat lumaEndN = FxaaLuma(FxaaTexTop(tex, posN));
  830. FxaaFloat subpixE = subpixC * subpixC;
  831. FxaaFloat lumaEndP = FxaaLuma(FxaaTexTop(tex, posP));
  832. /*--------------------------------------------------------------------------*/
  833. if(!pairN) lumaNN = lumaSS;
  834. FxaaFloat gradientScaled = gradient * 1.0/4.0;
  835. FxaaFloat lumaMM = lumaM - lumaNN * 0.5;
  836. FxaaFloat subpixF = subpixD * subpixE;
  837. FxaaBool lumaMLTZero = lumaMM < 0.0;
  838. /*--------------------------------------------------------------------------*/
  839. lumaEndN -= lumaNN * 0.5;
  840. lumaEndP -= lumaNN * 0.5;
  841. FxaaBool doneN = abs(lumaEndN) >= gradientScaled;
  842. FxaaBool doneP = abs(lumaEndP) >= gradientScaled;
  843. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P1;
  844. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P1;
  845. FxaaBool doneNP = (!doneN) || (!doneP);
  846. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P1;
  847. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P1;
  848. /*--------------------------------------------------------------------------*/
  849. if(doneNP) {
  850. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  851. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  852. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  853. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  854. doneN = abs(lumaEndN) >= gradientScaled;
  855. doneP = abs(lumaEndP) >= gradientScaled;
  856. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P2;
  857. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P2;
  858. doneNP = (!doneN) || (!doneP);
  859. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P2;
  860. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P2;
  861. /*--------------------------------------------------------------------------*/
  862. #if (FXAA_QUALITY__PS > 3)
  863. if(doneNP) {
  864. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  865. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  866. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  867. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  868. doneN = abs(lumaEndN) >= gradientScaled;
  869. doneP = abs(lumaEndP) >= gradientScaled;
  870. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P3;
  871. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P3;
  872. doneNP = (!doneN) || (!doneP);
  873. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P3;
  874. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P3;
  875. /*--------------------------------------------------------------------------*/
  876. #if (FXAA_QUALITY__PS > 4)
  877. if(doneNP) {
  878. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  879. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  880. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  881. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  882. doneN = abs(lumaEndN) >= gradientScaled;
  883. doneP = abs(lumaEndP) >= gradientScaled;
  884. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P4;
  885. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P4;
  886. doneNP = (!doneN) || (!doneP);
  887. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P4;
  888. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P4;
  889. /*--------------------------------------------------------------------------*/
  890. #if (FXAA_QUALITY__PS > 5)
  891. if(doneNP) {
  892. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  893. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  894. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  895. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  896. doneN = abs(lumaEndN) >= gradientScaled;
  897. doneP = abs(lumaEndP) >= gradientScaled;
  898. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P5;
  899. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P5;
  900. doneNP = (!doneN) || (!doneP);
  901. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P5;
  902. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P5;
  903. /*--------------------------------------------------------------------------*/
  904. #if (FXAA_QUALITY__PS > 6)
  905. if(doneNP) {
  906. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  907. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  908. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  909. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  910. doneN = abs(lumaEndN) >= gradientScaled;
  911. doneP = abs(lumaEndP) >= gradientScaled;
  912. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P6;
  913. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P6;
  914. doneNP = (!doneN) || (!doneP);
  915. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P6;
  916. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P6;
  917. /*--------------------------------------------------------------------------*/
  918. #if (FXAA_QUALITY__PS > 7)
  919. if(doneNP) {
  920. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  921. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  922. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  923. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  924. doneN = abs(lumaEndN) >= gradientScaled;
  925. doneP = abs(lumaEndP) >= gradientScaled;
  926. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P7;
  927. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P7;
  928. doneNP = (!doneN) || (!doneP);
  929. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P7;
  930. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P7;
  931. /*--------------------------------------------------------------------------*/
  932. #if (FXAA_QUALITY__PS > 8)
  933. if(doneNP) {
  934. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  935. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  936. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  937. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  938. doneN = abs(lumaEndN) >= gradientScaled;
  939. doneP = abs(lumaEndP) >= gradientScaled;
  940. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P8;
  941. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P8;
  942. doneNP = (!doneN) || (!doneP);
  943. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P8;
  944. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P8;
  945. /*--------------------------------------------------------------------------*/
  946. #if (FXAA_QUALITY__PS > 9)
  947. if(doneNP) {
  948. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  949. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  950. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  951. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  952. doneN = abs(lumaEndN) >= gradientScaled;
  953. doneP = abs(lumaEndP) >= gradientScaled;
  954. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P9;
  955. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P9;
  956. doneNP = (!doneN) || (!doneP);
  957. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P9;
  958. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P9;
  959. /*--------------------------------------------------------------------------*/
  960. #if (FXAA_QUALITY__PS > 10)
  961. if(doneNP) {
  962. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  963. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  964. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  965. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  966. doneN = abs(lumaEndN) >= gradientScaled;
  967. doneP = abs(lumaEndP) >= gradientScaled;
  968. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P10;
  969. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P10;
  970. doneNP = (!doneN) || (!doneP);
  971. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P10;
  972. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P10;
  973. /*--------------------------------------------------------------------------*/
  974. #if (FXAA_QUALITY__PS > 11)
  975. if(doneNP) {
  976. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  977. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  978. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  979. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  980. doneN = abs(lumaEndN) >= gradientScaled;
  981. doneP = abs(lumaEndP) >= gradientScaled;
  982. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P11;
  983. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P11;
  984. doneNP = (!doneN) || (!doneP);
  985. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P11;
  986. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P11;
  987. /*--------------------------------------------------------------------------*/
  988. #if (FXAA_QUALITY__PS > 12)
  989. if(doneNP) {
  990. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(tex, posN.xy));
  991. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(tex, posP.xy));
  992. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  993. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  994. doneN = abs(lumaEndN) >= gradientScaled;
  995. doneP = abs(lumaEndP) >= gradientScaled;
  996. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P12;
  997. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P12;
  998. doneNP = (!doneN) || (!doneP);
  999. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P12;
  1000. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P12;
  1001. /*--------------------------------------------------------------------------*/
  1002. }
  1003. #endif
  1004. /*--------------------------------------------------------------------------*/
  1005. }
  1006. #endif
  1007. /*--------------------------------------------------------------------------*/
  1008. }
  1009. #endif
  1010. /*--------------------------------------------------------------------------*/
  1011. }
  1012. #endif
  1013. /*--------------------------------------------------------------------------*/
  1014. }
  1015. #endif
  1016. /*--------------------------------------------------------------------------*/
  1017. }
  1018. #endif
  1019. /*--------------------------------------------------------------------------*/
  1020. }
  1021. #endif
  1022. /*--------------------------------------------------------------------------*/
  1023. }
  1024. #endif
  1025. /*--------------------------------------------------------------------------*/
  1026. }
  1027. #endif
  1028. /*--------------------------------------------------------------------------*/
  1029. }
  1030. #endif
  1031. /*--------------------------------------------------------------------------*/
  1032. }
  1033. /*--------------------------------------------------------------------------*/
  1034. FxaaFloat dstN = posM.x - posN.x;
  1035. FxaaFloat dstP = posP.x - posM.x;
  1036. if(!horzSpan) dstN = posM.y - posN.y;
  1037. if(!horzSpan) dstP = posP.y - posM.y;
  1038. /*--------------------------------------------------------------------------*/
  1039. FxaaBool goodSpanN = (lumaEndN < 0.0) != lumaMLTZero;
  1040. FxaaFloat spanLength = (dstP + dstN);
  1041. FxaaBool goodSpanP = (lumaEndP < 0.0) != lumaMLTZero;
  1042. FxaaFloat spanLengthRcp = 1.0/spanLength;
  1043. /*--------------------------------------------------------------------------*/
  1044. FxaaBool directionN = dstN < dstP;
  1045. FxaaFloat dst = min(dstN, dstP);
  1046. FxaaBool goodSpan = directionN ? goodSpanN : goodSpanP;
  1047. FxaaFloat subpixG = subpixF * subpixF;
  1048. FxaaFloat pixelOffset = (dst * (-spanLengthRcp)) + 0.5;
  1049. FxaaFloat subpixH = subpixG * fxaaQualitySubpix;
  1050. /*--------------------------------------------------------------------------*/
  1051. FxaaFloat pixelOffsetGood = goodSpan ? pixelOffset : 0.0;
  1052. FxaaFloat pixelOffsetSubpix = max(pixelOffsetGood, subpixH);
  1053. if(!horzSpan) posM.x += pixelOffsetSubpix * lengthSign;
  1054. if( horzSpan) posM.y += pixelOffsetSubpix * lengthSign;
  1055. #if (FXAA_DISCARD == 1)
  1056. return FxaaTexTop(tex, posM);
  1057. #else
  1058. return FxaaFloat4(FxaaTexTop(tex, posM).xyz, lumaM);
  1059. #endif
  1060. }
  1061. /*==========================================================================*/
  1062. #endif
  1063. vec4 mainImage(vec2 fragCoord)
  1064. {
  1065. vec2 rcpFrame = 1./invResolution.xy;
  1066. vec2 uv2 = fragCoord.xy / invResolution.xy;
  1067. float fxaaQualitySubpix = 0.75; // [0..1], default 0.75
  1068. float fxaaQualityEdgeThreshold = 0.166; // [0.125..0.33], default 0.166
  1069. float fxaaQualityEdgeThresholdMin = 0.02;//0.0625; // ?
  1070. vec4 dummy4 = vec4(0.0,0.0,0.0,0.0);
  1071. float dummy1 = 0.0;
  1072. vec4 col = FxaaPixelShader(uv2, dummy4,
  1073. inputTexture, inputTexture, inputTexture,
  1074. rcpFrame, dummy4, dummy4, dummy4,
  1075. fxaaQualitySubpix, fxaaQualityEdgeThreshold,
  1076. fxaaQualityEdgeThresholdMin,
  1077. dummy1, dummy1, dummy1, dummy4);
  1078. vec4 fragColor = vec4( col.xyz, 1. );
  1079. return fragColor;
  1080. }
  1081. void main()
  1082. {
  1083. ivec2 loc = ivec2(gl_GlobalInvocationID.x * 4, gl_GlobalInvocationID.y * 4);
  1084. for(int i = 0; i < 4; i++)
  1085. {
  1086. for(int j = 0; j < 4; j++)
  1087. {
  1088. ivec2 texelCoord = ivec2(loc.x + i, loc.y + j);
  1089. vec4 outColor = mainImage(texelCoord + vec2(0.5));
  1090. imageStore(imgOutput, texelCoord, outColor);
  1091. }
  1092. }
  1093. }