Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--source/blender/draw/DRW_engine.h10
-rw-r--r--source/blender/draw/engines/clay/clay.c6
-rw-r--r--source/blender/draw/intern/DRW_render.h2
-rw-r--r--source/blender/draw/intern/draw_manager.c225
-rw-r--r--source/blender/draw/modes/object_mode.c82
-rw-r--r--source/blender/editors/space_view3d/view3d_view.c16
-rw-r--r--source/blender/gpu/GPU_viewport.h3
-rw-r--r--source/blender/gpu/intern/gpu_viewport.c12
8 files changed, 299 insertions, 57 deletions
diff --git a/source/blender/draw/DRW_engine.h b/source/blender/draw/DRW_engine.h
index 60e8e40ea61..03ba8e39447 100644
--- a/source/blender/draw/DRW_engine.h
+++ b/source/blender/draw/DRW_engine.h
@@ -26,6 +26,7 @@
#ifndef __DRW_ENGINE_H__
#define __DRW_ENGINE_H__
+struct ARegion;
struct CollectionEngineSettings;
struct DRWPass;
struct Material;
@@ -34,6 +35,12 @@ struct DrawEngineType;
struct IDProperty;
struct bContext;
struct Object;
+struct SceneLayer;
+struct ViewContext;
+struct View3D;
+struct rcti;
+
+#include "BLI_sys_types.h" /* for bool */
/* Buffer and textures used by the viewport by default */
typedef struct DefaultFramebufferList {
@@ -54,6 +61,9 @@ void DRW_engine_viewport_data_size_get(
int *r_fbl_len, int *r_txl_len, int *r_psl_len, int *r_stl_len);
void DRW_draw_view(const struct bContext *C);
+void DRW_draw_select_loop(
+ struct ViewContext *vc, struct Scene *scene, struct SceneLayer *sl, struct View3D *v3d, struct ARegion *ar,
+ bool use_obedit_skip, bool use_nearest, const struct rcti *rect);
void DRW_object_engine_data_free(struct Object *ob);
diff --git a/source/blender/draw/engines/clay/clay.c b/source/blender/draw/engines/clay/clay.c
index 5b1c6045808..3466f4f8b67 100644
--- a/source/blender/draw/engines/clay/clay.c
+++ b/source/blender/draw/engines/clay/clay.c
@@ -335,7 +335,7 @@ static void CLAY_engine_init(void *vedata)
}
}
- {
+ if (DRW_viewport_is_fbo()) {
const float *viewport_size = DRW_viewport_size_get();
DRWFboTexture tex = {&txl->depth_dup, DRW_BUF_DEPTH_24, 0};
DRW_framebuffer_init(&fbl->dupli_depth,
@@ -607,7 +607,9 @@ static void CLAY_draw_scene(void *vedata)
/* Pass 2 : Duplicate depth */
/* Unless we go for deferred shading we need this to avoid manual depth test and artifacts */
- DRW_framebuffer_blit(dfbl->default_fb, fbl->dupli_depth, true);
+ if (DRW_viewport_is_fbo()) {
+ DRW_framebuffer_blit(dfbl->default_fb, fbl->dupli_depth, true);
+ }
/* Pass 3 : Shading */
DRW_draw_pass(psl->clay_pass);
diff --git a/source/blender/draw/intern/DRW_render.h b/source/blender/draw/intern/DRW_render.h
index 93fd8d610ea..f98f39d7bb3 100644
--- a/source/blender/draw/intern/DRW_render.h
+++ b/source/blender/draw/intern/DRW_render.h
@@ -295,6 +295,8 @@ const float *DRW_viewport_size_get(void);
const float *DRW_viewport_screenvecs_get(void);
const float *DRW_viewport_pixelsize_get(void);
bool DRW_viewport_is_persp_get(void);
+bool DRW_viewport_is_fbo(void);
+bool DRW_viewport_is_select(void);
bool DRW_viewport_cache_is_dirty(void);
struct DefaultFramebufferList *DRW_viewport_framebuffer_list_get(void);
diff --git a/source/blender/draw/intern/draw_manager.c b/source/blender/draw/intern/draw_manager.c
index 6046db874b8..67e2496e09f 100644
--- a/source/blender/draw/intern/draw_manager.c
+++ b/source/blender/draw/intern/draw_manager.c
@@ -77,6 +77,14 @@
#define MAX_ATTRIB_NAME 32
#define MAX_PASS_NAME 32
+/* Use draw manager to call GPU_select, see: DRW_draw_select_loop */
+#define USE_GPU_SELECT
+
+#ifdef USE_GPU_SELECT
+# include "ED_view3d.h"
+# include "GPU_select.h"
+#endif
+
extern char datatoc_gpu_shader_2D_vert_glsl[];
extern char datatoc_gpu_shader_3D_vert_glsl[];
extern char datatoc_gpu_shader_fullscreen_vert_glsl[];
@@ -155,12 +163,18 @@ struct DRWPass {
typedef struct DRWCall {
struct DRWCall *next, *prev;
+#ifdef USE_GPU_SELECT
+ int select_id;
+#endif
Batch *geometry;
float (*obmat)[4];
} DRWCall;
typedef struct DRWCallDynamic {
struct DRWCallDynamic *next, *prev;
+#ifdef USE_GPU_SELECT
+ int select_id;
+#endif
const void *data[];
} DRWCallDynamic;
@@ -175,6 +189,11 @@ struct DRWShadingGroup {
Batch *instance_geom; /* Geometry to instance */
Batch *batch_geom; /* Result of call batching */
+
+#ifdef USE_GPU_SELECT
+ /* backlink to pass we're in */
+ DRWPass *pass_parent;
+#endif
};
/* Used by DRWShadingGroup.type */
@@ -213,6 +232,15 @@ static struct DRWGlobalState {
ListBase DRW_engines = {NULL, NULL};
+#ifdef USE_GPU_SELECT
+static unsigned int g_DRW_select_id = (unsigned int)-1;
+
+static void DRW_select_id_set(unsigned int id)
+{
+ g_DRW_select_id = id;
+}
+#endif
+
/* ***************************************** TEXTURES ******************************************/
static void drw_texture_get_format(DRWTextureFormat format, GPUTextureFormat *data_type, int *channels)
{
@@ -457,6 +485,16 @@ static DRWInterface *DRW_interface_create(GPUShader *shader)
return interface;
}
+#ifdef USE_GPU_SELECT
+static DRWInterface *DRW_interface_duplicate(DRWInterface *interface_src)
+{
+ DRWInterface *interface_dst = MEM_dupallocN(interface_src);
+ BLI_duplicatelist(&interface_dst->uniforms, &interface_src->uniforms);
+ BLI_duplicatelist(&interface_dst->attribs, &interface_src->attribs);
+ return interface_dst;
+}
+#endif
+
static void DRW_interface_uniform(DRWShadingGroup *shgroup, const char *name,
DRWUniformType type, const void *value, int length, int arraysize, int bindloc)
{
@@ -532,6 +570,10 @@ DRWShadingGroup *DRW_shgroup_create(struct GPUShader *shader, DRWPass *pass)
BLI_addtail(&pass->shgroups, shgroup);
BLI_listbase_clear(&shgroup->calls);
+#ifdef USE_GPU_SELECT
+ shgroup->pass_parent = pass;
+#endif
+
return shgroup;
}
@@ -589,19 +631,40 @@ void DRW_shgroup_call_add(DRWShadingGroup *shgroup, Batch *geom, float (*obmat)[
call->obmat = obmat;
call->geometry = geom;
+#ifdef USE_GPU_SELECT
+ call->select_id = g_DRW_select_id;
+#endif
+
BLI_addtail(&shgroup->calls, call);
}
void DRW_shgroup_call_dynamic_add_array(DRWShadingGroup *shgroup, const void *attr[], unsigned int attr_len)
{
DRWInterface *interface = shgroup->interface;
+
+#ifdef USE_GPU_SELECT
+ if ((G.f & G_PICKSEL) && (interface->instance_count > 0)) {
+ shgroup = MEM_dupallocN(shgroup);
+ BLI_listbase_clear(&shgroup->calls);
+
+ shgroup->interface = interface = DRW_interface_duplicate(interface);
+ interface->instance_count = 0;
+
+ BLI_addtail(&shgroup->pass_parent->shgroups, shgroup);
+ }
+#endif
+
unsigned int data_size = sizeof(void *) * interface->attribs_count;
- int size = sizeof(ListBase) + data_size;
+ int size = sizeof(DRWCallDynamic) + data_size;
DRWCallDynamic *call = MEM_callocN(size, "DRWCallDynamic");
BLI_assert(attr_len == interface->attribs_count);
+#ifdef USE_GPU_SELECT
+ call->select_id = g_DRW_select_id;
+#endif
+
memcpy((void *)call->data, attr, data_size);
interface->instance_count += 1;
@@ -1097,6 +1160,9 @@ static void draw_shgroup(DRWShadingGroup *shgroup)
GPU_shader_uniform_texture(shgroup->shader, uni->location, tex);
break;
case DRW_UNIFORM_BUFFER:
+ if (!DRW_viewport_is_fbo()) {
+ break;
+ }
tex = *((GPUTexture **)uni->value);
GPU_texture_bind(tex, uni->bindloc);
GPU_texture_compare_mode(tex, false);
@@ -1115,6 +1181,22 @@ static void draw_shgroup(DRWShadingGroup *shgroup)
}
}
+#ifdef USE_GPU_SELECT
+ /* use the first item because of selection we only ever add one */
+# define GPU_SELECT_LOAD_IF_PICKSEL(_call) \
+ if ((G.f & G_PICKSEL) && (_call)) { \
+ GPU_select_load_id((_call)->select_id); \
+ } ((void)0)
+# define GPU_SELECT_LOAD_IF_PICKSEL_LIST(_call_ls) \
+ if ((G.f & G_PICKSEL) && (_call_ls)->first) { \
+ BLI_assert(BLI_listbase_is_single(_call_ls)); \
+ GPU_select_load_id(((DRWCall *)(_call_ls)->first)->select_id); \
+ } ((void)0)
+#else
+# define GPU_SELECT_LOAD_IF_PICKSEL(call)
+# define GPU_SELECT_LOAD_IF_PICKSEL_LIST(call)
+#endif
+
/* Rendering Calls */
if (shgroup->type != DRW_SHG_NORMAL) {
/* Replacing multiple calls with only one */
@@ -1122,17 +1204,20 @@ static void draw_shgroup(DRWShadingGroup *shgroup)
unit_m4(obmat);
if (shgroup->type == DRW_SHG_INSTANCE && interface->instance_count > 0) {
+ GPU_SELECT_LOAD_IF_PICKSEL_LIST(&shgroup->calls);
draw_geometry(shgroup, shgroup->instance_geom, obmat);
}
else {
/* Some dynamic batch can have no geom (no call to aggregate) */
if (shgroup->batch_geom) {
+ GPU_SELECT_LOAD_IF_PICKSEL_LIST(&shgroup->calls);
draw_geometry(shgroup, shgroup->batch_geom, obmat);
}
}
}
else {
for (DRWCall *call = shgroup->calls.first; call; call = call->next) {
+ GPU_SELECT_LOAD_IF_PICKSEL(call);
draw_geometry(shgroup, call->geometry, call->obmat);
}
}
@@ -1410,22 +1495,26 @@ const float *DRW_viewport_pixelsize_get(void)
* This is because a cache uniform only store reference
* to its value. And we don't want to invalidate the cache
* if this value change per viewport */
-static void DRW_viewport_var_init(const bContext *C)
+static void DRW_viewport_var_init(void)
{
- /* Save context for all later needs */
- DRW_context_state_init(C, &DST.draw_ctx);
-
RegionView3D *rv3d = DST.draw_ctx.rv3d;
/* Refresh DST.size */
- int size[2];
- GPU_viewport_size_get(DST.viewport, size);
- DST.size[0] = size[0];
- DST.size[1] = size[1];
+ if (DST.viewport) {
+ int size[2];
+ GPU_viewport_size_get(DST.viewport, size);
+ DST.size[0] = size[0];
+ DST.size[1] = size[1];
- DefaultFramebufferList *fbl = (DefaultFramebufferList *)GPU_viewport_framebuffer_list_get(DST.viewport);
- DST.default_framebuffer = fbl->default_fb;
+ DefaultFramebufferList *fbl = (DefaultFramebufferList *)GPU_viewport_framebuffer_list_get(DST.viewport);
+ DST.default_framebuffer = fbl->default_fb;
+ }
+ else {
+ DST.size[0] = 0;
+ DST.size[1] = 0;
+ DST.default_framebuffer = NULL;
+ }
/* Refresh DST.screenvecs */
copy_v3_v3(DST.screenvecs[0], rv3d->viewinv[0]);
copy_v3_v3(DST.screenvecs[1], rv3d->viewinv[1]);
@@ -1456,6 +1545,23 @@ bool DRW_viewport_is_persp_get(void)
return rv3d->is_persp;
}
+/**
+ * When false, drawing doesn't output to a pixel buffer
+ * eg: Occlusion queries, or when we have setup a context to draw in already.
+ */
+bool DRW_viewport_is_fbo(void)
+{
+ return (G.f & G_PICKSEL) == 0;
+}
+
+/**
+ * For when engines need to know if this is drawing for selection or not.
+ */
+bool DRW_viewport_is_select(void)
+{
+ return (G.f & G_PICKSEL) != 0;
+}
+
DefaultFramebufferList *DRW_viewport_framebuffer_list_get(void)
{
return GPU_viewport_framebuffer_list_get(DST.viewport);
@@ -1629,10 +1735,9 @@ static void use_drw_engine(DrawEngineType *engine)
/* TODO revisit this when proper layering is implemented */
/* Gather all draw engines needed and store them in DST.enabled_engines
* That also define the rendering order of engines */
-static void DRW_engines_enable(const bContext *C)
+static void DRW_engines_enable_no_modes(const Scene *scene)
{
/* TODO layers */
- Scene *scene = CTX_data_scene(C);
RenderEngineType *type = RE_engines_find(scene->r.engine);
use_drw_engine(type->draw_engine);
@@ -1640,6 +1745,12 @@ static void DRW_engines_enable(const bContext *C)
* not on global state.
* Order is important */
use_drw_engine(&draw_engine_object_type);
+}
+
+static void DRW_engines_enable(const bContext *C)
+{
+ Scene *scene = CTX_data_scene(C);
+ DRW_engines_enable_no_modes(scene);
switch (CTX_data_mode_enum(C)) {
case CTX_MODE_EDIT_MESH:
@@ -1858,7 +1969,10 @@ void DRW_draw_view(const bContext *C)
/* Setup viewport */
cache_is_dirty = GPU_viewport_cache_validate(DST.viewport, DRW_engines_get_hash());
- DRW_viewport_var_init(C);
+
+ /* Save context for all later needs */
+ DRW_context_state_init(C, &DST.draw_ctx);
+ DRW_viewport_var_init();
/* Update ubos */
DRW_globals_update();
@@ -1909,6 +2023,89 @@ void DRW_draw_view(const bContext *C)
memset(&DST, 0x0, sizeof(DST));
}
+/**
+ * object mode select-loop, see: ED_view3d_draw_select_loop (legacy drawing).
+ */
+void DRW_draw_select_loop(
+ struct ViewContext *vc, Scene *scene, struct SceneLayer *sl, View3D *v3d, ARegion *ar,
+ bool UNUSED(use_obedit_skip), bool UNUSED(use_nearest), const rcti *rect)
+{
+#ifndef USE_GPU_SELECT
+ UNUSED_VARS(vc, scene, sl, v3d, ar, rect);
+#else
+ RegionView3D *rv3d = vc->rv3d;
+
+ /* backup (_never_ use rv3d->viewport) */
+ void *backup_viewport = vc->rv3d->viewport;
+ rv3d->viewport = NULL;
+
+ struct GPUViewport *viewport = GPU_viewport_create();
+ GPU_viewport_size_set(viewport, (const int[2]){BLI_rcti_size_x(rect), BLI_rcti_size_y(rect)});
+
+ bool cache_is_dirty;
+ DST.viewport = viewport;
+ v3d->zbuf = true;
+
+ /* Get list of enabled engines */
+ DRW_engines_enable_no_modes(scene);
+
+ /* Setup viewport */
+ cache_is_dirty = true;
+
+ /* Instead of 'DRW_context_state_init(C, &DST.draw_ctx)', assign from args */
+ DST.draw_ctx = (DRWContextState){
+ ar, rv3d, v3d, scene, sl, (bContext *)NULL,
+ };
+
+ DRW_viewport_var_init();
+
+ /* Update ubos */
+ DRW_globals_update();
+
+ /* Init engines */
+ DRW_engines_init();
+
+ /* TODO : tag to refresh by the deps graph */
+ /* ideally only refresh when objects are added/removed */
+ /* or render properties / materials change */
+ if (cache_is_dirty) {
+ int code = 1;
+
+ DRW_engines_cache_init();
+
+ /* TODO, use DEG_OBJECT_ITER or similar.
+ * Currently its not well suited for selection
+ * since it loops over Objects instead of bases and does so recursively. */
+ for (Base *base = sl->object_bases.first; base; base = base->next) {
+ base->selcol = code++;
+ DRW_select_id_set(base->selcol);
+
+ DRW_engines_cache_populate(base->object);
+ }
+
+ DRW_engines_cache_finish();
+ }
+
+ /* Start Drawing */
+ DRW_draw_callbacks_pre_scene();
+ DRW_engines_draw_scene();
+ DRW_draw_callbacks_post_scene();
+
+ DRW_state_reset();
+ DRW_engines_disable();
+
+ /* avoid accidental reuse */
+ memset(&DST, 0x0, sizeof(DST));
+
+ /* Cleanup for selection state */
+ GPU_viewport_free(viewport);
+ MEM_freeN(viewport);
+
+ /* restore */
+ rv3d->viewport = backup_viewport;
+#endif /* USE_GPU_SELECT */
+}
+
/* ****************************************** OTHER ***************************************** */
void DRW_context_state_init(const bContext *C, DRWContextState *r_draw_ctx)
diff --git a/source/blender/draw/modes/object_mode.c b/source/blender/draw/modes/object_mode.c
index 14478b377da..2bb0ec06383 100644
--- a/source/blender/draw/modes/object_mode.c
+++ b/source/blender/draw/modes/object_mode.c
@@ -219,16 +219,19 @@ static void OBJECT_engine_init(void *vedata)
{&txl->outlines_depth_tx, DRW_BUF_DEPTH_24, 0},
{&txl->outlines_color_tx, DRW_BUF_RGBA_8, DRW_TEX_FILTER},
};
- DRW_framebuffer_init(
- &fbl->outlines,
- (int)viewport_size[0], (int)viewport_size[1],
- tex, 2);
- DRWFboTexture blur_tex = {&txl->outlines_blur_tx, DRW_BUF_RGBA_8, DRW_TEX_FILTER};
- DRW_framebuffer_init(
- &fbl->blur,
- (int)viewport_size[0], (int)viewport_size[1],
- &blur_tex, 1);
+ if (DRW_viewport_is_fbo()) {
+ DRW_framebuffer_init(
+ &fbl->outlines,
+ (int)viewport_size[0], (int)viewport_size[1],
+ tex, 2);
+
+ DRWFboTexture blur_tex = {&txl->outlines_blur_tx, DRW_BUF_RGBA_8, DRW_TEX_FILTER};
+ DRW_framebuffer_init(
+ &fbl->blur,
+ (int)viewport_size[0], (int)viewport_size[1],
+ &blur_tex, 1);
+ }
if (!e_data.outline_resolve_sh) {
e_data.outline_resolve_sh = DRW_shader_create_fullscreen(datatoc_object_outline_resolve_frag_glsl, NULL);
@@ -1268,50 +1271,55 @@ static void OBJECT_draw_scene(void *vedata)
DefaultFramebufferList *dfbl = DRW_viewport_framebuffer_list_get();
float clearcol[4] = {0.0f, 0.0f, 0.0f, 0.0f};
- /* Render filled polygon on a separate framebuffer */
- DRW_framebuffer_bind(fbl->outlines);
- DRW_framebuffer_clear(true, true, false, clearcol, 1.0f);
- DRW_draw_pass(psl->outlines);
+ if (!DRW_viewport_is_select()) {
+ /* Render filled polygon on a separate framebuffer */
+ DRW_framebuffer_bind(fbl->outlines);
+ DRW_framebuffer_clear(true, true, false, clearcol, 1.0f);
+ DRW_draw_pass(psl->outlines);
- /* detach textures */
- DRW_framebuffer_texture_detach(txl->outlines_depth_tx);
+ /* detach textures */
+ DRW_framebuffer_texture_detach(txl->outlines_depth_tx);
- /* Search outline pixels */
- DRW_framebuffer_bind(fbl->blur);
- DRW_draw_pass(psl->outlines_search);
+ /* Search outline pixels */
+ DRW_framebuffer_bind(fbl->blur);
+ DRW_draw_pass(psl->outlines_search);
- /* Expand and fade gradually */
- DRW_framebuffer_bind(fbl->outlines);
- DRW_draw_pass(psl->outlines_expand);
+ /* Expand and fade gradually */
+ DRW_framebuffer_bind(fbl->outlines);
+ DRW_draw_pass(psl->outlines_expand);
- DRW_framebuffer_bind(fbl->blur);
- DRW_draw_pass(psl->outlines_fade1);
+ DRW_framebuffer_bind(fbl->blur);
+ DRW_draw_pass(psl->outlines_fade1);
- DRW_framebuffer_bind(fbl->outlines);
- DRW_draw_pass(psl->outlines_fade2);
+ DRW_framebuffer_bind(fbl->outlines);
+ DRW_draw_pass(psl->outlines_fade2);
- DRW_framebuffer_bind(fbl->blur);
- DRW_draw_pass(psl->outlines_fade3);
+ DRW_framebuffer_bind(fbl->blur);
+ DRW_draw_pass(psl->outlines_fade3);
- DRW_framebuffer_bind(fbl->outlines);
- DRW_draw_pass(psl->outlines_fade4);
+ DRW_framebuffer_bind(fbl->outlines);
+ DRW_draw_pass(psl->outlines_fade4);
- DRW_framebuffer_bind(fbl->blur);
- DRW_draw_pass(psl->outlines_fade5);
+ DRW_framebuffer_bind(fbl->blur);
+ DRW_draw_pass(psl->outlines_fade5);
- /* reattach */
- DRW_framebuffer_texture_attach(fbl->outlines, txl->outlines_depth_tx, 0, 0);
- DRW_framebuffer_bind(dfbl->default_fb);
+ /* reattach */
+ DRW_framebuffer_texture_attach(fbl->outlines, txl->outlines_depth_tx, 0, 0);
+ DRW_framebuffer_bind(dfbl->default_fb);
+ }
/* This needs to be drawn after the oultine */
DRW_draw_pass(psl->bone_wire);
DRW_draw_pass(psl->bone_solid);
DRW_draw_pass(psl->non_meshes);
DRW_draw_pass(psl->ob_center);
- DRW_draw_pass(psl->grid);
- /* Combine with scene buffer last */
- DRW_draw_pass(psl->outlines_resolve);
+ if (!DRW_viewport_is_select()) {
+ DRW_draw_pass(psl->grid);
+
+ /* Combine with scene buffer last */
+ DRW_draw_pass(psl->outlines_resolve);
+ }
}
void OBJECT_collection_settings_create(IDProperty *props)
diff --git a/source/blender/editors/space_view3d/view3d_view.c b/source/blender/editors/space_view3d/view3d_view.c
index 4cfb30a9dd7..9fa616cee01 100644
--- a/source/blender/editors/space_view3d/view3d_view.c
+++ b/source/blender/editors/space_view3d/view3d_view.c
@@ -62,6 +62,8 @@
#include "ED_screen.h"
#include "ED_armature.h"
+#include "DRW_engine.h"
+
#ifdef WITH_GAMEENGINE
# include "BLI_listbase.h"
@@ -1180,7 +1182,12 @@ int view3d_opengl_select(
GPU_select_begin(buffer, bufsize, &rect, gpu_select_mode, 0);
- ED_view3d_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest);
+ if (IS_VIEWPORT_LEGACY(vc->v3d)) {
+ ED_view3d_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest);
+ }
+ else {
+ DRW_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest, &rect);
+ }
hits = GPU_select_end();
@@ -1188,7 +1195,12 @@ int view3d_opengl_select(
if (do_passes) {
GPU_select_begin(buffer, bufsize, &rect, GPU_SELECT_NEAREST_SECOND_PASS, hits);
- ED_view3d_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest);
+ if (IS_VIEWPORT_LEGACY(vc->v3d)) {
+ ED_view3d_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest);
+ }
+ else {
+ DRW_draw_select_loop(vc, scene, sl, v3d, ar, use_obedit_skip, use_nearest, &rect);
+ }
GPU_select_end();
}
diff --git a/source/blender/gpu/GPU_viewport.h b/source/blender/gpu/GPU_viewport.h
index 36e1eea5d61..f1a4e0bbcdb 100644
--- a/source/blender/gpu/GPU_viewport.h
+++ b/source/blender/gpu/GPU_viewport.h
@@ -89,7 +89,8 @@ void *GPU_viewport_engine_data_create(GPUViewport *viewport, void *engine_type);
void *GPU_viewport_engine_data_get(GPUViewport *viewport, void *engine_type);
void *GPU_viewport_framebuffer_list_get(GPUViewport *viewport);
void *GPU_viewport_texture_list_get(GPUViewport *viewport);
-void GPU_viewport_size_get(GPUViewport *viewport, int *size);
+void GPU_viewport_size_get(const GPUViewport *viewport, int size[2]);
+void GPU_viewport_size_set(GPUViewport *viewport, const int size[2]);
bool GPU_viewport_cache_validate(GPUViewport *viewport, unsigned int hash);
diff --git a/source/blender/gpu/intern/gpu_viewport.c b/source/blender/gpu/intern/gpu_viewport.c
index 162b7e2d87a..3781a9c8be0 100644
--- a/source/blender/gpu/intern/gpu_viewport.c
+++ b/source/blender/gpu/intern/gpu_viewport.c
@@ -151,12 +151,22 @@ void *GPU_viewport_texture_list_get(GPUViewport *viewport)
return viewport->txl;
}
-void GPU_viewport_size_get(GPUViewport *viewport, int *size)
+void GPU_viewport_size_get(const GPUViewport *viewport, int size[2])
{
size[0] = viewport->size[0];
size[1] = viewport->size[1];
}
+/**
+ * Special case, this is needed for when we have a viewport without a frame-buffer output
+ * (occlusion queries for eg) but still need to set the size since it may be used for other calculations.
+ */
+void GPU_viewport_size_set(GPUViewport *viewport, const int size[2])
+{
+ viewport->size[0] = size[0];
+ viewport->size[1] = size[1];
+}
+
bool GPU_viewport_cache_validate(GPUViewport *viewport, unsigned int hash)
{
bool dirty = false;