Advertisement
Guest User

Reshade_Modified_quInt_dof

a guest
Jul 21st, 2019
334
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 23.68 KB | None | 0 0
  1. /*=============================================================================
  2.  
  3. ReShade 4 effect file
  4. github.com/martymcmodding
  5.  
  6. Support me:
  7. paypal.me/mcflypg
  8. patreon.com/mcflypg
  9.  
  10. Advanced Depth of Field "ADOF"
  11. by Marty McFly / P.Gilcher
  12. part of qUINT shader library for ReShade 3
  13.  
  14. CC BY-NC-ND 3.0 licensed.
  15.  
  16. =============================================================================*/
  17.  
  18. /*=============================================================================
  19. Preprocessor settings
  20. =============================================================================*/
  21.  
  22. //------------------------------------------------------------------
  23. //Enables partial occlusion of bokeh disc at screen corners
  24. #ifndef ADOF_OPTICAL_VIGNETTE_ENABLE
  25. #define ADOF_OPTICAL_VIGNETTE_ENABLE 0 //[0 or 1]
  26. #endif
  27. //------------------------------------------------------------------
  28. //Enables chromatic aberration at bokeh shape borders.
  29. #ifndef ADOF_CHROMATIC_ABERRATION_ENABLE
  30. #define ADOF_CHROMATIC_ABERRATION_ENABLE 1 //[0 or 1]
  31. #endif
  32.  
  33. /*=============================================================================
  34. UI Uniforms
  35. =============================================================================*/
  36.  
  37. uniform bool bADOF_AutofocusEnable <
  38. ui_type = "bool";
  39. ui_label = "Enable Autofocus";
  40. ui_tooltip = "Enables automated focus calculation.";
  41. ui_category = "Focusing";
  42. > = true;
  43.  
  44. uniform float2 fADOF_AutofocusCenter <
  45. ui_type = "drag";
  46. ui_min = 0.0; ui_max = 1.0;
  47. ui_label = "Autofocus Center";
  48. ui_tooltip = "X and Y coordinates of autofocus center. Axes start from upper left screen corner.";
  49. ui_category = "Focusing";
  50. > = float2(0.5, 0.5);
  51.  
  52. uniform float fADOF_AutofocusRadius <
  53. ui_type = "drag";
  54. ui_min = 0.0;
  55. ui_max = 1.0;
  56. ui_label = "Autofocus sample radius";
  57. ui_tooltip = "Radius of area contributing to focus calculation.";
  58. ui_category = "Focusing";
  59. > = 0.6;
  60.  
  61. uniform float fADOF_AutofocusSpeed <
  62. ui_type = "drag";
  63. ui_min = 0.05;
  64. ui_max = 1.0;
  65. ui_label = "Autofocus Adjustment Speed";
  66. ui_tooltip = "Adjustment speed of autofocus on focus change";
  67. ui_category = "Focusing";
  68. > = 0.1;
  69.  
  70. uniform float fADOF_ManualfocusDepth <
  71. ui_type = "drag";
  72. ui_min = 0.0;
  73. ui_max = 1.0;
  74. ui_label = "Manual focus depth";
  75. ui_tooltip = "Manually adjusted static focus depth, disable autofocus to use it.";
  76. ui_category = "Focusing";
  77. > = 0.001;
  78.  
  79. uniform float fADOF_NearBlurCurve <
  80. ui_type = "drag";
  81. ui_min = 0.5;
  82. ui_max = 6.0;
  83. ui_label = "Near blur curve";
  84. ui_category = "Focusing";
  85. > = 6.0;
  86.  
  87. uniform float fADOF_FarBlurCurve <
  88. ui_type = "drag";
  89. ui_min = 0.5;
  90. ui_max = 6.0;
  91. ui_label = "Far blur curve";
  92. ui_category = "Focusing";
  93. > = 1.5;
  94.  
  95. uniform float fADOF_HyperFocus <
  96. ui_type = "drag";
  97. ui_min = 0.0;
  98. ui_max = 1.0;
  99. ui_label = "Hyperfocal depth distance";
  100. ui_category = "Focusing";
  101. > = 0.10;
  102.  
  103. uniform float fADOF_RenderResolutionMult <
  104. ui_type = "drag";
  105. ui_min = 0.5;
  106. ui_max = 1.0;
  107. ui_label = "Size Scale";
  108. ui_tooltip = "Resolution Scale of bokeh blur. 0.5 means 1/2 screen width and height.";
  109. ui_category = "Blur & Quality";
  110. > = 0.5;
  111.  
  112. uniform float fADOF_ShapeRadius <
  113. ui_type = "drag";
  114. ui_min = 0.0;
  115. ui_max = 100.0;
  116. ui_label = "Bokeh Maximal Blur Size";
  117. ui_tooltip = "Blur size of areas entirely out of focus.";
  118. ui_category = "Blur & Quality";
  119. > = 20.5;
  120.  
  121. uniform float fADOF_SmootheningAmount <
  122. ui_type = "drag";
  123. ui_min = 0.0;
  124. ui_max = 20.0;
  125. ui_label = "Gaussian blur width";
  126. ui_tooltip = "Width of gaussian blur after bokeh filter.";
  127. ui_category = "Blur & Quality";
  128. > = 4.0;
  129.  
  130. uniform float fADOF_BokehIntensity <
  131. ui_type = "drag";
  132. ui_min = 0.0;
  133. ui_max = 1.0;
  134. ui_label = "Bokeh Intensity";
  135. ui_tooltip = "Intensity of bokeh discs.";
  136. ui_category = "Bokeh";
  137. > = 0.3;
  138.  
  139. uniform int iADOF_ShapeVertices <
  140. ui_type = "drag";
  141. ui_min = 3;
  142. ui_max = 9;
  143. ui_label = "Bokeh shape vertices";
  144. ui_tooltip = "Vertices of bokeh kernel. 5 = pentagon, 6 = hexagon etc.";
  145. ui_category = "Bokeh";
  146. > = 6;
  147.  
  148. uniform int iADOF_ShapeQuality <
  149. ui_type = "drag";
  150. ui_min = 2;
  151. ui_max = 25;
  152. ui_label = "Bokeh shape quality";
  153. ui_category = "Bokeh";
  154. > = 5;
  155.  
  156. uniform float fADOF_ShapeCurvatureAmount <
  157. ui_type = "drag";
  158. ui_min = -1.0;
  159. ui_max = 1.0;
  160. ui_label = "Bokeh shape roundness";
  161. ui_tooltip = "Roundness of bokeh kernel. 1.0 = circle, 0.0 = polygon.";
  162. ui_category = "Bokeh";
  163. > = 1.0;
  164.  
  165. uniform float fADOF_ShapeRotation <
  166. ui_type = "drag";
  167. ui_min = 0.0;
  168. ui_max = 360.0;
  169. ui_label = "Bokeh shape rotation";
  170. ui_category = "Bokeh";
  171. > = 0.0;
  172.  
  173. uniform float fADOF_ShapeAnamorphRatio <
  174. ui_type = "drag";
  175. ui_min = 0.0;
  176. ui_max = 1.0;
  177. ui_label = "Bokeh shape aspect ratio";
  178. ui_category = "Bokeh";
  179. > = 1.0;
  180.  
  181. #if(ADOF_OPTICAL_VIGNETTE_ENABLE != 0)
  182. uniform float fADOF_ShapeVignetteCurve <
  183. ui_type = "drag";
  184. ui_min = 0.5;
  185. ui_max = 2.5;
  186. ui_label = "Bokeh shape vignette curve";
  187. ui_category = "Bokeh";
  188. > = 0.75;
  189.  
  190. uniform float fADOF_ShapeVignetteAmount <
  191. ui_type = "drag";
  192. ui_min = 0.0;
  193. ui_max = 2.0;
  194. ui_label = "Bokeh shape vignette amount";
  195. ui_category = "Bokeh";
  196. > = 1.0;
  197. #endif
  198.  
  199. #if(ADOF_CHROMATIC_ABERRATION_ENABLE != 0)
  200. uniform float fADOF_ShapeChromaAmount <
  201. ui_type = "drag";
  202. ui_min = -1.0;
  203. ui_max = 1.0;
  204. ui_label = "Shape chromatic aberration amount";
  205. ui_category = "Chromatic Aberration";
  206. > = -0.1;
  207.  
  208. uniform int iADOF_ShapeChromaMode <
  209. ui_type = "drag";
  210. ui_min = 0;
  211. ui_max = 2;
  212. ui_label = "Shape chromatic aberration type";
  213. ui_category = "Chromatic Aberration";
  214. > = 2;
  215. #endif
  216.  
  217. /*=============================================================================
  218. Textures, Samplers, Globals
  219. =============================================================================*/
  220.  
  221. #define DISCRADIUS_RESOLUTION_BOUNDARY_LOWER 0.25//1.0 //used for blending blurred scene.
  222. #define DISCRADIUS_RESOLUTION_BOUNDARY_UPPER 2.0//6.0 //used for blending blurred scene.
  223. #define DISCRADIUS_RESOLUTION_BOUNDARY_CURVE 0.5 //used for blending blurred scene.
  224. #define FPS_HAND_BLUR_CUTOFF_DIST 0.3353 //fps hand depth (x10.000), change if you perceive blurred fps weapons.
  225. #define FPS_HAND_BLUR_CUTOFF_CHECK 0 //blur = max if depth > hand depth, else 0, useful for tweaking above param
  226. #define GAUSSIAN_BUILDUP_MULT 4.0 //value of x -> gaussian reaches max radius at |CoC| == 1/x
  227.  
  228. #include "qUINT_common.fxh"
  229.  
  230. texture2D ADOF_FocusTex { Format = R16F; };
  231. texture2D ADOF_FocusTexPrev { Format = R16F; };
  232.  
  233. sampler2D sADOF_FocusTex { Texture = ADOF_FocusTex; };
  234. sampler2D sADOF_FocusTexPrev { Texture = ADOF_FocusTexPrev; };
  235.  
  236. /*=============================================================================
  237. Vertex Shader
  238. =============================================================================*/
  239.  
  240. struct ADOF_VSOUT
  241. {
  242. float4 vpos : SV_Position;
  243. float4 txcoord : TEXCOORD0;
  244. float4 offset0 : TEXCOORD1;
  245. float2x2 offsmat : TEXCOORD2;
  246.  
  247. };
  248.  
  249. ADOF_VSOUT VS_ADOF(in uint id : SV_VertexID)
  250. {
  251. ADOF_VSOUT OUT;
  252.  
  253. OUT.txcoord.x = (id == 2) ? 2.0 : 0.0;
  254. OUT.txcoord.y = (id == 1) ? 2.0 : 0.0;
  255. OUT.txcoord.zw = OUT.txcoord.xy / fADOF_RenderResolutionMult;
  256. OUT.vpos = float4(OUT.txcoord.xy * float2(2.0, -2.0) + float2(-1.0, 1.0), 0.0, 1.0);
  257.  
  258. //can't precompute vertices directly, not enough registers in sm3
  259. sincos(6.2831853 / iADOF_ShapeVertices, OUT.offsmat._21, OUT.offsmat._22);
  260. OUT.offsmat._11 = OUT.offsmat._22;
  261. OUT.offsmat._12 = -OUT.offsmat._21;
  262.  
  263. sincos(radians(fADOF_ShapeRotation), OUT.offset0.x, OUT.offset0.y);
  264. OUT.offset0.zw = mul(OUT.offset0.xy, OUT.offsmat);
  265.  
  266. return OUT;
  267. }
  268.  
  269. /*=============================================================================
  270. Functions
  271. =============================================================================*/
  272.  
  273. float GetLinearDepth(float2 coords)
  274. {
  275. return qUINT::linear_depth_resized(coords);
  276. }
  277.  
  278. float CircleOfConfusion(float2 texcoord, bool aggressiveLeakReduction)
  279. {
  280. float2 depthdata; //x - linear scene depth, y - linear scene focus
  281. float scenecoc; //blur value, signed by position relative to focus plane
  282.  
  283. depthdata.x = GetLinearDepth(texcoord.xy);
  284.  
  285. [branch]
  286. if(aggressiveLeakReduction)
  287. {
  288. float3 neighbourOffsets = float3(qUINT::PIXEL_SIZE.xy, 0);
  289. //sadly, flipped depth buffers etc don't allow for gather or linearizing in batch
  290. float4 neighbourDepths = float4(GetLinearDepth(texcoord.xy - neighbourOffsets.xz), //left
  291. GetLinearDepth(texcoord.xy + neighbourOffsets.xz), //right
  292. GetLinearDepth(texcoord.xy - neighbourOffsets.zy), //top
  293. GetLinearDepth(texcoord.xy + neighbourOffsets.zy));//bottom
  294.  
  295. float neighbourMin = min(min(neighbourDepths.x,neighbourDepths.y),min(neighbourDepths.z,neighbourDepths.w));
  296. depthdata.x = lerp(min(neighbourMin, depthdata.x), depthdata.x, 0.001);
  297. }
  298.  
  299. depthdata.y = tex2D(sADOF_FocusTex, texcoord.xy).x;
  300. float handdepth = depthdata.x;
  301.  
  302. depthdata.xy = saturate(depthdata.xy / fADOF_HyperFocus);
  303.  
  304. [branch]
  305. if(depthdata.x < depthdata.y)
  306. {
  307. scenecoc = depthdata.x / depthdata.y - 1.0;
  308. scenecoc = ldexp(scenecoc, -0.5*fADOF_NearBlurCurve*fADOF_NearBlurCurve);
  309. }
  310. else
  311. {
  312. scenecoc = (depthdata.x - depthdata.y)/(ldexp(depthdata.y, fADOF_FarBlurCurve*fADOF_FarBlurCurve) - depthdata.y);
  313. scenecoc = saturate(scenecoc);
  314. }
  315.  
  316. #if(FPS_HAND_BLUR_CUTOFF_CHECK != 0)
  317. scenecoc = (handdepth < FPS_HAND_BLUR_CUTOFF_DIST * 1e-4) ? 0.0 : 1.0;
  318. #else //FPS_HAND_BLUR_CUTOFF_CHECK
  319. scenecoc = (handdepth < FPS_HAND_BLUR_CUTOFF_DIST * 1e-4) ? 0.0 : scenecoc;
  320. #endif //FPS_HAND_BLUR_CUTOFF_CHECK
  321.  
  322. return scenecoc;
  323. }
  324.  
  325. void ShapeRoundness(inout float2 sampleOffset, in float roundness)
  326. {
  327. sampleOffset *= (1.0-roundness) + rsqrt(dot(sampleOffset,sampleOffset))*roundness;
  328. }
  329.  
  330. void OpticalVignette(in float2 sampleOffset, in float2 centerVec, inout float sampleWeight)
  331. {
  332. sampleOffset -= centerVec; //scaled by vignette intensity
  333. sampleWeight *= saturate(3.333 - dot(sampleOffset,sampleOffset) * 1.666); //notsosmoothstep to avoid aliasing
  334. }
  335.  
  336. float2 CoC2BlurRadius(float CoC)
  337. {
  338. return float2(fADOF_ShapeAnamorphRatio, qUINT::ASPECT_RATIO.y) * CoC * fADOF_ShapeRadius * 6e-4;
  339. }
  340.  
  341. /*=============================================================================
  342. Pixel Shaders
  343. =============================================================================*/
  344.  
  345. void PS_ResizeDepth(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  346. {
  347. color = tex2D(qUINT::sDepthBufferTex, IN.txcoord.xy).x;
  348. }
  349.  
  350. void PS_CopyBackBuffer(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  351. {
  352. color = tex2D(qUINT::sBackBufferTex, IN.txcoord.xy);
  353. }
  354.  
  355. void PS_ReadFocus(in ADOF_VSOUT IN, out float focus : SV_Target0)
  356. {
  357. float scenefocus = 0.0;
  358.  
  359. [branch]
  360. if(bADOF_AutofocusEnable == true)
  361. {
  362. float samples = 10.0;
  363. float weightsum = 1e-6;
  364.  
  365. for(float xcoord = 0.0; xcoord < samples; xcoord++)
  366. for(float ycoord = 0.0; ycoord < samples; ycoord++)
  367. {
  368. float2 sampleOffset = (float2(xcoord,ycoord) + 0.5) / samples;
  369. sampleOffset = sampleOffset * 2.0 - 1.0;
  370. sampleOffset *= fADOF_AutofocusRadius;
  371. sampleOffset += (fADOF_AutofocusCenter - 0.5);
  372.  
  373. float sampleWeight = saturate(1.2 * exp2(-dot(sampleOffset,sampleOffset)*4.0));
  374.  
  375. float tempfocus = GetLinearDepth(sampleOffset * 0.5 + 0.5);
  376. sampleWeight *= rcp(tempfocus + 0.001);
  377.  
  378. sampleWeight *= saturate(tempfocus > FPS_HAND_BLUR_CUTOFF_DIST * 1e-4); //remove fps hands from focus calculations
  379.  
  380. scenefocus += tempfocus * sampleWeight;
  381. weightsum += sampleWeight;
  382. }
  383. scenefocus /= weightsum;
  384. }
  385. else
  386. {
  387. scenefocus = fADOF_ManualfocusDepth;
  388. }
  389.  
  390. float prevscenefocus = tex2D(sADOF_FocusTexPrev, 0.5).x;
  391. float adjustmentspeed = fADOF_AutofocusSpeed * fADOF_AutofocusSpeed;
  392. adjustmentspeed *= prevscenefocus > scenefocus ? 2.0 : 1.0;
  393.  
  394. focus = lerp(prevscenefocus, scenefocus, saturate(adjustmentspeed));
  395. }
  396.  
  397. void PS_CopyFocus(in ADOF_VSOUT IN, out float focus : SV_Target0)
  398. {
  399. focus = tex2D(sADOF_FocusTex, IN.txcoord.xy).x;
  400. }
  401.  
  402. void PS_CoC(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  403. {
  404. color = tex2D(qUINT::sBackBufferTex, IN.txcoord.xy);
  405.  
  406. static const float2 sampleOffsets[4] = { float2( 1.5, 0.5) * qUINT::PIXEL_SIZE.xy,
  407. float2( 0.5,-1.5) * qUINT::PIXEL_SIZE.xy,
  408. float2(-1.5,-0.5) * qUINT::PIXEL_SIZE.xy,
  409. float2(-0.5, 1.5) * qUINT::PIXEL_SIZE.xy};
  410.  
  411. float centerDepth = GetLinearDepth(IN.txcoord.xy);
  412. float4 sampleCoord = 0.0;
  413. float3 neighbourOffsets = float3(qUINT::PIXEL_SIZE.xy, 0);
  414. float4 coccolor = 0.0;
  415.  
  416. [loop]
  417. for(int i=0; i<4; i++)
  418. {
  419. sampleCoord.xy = IN.txcoord.xy + sampleOffsets[i];
  420.  
  421. float3 sampleColor = tex2Dlod(qUINT::sBackBufferTex, sampleCoord).rgb;
  422.  
  423. float4 sampleDepths = float4(GetLinearDepth(sampleCoord.xy + neighbourOffsets.xz), //right
  424. GetLinearDepth(sampleCoord.xy - neighbourOffsets.xz), //left
  425. GetLinearDepth(sampleCoord.xy + neighbourOffsets.zy), //bottom
  426. GetLinearDepth(sampleCoord.xy - neighbourOffsets.zy)); //top
  427.  
  428. float sampleDepthMin = min(min(sampleDepths.x,sampleDepths.y),min(sampleDepths.z,sampleDepths.w));
  429.  
  430. sampleColor /= 1.0 + max(max(sampleColor.r, sampleColor.g), sampleColor.b);
  431.  
  432. float sampleWeight = saturate(sampleDepthMin * rcp(centerDepth) + 1e-3);
  433. coccolor += float4(sampleColor.rgb * sampleWeight, sampleWeight);
  434. }
  435.  
  436. coccolor.rgb /= coccolor.a;
  437. coccolor.rgb /= 1.0 - max(coccolor.r, max(coccolor.g, coccolor.b));
  438.  
  439. color.rgb = lerp(color.rgb, coccolor.rgb, saturate(coccolor.w * 8.0));
  440. color.w = CircleOfConfusion(IN.txcoord.xy, 1);
  441. color.w = saturate(color.w * 0.5 + 0.5);
  442. }
  443.  
  444. float4 PS_DoF_Main(in ADOF_VSOUT IN) : SV_Target0
  445. {
  446. if(max(IN.txcoord.z,IN.txcoord.w) > 1.01) discard;
  447.  
  448. float4 BokehSum, BokehMax;
  449. BokehMax = tex2D(qUINT::sCommonTex0, IN.txcoord.zw);
  450. BokehSum = BokehMax;
  451. float weightSum = 1.0;
  452. float CoC = abs(BokehSum.w * 2.0 - 1.0);
  453. float2 bokehRadiusScaled = CoC2BlurRadius(CoC);
  454. float nRings = lerp(1.0,iADOF_ShapeQuality,saturate(CoC)) + (dot(IN.vpos.xy,1) % 2) * 0.5;
  455.  
  456. if(bokehRadiusScaled.x < DISCRADIUS_RESOLUTION_BOUNDARY_LOWER * qUINT::PIXEL_SIZE.x) return BokehSum;
  457.  
  458. bokehRadiusScaled /= nRings;
  459. CoC /= nRings;
  460.  
  461. #if (ADOF_OPTICAL_VIGNETTE_ENABLE != 0)
  462. float2 centerVec = IN.txcoord.zw - 0.5;
  463. float centerDist = sqrt(dot(centerVec,centerVec));
  464. float vignette = pow(centerDist, fADOF_ShapeVignetteCurve) * fADOF_ShapeVignetteAmount;
  465. centerVec = centerVec / centerDist * vignette;
  466. weightSum *= saturate(3.33 - vignette * 2.0);
  467. BokehSum *= weightSum;
  468. BokehMax *= weightSum;
  469. #endif
  470.  
  471. [loop]
  472. for (int iVertices = 0; iVertices < iADOF_ShapeVertices && iVertices < 10; iVertices++)
  473. {
  474. [loop]
  475. for(float iRings = 1; iRings <= nRings && iRings < 26; iRings++)
  476. {
  477. [loop]
  478. for(float iSamplesPerRing = 0; iSamplesPerRing < iRings && iSamplesPerRing < 26; iSamplesPerRing++)
  479. {
  480. float2 sampleOffset = lerp(IN.offset0.xy,IN.offset0.zw,iSamplesPerRing/iRings);
  481. ShapeRoundness(sampleOffset,fADOF_ShapeCurvatureAmount);
  482.  
  483. float4 sampleBokeh = tex2Dlod(qUINT::sCommonTex0, float4(IN.txcoord.zw + sampleOffset.xy * (bokehRadiusScaled * iRings),0,0));
  484. float sampleWeight = saturate(1e6 * (abs(sampleBokeh.a * 2.0 - 1.0) - CoC * (float)iRings) + 1.0);
  485.  
  486. #if (ADOF_OPTICAL_VIGNETTE_ENABLE != 0)
  487. OpticalVignette(sampleOffset.xy * iRings/nRings, centerVec, sampleWeight);
  488. #endif
  489. sampleBokeh.rgb *= sampleWeight;
  490. weightSum += sampleWeight;
  491. BokehSum += sampleBokeh;
  492. BokehMax = max(BokehMax,sampleBokeh);
  493. }
  494. }
  495.  
  496. IN.offset0.xy = IN.offset0.zw;
  497. IN.offset0.zw = mul(IN.offset0.zw, IN.offsmat);
  498. }
  499.  
  500. return lerp(BokehSum / weightSum, BokehMax, fADOF_BokehIntensity * saturate(CoC*nRings*2.0));
  501. }
  502.  
  503. void PS_DoF_Combine(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  504. {
  505. float4 blurredColor = tex2D(qUINT::sCommonTex1, IN.txcoord.xy * fADOF_RenderResolutionMult);
  506. float4 originalColor = tex2D(qUINT::sBackBufferTex, IN.txcoord.xy);
  507.  
  508. float CoC = abs(CircleOfConfusion(IN.txcoord.xy, 0));
  509. float bokehRadiusPixels = CoC2BlurRadius(CoC).x * BUFFER_WIDTH;
  510.  
  511. #define linearstep(a,b,x) saturate((x-a)/(b-a))
  512. float blendWeight = linearstep(DISCRADIUS_RESOLUTION_BOUNDARY_LOWER, DISCRADIUS_RESOLUTION_BOUNDARY_UPPER, bokehRadiusPixels);
  513. blendWeight = pow(blendWeight,DISCRADIUS_RESOLUTION_BOUNDARY_CURVE);
  514.  
  515. color.rgb = lerp(originalColor.rgb, blurredColor.rgb, blendWeight);
  516. color.a = saturate(CoC * GAUSSIAN_BUILDUP_MULT) * 0.5 + 0.5;
  517. }
  518.  
  519. void PS_DoF_Gauss1(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  520. {
  521. float4 centerTap = tex2D(qUINT::sCommonTex0, IN.txcoord.xy);
  522. float CoC = abs(centerTap.a * 2.0 - 1.0);
  523.  
  524. float nSteps = floor(CoC * (fADOF_SmootheningAmount + 0.0));
  525. float expCoeff = -2.0 * rcp(nSteps * nSteps + 1e-3); //sigma adjusted for blur width
  526. float2 blurAxisScaled = float2(1,0) * qUINT::PIXEL_SIZE.xy;
  527.  
  528. float4 gaussianSum = 0.0;
  529. float gaussianSumWeight = 1e-3;
  530.  
  531. for(float iStep = -nSteps; iStep <= nSteps; iStep++)
  532. {
  533. float currentWeight = exp(iStep * iStep * expCoeff);
  534. float currentOffset = 2.0 * iStep - 0.5; //Sample between texels to double blur width at no cost
  535.  
  536. float4 currentTap = tex2Dlod(qUINT::sCommonTex0, float4(IN.txcoord.xy + blurAxisScaled.xy * currentOffset, 0, 0));
  537. currentWeight *= saturate(abs(currentTap.a * 2.0 - 1.0) - CoC * 0.25); //bleed fix
  538.  
  539. gaussianSum += currentTap * currentWeight;
  540. gaussianSumWeight += currentWeight;
  541. }
  542.  
  543. gaussianSum /= gaussianSumWeight;
  544.  
  545. color.rgb = lerp(centerTap.rgb, gaussianSum.rgb, saturate(gaussianSumWeight));
  546. color.a = centerTap.a;
  547. }
  548.  
  549. void PS_DoF_Gauss2(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  550. {
  551. float4 centerTap = tex2D(qUINT::sCommonTex1, IN.txcoord.xy);
  552. float CoC = abs(centerTap.a * 2.0 - 1.0);
  553.  
  554. float nSteps = min(50,floor(CoC * (fADOF_SmootheningAmount + 0.0)));
  555. float expCoeff = -2.0 * rcp(nSteps * nSteps + 1e-3); //sigma adjusted for blur width
  556. float2 blurAxisScaled = float2(0,1) * qUINT::PIXEL_SIZE.xy;
  557.  
  558. float4 gaussianSum = 0.0;
  559. float gaussianSumWeight = 1e-3;
  560.  
  561. for(float iStep = -nSteps; iStep <= nSteps; iStep++)
  562. {
  563. float currentWeight = exp(iStep * iStep * expCoeff);
  564. float currentOffset = 2.0 * iStep - 0.5; //Sample between texels to double blur width at no cost
  565.  
  566. float4 currentTap = tex2Dlod(qUINT::sCommonTex1, float4(IN.txcoord.xy + blurAxisScaled.xy * currentOffset, 0, 0));
  567. currentWeight *= saturate(abs(currentTap.a * 2.0 - 1.0) - CoC * 0.25); //bleed fix
  568.  
  569. gaussianSum += currentTap * currentWeight;
  570. gaussianSumWeight += currentWeight;
  571. }
  572.  
  573. gaussianSum /= gaussianSumWeight;
  574.  
  575. color.rgb = lerp(centerTap.rgb, gaussianSum.rgb, saturate(gaussianSumWeight));
  576. color.a = centerTap.a;
  577. }
  578.  
  579. #if (ADOF_CHROMATIC_ABERRATION_ENABLE != 0)
  580. void PS_DoF_ChromaticAberration(in ADOF_VSOUT IN, out float4 color : SV_Target0)
  581. {
  582. float4 colorVals[5];
  583. float3 neighbourOffsets = float3(qUINT::PIXEL_SIZE.xy, 0);
  584.  
  585. colorVals[0] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy); //C
  586. colorVals[1] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy - neighbourOffsets.xz); //L
  587. colorVals[2] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy - neighbourOffsets.zy); //T
  588. colorVals[3] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy + neighbourOffsets.xz); //R
  589. colorVals[4] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy + neighbourOffsets.zy); //B
  590.  
  591. float CoC = abs(colorVals[0].a * 2.0 - 1.0);
  592. float2 bokehRadiusScaled = CoC2BlurRadius(CoC);
  593.  
  594. float4 vGradTwosided = float4(dot(colorVals[0].rgb - colorVals[1].rgb, 1), //C - L
  595. dot(colorVals[0].rgb - colorVals[2].rgb, 1), //C - T
  596. dot(colorVals[3].rgb - colorVals[0].rgb, 1), //R - C
  597. dot(colorVals[4].rgb - colorVals[0].rgb, 1)); //B - C
  598.  
  599. float2 vGrad = min(vGradTwosided.xy, vGradTwosided.zw);
  600.  
  601. float vGradLen = sqrt(dot(vGrad,vGrad)) + 1e-6;
  602. vGrad = vGrad / vGradLen * saturate(vGradLen * 32.0) * bokehRadiusScaled * 0.125 * fADOF_ShapeChromaAmount;
  603.  
  604. float4 chromaVals[3];
  605.  
  606. chromaVals[0] = colorVals[0];
  607. chromaVals[1] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy + vGrad);
  608. chromaVals[2] = tex2D(qUINT::sCommonTex0, IN.txcoord.xy - vGrad);
  609.  
  610. chromaVals[1].rgb = lerp(chromaVals[0].rgb, chromaVals[1].rgb, saturate(4.0 * abs(chromaVals[1].w)));
  611. chromaVals[2].rgb = lerp(chromaVals[0].rgb, chromaVals[2].rgb, saturate(4.0 * abs(chromaVals[2].w)));
  612.  
  613. uint3 chromaMode = (uint3(0,1,2) + iADOF_ShapeChromaMode.xxx) % 3;
  614.  
  615. color.rgb = float3(chromaVals[chromaMode.x].r,
  616. chromaVals[chromaMode.y].g,
  617. chromaVals[chromaMode.z].b);
  618. color.a = 1.0;
  619. }
  620. #endif
  621.  
  622. /*=============================================================================
  623. Techniques
  624. =============================================================================*/
  625.  
  626. technique ADOF
  627. < ui_tooltip = " >> qUINT::ADOF <<\n\n"
  628. "ADOF is a bokeh depth of field shader.\n"
  629. "It blurs the scene in front of and behind the focus plane\n"
  630. "to simulate the behaviour of real lenses. A multitude of features\n"
  631. "allows to simulate various types of bokeh blur that cameras produce.\n"
  632. "\nADOF is written by Marty McFly / Pascal Gilcher"; >
  633. {
  634. pass
  635. {
  636. VertexShader = PostProcessVS;
  637. PixelShader = PS_ResizeDepth;
  638. RenderTarget = qUINT::DepthBufferTexResized;
  639. }
  640. /* pass
  641. {
  642. VertexShader = VS_ADOF;
  643. PixelShader = PS_CopyBackBuffer;
  644. RenderTarget = texOriginal;
  645. }*/
  646. pass
  647. {
  648. VertexShader = VS_ADOF;
  649. PixelShader = PS_ReadFocus;
  650. RenderTarget = ADOF_FocusTex;
  651. }
  652. pass
  653. {
  654. VertexShader = VS_ADOF;
  655. PixelShader = PS_CopyFocus;
  656. RenderTarget = ADOF_FocusTexPrev;
  657. }
  658. pass
  659. {
  660. VertexShader = VS_ADOF;
  661. PixelShader = PS_CoC;
  662. RenderTarget = qUINT::CommonTex0;
  663. }
  664. pass
  665. {
  666. VertexShader = VS_ADOF;
  667. PixelShader = PS_DoF_Main;
  668. RenderTarget = qUINT::CommonTex1;
  669. }
  670. pass
  671. {
  672. VertexShader = VS_ADOF;
  673. PixelShader = PS_DoF_Combine;
  674. RenderTarget = qUINT::CommonTex0;
  675. }
  676. pass
  677. {
  678. VertexShader = VS_ADOF;
  679. PixelShader = PS_DoF_Gauss1;
  680. RenderTarget = qUINT::CommonTex1;
  681. }
  682. #if(ADOF_CHROMATIC_ABERRATION_ENABLE != 0)
  683. pass
  684. {
  685. VertexShader = VS_ADOF;
  686. PixelShader = PS_DoF_Gauss2;
  687. RenderTarget = qUINT::CommonTex0;
  688. }
  689. pass
  690. {
  691. VertexShader = VS_ADOF;
  692. PixelShader = PS_DoF_ChromaticAberration;
  693. }
  694. #else
  695. pass
  696. {
  697. VertexShader = VS_ADOF;
  698. PixelShader = PS_DoF_Gauss2;
  699. }
  700. #endif
  701. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement