PPFXAA.bsl 37 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934
  1. #include "$ENGINE$\PPBase.bslinc"
  2. technique PPFXAA
  3. {
  4. mixin PPBase;
  5. code
  6. {
  7. //----------------------------------------------------------------------------------
  8. // File: FXAA\media/FXAA.hlsl
  9. // SDK Version: v1.2
  10. // Email: [email protected]
  11. // Site: http://developer.nvidia.com/
  12. //
  13. // Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
  14. //
  15. // Redistribution and use in source and binary forms, with or without
  16. // modification, are permitted provided that the following conditions
  17. // are met:
  18. // * Redistributions of source code must retain the above copyright
  19. // notice, this list of conditions and the following disclaimer.
  20. // * Redistributions in binary form must reproduce the above copyright
  21. // notice, this list of conditions and the following disclaimer in the
  22. // documentation and/or other materials provided with the distribution.
  23. // * Neither the name of NVIDIA CORPORATION nor the names of its
  24. // contributors may be used to endorse or promote products derived
  25. // from this software without specific prior written permission.
  26. //
  27. // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ``AS IS'' AND ANY
  28. // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  29. // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
  30. // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  31. // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  32. // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  33. // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  34. // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
  35. // OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  36. // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  37. // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  38. //
  39. //----------------------------------------------------------------------------------
  40. /*============================================================================
  41. NVIDIA FXAA 3.11 by TIMOTHY LOTTES
  42. ------------------------------------------------------------------------------
  43. INTEGRATION CHECKLIST
  44. ------------------------------------------------------------------------------
  45. (1.)
  46. In the shader source, setup defines for the desired configuration.
  47. When providing multiple shaders (for different presets),
  48. simply setup the defines differently in multiple files.
  49. Example,
  50. #define FXAA_PC 1
  51. #define FXAA_HLSL_5 1
  52. #define FXAA_QUALITY__PRESET 12
  53. Or,
  54. #define FXAA_360 1
  55. Or,
  56. #define FXAA_PS3 1
  57. Etc.
  58. (2.)
  59. Then include this file,
  60. #include "Fxaa3_11.h"
  61. (3.)
  62. Then call the FXAA pixel shader from within your desired shader.
  63. Look at the FXAA Quality FxaaPixelShader() for docs on inputs.
  64. As for FXAA 3.11 all inputs for all shaders are the same
  65. to enable easy porting between platforms.
  66. return FxaaPixelShader(...);
  67. (4.)
  68. Insure pass prior to FXAA outputs RGBL (see next section).
  69. Or use,
  70. #define FXAA_GREEN_AS_LUMA 1
  71. (5.)
  72. Setup engine to provide the following constants
  73. which are used in the FxaaPixelShader() inputs,
  74. FxaaFloat2 fxaaQualityRcpFrame,
  75. FxaaFloat fxaaQualitySubpix,
  76. FxaaFloat fxaaQualityEdgeThreshold,
  77. FxaaFloat fxaaQualityEdgeThresholdMin,
  78. Look at the FXAA Quality FxaaPixelShader() for docs on inputs.
  79. (6.)
  80. Have FXAA vertex shader run as a full screen triangle,
  81. and output "pos" and "fxaaConsolePosPos"
  82. such that inputs in the pixel shader provide,
  83. // {xy} = center of pixel
  84. FxaaFloat2 pos,
  85. // {xy__} = upper left of pixel
  86. // {__zw} = lower right of pixel
  87. FxaaFloat4 fxaaConsolePosPos,
  88. (7.)
  89. Insure the texture sampler(s) used by FXAA are set to bilinear filtering.
  90. ------------------------------------------------------------------------------
  91. INTEGRATION - RGBL AND COLORSPACE
  92. ------------------------------------------------------------------------------
  93. FXAA3 requires RGBL as input unless the following is set,
  94. #define FXAA_GREEN_AS_LUMA 1
  95. In which case the engine uses green in place of luma,
  96. and requires RGB input is in a non-linear colorspace.
  97. RGB should be LDR (low dynamic range).
  98. Specifically do FXAA after tonemapping.
  99. RGB data as returned by a texture fetch can be non-linear,
  100. or linear when FXAA_GREEN_AS_LUMA is not set.
  101. Note an "sRGB format" texture counts as linear,
  102. because the result of a texture fetch is linear data.
  103. Regular "RGBA8" textures in the sRGB colorspace are non-linear.
  104. If FXAA_GREEN_AS_LUMA is not set,
  105. luma must be stored in the alpha channel prior to running FXAA.
  106. This luma should be in a perceptual space (could be gamma 2.0).
  107. Example pass before FXAA where output is gamma 2.0 encoded,
  108. color.rgb = ToneMap(color.rgb); // linear color output
  109. color.rgb = sqrt(color.rgb); // gamma 2.0 color output
  110. return color;
  111. To use FXAA,
  112. color.rgb = ToneMap(color.rgb); // linear color output
  113. color.rgb = sqrt(color.rgb); // gamma 2.0 color output
  114. color.a = dot(color.rgb, FxaaFloat3(0.299, 0.587, 0.114)); // compute luma
  115. return color;
  116. Another example where output is linear encoded,
  117. say for instance writing to an sRGB formated render target,
  118. where the render target does the conversion back to sRGB after blending,
  119. color.rgb = ToneMap(color.rgb); // linear color output
  120. return color;
  121. To use FXAA,
  122. color.rgb = ToneMap(color.rgb); // linear color output
  123. color.a = sqrt(dot(color.rgb, FxaaFloat3(0.299, 0.587, 0.114))); // compute luma
  124. return color;
  125. Getting luma correct is required for the algorithm to work correctly.
  126. ------------------------------------------------------------------------------
  127. BEING LINEARLY CORRECT?
  128. ------------------------------------------------------------------------------
  129. Applying FXAA to a framebuffer with linear RGB color will look worse.
  130. This is very counter intuitive, but happends to be true in this case.
  131. The reason is because dithering artifacts will be more visiable
  132. in a linear colorspace.
  133. ------------------------------------------------------------------------------
  134. COMPLEX INTEGRATION
  135. ------------------------------------------------------------------------------
  136. Q. What if the engine is blending into RGB before wanting to run FXAA?
  137. A. In the last opaque pass prior to FXAA,
  138. have the pass write out luma into alpha.
  139. Then blend into RGB only.
  140. FXAA should be able to run ok
  141. assuming the blending pass did not any add aliasing.
  142. This should be the common case for particles and common blending passes.
  143. A. Or use FXAA_GREEN_AS_LUMA.
  144. ============================================================================*/
  145. /*============================================================================
  146. INTEGRATION KNOBS
  147. ============================================================================*/
  148. #ifndef FXAA_GREEN_AS_LUMA
  149. //
  150. // For those using non-linear color,
  151. // and either not able to get luma in alpha, or not wanting to,
  152. // this enables FXAA to run using green as a proxy for luma.
  153. // So with this enabled, no need to pack luma in alpha.
  154. //
  155. // This will turn off AA on anything which lacks some amount of green.
  156. // Pure red and blue or combination of only R and B, will get no AA.
  157. //
  158. // Might want to lower the settings for both,
  159. // fxaaConsoleEdgeThresholdMin
  160. // fxaaQualityEdgeThresholdMin
  161. // In order to insure AA does not get turned off on colors
  162. // which contain a minor amount of green.
  163. //
  164. // 1 = On.
  165. // 0 = Off.
  166. //
  167. #define FXAA_GREEN_AS_LUMA 1
  168. #endif
  169. /*--------------------------------------------------------------------------*/
  170. #ifndef FXAA_DISCARD
  171. //
  172. // Only valid for PC OpenGL currently.
  173. // Probably will not work when FXAA_GREEN_AS_LUMA = 1.
  174. //
  175. // 1 = Use discard on pixels which don't need AA.
  176. // For APIs which enable concurrent TEX+ROP from same surface.
  177. // 0 = Return unchanged color on pixels which don't need AA.
  178. //
  179. #define FXAA_DISCARD 0
  180. #endif
  181. /*--------------------------------------------------------------------------*/
  182. #ifndef FXAA_GATHER4_ALPHA
  183. #define FXAA_GATHER4_ALPHA 1
  184. #endif
  185. /*============================================================================
  186. FXAA QUALITY - TUNING KNOBS
  187. ------------------------------------------------------------------------------
  188. NOTE the other tuning knobs are now in the shader function inputs!
  189. ============================================================================*/
  190. #ifndef FXAA_QUALITY__PRESET
  191. //
  192. // Choose the quality preset.
  193. // This needs to be compiled into the shader as it effects code.
  194. // Best option to include multiple presets is to
  195. // in each shader define the preset, then include this file.
  196. //
  197. // OPTIONS
  198. // -----------------------------------------------------------------------
  199. // 10 to 15 - default medium dither (10=fastest, 15=highest quality)
  200. // 20 to 29 - less dither, more expensive (20=fastest, 29=highest quality)
  201. // 39 - no dither, very expensive
  202. //
  203. // NOTES
  204. // -----------------------------------------------------------------------
  205. // 12 = slightly faster then FXAA 3.9 and higher edge quality (default)
  206. // 13 = about same speed as FXAA 3.9 and better than 12
  207. // 23 = closest to FXAA 3.9 visually and performance wise
  208. // _ = the lowest digit is directly related to performance
  209. // _ = the highest digit is directly related to style
  210. //
  211. #define FXAA_QUALITY__PRESET 12
  212. #endif
  213. /*============================================================================
  214. FXAA QUALITY - PRESETS
  215. ============================================================================*/
  216. /*============================================================================
  217. FXAA QUALITY - MEDIUM DITHER PRESETS
  218. ============================================================================*/
  219. #if (FXAA_QUALITY__PRESET == 10)
  220. #define FXAA_QUALITY__PS 3
  221. #define FXAA_QUALITY__P0 1.5
  222. #define FXAA_QUALITY__P1 3.0
  223. #define FXAA_QUALITY__P2 12.0
  224. #endif
  225. /*--------------------------------------------------------------------------*/
  226. #if (FXAA_QUALITY__PRESET == 11)
  227. #define FXAA_QUALITY__PS 4
  228. #define FXAA_QUALITY__P0 1.0
  229. #define FXAA_QUALITY__P1 1.5
  230. #define FXAA_QUALITY__P2 3.0
  231. #define FXAA_QUALITY__P3 12.0
  232. #endif
  233. /*--------------------------------------------------------------------------*/
  234. #if (FXAA_QUALITY__PRESET == 12)
  235. #define FXAA_QUALITY__PS 5
  236. #define FXAA_QUALITY__P0 1.0
  237. #define FXAA_QUALITY__P1 1.5
  238. #define FXAA_QUALITY__P2 2.0
  239. #define FXAA_QUALITY__P3 4.0
  240. #define FXAA_QUALITY__P4 12.0
  241. #endif
  242. /*--------------------------------------------------------------------------*/
  243. #if (FXAA_QUALITY__PRESET == 13)
  244. #define FXAA_QUALITY__PS 6
  245. #define FXAA_QUALITY__P0 1.0
  246. #define FXAA_QUALITY__P1 1.5
  247. #define FXAA_QUALITY__P2 2.0
  248. #define FXAA_QUALITY__P3 2.0
  249. #define FXAA_QUALITY__P4 4.0
  250. #define FXAA_QUALITY__P5 12.0
  251. #endif
  252. /*--------------------------------------------------------------------------*/
  253. #if (FXAA_QUALITY__PRESET == 14)
  254. #define FXAA_QUALITY__PS 7
  255. #define FXAA_QUALITY__P0 1.0
  256. #define FXAA_QUALITY__P1 1.5
  257. #define FXAA_QUALITY__P2 2.0
  258. #define FXAA_QUALITY__P3 2.0
  259. #define FXAA_QUALITY__P4 2.0
  260. #define FXAA_QUALITY__P5 4.0
  261. #define FXAA_QUALITY__P6 12.0
  262. #endif
  263. /*--------------------------------------------------------------------------*/
  264. #if (FXAA_QUALITY__PRESET == 15)
  265. #define FXAA_QUALITY__PS 8
  266. #define FXAA_QUALITY__P0 1.0
  267. #define FXAA_QUALITY__P1 1.5
  268. #define FXAA_QUALITY__P2 2.0
  269. #define FXAA_QUALITY__P3 2.0
  270. #define FXAA_QUALITY__P4 2.0
  271. #define FXAA_QUALITY__P5 2.0
  272. #define FXAA_QUALITY__P6 4.0
  273. #define FXAA_QUALITY__P7 12.0
  274. #endif
  275. /*============================================================================
  276. FXAA QUALITY - LOW DITHER PRESETS
  277. ============================================================================*/
  278. #if (FXAA_QUALITY__PRESET == 20)
  279. #define FXAA_QUALITY__PS 3
  280. #define FXAA_QUALITY__P0 1.5
  281. #define FXAA_QUALITY__P1 2.0
  282. #define FXAA_QUALITY__P2 8.0
  283. #endif
  284. /*--------------------------------------------------------------------------*/
  285. #if (FXAA_QUALITY__PRESET == 21)
  286. #define FXAA_QUALITY__PS 4
  287. #define FXAA_QUALITY__P0 1.0
  288. #define FXAA_QUALITY__P1 1.5
  289. #define FXAA_QUALITY__P2 2.0
  290. #define FXAA_QUALITY__P3 8.0
  291. #endif
  292. /*--------------------------------------------------------------------------*/
  293. #if (FXAA_QUALITY__PRESET == 22)
  294. #define FXAA_QUALITY__PS 5
  295. #define FXAA_QUALITY__P0 1.0
  296. #define FXAA_QUALITY__P1 1.5
  297. #define FXAA_QUALITY__P2 2.0
  298. #define FXAA_QUALITY__P3 2.0
  299. #define FXAA_QUALITY__P4 8.0
  300. #endif
  301. /*--------------------------------------------------------------------------*/
  302. #if (FXAA_QUALITY__PRESET == 23)
  303. #define FXAA_QUALITY__PS 6
  304. #define FXAA_QUALITY__P0 1.0
  305. #define FXAA_QUALITY__P1 1.5
  306. #define FXAA_QUALITY__P2 2.0
  307. #define FXAA_QUALITY__P3 2.0
  308. #define FXAA_QUALITY__P4 2.0
  309. #define FXAA_QUALITY__P5 8.0
  310. #endif
  311. /*--------------------------------------------------------------------------*/
  312. #if (FXAA_QUALITY__PRESET == 24)
  313. #define FXAA_QUALITY__PS 7
  314. #define FXAA_QUALITY__P0 1.0
  315. #define FXAA_QUALITY__P1 1.5
  316. #define FXAA_QUALITY__P2 2.0
  317. #define FXAA_QUALITY__P3 2.0
  318. #define FXAA_QUALITY__P4 2.0
  319. #define FXAA_QUALITY__P5 3.0
  320. #define FXAA_QUALITY__P6 8.0
  321. #endif
  322. /*--------------------------------------------------------------------------*/
  323. #if (FXAA_QUALITY__PRESET == 25)
  324. #define FXAA_QUALITY__PS 8
  325. #define FXAA_QUALITY__P0 1.0
  326. #define FXAA_QUALITY__P1 1.5
  327. #define FXAA_QUALITY__P2 2.0
  328. #define FXAA_QUALITY__P3 2.0
  329. #define FXAA_QUALITY__P4 2.0
  330. #define FXAA_QUALITY__P5 2.0
  331. #define FXAA_QUALITY__P6 4.0
  332. #define FXAA_QUALITY__P7 8.0
  333. #endif
  334. /*--------------------------------------------------------------------------*/
  335. #if (FXAA_QUALITY__PRESET == 26)
  336. #define FXAA_QUALITY__PS 9
  337. #define FXAA_QUALITY__P0 1.0
  338. #define FXAA_QUALITY__P1 1.5
  339. #define FXAA_QUALITY__P2 2.0
  340. #define FXAA_QUALITY__P3 2.0
  341. #define FXAA_QUALITY__P4 2.0
  342. #define FXAA_QUALITY__P5 2.0
  343. #define FXAA_QUALITY__P6 2.0
  344. #define FXAA_QUALITY__P7 4.0
  345. #define FXAA_QUALITY__P8 8.0
  346. #endif
  347. /*--------------------------------------------------------------------------*/
  348. #if (FXAA_QUALITY__PRESET == 27)
  349. #define FXAA_QUALITY__PS 10
  350. #define FXAA_QUALITY__P0 1.0
  351. #define FXAA_QUALITY__P1 1.5
  352. #define FXAA_QUALITY__P2 2.0
  353. #define FXAA_QUALITY__P3 2.0
  354. #define FXAA_QUALITY__P4 2.0
  355. #define FXAA_QUALITY__P5 2.0
  356. #define FXAA_QUALITY__P6 2.0
  357. #define FXAA_QUALITY__P7 2.0
  358. #define FXAA_QUALITY__P8 4.0
  359. #define FXAA_QUALITY__P9 8.0
  360. #endif
  361. /*--------------------------------------------------------------------------*/
  362. #if (FXAA_QUALITY__PRESET == 28)
  363. #define FXAA_QUALITY__PS 11
  364. #define FXAA_QUALITY__P0 1.0
  365. #define FXAA_QUALITY__P1 1.5
  366. #define FXAA_QUALITY__P2 2.0
  367. #define FXAA_QUALITY__P3 2.0
  368. #define FXAA_QUALITY__P4 2.0
  369. #define FXAA_QUALITY__P5 2.0
  370. #define FXAA_QUALITY__P6 2.0
  371. #define FXAA_QUALITY__P7 2.0
  372. #define FXAA_QUALITY__P8 2.0
  373. #define FXAA_QUALITY__P9 4.0
  374. #define FXAA_QUALITY__P10 8.0
  375. #endif
  376. /*--------------------------------------------------------------------------*/
  377. #if (FXAA_QUALITY__PRESET == 29)
  378. #define FXAA_QUALITY__PS 12
  379. #define FXAA_QUALITY__P0 1.0
  380. #define FXAA_QUALITY__P1 1.5
  381. #define FXAA_QUALITY__P2 2.0
  382. #define FXAA_QUALITY__P3 2.0
  383. #define FXAA_QUALITY__P4 2.0
  384. #define FXAA_QUALITY__P5 2.0
  385. #define FXAA_QUALITY__P6 2.0
  386. #define FXAA_QUALITY__P7 2.0
  387. #define FXAA_QUALITY__P8 2.0
  388. #define FXAA_QUALITY__P9 2.0
  389. #define FXAA_QUALITY__P10 4.0
  390. #define FXAA_QUALITY__P11 8.0
  391. #endif
  392. /*============================================================================
  393. FXAA QUALITY - EXTREME QUALITY
  394. ============================================================================*/
  395. #if (FXAA_QUALITY__PRESET == 39)
  396. #define FXAA_QUALITY__PS 12
  397. #define FXAA_QUALITY__P0 1.0
  398. #define FXAA_QUALITY__P1 1.0
  399. #define FXAA_QUALITY__P2 1.0
  400. #define FXAA_QUALITY__P3 1.0
  401. #define FXAA_QUALITY__P4 1.0
  402. #define FXAA_QUALITY__P5 1.5
  403. #define FXAA_QUALITY__P6 2.0
  404. #define FXAA_QUALITY__P7 2.0
  405. #define FXAA_QUALITY__P8 2.0
  406. #define FXAA_QUALITY__P9 2.0
  407. #define FXAA_QUALITY__P10 4.0
  408. #define FXAA_QUALITY__P11 8.0
  409. #endif
  410. SamplerState gInputSamp;
  411. Texture2D gInputTex;
  412. /*============================================================================
  413. API PORTING
  414. ============================================================================*/
  415. #define FxaaBool bool
  416. #define FxaaDiscard clip(-1)
  417. #define FxaaFloat float
  418. #define FxaaFloat2 float2
  419. #define FxaaFloat3 float3
  420. #define FxaaFloat4 float4
  421. #define FxaaHalf half
  422. #define FxaaHalf2 half2
  423. #define FxaaHalf3 half3
  424. #define FxaaHalf4 half4
  425. #define FxaaSat(x) saturate(x)
  426. #define FxaaInt2 int2
  427. #define FxaaTexTop(p) gInputTex.SampleLevel(gInputSamp, p, 0.0)
  428. #define FxaaTexOff(p, o, r) gInputTex.SampleLevel(gInputSamp, p, 0.0, o)
  429. #define FxaaTexAlpha4(p) gInputTex.GatherAlpha(gInputSamp, p)
  430. #define FxaaTexOffAlpha4(p, o) gInputTex.GatherAlpha(gInputSamp, p, o)
  431. #define FxaaTexGreen4(p) gInputTex.GatherGreen(gInputSamp, p)
  432. #define FxaaTexOffGreen4(p, o) gInputTex.GatherGreen(gInputSamp, p, o)
  433. /*============================================================================
  434. GREEN AS LUMA OPTION SUPPORT FUNCTION
  435. ============================================================================*/
  436. #if (FXAA_GREEN_AS_LUMA == 0)
  437. FxaaFloat FxaaLuma(FxaaFloat4 rgba) { return rgba.w; }
  438. #else
  439. FxaaFloat FxaaLuma(FxaaFloat4 rgba) { return rgba.y; }
  440. #endif
  441. /*============================================================================
  442. FXAA3 QUALITY - PC
  443. ============================================================================*/
  444. FxaaFloat4 FxaaPixelShader(
  445. //
  446. // Use noperspective interpolation here (turn off perspective interpolation).
  447. // {xy} = center of pixel
  448. FxaaFloat2 pos,
  449. //
  450. // Only used on FXAA Quality.
  451. // This must be from a constant/uniform.
  452. // {x_} = 1.0/screenWidthInPixels
  453. // {_y} = 1.0/screenHeightInPixels
  454. FxaaFloat2 fxaaQualityRcpFrame,
  455. //
  456. // Only used on FXAA Quality.
  457. // This used to be the FXAA_QUALITY__SUBPIX define.
  458. // It is here now to allow easier tuning.
  459. // Choose the amount of sub-pixel aliasing removal.
  460. // This can effect sharpness.
  461. // 1.00 - upper limit (softer)
  462. // 0.75 - default amount of filtering
  463. // 0.50 - lower limit (sharper, less sub-pixel aliasing removal)
  464. // 0.25 - almost off
  465. // 0.00 - completely off
  466. FxaaFloat fxaaQualitySubpix,
  467. //
  468. // Only used on FXAA Quality.
  469. // This used to be the FXAA_QUALITY__EDGE_THRESHOLD define.
  470. // It is here now to allow easier tuning.
  471. // The minimum amount of local contrast required to apply algorithm.
  472. // 0.333 - too little (faster)
  473. // 0.250 - low quality
  474. // 0.166 - default
  475. // 0.125 - high quality
  476. // 0.063 - overkill (slower)
  477. FxaaFloat fxaaQualityEdgeThreshold,
  478. //
  479. // Only used on FXAA Quality.
  480. // This used to be the FXAA_QUALITY__EDGE_THRESHOLD_MIN define.
  481. // It is here now to allow easier tuning.
  482. // Trims the algorithm from processing darks.
  483. // 0.0833 - upper limit (default, the start of visible unfiltered edges)
  484. // 0.0625 - high quality (faster)
  485. // 0.0312 - visible limit (slower)
  486. // Special notes when using FXAA_GREEN_AS_LUMA,
  487. // Likely want to set this to zero.
  488. // As colors that are mostly not-green
  489. // will appear very dark in the green channel!
  490. // Tune by looking at mostly non-green content,
  491. // then start at zero and increase until aliasing is a problem.
  492. FxaaFloat fxaaQualityEdgeThresholdMin
  493. ) {
  494. /*--------------------------------------------------------------------------*/
  495. FxaaFloat2 posM;
  496. posM.x = pos.x;
  497. posM.y = pos.y;
  498. #if (FXAA_GATHER4_ALPHA == 1)
  499. #if (FXAA_DISCARD == 0)
  500. FxaaFloat4 rgbyM = FxaaTexTop(posM);
  501. #if (FXAA_GREEN_AS_LUMA == 0)
  502. #define lumaM rgbyM.w
  503. #else
  504. #define lumaM rgbyM.y
  505. #endif
  506. #endif
  507. #if (FXAA_GREEN_AS_LUMA == 0)
  508. FxaaFloat4 luma4A = FxaaTexAlpha4(posM);
  509. FxaaFloat4 luma4B = FxaaTexOffAlpha4(posM, FxaaInt2(-1, -1));
  510. #else
  511. FxaaFloat4 luma4A = FxaaTexGreen4(posM);
  512. FxaaFloat4 luma4B = FxaaTexOffGreen4(posM, FxaaInt2(-1, -1));
  513. #endif
  514. #if (FXAA_DISCARD == 1)
  515. #define lumaM luma4A.w
  516. #endif
  517. #define lumaE luma4A.z
  518. #define lumaS luma4A.x
  519. #define lumaSE luma4A.y
  520. #define lumaNW luma4B.w
  521. #define lumaN luma4B.z
  522. #define lumaW luma4B.x
  523. #else
  524. FxaaFloat4 rgbyM = FxaaTexTop(posM);
  525. #if (FXAA_GREEN_AS_LUMA == 0)
  526. #define lumaM rgbyM.w
  527. #else
  528. #define lumaM rgbyM.y
  529. #endif
  530. FxaaFloat lumaS = FxaaLuma(FxaaTexOff(posM, FxaaInt2( 0, 1), fxaaQualityRcpFrame.xy));
  531. FxaaFloat lumaE = FxaaLuma(FxaaTexOff(posM, FxaaInt2( 1, 0), fxaaQualityRcpFrame.xy));
  532. FxaaFloat lumaN = FxaaLuma(FxaaTexOff(posM, FxaaInt2( 0,-1), fxaaQualityRcpFrame.xy));
  533. FxaaFloat lumaW = FxaaLuma(FxaaTexOff(posM, FxaaInt2(-1, 0), fxaaQualityRcpFrame.xy));
  534. #endif
  535. /*--------------------------------------------------------------------------*/
  536. FxaaFloat maxSM = max(lumaS, lumaM);
  537. FxaaFloat minSM = min(lumaS, lumaM);
  538. FxaaFloat maxESM = max(lumaE, maxSM);
  539. FxaaFloat minESM = min(lumaE, minSM);
  540. FxaaFloat maxWN = max(lumaN, lumaW);
  541. FxaaFloat minWN = min(lumaN, lumaW);
  542. FxaaFloat rangeMax = max(maxWN, maxESM);
  543. FxaaFloat rangeMin = min(minWN, minESM);
  544. FxaaFloat rangeMaxScaled = rangeMax * fxaaQualityEdgeThreshold;
  545. FxaaFloat range = rangeMax - rangeMin;
  546. FxaaFloat rangeMaxClamped = max(fxaaQualityEdgeThresholdMin, rangeMaxScaled);
  547. FxaaBool earlyExit = range < rangeMaxClamped;
  548. /*--------------------------------------------------------------------------*/
  549. if(earlyExit)
  550. #if (FXAA_DISCARD == 1)
  551. FxaaDiscard;
  552. #else
  553. return rgbyM;
  554. #endif
  555. /*--------------------------------------------------------------------------*/
  556. #if (FXAA_GATHER4_ALPHA == 0)
  557. FxaaFloat lumaNW = FxaaLuma(FxaaTexOff(posM, FxaaInt2(-1,-1), fxaaQualityRcpFrame.xy));
  558. FxaaFloat lumaSE = FxaaLuma(FxaaTexOff(posM, FxaaInt2( 1, 1), fxaaQualityRcpFrame.xy));
  559. FxaaFloat lumaNE = FxaaLuma(FxaaTexOff(posM, FxaaInt2( 1,-1), fxaaQualityRcpFrame.xy));
  560. FxaaFloat lumaSW = FxaaLuma(FxaaTexOff(posM, FxaaInt2(-1, 1), fxaaQualityRcpFrame.xy));
  561. #else
  562. FxaaFloat lumaNE = FxaaLuma(FxaaTexOff(posM, FxaaInt2(1, -1), fxaaQualityRcpFrame.xy));
  563. FxaaFloat lumaSW = FxaaLuma(FxaaTexOff(posM, FxaaInt2(-1, 1), fxaaQualityRcpFrame.xy));
  564. #endif
  565. /*--------------------------------------------------------------------------*/
  566. FxaaFloat lumaNS = lumaN + lumaS;
  567. FxaaFloat lumaWE = lumaW + lumaE;
  568. FxaaFloat subpixRcpRange = 1.0/range;
  569. FxaaFloat subpixNSWE = lumaNS + lumaWE;
  570. FxaaFloat edgeHorz1 = (-2.0 * lumaM) + lumaNS;
  571. FxaaFloat edgeVert1 = (-2.0 * lumaM) + lumaWE;
  572. /*--------------------------------------------------------------------------*/
  573. FxaaFloat lumaNESE = lumaNE + lumaSE;
  574. FxaaFloat lumaNWNE = lumaNW + lumaNE;
  575. FxaaFloat edgeHorz2 = (-2.0 * lumaE) + lumaNESE;
  576. FxaaFloat edgeVert2 = (-2.0 * lumaN) + lumaNWNE;
  577. /*--------------------------------------------------------------------------*/
  578. FxaaFloat lumaNWSW = lumaNW + lumaSW;
  579. FxaaFloat lumaSWSE = lumaSW + lumaSE;
  580. FxaaFloat edgeHorz4 = (abs(edgeHorz1) * 2.0) + abs(edgeHorz2);
  581. FxaaFloat edgeVert4 = (abs(edgeVert1) * 2.0) + abs(edgeVert2);
  582. FxaaFloat edgeHorz3 = (-2.0 * lumaW) + lumaNWSW;
  583. FxaaFloat edgeVert3 = (-2.0 * lumaS) + lumaSWSE;
  584. FxaaFloat edgeHorz = abs(edgeHorz3) + edgeHorz4;
  585. FxaaFloat edgeVert = abs(edgeVert3) + edgeVert4;
  586. /*--------------------------------------------------------------------------*/
  587. FxaaFloat subpixNWSWNESE = lumaNWSW + lumaNESE;
  588. FxaaFloat lengthSign = fxaaQualityRcpFrame.x;
  589. FxaaBool horzSpan = edgeHorz >= edgeVert;
  590. FxaaFloat subpixA = subpixNSWE * 2.0 + subpixNWSWNESE;
  591. /*--------------------------------------------------------------------------*/
  592. if(!horzSpan) lumaN = lumaW;
  593. if(!horzSpan) lumaS = lumaE;
  594. if(horzSpan) lengthSign = fxaaQualityRcpFrame.y;
  595. FxaaFloat subpixB = (subpixA * (1.0/12.0)) - lumaM;
  596. /*--------------------------------------------------------------------------*/
  597. FxaaFloat gradientN = lumaN - lumaM;
  598. FxaaFloat gradientS = lumaS - lumaM;
  599. FxaaFloat lumaNN = lumaN + lumaM;
  600. FxaaFloat lumaSS = lumaS + lumaM;
  601. FxaaBool pairN = abs(gradientN) >= abs(gradientS);
  602. FxaaFloat gradient = max(abs(gradientN), abs(gradientS));
  603. if(pairN) lengthSign = -lengthSign;
  604. FxaaFloat subpixC = FxaaSat(abs(subpixB) * subpixRcpRange);
  605. /*--------------------------------------------------------------------------*/
  606. FxaaFloat2 posB;
  607. posB.x = posM.x;
  608. posB.y = posM.y;
  609. FxaaFloat2 offNP;
  610. offNP.x = (!horzSpan) ? 0.0 : fxaaQualityRcpFrame.x;
  611. offNP.y = ( horzSpan) ? 0.0 : fxaaQualityRcpFrame.y;
  612. if(!horzSpan) posB.x += lengthSign * 0.5;
  613. if( horzSpan) posB.y += lengthSign * 0.5;
  614. /*--------------------------------------------------------------------------*/
  615. FxaaFloat2 posN;
  616. posN.x = posB.x - offNP.x * FXAA_QUALITY__P0;
  617. posN.y = posB.y - offNP.y * FXAA_QUALITY__P0;
  618. FxaaFloat2 posP;
  619. posP.x = posB.x + offNP.x * FXAA_QUALITY__P0;
  620. posP.y = posB.y + offNP.y * FXAA_QUALITY__P0;
  621. FxaaFloat subpixD = ((-2.0)*subpixC) + 3.0;
  622. FxaaFloat lumaEndN = FxaaLuma(FxaaTexTop(posN));
  623. FxaaFloat subpixE = subpixC * subpixC;
  624. FxaaFloat lumaEndP = FxaaLuma(FxaaTexTop(posP));
  625. /*--------------------------------------------------------------------------*/
  626. if(!pairN) lumaNN = lumaSS;
  627. FxaaFloat gradientScaled = gradient * 1.0/4.0;
  628. FxaaFloat lumaMM = lumaM - lumaNN * 0.5;
  629. FxaaFloat subpixF = subpixD * subpixE;
  630. FxaaBool lumaMLTZero = lumaMM < 0.0;
  631. /*--------------------------------------------------------------------------*/
  632. lumaEndN -= lumaNN * 0.5;
  633. lumaEndP -= lumaNN * 0.5;
  634. FxaaBool doneN = abs(lumaEndN) >= gradientScaled;
  635. FxaaBool doneP = abs(lumaEndP) >= gradientScaled;
  636. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P1;
  637. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P1;
  638. FxaaBool doneNP = (!doneN) || (!doneP);
  639. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P1;
  640. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P1;
  641. /*--------------------------------------------------------------------------*/
  642. if(doneNP) {
  643. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  644. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  645. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  646. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  647. doneN = abs(lumaEndN) >= gradientScaled;
  648. doneP = abs(lumaEndP) >= gradientScaled;
  649. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P2;
  650. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P2;
  651. doneNP = (!doneN) || (!doneP);
  652. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P2;
  653. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P2;
  654. /*--------------------------------------------------------------------------*/
  655. #if (FXAA_QUALITY__PS > 3)
  656. if(doneNP) {
  657. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  658. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  659. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  660. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  661. doneN = abs(lumaEndN) >= gradientScaled;
  662. doneP = abs(lumaEndP) >= gradientScaled;
  663. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P3;
  664. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P3;
  665. doneNP = (!doneN) || (!doneP);
  666. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P3;
  667. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P3;
  668. /*--------------------------------------------------------------------------*/
  669. #if (FXAA_QUALITY__PS > 4)
  670. if(doneNP) {
  671. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  672. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  673. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  674. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  675. doneN = abs(lumaEndN) >= gradientScaled;
  676. doneP = abs(lumaEndP) >= gradientScaled;
  677. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P4;
  678. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P4;
  679. doneNP = (!doneN) || (!doneP);
  680. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P4;
  681. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P4;
  682. /*--------------------------------------------------------------------------*/
  683. #if (FXAA_QUALITY__PS > 5)
  684. if(doneNP) {
  685. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  686. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  687. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  688. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  689. doneN = abs(lumaEndN) >= gradientScaled;
  690. doneP = abs(lumaEndP) >= gradientScaled;
  691. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P5;
  692. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P5;
  693. doneNP = (!doneN) || (!doneP);
  694. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P5;
  695. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P5;
  696. /*--------------------------------------------------------------------------*/
  697. #if (FXAA_QUALITY__PS > 6)
  698. if(doneNP) {
  699. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  700. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  701. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  702. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  703. doneN = abs(lumaEndN) >= gradientScaled;
  704. doneP = abs(lumaEndP) >= gradientScaled;
  705. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P6;
  706. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P6;
  707. doneNP = (!doneN) || (!doneP);
  708. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P6;
  709. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P6;
  710. /*--------------------------------------------------------------------------*/
  711. #if (FXAA_QUALITY__PS > 7)
  712. if(doneNP) {
  713. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  714. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  715. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  716. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  717. doneN = abs(lumaEndN) >= gradientScaled;
  718. doneP = abs(lumaEndP) >= gradientScaled;
  719. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P7;
  720. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P7;
  721. doneNP = (!doneN) || (!doneP);
  722. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P7;
  723. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P7;
  724. /*--------------------------------------------------------------------------*/
  725. #if (FXAA_QUALITY__PS > 8)
  726. if(doneNP) {
  727. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  728. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  729. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  730. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  731. doneN = abs(lumaEndN) >= gradientScaled;
  732. doneP = abs(lumaEndP) >= gradientScaled;
  733. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P8;
  734. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P8;
  735. doneNP = (!doneN) || (!doneP);
  736. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P8;
  737. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P8;
  738. /*--------------------------------------------------------------------------*/
  739. #if (FXAA_QUALITY__PS > 9)
  740. if(doneNP) {
  741. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  742. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  743. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  744. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  745. doneN = abs(lumaEndN) >= gradientScaled;
  746. doneP = abs(lumaEndP) >= gradientScaled;
  747. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P9;
  748. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P9;
  749. doneNP = (!doneN) || (!doneP);
  750. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P9;
  751. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P9;
  752. /*--------------------------------------------------------------------------*/
  753. #if (FXAA_QUALITY__PS > 10)
  754. if(doneNP) {
  755. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  756. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  757. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  758. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  759. doneN = abs(lumaEndN) >= gradientScaled;
  760. doneP = abs(lumaEndP) >= gradientScaled;
  761. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P10;
  762. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P10;
  763. doneNP = (!doneN) || (!doneP);
  764. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P10;
  765. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P10;
  766. /*--------------------------------------------------------------------------*/
  767. #if (FXAA_QUALITY__PS > 11)
  768. if(doneNP) {
  769. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  770. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  771. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  772. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  773. doneN = abs(lumaEndN) >= gradientScaled;
  774. doneP = abs(lumaEndP) >= gradientScaled;
  775. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P11;
  776. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P11;
  777. doneNP = (!doneN) || (!doneP);
  778. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P11;
  779. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P11;
  780. /*--------------------------------------------------------------------------*/
  781. #if (FXAA_QUALITY__PS > 12)
  782. if(doneNP) {
  783. if(!doneN) lumaEndN = FxaaLuma(FxaaTexTop(posN.xy));
  784. if(!doneP) lumaEndP = FxaaLuma(FxaaTexTop(posP.xy));
  785. if(!doneN) lumaEndN = lumaEndN - lumaNN * 0.5;
  786. if(!doneP) lumaEndP = lumaEndP - lumaNN * 0.5;
  787. doneN = abs(lumaEndN) >= gradientScaled;
  788. doneP = abs(lumaEndP) >= gradientScaled;
  789. if(!doneN) posN.x -= offNP.x * FXAA_QUALITY__P12;
  790. if(!doneN) posN.y -= offNP.y * FXAA_QUALITY__P12;
  791. doneNP = (!doneN) || (!doneP);
  792. if(!doneP) posP.x += offNP.x * FXAA_QUALITY__P12;
  793. if(!doneP) posP.y += offNP.y * FXAA_QUALITY__P12;
  794. /*--------------------------------------------------------------------------*/
  795. }
  796. #endif
  797. /*--------------------------------------------------------------------------*/
  798. }
  799. #endif
  800. /*--------------------------------------------------------------------------*/
  801. }
  802. #endif
  803. /*--------------------------------------------------------------------------*/
  804. }
  805. #endif
  806. /*--------------------------------------------------------------------------*/
  807. }
  808. #endif
  809. /*--------------------------------------------------------------------------*/
  810. }
  811. #endif
  812. /*--------------------------------------------------------------------------*/
  813. }
  814. #endif
  815. /*--------------------------------------------------------------------------*/
  816. }
  817. #endif
  818. /*--------------------------------------------------------------------------*/
  819. }
  820. #endif
  821. /*--------------------------------------------------------------------------*/
  822. }
  823. #endif
  824. /*--------------------------------------------------------------------------*/
  825. }
  826. /*--------------------------------------------------------------------------*/
  827. FxaaFloat dstN = posM.x - posN.x;
  828. FxaaFloat dstP = posP.x - posM.x;
  829. if(!horzSpan) dstN = posM.y - posN.y;
  830. if(!horzSpan) dstP = posP.y - posM.y;
  831. /*--------------------------------------------------------------------------*/
  832. FxaaBool goodSpanN = (lumaEndN < 0.0) != lumaMLTZero;
  833. FxaaFloat spanLength = (dstP + dstN);
  834. FxaaBool goodSpanP = (lumaEndP < 0.0) != lumaMLTZero;
  835. FxaaFloat spanLengthRcp = 1.0/spanLength;
  836. /*--------------------------------------------------------------------------*/
  837. FxaaBool directionN = dstN < dstP;
  838. FxaaFloat dst = min(dstN, dstP);
  839. FxaaBool goodSpan = directionN ? goodSpanN : goodSpanP;
  840. FxaaFloat subpixG = subpixF * subpixF;
  841. FxaaFloat pixelOffset = (dst * (-spanLengthRcp)) + 0.5;
  842. FxaaFloat subpixH = subpixG * fxaaQualitySubpix;
  843. /*--------------------------------------------------------------------------*/
  844. FxaaFloat pixelOffsetGood = goodSpan ? pixelOffset : 0.0;
  845. FxaaFloat pixelOffsetSubpix = max(pixelOffsetGood, subpixH);
  846. if(!horzSpan) posM.x += pixelOffsetSubpix * lengthSign;
  847. if( horzSpan) posM.y += pixelOffsetSubpix * lengthSign;
  848. #if (FXAA_DISCARD == 1)
  849. return FxaaTexTop(posM);
  850. #else
  851. return FxaaFloat4(FxaaTexTop(posM).xyz, lumaM);
  852. #endif
  853. }
  854. /*==========================================================================*/
  855. [internal]
  856. cbuffer Input
  857. {
  858. float2 gInvTexSize;
  859. }
  860. float4 fsmain(VStoFS input) : SV_Target0
  861. {
  862. return FxaaPixelShader(input.uv0, gInvTexSize, 0.75f, 0.166f, 0.0833f);
  863. }
  864. };
  865. };