Blender  V2.93
overlay_antialiasing.c
Go to the documentation of this file.
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * Copyright 2019, Blender Foundation.
17  */
18 
57 #include "DRW_render.h"
58 
59 #include "ED_screen.h"
60 
61 #include "overlay_private.h"
62 
64 {
65  OVERLAY_FramebufferList *fbl = vedata->fbl;
66  OVERLAY_TextureList *txl = vedata->txl;
67  OVERLAY_PrivateData *pd = vedata->stl->pd;
69 
70  /* Small texture which will have very small impact on rendertime. */
71  if (txl->dummy_depth_tx == NULL) {
72  const float pixel[1] = {1.0f};
74  }
75 
76  if (!DRW_state_is_fbo()) {
77  pd->antialiasing.enabled = false;
78  return;
79  }
80 
81  bool need_wire_expansion = (G_draw.block.sizePixel > 1.0f);
82  pd->antialiasing.enabled = need_wire_expansion ||
83  ((U.gpu_flag & USER_GPU_FLAG_OVERLAY_SMOOTH_WIRE) != 0);
84 
85  GPUTexture *color_tex = NULL;
86  GPUTexture *line_tex = NULL;
87 
88  if (pd->antialiasing.enabled) {
91 
92  color_tex = txl->overlay_color_tx;
93  line_tex = txl->overlay_line_tx;
94  }
95  else {
96  /* Just a copy of the defaults frame-buffers. */
97  color_tex = dtxl->color_overlay;
98  }
99 
100  GPU_framebuffer_ensure_config(&fbl->overlay_color_only_fb,
101  {
102  GPU_ATTACHMENT_NONE,
103  GPU_ATTACHMENT_TEXTURE(color_tex),
104  });
105  GPU_framebuffer_ensure_config(&fbl->overlay_default_fb,
106  {
107  GPU_ATTACHMENT_TEXTURE(dtxl->depth),
108  GPU_ATTACHMENT_TEXTURE(color_tex),
109  });
110  GPU_framebuffer_ensure_config(&fbl->overlay_line_fb,
111  {
112  GPU_ATTACHMENT_TEXTURE(dtxl->depth),
113  GPU_ATTACHMENT_TEXTURE(color_tex),
114  GPU_ATTACHMENT_TEXTURE(line_tex),
115  });
116 }
117 
119 {
120  OVERLAY_TextureList *txl = vedata->txl;
121  OVERLAY_PrivateData *pd = vedata->stl->pd;
122  OVERLAY_PassList *psl = vedata->psl;
124  struct GPUShader *sh;
125  DRWShadingGroup *grp;
126 
127  if (pd->antialiasing.enabled) {
128  /* `antialiasing.enabled` is also enabled for wire expansion. Check here if
129  * anti aliasing is needed. */
130  const bool do_smooth_lines = (U.gpu_flag & USER_GPU_FLAG_OVERLAY_SMOOTH_WIRE) != 0;
131 
133 
135  grp = DRW_shgroup_create(sh, psl->antialiasing_ps);
136  DRW_shgroup_uniform_block(grp, "globalsBlock", G_draw.block_ubo);
137  DRW_shgroup_uniform_bool_copy(grp, "doSmoothLines", do_smooth_lines);
138  DRW_shgroup_uniform_texture_ref(grp, "depthTex", &dtxl->depth);
139  DRW_shgroup_uniform_texture_ref(grp, "colorTex", &txl->overlay_color_tx);
140  DRW_shgroup_uniform_texture_ref(grp, "lineTex", &txl->overlay_line_tx);
142  }
143 
144  /* A bit out of place... not related to antialiasing. */
145  if (pd->xray_enabled) {
147 
149  grp = DRW_shgroup_create(sh, psl->xray_fade_ps);
150  DRW_shgroup_uniform_texture_ref(grp, "depthTex", &dtxl->depth);
151  DRW_shgroup_uniform_texture_ref(grp, "xrayDepthTex", &txl->temp_depth_tx);
152  DRW_shgroup_uniform_float_copy(grp, "opacity", 1.0f - pd->xray_opacity);
154  }
155 }
156 
158 {
159  OVERLAY_FramebufferList *fbl = vedata->fbl;
160  OVERLAY_TextureList *txl = vedata->txl;
161  OVERLAY_PassList *psl = vedata->psl;
162  OVERLAY_PrivateData *pd = vedata->stl->pd;
164 
165  if (pd->antialiasing.enabled) {
166  GPU_framebuffer_ensure_config(&fbl->overlay_in_front_fb,
167  {GPU_ATTACHMENT_TEXTURE(dtxl->depth_in_front),
168  GPU_ATTACHMENT_TEXTURE(txl->overlay_color_tx)});
169 
170  GPU_framebuffer_ensure_config(&fbl->overlay_line_in_front_fb,
171  {GPU_ATTACHMENT_TEXTURE(dtxl->depth_in_front),
172  GPU_ATTACHMENT_TEXTURE(txl->overlay_color_tx),
173  GPU_ATTACHMENT_TEXTURE(txl->overlay_line_tx)});
174  }
175  else {
176  GPU_framebuffer_ensure_config(&fbl->overlay_in_front_fb,
177  {GPU_ATTACHMENT_TEXTURE(dtxl->depth_in_front),
178  GPU_ATTACHMENT_TEXTURE(dtxl->color_overlay)});
179 
180  GPU_framebuffer_ensure_config(&fbl->overlay_line_in_front_fb,
181  {GPU_ATTACHMENT_TEXTURE(dtxl->depth_in_front),
182  GPU_ATTACHMENT_TEXTURE(dtxl->color_overlay),
183  GPU_ATTACHMENT_TEXTURE(txl->overlay_line_tx)});
184  }
185 
186  pd->antialiasing.do_depth_copy = !(psl->wireframe_ps == NULL ||
188  (pd->xray_enabled && pd->xray_opacity > 0.0f);
191 
192  const bool do_wireframe = pd->antialiasing.do_depth_copy ||
194  if (pd->xray_enabled || do_wireframe) {
196  }
197 }
198 
200 {
201  OVERLAY_FramebufferList *fbl = vedata->fbl;
202  OVERLAY_PrivateData *pd = vedata->stl->pd;
203 
204  if (pd->antialiasing.enabled) {
205  const float clear_col[4] = {0.0f, 0.0f, 0.0f, 0.0f};
207  GPU_framebuffer_clear_color(fbl->overlay_line_fb, clear_col);
208  }
209 
210  /* If we are not in solid shading mode, we clear the depth. */
211  if (DRW_state_is_fbo() && pd->clear_in_front) {
212  /* TODO(fclem): This clear should be done in a global place. */
214  GPU_framebuffer_clear_depth(fbl->overlay_in_front_fb, 1.0f);
215  }
216 }
217 
219 {
220  OVERLAY_FramebufferList *fbl = vedata->fbl;
221  OVERLAY_TextureList *txl = vedata->txl;
222  OVERLAY_PrivateData *pd = vedata->stl->pd;
223 
226  /* We copy the depth of the rendered geometry to be able to compare to the overlays depth. */
227  GPU_texture_copy(txl->temp_depth_tx, dtxl->depth);
228  }
229 
230  if (DRW_state_is_fbo() && pd->xray_enabled) {
231  /* We then clear to not occlude the overlays directly. */
233  GPU_framebuffer_clear_depth(fbl->overlay_default_fb, 1.0f);
234  }
235 }
236 
238 {
239  OVERLAY_TextureList *txl = vedata->txl;
240  OVERLAY_PrivateData *pd = vedata->stl->pd;
241 
244  /* We copy the depth of the rendered geometry to be able to compare to the overlays depth. */
246  }
247 }
248 
250 {
251  OVERLAY_PassList *psl = vedata->psl;
252  OVERLAY_PrivateData *pd = vedata->stl->pd;
253 
254  if (DRW_state_is_fbo() && pd->xray_enabled && pd->xray_opacity > 0.0f) {
255  /* Partially occlude overlays using the geometry depth pass. */
257  }
258 }
259 
261 {
262  OVERLAY_PassList *psl = vedata->psl;
263  OVERLAY_PrivateData *pd = vedata->stl->pd;
265 
266  if (pd->antialiasing.enabled) {
269  }
270 }
@ USER_GPU_FLAG_OVERLAY_SMOOTH_WIRE
@ DRW_TEX_FILTER
Definition: DRW_render.h:139
@ DRW_STATE_WRITE_COLOR
Definition: DRW_render.h:315
@ DRW_STATE_BLEND_ALPHA_PREMUL
Definition: DRW_render.h:342
@ DRW_STATE_BLEND_MUL
Definition: DRW_render.h:345
#define DRW_PASS_CREATE(pass, state)
Definition: DRW_render.h:593
void GPU_framebuffer_bind(GPUFrameBuffer *fb)
struct GPUShader GPUShader
Definition: GPU_shader.h:33
void GPU_texture_copy(GPUTexture *dst, GPUTexture *src)
Definition: gpu_texture.cc:453
struct GPUTexture GPUTexture
Definition: GPU_texture.h:33
@ GPU_SRGB8_A8
Definition: GPU_texture.h:122
@ GPU_DEPTH24_STENCIL8
Definition: GPU_texture.h:121
@ GPU_DEPTH_COMPONENT24
Definition: GPU_texture.h:167
@ GPU_RGBA8
Definition: GPU_texture.h:88
unsigned int U
Definition: btGjkEpa3.h:78
struct DRW_Global G_draw
Definition: draw_common.c:45
DefaultFramebufferList * DRW_viewport_framebuffer_list_get(void)
Definition: draw_manager.c:697
bool DRW_state_is_fbo(void)
DefaultTextureList * DRW_viewport_texture_list_get(void)
Definition: draw_manager.c:702
void DRW_shgroup_uniform_float_copy(DRWShadingGroup *shgroup, const char *name, const float value)
void DRW_shgroup_uniform_block(DRWShadingGroup *shgroup, const char *name, const GPUUniformBuf *ubo)
void DRW_shgroup_call_procedural_triangles(DRWShadingGroup *shgroup, Object *ob, uint tri_count)
bool DRW_pass_is_empty(DRWPass *pass)
DRWShadingGroup * DRW_shgroup_create(struct GPUShader *shader, DRWPass *pass)
void DRW_shgroup_uniform_texture_ref(DRWShadingGroup *shgroup, const char *name, GPUTexture **tex)
void DRW_shgroup_uniform_bool_copy(DRWShadingGroup *shgroup, const char *name, const bool value)
void DRW_draw_pass(DRWPass *pass)
void DRW_texture_ensure_fullscreen_2d(GPUTexture **tex, eGPUTextureFormat format, DRWTextureFlag flags)
GPUTexture * DRW_texture_create_2d(int w, int h, eGPUTextureFormat format, DRWTextureFlag flags, const float *fpixels)
void OVERLAY_antialiasing_cache_init(OVERLAY_Data *vedata)
void OVERLAY_antialiasing_cache_finish(OVERLAY_Data *vedata)
void OVERLAY_antialiasing_init(OVERLAY_Data *vedata)
void OVERLAY_xray_depth_copy(OVERLAY_Data *vedata)
void OVERLAY_antialiasing_start(OVERLAY_Data *vedata)
void OVERLAY_xray_depth_infront_copy(OVERLAY_Data *vedata)
void OVERLAY_xray_fade_draw(OVERLAY_Data *vedata)
void OVERLAY_antialiasing_end(OVERLAY_Data *vedata)
GPUShader * OVERLAY_shader_xray_fade(void)
GPUShader * OVERLAY_shader_antialiasing(void)
GlobalsUboStorage block
Definition: draw_common.h:208
struct GPUUniformBuf * block_ubo
Definition: draw_common.h:210
struct GPUFrameBuffer * overlay_only_fb
struct GPUTexture * depth
struct GPUTexture * depth_in_front
struct GPUTexture * color_overlay
OVERLAY_PassList * psl
OVERLAY_StorageList * stl
OVERLAY_FramebufferList * fbl
OVERLAY_TextureList * txl
struct GPUFrameBuffer * overlay_line_in_front_fb
struct GPUFrameBuffer * overlay_in_front_fb
struct GPUFrameBuffer * overlay_default_fb
struct GPUFrameBuffer * overlay_line_fb
struct GPUFrameBuffer * overlay_color_only_fb
DRWPass * wireframe_ps
DRWPass * antialiasing_ps
DRWPass * wireframe_xray_ps
DRWPass * xray_fade_ps
struct OVERLAY_PrivateData::@239 antialiasing
struct OVERLAY_PrivateData * pd
struct GPUTexture * dummy_depth_tx
struct GPUTexture * temp_depth_tx
struct GPUTexture * overlay_line_tx
struct GPUTexture * overlay_color_tx