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/CMakeLists.txt8
-rw-r--r--source/blender/draw/DRW_engine.h19
-rw-r--r--source/blender/draw/engines/clay/clay.c166
-rw-r--r--source/blender/draw/engines/clay/clay.h2
-rw-r--r--source/blender/draw/intern/DRW_render.h53
-rw-r--r--source/blender/draw/intern/draw_armature.c121
-rw-r--r--source/blender/draw/intern/draw_common.c315
-rw-r--r--source/blender/draw/intern/draw_common.h (renamed from source/blender/draw/intern/draw_mode_pass.h)60
-rw-r--r--source/blender/draw/intern/draw_manager.c381
-rw-r--r--source/blender/draw/intern/draw_mode_pass.c974
-rw-r--r--source/blender/draw/modes/draw_mode_engines.h (renamed from source/blender/draw/modes/object_mode.h)18
-rw-r--r--source/blender/draw/modes/edit_armature_mode.c123
-rw-r--r--source/blender/draw/modes/edit_armature_mode.h37
-rw-r--r--source/blender/draw/modes/edit_mesh_mode.c146
-rw-r--r--source/blender/draw/modes/edit_mesh_mode.h41
-rw-r--r--source/blender/draw/modes/object_mode.c593
-rw-r--r--source/blender/editors/space_view3d/CMakeLists.txt1
-rw-r--r--source/blender/editors/space_view3d/view3d_draw.c26
-rw-r--r--source/blender/gpu/GPU_viewport.h31
-rw-r--r--source/blender/gpu/intern/gpu_viewport.c173
-rw-r--r--source/blender/render/extern/include/RE_engine.h2
-rw-r--r--source/blender/render/intern/source/external_engine.c9
22 files changed, 1650 insertions, 1649 deletions
diff --git a/source/blender/draw/CMakeLists.txt b/source/blender/draw/CMakeLists.txt
index cb2681fcf81..c04063d22f8 100644
--- a/source/blender/draw/CMakeLists.txt
+++ b/source/blender/draw/CMakeLists.txt
@@ -52,7 +52,7 @@ set(INC_SYS
set(SRC
intern/draw_manager.c
- intern/draw_mode_pass.c
+ intern/draw_common.c
intern/draw_cache.c
intern/draw_view.c
intern/draw_armature.c
@@ -62,13 +62,11 @@ set(SRC
modes/object_mode.c
intern/DRW_render.h
- intern/draw_mode_pass.h
+ intern/draw_common.h
intern/draw_cache.h
intern/draw_view.h
engines/clay/clay.h
- modes/edit_armature_mode.h
- modes/edit_mesh_mode.h
- modes/object_mode.h
+ modes/draw_mode_engines.h
./DRW_engine.h
)
diff --git a/source/blender/draw/DRW_engine.h b/source/blender/draw/DRW_engine.h
index 05ecc7390d1..e8dc47245e3 100644
--- a/source/blender/draw/DRW_engine.h
+++ b/source/blender/draw/DRW_engine.h
@@ -30,10 +30,27 @@ struct CollectionEngineSettings;
struct DRWPass;
struct Material;
struct Scene;
+struct DrawEngineType;
+struct bContext;
+struct Object;
-void DRW_engines_init(void);
+/* Buffer and textures used by the viewport by default */
+typedef struct DefaultFramebufferList {
+ struct GPUFrameBuffer *default_fb;
+} DefaultFramebufferList;
+
+typedef struct DefaultTextureList {
+ struct GPUTexture *color;
+ struct GPUTexture *depth;
+} DefaultTextureList;
+
+void DRW_engines_register(void);
void DRW_engines_free(void);
+void DRW_engine_register(struct DrawEngineType *draw_engine_type);
+
+void DRW_draw_view(const struct bContext *C);
+
/* This is here because GPUViewport needs it */
void DRW_pass_free(struct DRWPass *pass);
diff --git a/source/blender/draw/engines/clay/clay.c b/source/blender/draw/engines/clay/clay.c
index cd19595b107..a91027cb314 100644
--- a/source/blender/draw/engines/clay/clay.c
+++ b/source/blender/draw/engines/clay/clay.c
@@ -124,6 +124,15 @@ typedef struct CLAY_PassList {
struct DRWPass *clay_pass;
} CLAY_PassList;
+typedef struct CLAY_Data {
+ char engine_name[32];
+ CLAY_FramebufferList *fbl;
+ CLAY_TextureList *txl;
+ CLAY_PassList *psl;
+ CLAY_StorageList *stl;
+} CLAY_Data;
+
+
//#define GTAO
/* Functions */
@@ -262,20 +271,12 @@ RenderEngineSettings *CLAY_render_settings_create(void)
return (RenderEngineSettings *)settings;
}
-MaterialEngineSettings *CLAY_material_settings_create(void)
-{
- MaterialEngineSettingsClay *settings = MEM_callocN(sizeof(MaterialEngineSettingsClay), "MaterialEngineSettingsClay");
-
- clay_material_settings_init(settings);
-
- return (MaterialEngineSettings *)settings;
-}
-
static void CLAY_engine_init(void)
{
- CLAY_StorageList *stl = DRW_engine_storage_list_get();
- CLAY_TextureList *txl = DRW_engine_texture_list_get();
- CLAY_FramebufferList *fbl = DRW_engine_framebuffer_list_get();
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_StorageList *stl = vedata->stl;
+ CLAY_TextureList *txl = vedata->txl;
+ CLAY_FramebufferList *fbl = vedata->fbl;
/* Create Texture Array */
if (!data.matcap_array) {
@@ -428,10 +429,11 @@ static void CLAY_engine_init(void)
static DRWShadingGroup *CLAY_shgroup_create(DRWPass *pass, int *material_id)
{
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_TextureList *txl = vedata->txl;
const int depthloc = 0, matcaploc = 1, jitterloc = 2, sampleloc = 3;
DRWShadingGroup *grp = DRW_shgroup_create(data.clay_sh, pass);
- CLAY_TextureList *txl = DRW_engine_texture_list_get();
DRW_shgroup_uniform_vec2(grp, "screenres", DRW_viewport_size_get(), 1);
DRW_shgroup_uniform_buffer(grp, "depthtex", &txl->depth_dup, depthloc);
@@ -599,9 +601,9 @@ static DRWShadingGroup *depth_shgrp_cull;
static void CLAY_cache_init(void)
{
- CLAY_PassList *psl = DRW_engine_pass_list_get();
- CLAY_StorageList *stl = DRW_engine_storage_list_get();
-
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_PassList *psl = vedata->psl;
+ CLAY_StorageList *stl = vedata->stl;
/* Depth Pass */
{
@@ -622,100 +624,46 @@ static void CLAY_cache_init(void)
static void CLAY_cache_populate(Object *ob)
{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
- CLAY_StorageList *stl = DRW_engine_storage_list_get();
- CLAY_PassList *psl = DRW_engine_pass_list_get();
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_PassList *psl = vedata->psl;
+ CLAY_StorageList *stl = vedata->stl;
+
struct Batch *geom;
DRWShadingGroup *clay_shgrp;
- bool do_occlude_wire = false;
- bool do_cull = false;
- CollectionEngineSettings *ces_mode_ed, *ces_mode_ob;
-
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- case CTX_MODE_EDIT_CURVE:
- case CTX_MODE_EDIT_SURFACE:
- case CTX_MODE_EDIT_TEXT:
- case CTX_MODE_EDIT_ARMATURE:
- case CTX_MODE_EDIT_METABALL:
- case CTX_MODE_EDIT_LATTICE:
- case CTX_MODE_POSE:
- case CTX_MODE_SCULPT:
- case CTX_MODE_PAINT_WEIGHT:
- case CTX_MODE_PAINT_VERTEX:
- case CTX_MODE_PAINT_TEXTURE:
- case CTX_MODE_PARTICLE:
- ces_mode_ed = BKE_object_collection_engine_get(ob, COLLECTION_MODE_EDIT, "");
- do_occlude_wire = BKE_collection_engine_property_value_get_bool(ces_mode_ed, "show_occlude_wire");
- break;
- case CTX_MODE_OBJECT:
- ces_mode_ob = BKE_object_collection_engine_get(ob, COLLECTION_MODE_OBJECT, "");
- do_cull = BKE_collection_engine_property_value_get_bool(ces_mode_ob, "show_backface_culling");
- break;
- }
- if (do_occlude_wire)
+ if (!DRW_is_object_renderable(ob))
return;
- switch (ob->type) {
- case OB_MESH:
- geom = DRW_cache_surface_get(ob);
+ CollectionEngineSettings *ces_mode_ob = BKE_object_collection_engine_get(ob, COLLECTION_MODE_OBJECT, "");
+ bool do_cull = BKE_collection_engine_property_value_get_bool(ces_mode_ob, "show_backface_culling");
- /* Depth Prepass */
- DRW_shgroup_call_add((do_cull) ? depth_shgrp_cull : depth_shgrp, geom, ob->obmat);
+ /* TODO all renderable */
+ if (ob->type == OB_MESH) {
+ geom = DRW_cache_surface_get(ob);
- /* Shading */
- clay_shgrp = CLAY_object_shgrp_get(ob, stl, psl);
- DRW_shgroup_call_add(clay_shgrp, geom, ob->obmat);
- break;
+ /* Depth Prepass */
+ DRW_shgroup_call_add((do_cull) ? depth_shgrp_cull : depth_shgrp, geom, ob->obmat);
+
+ /* Shading */
+ clay_shgrp = CLAY_object_shgrp_get(ob, stl, psl);
+ DRW_shgroup_call_add(clay_shgrp, geom, ob->obmat);
}
}
static void CLAY_cache_finish(void)
{
- CLAY_StorageList *stl = DRW_engine_storage_list_get();
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_StorageList *stl = vedata->stl;
DRW_uniformbuffer_update(stl->mat_ubo, &stl->storage->mat_storage);
}
-static void CLAY_view_draw(RenderEngine *UNUSED(engine), const bContext *context)
+static void CLAY_draw_scene(void)
{
- DRW_viewport_init(context);
-
- /* This function may run for multiple viewports
- * so get the current viewport buffers */
- CLAY_PassList *psl = DRW_engine_pass_list_get();
- CLAY_FramebufferList *fbl = DRW_engine_framebuffer_list_get();
-
- CLAY_engine_init();
- DRW_mode_init();
-
- /* TODO : tag to refresh by the deps graph */
- /* ideally only refresh when objects are added/removed */
- /* or render properties / materials change */
- if (DRW_viewport_cache_is_dirty()) {
-
- SceneLayer *sl = CTX_data_scene_layer(context);
-
- CLAY_cache_init();
- DRW_mode_cache_init();
-
- DEG_OBJECT_ITER(sl, ob);
- {
- CLAY_cache_populate(ob);
- DRW_mode_cache_populate(ob);
- }
- DEG_OBJECT_ITER_END
-
- CLAY_cache_finish();
- DRW_mode_cache_finish();
- }
-
- /* Start Drawing */
- DRW_draw_background();
-
- DRW_draw_callbacks_pre_scene();
+ CLAY_Data *vedata = DRW_viewport_engine_data_get("Clay");
+ CLAY_PassList *psl = vedata->psl;
+ CLAY_FramebufferList *fbl = vedata->fbl;
+ DefaultFramebufferList *dfbl = DRW_viewport_framebuffer_list_get();
/* Pass 1 : Depth pre-pass */
DRW_draw_pass(psl->depth_pass);
@@ -723,19 +671,10 @@ static void CLAY_view_draw(RenderEngine *UNUSED(engine), const bContext *context
/* Pass 2 : Duplicate depth */
/* Unless we go for deferred shading we need this to avoid manual depth test and artifacts */
- DRW_framebuffer_blit(fbl->default_fb, fbl->dupli_depth, true);
+ DRW_framebuffer_blit(dfbl->default_fb, fbl->dupli_depth, true);
/* Pass 3 : Shading */
DRW_draw_pass(psl->clay_pass);
-
- /* Pass 4 : Overlays */
- /* At this point all shaded geometry should have been rendered and their depth written */
- DRW_draw_mode_overlays();
-
- DRW_draw_callbacks_post_scene();
-
- /* Always finish by this */
- DRW_state_reset();
}
static void CLAY_collection_settings_create(RenderEngine *UNUSED(engine), CollectionEngineSettings *ces)
@@ -753,30 +692,39 @@ static void CLAY_collection_settings_create(RenderEngine *UNUSED(engine), Collec
BKE_collection_engine_property_add_float(ces, "ssao_factor_edge", 1.0f);
}
-void CLAY_engine_free(void)
+static void CLAY_engine_free(void)
{
- /* data.depth_sh Is builtin so it's automaticaly freed */
if (data.clay_sh) {
DRW_shader_free(data.clay_sh);
}
-
if (data.matcap_array) {
DRW_texture_free(data.matcap_array);
}
-
if (data.jitter_tx) {
DRW_texture_free(data.jitter_tx);
}
-
if (data.sampling_tx) {
DRW_texture_free(data.sampling_tx);
}
}
+DrawEngineType draw_engine_clay_type = {
+ NULL, NULL,
+ N_("Clay"),
+ &CLAY_engine_init,
+ &CLAY_engine_free,
+ &CLAY_cache_init,
+ &CLAY_cache_populate,
+ &CLAY_cache_finish,
+ NULL,
+ &CLAY_draw_scene
+};
+
RenderEngineType viewport_clay_type = {
NULL, NULL,
CLAY_ENGINE, N_("Clay"), RE_INTERNAL | RE_USE_OGL_PIPELINE,
- NULL, NULL, NULL, NULL, &CLAY_view_draw, NULL, &CLAY_collection_settings_create,
+ NULL, NULL, NULL, NULL, NULL, NULL, &CLAY_collection_settings_create,
+ &draw_engine_clay_type,
{NULL, NULL, NULL}
};
diff --git a/source/blender/draw/engines/clay/clay.h b/source/blender/draw/engines/clay/clay.h
index 34dd74b9500..1afe1ac5ea8 100644
--- a/source/blender/draw/engines/clay/clay.h
+++ b/source/blender/draw/engines/clay/clay.h
@@ -31,6 +31,4 @@ extern RenderEngineType viewport_clay_type;
struct RenderEngineSettings *CLAY_render_settings_create(void);
struct MaterialEngineSettings *CLAY_material_settings_create(void);
-void CLAY_engine_free(void);
-
#endif /* __CLAY_H__ */
diff --git a/source/blender/draw/intern/DRW_render.h b/source/blender/draw/intern/DRW_render.h
index 77687ebfaa4..27515686fd2 100644
--- a/source/blender/draw/intern/DRW_render.h
+++ b/source/blender/draw/intern/DRW_render.h
@@ -44,7 +44,7 @@
#include "DNA_material_types.h"
#include "DNA_scene_types.h"
-#include "draw_mode_pass.h"
+#include "draw_common.h"
#include "draw_cache.h"
#include "draw_view.h"
@@ -59,12 +59,42 @@ struct GPUTexture;
struct GPUUniformBuffer;
struct Object;
struct Batch;
+struct DefaultFramebufferList;
+struct DefaultTextureList;
typedef struct DRWUniform DRWUniform;
typedef struct DRWInterface DRWInterface;
typedef struct DRWPass DRWPass;
typedef struct DRWShadingGroup DRWShadingGroup;
+typedef struct DrawEngineType {
+ struct DrawEngineType *next, *prev;
+
+ char idname[32];
+
+ void (*engine_init)(void);
+ void (*engine_free)(void);
+
+ void (*cache_init)(void);
+ void (*cache_populate)(struct Object *ob);
+ void (*cache_finish)(void);
+
+ void (*draw_background)(void);
+ void (*draw_scene)(void);
+} DrawEngineType;
+
+#ifndef __DRW_ENGINE_H__
+/* Buffer and textures used by the viewport by default */
+typedef struct DefaultFramebufferList {
+ struct GPUFrameBuffer *default_fb;
+} DefaultFramebufferList;
+
+typedef struct DefaultTextureList {
+ struct GPUTexture *color;
+ struct GPUTexture *depth;
+} DefaultTextureList;
+#endif
+
/* Textures */
typedef enum {
@@ -199,27 +229,26 @@ typedef enum {
void DRW_viewport_init(const bContext *C);
void DRW_viewport_matrix_get(float mat[4][4], DRWViewportMatrixType type);
+void DRW_viewport_engine_data_set(const char *engine_name, void *fbl, void *txl, void *psl, void *stl);
+void *DRW_viewport_engine_data_get(const char *engine_name);
float *DRW_viewport_size_get(void);
float *DRW_viewport_screenvecs_get(void);
float *DRW_viewport_pixelsize_get(void);
bool DRW_viewport_is_persp_get(void);
bool DRW_viewport_cache_is_dirty(void);
+struct DefaultFramebufferList *DRW_viewport_framebuffer_list_get(void);
+struct DefaultTextureList *DRW_viewport_texture_list_get(void);
+
/* Settings */
+bool DRW_is_object_renderable(struct Object *ob);
#ifndef __DRW_ENGINE_H__
void *DRW_material_settings_get(Material *ma, const char *engine_name);
void *DRW_render_settings_get(Scene *scene, const char *engine_name);
#endif /* __DRW_ENGINE_H__ */
-/* Cache */
-void DRW_mode_init(void);
-void DRW_mode_cache_init(void);
-void DRW_mode_cache_populate(struct Object *ob);
-void DRW_mode_cache_finish(void);
-
/* Draw commands */
void DRW_draw_pass(DRWPass *pass);
-void DRW_draw_mode_overlays(void);
void DRW_draw_callbacks_pre_scene(void);
void DRW_draw_callbacks_post_scene(void);
@@ -229,12 +258,4 @@ void DRW_state_reset(void);
/* Other */
void DRW_get_dfdy_factors(float dfdyfac[2]);
const struct bContext *DRW_get_context(void);
-void *DRW_engine_pass_list_get(void);
-void *DRW_engine_storage_list_get(void);
-void *DRW_engine_texture_list_get(void);
-void *DRW_engine_framebuffer_list_get(void);
-void *DRW_mode_pass_list_get(void);
-void *DRW_mode_storage_list_get(void);
-void *DRW_mode_texture_list_get(void);
-void *DRW_mode_framebuffer_list_get(void);
#endif /* __DRW_RENDER_H__ */
diff --git a/source/blender/draw/intern/draw_armature.c b/source/blender/draw/intern/draw_armature.c
index 24a183d38ca..51c269a7b97 100644
--- a/source/blender/draw/intern/draw_armature.c
+++ b/source/blender/draw/intern/draw_armature.c
@@ -35,6 +35,8 @@
#include "DNA_view3d_types.h"
#include "DNA_object_types.h"
+#include "DRW_render.h"
+
#include "BLI_blenlib.h"
#include "BLI_math.h"
#include "BLI_dlrbTree.h"
@@ -56,11 +58,83 @@
#include "UI_resources.h"
-#include "draw_mode_pass.h"
+#include "draw_common.h"
#define BONE_VAR(eBone, pchan, var) ((eBone) ? (eBone->var) : (pchan->var))
#define BONE_FLAG(eBone, pchan) ((eBone) ? (eBone->flag) : (pchan->bone->flag))
+static Object *current_armature;
+/* Reset when changing current_armature */
+static DRWShadingGroup *bone_octahedral_solid;
+static DRWShadingGroup *bone_octahedral_wire;
+static DRWShadingGroup *bone_point_solid;
+static DRWShadingGroup *bone_point_wire;
+static DRWShadingGroup *bone_axes;
+static DRWShadingGroup *relationship_lines;
+
+static DRWPass *bone_solid;
+static DRWPass *bone_wire;
+
+/* Octahedral */
+static void DRW_shgroup_bone_octahedral_solid(const float (*bone_mat)[4], const float color[4])
+{
+ if (bone_octahedral_solid == NULL) {
+ struct Batch *geom = DRW_cache_bone_octahedral_get();
+ bone_octahedral_solid = shgroup_instance_objspace_solid(bone_solid, geom, current_armature->obmat);
+ }
+
+ DRW_shgroup_dynamic_call_add(bone_octahedral_solid, bone_mat, color);
+}
+
+static void DRW_shgroup_bone_octahedral_wire(const float (*bone_mat)[4], const float color[4])
+{
+ if (bone_octahedral_wire == NULL) {
+ struct Batch *geom = DRW_cache_bone_octahedral_wire_outline_get();
+ bone_octahedral_wire = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
+ }
+
+ DRW_shgroup_dynamic_call_add(bone_octahedral_wire, bone_mat, color);
+}
+
+/* Head and tail sphere */
+static void DRW_shgroup_bone_point_solid(const float (*bone_mat)[4], const float color[4])
+{
+ if (bone_point_solid == NULL) {
+ struct Batch *geom = DRW_cache_bone_point_get();
+ bone_point_solid = shgroup_instance_objspace_solid(bone_solid, geom, current_armature->obmat);
+ }
+
+ DRW_shgroup_dynamic_call_add(bone_point_solid, bone_mat, color);
+}
+
+static void DRW_shgroup_bone_point_wire(const float (*bone_mat)[4], const float color[4])
+{
+ if (bone_point_wire == NULL) {
+ struct Batch *geom = DRW_cache_bone_point_wire_outline_get();
+ bone_point_wire = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
+ }
+
+ DRW_shgroup_dynamic_call_add(bone_point_wire, bone_mat, color);
+}
+
+/* Axes */
+static void DRW_shgroup_bone_axes(const float (*bone_mat)[4], const float color[4])
+{
+ if (bone_axes == NULL) {
+ struct Batch *geom = DRW_cache_bone_arrows_get();
+ bone_axes = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
+ }
+
+ DRW_shgroup_dynamic_call_add(bone_axes, bone_mat, color);
+}
+
+/* Relationship lines */
+static void UNUSED_FUNCTION(DRW_shgroup_bone_relationship_lines)(const float head[3], const float tail[3])
+{
+ DRW_shgroup_dynamic_call_add(relationship_lines, head);
+ DRW_shgroup_dynamic_call_add(relationship_lines, tail);
+}
+
/* *************** Armature Drawing - Coloring API ***************************** */
static float colorBoneSolid[4];
@@ -246,7 +320,7 @@ static void draw_bone_octahedral(EditBone *eBone, bPoseChannel *pchan, bArmature
draw_points(eBone, pchan, arm);
}
-void draw_armature_edit(Object *ob)
+static void draw_armature_edit(Object *ob)
{
EditBone *eBone;
bArmature *arm = ob->data;
@@ -280,7 +354,7 @@ void draw_armature_edit(Object *ob)
}
/* if const_color is NULL do pose mode coloring */
-void draw_armature_pose(Object *ob, const float const_color[4])
+static void draw_armature_pose(Object *ob, const float const_color[4])
{
bArmature *arm = ob->data;
bPoseChannel *pchan;
@@ -325,4 +399,45 @@ void draw_armature_pose(Object *ob, const float const_color[4])
}
}
}
+}
+
+/* this function set the object space to use
+ * for all subsequent DRW_shgroup_bone_*** calls */
+static void DRW_shgroup_armature(
+ Object *ob, DRWPass *pass_bone_solid, DRWPass *pass_bone_wire, DRWShadingGroup *shgrp_relationship_lines)
+{
+ current_armature = ob;
+ bone_octahedral_solid = NULL;
+ bone_octahedral_wire = NULL;
+ bone_point_solid = NULL;
+ bone_point_wire = NULL;
+ bone_axes = NULL;
+
+ bone_solid = pass_bone_solid;
+ bone_wire = pass_bone_wire;
+ relationship_lines = shgrp_relationship_lines;
+}
+
+void DRW_shgroup_armature_object(
+ Object *ob, DRWPass *pass_bone_solid, DRWPass *pass_bone_wire, DRWShadingGroup *shgrp_relationship_lines)
+{
+ float *color;
+ DRW_object_wire_theme_get(ob, &color);
+
+ DRW_shgroup_armature(ob, pass_bone_solid, pass_bone_wire, shgrp_relationship_lines);
+ draw_armature_pose(ob, color);
+}
+
+void DRW_shgroup_armature_pose(
+ Object *ob, DRWPass *pass_bone_solid, DRWPass *pass_bone_wire, DRWShadingGroup *shgrp_relationship_lines)
+{
+ DRW_shgroup_armature(ob, pass_bone_solid, pass_bone_wire, shgrp_relationship_lines);
+ draw_armature_pose(ob, NULL);
+}
+
+void DRW_shgroup_armature_edit(
+ Object *ob, DRWPass *pass_bone_solid, DRWPass *pass_bone_wire, DRWShadingGroup *shgrp_relationship_lines)
+{
+ DRW_shgroup_armature(ob, pass_bone_solid, pass_bone_wire, shgrp_relationship_lines);
+ draw_armature_edit(ob);
} \ No newline at end of file
diff --git a/source/blender/draw/intern/draw_common.c b/source/blender/draw/intern/draw_common.c
new file mode 100644
index 00000000000..b9c73e8c352
--- /dev/null
+++ b/source/blender/draw/intern/draw_common.c
@@ -0,0 +1,315 @@
+/*
+ * Copyright 2016, Blender Foundation.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ *
+ * Contributor(s): Blender Institute
+ *
+ */
+
+/** \file blender/draw/intern/draw_common.c
+ * \ingroup draw
+ */
+
+#include "DRW_render.h"
+
+#include "GPU_shader.h"
+
+#include "UI_resources.h"
+
+#include "BKE_global.h"
+
+#include "draw_common.h"
+
+/* Colors & Constant */
+GlobalsUboStorage ts;
+struct GPUUniformBuffer *globals_ubo = NULL;
+
+void DRW_globals_update(void)
+{
+ UI_GetThemeColor4fv(TH_WIRE, ts.colorWire);
+ UI_GetThemeColor4fv(TH_WIRE_EDIT, ts.colorWireEdit);
+ UI_GetThemeColor4fv(TH_ACTIVE, ts.colorActive);
+ UI_GetThemeColor4fv(TH_SELECT, ts.colorSelect);
+ UI_GetThemeColor4fv(TH_TRANSFORM, ts.colorTransform);
+ UI_GetThemeColor4fv(TH_GROUP_ACTIVE, ts.colorGroupActive);
+ UI_GetThemeColor4fv(TH_GROUP, ts.colorGroup);
+ UI_GetThemeColor4fv(TH_LAMP, ts.colorLamp);
+ UI_GetThemeColor4fv(TH_SPEAKER, ts.colorSpeaker);
+ UI_GetThemeColor4fv(TH_CAMERA, ts.colorCamera);
+ UI_GetThemeColor4fv(TH_EMPTY, ts.colorEmpty);
+ UI_GetThemeColor4fv(TH_VERTEX, ts.colorVertex);
+ UI_GetThemeColor4fv(TH_VERTEX_SELECT, ts.colorVertexSelect);
+ UI_GetThemeColor4fv(TH_EDITMESH_ACTIVE, ts.colorEditMeshActive);
+ UI_GetThemeColor4fv(TH_EDGE_SELECT, ts.colorEdgeSelect);
+ UI_GetThemeColor4fv(TH_EDGE_SEAM, ts.colorEdgeSeam);
+ UI_GetThemeColor4fv(TH_EDGE_SHARP, ts.colorEdgeSharp);
+ UI_GetThemeColor4fv(TH_EDGE_CREASE, ts.colorEdgeCrease);
+ UI_GetThemeColor4fv(TH_EDGE_BEVEL, ts.colorEdgeBWeight);
+ UI_GetThemeColor4fv(TH_EDGE_FACESEL, ts.colorEdgeFaceSelect);
+ UI_GetThemeColor4fv(TH_FACE, ts.colorFace);
+ UI_GetThemeColor4fv(TH_FACE_SELECT, ts.colorFaceSelect);
+ UI_GetThemeColor4fv(TH_NORMAL, ts.colorNormal);
+ UI_GetThemeColor4fv(TH_VNORMAL, ts.colorVNormal);
+ UI_GetThemeColor4fv(TH_LNORMAL, ts.colorLNormal);
+ UI_GetThemeColor4fv(TH_FACE_DOT, ts.colorFaceDot);
+
+ UI_GetThemeColorShadeAlpha4fv(TH_TRANSFORM, 0, -80, ts.colorDeselect);
+ UI_GetThemeColorShadeAlpha4fv(TH_WIRE, 0, -30, ts.colorOutline);
+ UI_GetThemeColorShadeAlpha4fv(TH_LAMP, 0, 255, ts.colorLampNoAlpha);
+
+ ts.sizeLampCenter = (U.obcenter_dia + 1.5f) * U.pixelsize;
+ ts.sizeLampCircle = U.pixelsize * 9.0f;
+ ts.sizeLampCircleShadow = ts.sizeLampCircle + U.pixelsize * 3.0f;
+
+ /* M_SQRT2 to be at least the same size of the old square */
+ ts.sizeVertex = UI_GetThemeValuef(TH_VERTEX_SIZE) * M_SQRT2 / 2.0f;
+ ts.sizeFaceDot = UI_GetThemeValuef(TH_FACEDOT_SIZE) * M_SQRT2;
+ ts.sizeEdge = 1.0f / 2.0f; /* TODO Theme */
+ ts.sizeEdgeFix = 0.5f + 2.0f * (2.0f * (MAX2(ts.sizeVertex, ts.sizeEdge)) * M_SQRT1_2);
+ ts.sizeNormal = 1.0f; /* TODO compute */
+
+ /* TODO Waiting for notifiers to invalidate cache */
+ if (globals_ubo) {
+ DRW_uniformbuffer_free(globals_ubo);
+ }
+
+ globals_ubo = DRW_uniformbuffer_create(sizeof(GlobalsUboStorage), &ts);
+}
+
+/* ********************************* SHGROUP ************************************* */
+
+DRWShadingGroup *shgroup_dynlines_uniform_color(DRWPass *pass, float color[4])
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_UNIFORM_COLOR);
+
+ DRWShadingGroup *grp = DRW_shgroup_line_batch_create(sh, pass);
+ DRW_shgroup_uniform_vec4(grp, "color", color, 1);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_dynpoints_uniform_color(DRWPass *pass, float color[4], float *size)
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_POINT_UNIFORM_SIZE_UNIFORM_COLOR_AA);
+
+ DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
+ DRW_shgroup_uniform_vec4(grp, "color", color, 1);
+ DRW_shgroup_uniform_float(grp, "size", size, 1);
+ DRW_shgroup_state_set(grp, DRW_STATE_POINT);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_groundlines_uniform_color(DRWPass *pass, float color[4])
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_GROUNDLINE);
+
+ DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
+ DRW_shgroup_uniform_vec4(grp, "color", color, 1);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_groundpoints_uniform_color(DRWPass *pass, float color[4])
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_GROUNDPOINT);
+
+ DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
+ DRW_shgroup_uniform_vec4(grp, "color", color, 1);
+ DRW_shgroup_state_set(grp, DRW_STATE_POINT);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_instance_screenspace(DRWPass *pass, struct Batch *geom, float *size)
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_SCREENSPACE_VARIYING_COLOR);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
+ DRW_shgroup_attrib_float(grp, "world_pos", 3);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_uniform_float(grp, "size", size, 1);
+ DRW_shgroup_uniform_float(grp, "pixel_size", DRW_viewport_pixelsize_get(), 1);
+ DRW_shgroup_uniform_vec3(grp, "screen_vecs", DRW_viewport_screenvecs_get(), 2);
+ DRW_shgroup_state_set(grp, DRW_STATE_STIPPLE_3);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_instance_objspace_solid(DRWPass *pass, struct Batch *geom, float (*obmat)[4])
+{
+ static float light[3] = {0.0f, 0.0f, 1.0f};
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_OBJECTSPACE_SIMPLE_LIGHTING_VARIYING_COLOR);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+ DRW_shgroup_attrib_float(grp, "color", 4);
+ DRW_shgroup_uniform_mat4(grp, "ModelMatrix", (float *)obmat);
+ DRW_shgroup_uniform_vec3(grp, "light", light, 1);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_instance_objspace_wire(DRWPass *pass, struct Batch *geom, float (*obmat)[4])
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_OBJECTSPACE_VARIYING_COLOR);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+ DRW_shgroup_attrib_float(grp, "color", 4);
+ DRW_shgroup_uniform_mat4(grp, "ModelMatrix", (float *)obmat);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_instance_axis_names(DRWPass *pass, struct Batch *geom)
+{
+ GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_INSTANCE_SCREEN_ALIGNED_AXIS);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_attrib_float(grp, "size", 1);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+ DRW_shgroup_uniform_vec3(grp, "screen_vecs", DRW_viewport_screenvecs_get(), 2);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_instance(DRWPass *pass, struct Batch *geom)
+{
+ GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_INSTANCE_VARIYING_COLOR_VARIYING_SIZE);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_attrib_float(grp, "size", 1);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_camera_instance(DRWPass *pass, struct Batch *geom)
+{
+ GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_CAMERA);
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_attrib_float(grp, "corners", 8);
+ DRW_shgroup_attrib_float(grp, "depth", 1);
+ DRW_shgroup_attrib_float(grp, "tria", 4);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_distance_lines_instance(DRWPass *pass, struct Batch *geom)
+{
+ GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_DISTANCE_LINES);
+ static float point_size = 4.0f;
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_attrib_float(grp, "start", 1);
+ DRW_shgroup_attrib_float(grp, "end", 1);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+ DRW_shgroup_uniform_float(grp, "size", &point_size, 1);
+
+ return grp;
+}
+
+DRWShadingGroup *shgroup_spot_instance(DRWPass *pass, struct Batch *geom)
+{
+ GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_INSTANCE_EDGES_VARIYING_COLOR);
+ static bool True = true;
+ static bool False = false;
+
+ DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
+ DRW_shgroup_attrib_float(grp, "color", 3);
+ DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
+ DRW_shgroup_uniform_bool(grp, "drawFront", &False, 1);
+ DRW_shgroup_uniform_bool(grp, "drawBack", &False, 1);
+ DRW_shgroup_uniform_bool(grp, "drawSilhouette", &True, 1);
+
+ return grp;
+}
+
+/* ******************************************** WIRES *********************************************** */
+
+/* TODO FINISH */
+/* Get the wire color theme_id of an object based on it's state
+ * **color is a way to get a pointer to the static color var associated */
+int DRW_object_wire_theme_get(Object *ob, float **color)
+{
+ const bool is_edit = (ob->mode & OB_MODE_EDIT) != 0;
+ /* confusing logic here, there are 2 methods of setting the color
+ * 'colortab[colindex]' and 'theme_id', colindex overrides theme_id.
+ *
+ * note: no theme yet for 'colindex' */
+ int theme_id = is_edit ? TH_WIRE_EDIT : TH_WIRE;
+
+ if (//(scene->obedit == NULL) &&
+ ((G.moving & G_TRANSFORM_OBJ) != 0) &&
+ ((ob->base_flag & BASE_SELECTED) != 0))
+ {
+ theme_id = TH_TRANSFORM;
+ }
+ else {
+ /* Sets the 'theme_id' or fallback to wire */
+ if ((ob->flag & OB_FROMGROUP) != 0) {
+ if ((ob->base_flag & BASE_SELECTED) != 0) {
+ /* uses darker active color for non-active + selected */
+ theme_id = TH_GROUP_ACTIVE;
+
+ // if (scene->basact != base) {
+ // theme_shade = -16;
+ // }
+ }
+ else {
+ theme_id = TH_GROUP;
+ }
+ }
+ else {
+ if ((ob->base_flag & BASE_SELECTED) != 0) {
+ theme_id = //scene->basact == base ? TH_ACTIVE :
+ TH_SELECT;
+ }
+ else {
+ if (ob->type == OB_LAMP) theme_id = TH_LAMP;
+ else if (ob->type == OB_SPEAKER) theme_id = TH_SPEAKER;
+ else if (ob->type == OB_CAMERA) theme_id = TH_CAMERA;
+ else if (ob->type == OB_EMPTY) theme_id = TH_EMPTY;
+ /* fallback to TH_WIRE */
+ }
+ }
+ }
+
+ if (color != NULL) {
+ switch (theme_id) {
+ case TH_WIRE_EDIT: *color = ts.colorTransform; break;
+ case TH_ACTIVE: *color = ts.colorActive; break;
+ case TH_SELECT: *color = ts.colorSelect; break;
+ case TH_GROUP: *color = ts.colorGroup; break;
+ case TH_GROUP_ACTIVE: *color = ts.colorGroupActive; break;
+ case TH_TRANSFORM: *color = ts.colorTransform; break;
+ case OB_SPEAKER: *color = ts.colorSpeaker; break;
+ case OB_CAMERA: *color = ts.colorCamera; break;
+ case OB_EMPTY: *color = ts.colorEmpty; break;
+ case OB_LAMP: *color = ts.colorLamp; break;
+ default: *color = ts.colorWire; break;
+ }
+ }
+
+ return theme_id;
+}
diff --git a/source/blender/draw/intern/draw_mode_pass.h b/source/blender/draw/intern/draw_common.h
index fd66120f48d..400a7e73998 100644
--- a/source/blender/draw/intern/draw_mode_pass.h
+++ b/source/blender/draw/intern/draw_common.h
@@ -19,14 +19,15 @@
*
*/
-/** \file draw_mode_pass.h
+/** \file draw_common.h
* \ingroup draw
*/
-#ifndef __DRAW_MODE_PASS_H__
-#define __DRAW_MODE_PASS_H__
+#ifndef __DRAW_COMMON__
+#define __DRAW_COMMON__
struct DRWPass;
+struct DRWShadingGroup;
struct Batch;
struct Object;
@@ -72,37 +73,34 @@ typedef struct GlobalsUboStorage {
} GlobalsUboStorage;
/* Keep in sync with globalsBlock in shaders */
-void DRW_update_global_values(void);
+void DRW_globals_update(void);
-void DRW_mode_passes_setup(struct DRWPass **psl_wire_overlay,
- struct DRWPass **psl_wire_overlay_hidden_wire,
- struct DRWPass **psl_wire_outline,
- struct DRWPass **psl_non_meshes,
- struct DRWPass **psl_ob_center,
- struct DRWPass **psl_bone_solid,
- struct DRWPass **psl_bone_wire);
+struct DRWShadingGroup *shgroup_dynlines_uniform_color(struct DRWPass *pass, float color[4]);
+struct DRWShadingGroup *shgroup_dynpoints_uniform_color(struct DRWPass *pass, float color[4], float *size);
+struct DRWShadingGroup *shgroup_groundlines_uniform_color(struct DRWPass *pass, float color[4]);
+struct DRWShadingGroup *shgroup_groundpoints_uniform_color(struct DRWPass *pass, float color[4]);
+struct DRWShadingGroup *shgroup_instance_screenspace(struct DRWPass *pass, struct Batch *geom, float *size);
+struct DRWShadingGroup *shgroup_instance_objspace_solid(struct DRWPass *pass, struct Batch *geom, float (*obmat)[4]);
+struct DRWShadingGroup *shgroup_instance_objspace_wire(struct DRWPass *pass, struct Batch *geom, float (*obmat)[4]);
+struct DRWShadingGroup *shgroup_instance_axis_names(struct DRWPass *pass, struct Batch *geom);
+struct DRWShadingGroup *shgroup_instance(struct DRWPass *pass, struct Batch *geom);
+struct DRWShadingGroup *shgroup_camera_instance(struct DRWPass *pass, struct Batch *geom);
+struct DRWShadingGroup *shgroup_distance_lines_instance(struct DRWPass *pass, struct Batch *geom);
+struct DRWShadingGroup *shgroup_spot_instance(struct DRWPass *pass, struct Batch *geom);
-void DRW_shgroup_wire_outline(struct Object *ob, const bool do_front, const bool do_back, const bool do_outline);
-void DRW_shgroup_lamp(struct Object *ob);
-void DRW_shgroup_camera(struct Object *ob);
-void DRW_shgroup_empty(struct Object *ob);
-void DRW_shgroup_speaker(struct Object *ob);
-void DRW_shgroup_relationship_lines(struct Object *ob);
-void DRW_shgroup_object_center(struct Object *ob);
+int DRW_object_wire_theme_get(struct Object *ob, float **color);
-void DRW_shgroup_armature_object(struct Object *ob);
-void DRW_shgroup_armature_edit(struct Object *ob);
-void DRW_shgroup_armature_pose(struct Object *ob);
+/* draw_armature.c */
+void DRW_shgroup_armature_object(
+ struct Object *ob, struct DRWPass *pass_bone_solid,
+ struct DRWPass *pass_bone_wire, struct DRWShadingGroup *shgrp_relationship_lines);
-void DRW_shgroup_bone_octahedral_solid(const float (*arm_mat)[4], const float color[4]);
-void DRW_shgroup_bone_octahedral_wire(const float (*arm_mat)[4], const float color[4]);
-void DRW_shgroup_bone_point_solid(const float (*arm_mat)[4], const float color[4]);
-void DRW_shgroup_bone_point_wire(const float (*arm_mat)[4], const float color[4]);
-void DRW_shgroup_bone_relationship_lines(const float head[3], const float tail[3]);
-void DRW_shgroup_bone_axes(const float (*arm_mat)[4], const float color[4]);
+void DRW_shgroup_armature_pose(
+ struct Object *ob, struct DRWPass *pass_bone_solid,
+ struct DRWPass *pass_bone_wire, struct DRWShadingGroup *shgrp_relationship_lines);
-/* draw_armature.c */
-void draw_armature_edit(struct Object *ob);
-void draw_armature_pose(struct Object *ob, const float const_color[4]);
+void DRW_shgroup_armature_edit(
+ struct Object *ob, struct DRWPass *pass_bone_solid,
+ struct DRWPass *pass_bone_wire, struct DRWShadingGroup *shgrp_relationship_lines);
-#endif /* __DRAW_MODE_PASS_H__ */ \ No newline at end of file
+#endif /* __DRAW_COMMON__ */ \ No newline at end of file
diff --git a/source/blender/draw/intern/draw_manager.c b/source/blender/draw/intern/draw_manager.c
index 381414f06dc..54e5fa5440c 100644
--- a/source/blender/draw/intern/draw_manager.c
+++ b/source/blender/draw/intern/draw_manager.c
@@ -39,6 +39,7 @@
#include "DRW_render.h"
#include "DNA_view3d_types.h"
+#include "DNA_screen_types.h"
#include "ED_space_api.h"
@@ -55,9 +56,7 @@
#include "UI_resources.h"
-#include "object_mode.h"
-#include "edit_armature_mode.h"
-#include "edit_mesh_mode.h"
+#include "draw_mode_engines.h"
#include "clay.h"
#define MAX_ATTRIB_NAME 32
@@ -163,21 +162,25 @@ enum {
/* Render State */
static struct DRWGlobalState {
+ /* Rendering state */
GPUShader *shader;
- struct GPUFrameBuffer *default_framebuffer;
- FramebufferList *fbl, *fbl_mode;
- TextureList *txl, *txl_mode;
- PassList *psl, *psl_mode;
- StorageList *stl, *stl_mode;
ListBase bound_texs;
int tex_bind_id;
+
+ /* Per viewport */
+ GPUViewport *viewport;
+ struct GPUFrameBuffer *default_framebuffer;
float size[2];
float screenvecs[2][3];
float pixsize;
- /* Current rendering context set by DRW_viewport_init */
+
+ /* Current rendering context */
const struct bContext *context;
+ ListBase enabled_engines; /* RenderEngineType */
} DST = {NULL};
+ListBase DRW_engines = {NULL, NULL};
+
/* ***************************************** TEXTURES ******************************************/
static void drw_texture_get_format(DRWTextureFormat format, GPUTextureFormat *data_type, int *channels)
{
@@ -1067,28 +1070,6 @@ void DRW_state_reset(void)
set_state(state);
}
-void DRW_draw_mode_overlays(void)
-{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
-
- DRW_draw_grid();
-
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- EDIT_MESH_draw();
- break;
- case CTX_MODE_EDIT_ARMATURE:
- EDIT_ARMATURE_draw();
- break;
- case CTX_MODE_OBJECT:
- OBJECT_draw();
- break;
- }
-
- DRW_draw_manipulator();
- DRW_draw_region_info();
-}
#else
void DRW_draw_pass(DRWPass *UNUSED(pass))
{
@@ -1096,79 +1077,26 @@ void DRW_draw_pass(DRWPass *UNUSED(pass))
#endif
-/* ******************************************* Mode Engine Cache ****************************************** */
+/* ****************************************** Settings ******************************************/
-void DRW_mode_init(void)
+bool DRW_is_object_renderable(Object *ob)
{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
-
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- EDIT_MESH_init();
- break;
- case CTX_MODE_EDIT_ARMATURE:
- break;
- case CTX_MODE_OBJECT:
- break;
- }
-}
+ Scene *scene = CTX_data_scene(DST.context);
+ Object *obedit = scene->obedit;
-void DRW_mode_cache_init(void)
-{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
+ if (ob->type == OB_MESH) {
+ if (ob == obedit) {
+ CollectionEngineSettings *ces_mode_ed = BKE_object_collection_engine_get(ob, COLLECTION_MODE_EDIT, "");
+ bool do_occlude_wire = BKE_collection_engine_property_value_get_bool(ces_mode_ed, "show_occlude_wire");
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- EDIT_MESH_cache_init();
- break;
- case CTX_MODE_EDIT_ARMATURE:
- EDIT_ARMATURE_cache_init();
- break;
- case CTX_MODE_OBJECT:
- OBJECT_cache_init();
- break;
- }
-}
-
-void DRW_mode_cache_populate(Object *ob)
-{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
-
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- EDIT_MESH_cache_populate(ob);
- break;
- case CTX_MODE_EDIT_ARMATURE:
- EDIT_ARMATURE_cache_populate(ob);
- break;
- case CTX_MODE_OBJECT:
- OBJECT_cache_populate(ob);
- break;
+ if (do_occlude_wire)
+ return false;
+ }
}
-}
-
-void DRW_mode_cache_finish(void)
-{
- const bContext *C = DRW_get_context();
- int mode = CTX_data_mode_enum(C);
- switch (mode) {
- case CTX_MODE_EDIT_MESH:
- EDIT_MESH_cache_finish();
- break;
- case CTX_MODE_EDIT_ARMATURE:
- EDIT_ARMATURE_cache_finish();
- break;
- case CTX_MODE_OBJECT:
- OBJECT_cache_finish();
- break;
- }
+ return true;
}
-/* ****************************************** Settings ******************************************/
void *DRW_material_settings_get(Material *ma, const char *engine_name)
{
MaterialEngineSettings *ms = NULL;
@@ -1184,7 +1112,8 @@ void *DRW_material_settings_get(Material *ma, const char *engine_name)
/* TODO make render_settings_create a polymorphic function */
if (STREQ(engine_name, RE_engine_id_BLENDER_CLAY)) {
- ms->data = CLAY_material_settings_create();
+ /* No material support */
+ BLI_assert(false);
}
else {
/* No engine matched */
@@ -1309,6 +1238,15 @@ void DRW_framebuffer_blit(struct GPUFrameBuffer *fb_read, struct GPUFrameBuffer
}
/* ****************************************** Viewport ******************************************/
+void *DRW_viewport_engine_data_get(const char *engine_name)
+{
+ void *data = GPU_viewport_engine_data_get(DST.viewport, engine_name);
+
+ if (data == NULL) {
+ data = GPU_viewport_engine_data_create(DST.viewport, engine_name);
+ }
+ return data;
+}
float *DRW_viewport_size_get(void)
{
@@ -1325,20 +1263,21 @@ float *DRW_viewport_pixelsize_get(void)
return &DST.pixsize;
}
-void DRW_viewport_init(const bContext *C)
+/* It also stores viewport variable to an immutable place: DST
+ * 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)
{
RegionView3D *rv3d = CTX_wm_region_view3d(C);
- GPUViewport *viewport = rv3d->viewport;
-
- GPU_viewport_get_engine_data(viewport, &DST.fbl, &DST.txl, &DST.psl, &DST.stl);
- GPU_viewport_get_mode_data(viewport, &DST.fbl_mode, &DST.txl_mode, &DST.psl_mode, &DST.stl_mode);
/* Refresh DST.size */
- DefaultTextureList *txl = (DefaultTextureList *)DST.txl;
- DST.size[0] = (float)GPU_texture_width(txl->color);
- DST.size[1] = (float)GPU_texture_height(txl->color);
+ int size[2];
+ GPU_viewport_size_get(DST.viewport, size);
+ DST.size[0] = size[0];
+ DST.size[1] = size[1];
- DefaultFramebufferList *fbl = (DefaultFramebufferList *)DST.fbl;
+ DefaultFramebufferList *fbl = (DefaultFramebufferList *)GPU_viewport_framebuffer_list_get(DST.viewport);
DST.default_framebuffer = fbl->default_fb;
/* Refresh DST.screenvecs */
@@ -1352,8 +1291,6 @@ void DRW_viewport_init(const bContext *C)
/* Save context for all later needs */
DST.context = C;
-
- DRW_update_global_values();
}
void DRW_viewport_matrix_get(float mat[4][4], DRWViewportMatrixType type)
@@ -1374,77 +1311,251 @@ bool DRW_viewport_is_persp_get(void)
return rv3d->is_persp;
}
-bool DRW_viewport_cache_is_dirty(void)
+DefaultFramebufferList *DRW_viewport_framebuffer_list_get(void)
{
- /* TODO Use a dirty flag */
- return (DST.psl->passes[0] == NULL);
+ return GPU_viewport_framebuffer_list_get(DST.viewport);
}
-/* ****************************************** OTHER ***************************************** */
+DefaultTextureList *DRW_viewport_texture_list_get(void)
+{
+ return GPU_viewport_texture_list_get(DST.viewport);
+}
-const bContext *DRW_get_context(void)
+/* **************************************** RENDERING ************************************** */
+
+static void DRW_engines_init(void)
{
- return DST.context;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->engine_init) {
+ engine->engine_init();
+ }
+ }
}
-void *DRW_engine_pass_list_get(void)
+static void DRW_engines_cache_init(void)
{
- return DST.psl;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->cache_init) {
+ engine->cache_init();
+ }
+ }
}
-void *DRW_engine_storage_list_get(void)
+static void DRW_engines_cache_populate(Object *ob)
{
- return DST.stl;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->cache_populate) {
+ engine->cache_populate(ob);
+ }
+ }
}
-void *DRW_engine_texture_list_get(void)
+static void DRW_engines_cache_finish(void)
{
- return DST.txl;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->cache_finish) {
+ engine->cache_finish();
+ }
+ }
}
-void *DRW_engine_framebuffer_list_get(void)
+static void DRW_engines_draw_background(void)
{
- return DST.fbl;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->draw_background) {
+ engine->draw_background();
+ return;
+ }
+ }
+
+ /* No draw_background found, doing default background */
+ DRW_draw_background();
}
-void *DRW_mode_pass_list_get(void)
+static void DRW_engines_draw_scene(void)
{
- return DST.psl_mode;
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ if (engine->draw_scene) {
+ engine->draw_scene();
+ }
+ }
}
-void *DRW_mode_storage_list_get(void)
+static void use_drw_engine(DrawEngineType *engine)
{
- return DST.stl_mode;
+ LinkData *ld = MEM_callocN(sizeof(LinkData), "enabled engine link data");
+ ld->data = engine;
+ BLI_addtail(&DST.enabled_engines, ld);
}
-void *DRW_mode_texture_list_get(void)
+/* 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)
{
- return DST.txl_mode;
+ /* TODO layers */
+ Scene *scene = CTX_data_scene(C);
+ RenderEngineType *type = RE_engines_find(scene->r.engine);
+ use_drw_engine(type->draw_engine);
+
+ /* TODO Refine the folowing logic based on objects states
+ * not on global state.
+ * Order is important */
+ use_drw_engine(&draw_engine_object_type);
+
+ switch (CTX_data_mode_enum(C)) {
+ case CTX_MODE_EDIT_MESH:
+ use_drw_engine(&draw_engine_edit_mesh_type);
+ break;
+ case CTX_MODE_EDIT_CURVE:
+ break;
+ case CTX_MODE_EDIT_SURFACE:
+ break;
+ case CTX_MODE_EDIT_TEXT:
+ break;
+ case CTX_MODE_EDIT_ARMATURE:
+ use_drw_engine(&draw_engine_edit_armature_type);
+ break;
+ case CTX_MODE_EDIT_METABALL:
+ break;
+ case CTX_MODE_EDIT_LATTICE:
+ break;
+ case CTX_MODE_POSE:
+ break;
+ case CTX_MODE_SCULPT:
+ break;
+ case CTX_MODE_PAINT_WEIGHT:
+ break;
+ case CTX_MODE_PAINT_VERTEX:
+ break;
+ case CTX_MODE_PAINT_TEXTURE:
+ break;
+ case CTX_MODE_PARTICLE:
+ break;
+ case CTX_MODE_OBJECT:
+ break;
+ }
}
-void *DRW_mode_framebuffer_list_get(void)
+static void DRW_engines_disable(void)
{
- return DST.fbl_mode;
+ BLI_freelistN(&DST.enabled_engines);
+}
+
+static int DRW_engines_get_hash(void)
+{
+ unsigned int hash = 0;
+ /* The cache depends on enabled engines */
+ /* FIXME : if collision occurs ... segfault */
+ for (LinkData *link = DST.enabled_engines.first; link; link = link->next) {
+ DrawEngineType *engine = link->data;
+ hash += BLI_ghashutil_strhash_p(engine->idname);
+ }
+
+ return hash;
+}
+
+/* Everything starts here.
+ * This function takes care of calling all cache and rendering functions
+ * for each relevant engine / mode engine. */
+void DRW_draw_view(const bContext *C)
+{
+ bool cache_is_dirty;
+ RegionView3D *rv3d = CTX_wm_region_view3d(C);
+ View3D *v3d = CTX_wm_view3d(C);
+ DST.viewport = rv3d->viewport;
+ v3d->zbuf = true;
+
+ /* Get list of enabled engines */
+ DRW_engines_enable(C);
+
+ /* Setup viewport */
+ cache_is_dirty = GPU_viewport_cache_validate(DST.viewport, DRW_engines_get_hash());
+ DRW_viewport_var_init(C);
+
+ /* 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) {
+ SceneLayer *sl = CTX_data_scene_layer(C);
+
+ DRW_engines_cache_init();
+ DEG_OBJECT_ITER(sl, ob);
+ {
+ DRW_engines_cache_populate(ob);
+ }
+ DEG_OBJECT_ITER_END
+ DRW_engines_cache_finish();
+ }
+
+ /* Start Drawing */
+ DRW_engines_draw_background();
+
+ DRW_draw_callbacks_pre_scene();
+ DRW_engines_draw_scene();
+ DRW_draw_callbacks_post_scene();
+
+ DRW_draw_region_info();
+
+ DRW_state_reset();
+ DRW_engines_disable();
+
+ /* Unbind fbo and draw result */
+ GPU_viewport_unbind(DST.viewport);
+}
+
+/* ****************************************** OTHER ***************************************** */
+
+const bContext *DRW_get_context(void)
+{
+ return DST.context;
}
/* ****************************************** INIT ***************************************** */
-void DRW_engines_init(void)
+void DRW_engine_register(DrawEngineType *draw_engine_type)
+{
+ BLI_addtail(&DRW_engines, draw_engine_type);
+}
+
+void DRW_engines_register(void)
{
#ifdef WITH_CLAY_ENGINE
RE_engines_register(NULL, &viewport_clay_type);
+
+ DRW_engine_register(&draw_engine_object_type);
+ DRW_engine_register(&draw_engine_edit_mesh_type);
+ DRW_engine_register(&draw_engine_edit_armature_type);
#endif
}
-extern struct GPUUniformBuffer *globals_ubo; /* draw_mode_pass.c */
+extern struct GPUUniformBuffer *globals_ubo; /* draw_common.c */
void DRW_engines_free(void)
{
#ifdef WITH_CLAY_ENGINE
- CLAY_engine_free();
+ DRW_shape_cache_free();
- EDIT_MESH_engine_free();
+ DrawEngineType *next;
+ for (DrawEngineType *type = DRW_engines.first; type; type = next) {
+ next = type->next;
+ BLI_remlink(&R_engines, type);
- DRW_shape_cache_free();
+ if (type->engine_free) {
+ type->engine_free();
+ }
+ }
if (globals_ubo)
GPU_uniformbuffer_free(globals_ubo);
diff --git a/source/blender/draw/intern/draw_mode_pass.c b/source/blender/draw/intern/draw_mode_pass.c
deleted file mode 100644
index b21e6a23b72..00000000000
--- a/source/blender/draw/intern/draw_mode_pass.c
+++ /dev/null
@@ -1,974 +0,0 @@
-/*
- * Copyright 2016, Blender Foundation.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- * Contributor(s): Blender Institute
- *
- */
-
-/** \file blender/draw/intern/draw_mode_pass.c
- * \ingroup draw
- */
-
-#include "DNA_camera_types.h"
-#include "DNA_userdef_types.h"
-#include "DNA_view3d_types.h"
-#include "DNA_world_types.h"
-
-#include "GPU_shader.h"
-
-#include "UI_resources.h"
-
-#include "BKE_global.h"
-#include "BKE_camera.h"
-
-#include "DRW_render.h"
-
-#include "draw_mode_pass.h"
-
-/* ************************** OBJECT MODE ******************************* */
-
-/* Store list of shading group for easy access*/
-
-/* Empties */
-static DRWShadingGroup *plain_axes;
-static DRWShadingGroup *cube;
-static DRWShadingGroup *circle;
-static DRWShadingGroup *sphere;
-static DRWShadingGroup *cone;
-static DRWShadingGroup *single_arrow;
-static DRWShadingGroup *single_arrow_line;
-static DRWShadingGroup *arrows;
-static DRWShadingGroup *axis_names;
-
-/* Speaker */
-static DRWShadingGroup *speaker;
-
-/* Lamps */
-static DRWShadingGroup *lamp_center;
-static DRWShadingGroup *lamp_center_group;
-static DRWShadingGroup *lamp_groundpoint;
-static DRWShadingGroup *lamp_groundline;
-static DRWShadingGroup *lamp_circle;
-static DRWShadingGroup *lamp_circle_shadow;
-static DRWShadingGroup *lamp_sunrays;
-static DRWShadingGroup *lamp_distance;
-static DRWShadingGroup *lamp_buflimit;
-static DRWShadingGroup *lamp_buflimit_points;
-static DRWShadingGroup *lamp_area;
-static DRWShadingGroup *lamp_hemi;
-static DRWShadingGroup *lamp_spot_cone;
-static DRWShadingGroup *lamp_spot_blend;
-static DRWShadingGroup *lamp_spot_pyramid;
-static DRWShadingGroup *lamp_spot_blend_rect;
-
-/* Helpers */
-static DRWShadingGroup *relationship_lines;
-
-/* Objects Centers */
-static DRWShadingGroup *center_active;
-static DRWShadingGroup *center_selected;
-static DRWShadingGroup *center_deselected;
-
-/* Camera */
-static DRWShadingGroup *camera;
-static DRWShadingGroup *camera_tria;
-static DRWShadingGroup *camera_focus;
-static DRWShadingGroup *camera_clip;
-static DRWShadingGroup *camera_clip_points;
-static DRWShadingGroup *camera_mist;
-static DRWShadingGroup *camera_mist_points;
-
-/* Colors & Constant */
-GlobalsUboStorage ts;
-struct GPUUniformBuffer *globals_ubo = NULL;
-
-void DRW_update_global_values(void)
-{
- UI_GetThemeColor4fv(TH_WIRE, ts.colorWire);
- UI_GetThemeColor4fv(TH_WIRE_EDIT, ts.colorWireEdit);
- UI_GetThemeColor4fv(TH_ACTIVE, ts.colorActive);
- UI_GetThemeColor4fv(TH_SELECT, ts.colorSelect);
- UI_GetThemeColor4fv(TH_TRANSFORM, ts.colorTransform);
- UI_GetThemeColor4fv(TH_GROUP_ACTIVE, ts.colorGroupActive);
- UI_GetThemeColor4fv(TH_GROUP, ts.colorGroup);
- UI_GetThemeColor4fv(TH_LAMP, ts.colorLamp);
- UI_GetThemeColor4fv(TH_SPEAKER, ts.colorSpeaker);
- UI_GetThemeColor4fv(TH_CAMERA, ts.colorCamera);
- UI_GetThemeColor4fv(TH_EMPTY, ts.colorEmpty);
- UI_GetThemeColor4fv(TH_VERTEX, ts.colorVertex);
- UI_GetThemeColor4fv(TH_VERTEX_SELECT, ts.colorVertexSelect);
- UI_GetThemeColor4fv(TH_EDITMESH_ACTIVE, ts.colorEditMeshActive);
- UI_GetThemeColor4fv(TH_EDGE_SELECT, ts.colorEdgeSelect);
- UI_GetThemeColor4fv(TH_EDGE_SEAM, ts.colorEdgeSeam);
- UI_GetThemeColor4fv(TH_EDGE_SHARP, ts.colorEdgeSharp);
- UI_GetThemeColor4fv(TH_EDGE_CREASE, ts.colorEdgeCrease);
- UI_GetThemeColor4fv(TH_EDGE_BEVEL, ts.colorEdgeBWeight);
- UI_GetThemeColor4fv(TH_EDGE_FACESEL, ts.colorEdgeFaceSelect);
- UI_GetThemeColor4fv(TH_FACE, ts.colorFace);
- UI_GetThemeColor4fv(TH_FACE_SELECT, ts.colorFaceSelect);
- UI_GetThemeColor4fv(TH_NORMAL, ts.colorNormal);
- UI_GetThemeColor4fv(TH_VNORMAL, ts.colorVNormal);
- UI_GetThemeColor4fv(TH_LNORMAL, ts.colorLNormal);
- UI_GetThemeColor4fv(TH_FACE_DOT, ts.colorFaceDot);
-
- UI_GetThemeColorShadeAlpha4fv(TH_TRANSFORM, 0, -80, ts.colorDeselect);
- UI_GetThemeColorShadeAlpha4fv(TH_WIRE, 0, -30, ts.colorOutline);
- UI_GetThemeColorShadeAlpha4fv(TH_LAMP, 0, 255, ts.colorLampNoAlpha);
-
- ts.sizeLampCenter = (U.obcenter_dia + 1.5f) * U.pixelsize;
- ts.sizeLampCircle = U.pixelsize * 9.0f;
- ts.sizeLampCircleShadow = ts.sizeLampCircle + U.pixelsize * 3.0f;
-
- /* M_SQRT2 to be at least the same size of the old square */
- ts.sizeVertex = UI_GetThemeValuef(TH_VERTEX_SIZE) * M_SQRT2 / 2.0f;
- ts.sizeFaceDot = UI_GetThemeValuef(TH_FACEDOT_SIZE) * M_SQRT2;
- ts.sizeEdge = 1.0f / 2.0f; /* TODO Theme */
- ts.sizeEdgeFix = 0.5f + 2.0f * (2.0f * (MAX2(ts.sizeVertex, ts.sizeEdge)) * M_SQRT1_2);
- ts.sizeNormal = 1.0f; /* TODO compute */
-
- /* TODO Waiting for notifiers to invalidate cache */
- if (globals_ubo) {
- DRW_uniformbuffer_free(globals_ubo);
- }
-
- globals_ubo = DRW_uniformbuffer_create(sizeof(GlobalsUboStorage), &ts);
-}
-
-/* Store list of passes for easy access */
-static DRWPass *wire_overlay;
-static DRWPass *wire_overlay_hidden_wire;
-static DRWPass *wire_outline;
-static DRWPass *non_meshes;
-static DRWPass *ob_center;
-static DRWPass *bone_solid;
-static DRWPass *bone_wire;
-
-static DRWShadingGroup *shgroup_dynlines_uniform_color(DRWPass *pass, float color[4])
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_UNIFORM_COLOR);
-
- DRWShadingGroup *grp = DRW_shgroup_line_batch_create(sh, pass);
- DRW_shgroup_uniform_vec4(grp, "color", color, 1);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_dynpoints_uniform_color(DRWPass *pass, float color[4], float *size)
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_POINT_UNIFORM_SIZE_UNIFORM_COLOR_AA);
-
- DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
- DRW_shgroup_uniform_vec4(grp, "color", color, 1);
- DRW_shgroup_uniform_float(grp, "size", size, 1);
- DRW_shgroup_state_set(grp, DRW_STATE_POINT);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_groundlines_uniform_color(DRWPass *pass, float color[4])
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_GROUNDLINE);
-
- DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
- DRW_shgroup_uniform_vec4(grp, "color", color, 1);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_groundpoints_uniform_color(DRWPass *pass, float color[4])
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_GROUNDPOINT);
-
- DRWShadingGroup *grp = DRW_shgroup_point_batch_create(sh, pass);
- DRW_shgroup_uniform_vec4(grp, "color", color, 1);
- DRW_shgroup_state_set(grp, DRW_STATE_POINT);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_instance_screenspace(DRWPass *pass, struct Batch *geom, float *size)
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_SCREENSPACE_VARIYING_COLOR);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
- DRW_shgroup_attrib_float(grp, "world_pos", 3);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_uniform_float(grp, "size", size, 1);
- DRW_shgroup_uniform_float(grp, "pixel_size", DRW_viewport_pixelsize_get(), 1);
- DRW_shgroup_uniform_vec3(grp, "screen_vecs", DRW_viewport_screenvecs_get(), 2);
- DRW_shgroup_state_set(grp, DRW_STATE_STIPPLE_3);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_instance_objspace_solid(DRWPass *pass, struct Batch *geom, float (*obmat)[4])
-{
- static float light[3] = {0.0f, 0.0f, 1.0f};
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_OBJECTSPACE_SIMPLE_LIGHTING_VARIYING_COLOR);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
- DRW_shgroup_attrib_float(grp, "color", 4);
- DRW_shgroup_uniform_mat4(grp, "ModelMatrix", (float *)obmat);
- DRW_shgroup_uniform_vec3(grp, "light", light, 1);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_instance_objspace_wire(DRWPass *pass, struct Batch *geom, float (*obmat)[4])
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_OBJECTSPACE_VARIYING_COLOR);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
- DRW_shgroup_attrib_float(grp, "color", 4);
- DRW_shgroup_uniform_mat4(grp, "ModelMatrix", (float *)obmat);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_instance_axis_names(DRWPass *pass, struct Batch *geom)
-{
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_INSTANCE_SCREEN_ALIGNED_AXIS);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh, pass, geom);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_attrib_float(grp, "size", 1);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
- DRW_shgroup_uniform_vec3(grp, "screen_vecs", DRW_viewport_screenvecs_get(), 2);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_instance(DRWPass *pass, struct Batch *geom)
-{
- GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_INSTANCE_VARIYING_COLOR_VARIYING_SIZE);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_attrib_float(grp, "size", 1);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_camera_instance(DRWPass *pass, struct Batch *geom)
-{
- GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_CAMERA);
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_attrib_float(grp, "corners", 8);
- DRW_shgroup_attrib_float(grp, "depth", 1);
- DRW_shgroup_attrib_float(grp, "tria", 4);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_distance_lines_instance(DRWPass *pass, struct Batch *geom)
-{
- GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_DISTANCE_LINES);
- static float point_size = 4.0f;
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_attrib_float(grp, "start", 1);
- DRW_shgroup_attrib_float(grp, "end", 1);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
- DRW_shgroup_uniform_float(grp, "size", &point_size, 1);
-
- return grp;
-}
-
-static DRWShadingGroup *shgroup_spot_instance(DRWPass *pass, struct Batch *geom)
-{
- GPUShader *sh_inst = GPU_shader_get_builtin_shader(GPU_SHADER_INSTANCE_EDGES_VARIYING_COLOR);
- static bool True = true;
- static bool False = false;
-
- DRWShadingGroup *grp = DRW_shgroup_instance_create(sh_inst, pass, geom);
- DRW_shgroup_attrib_float(grp, "color", 3);
- DRW_shgroup_attrib_float(grp, "InstanceModelMatrix", 16);
- DRW_shgroup_uniform_bool(grp, "drawFront", &False, 1);
- DRW_shgroup_uniform_bool(grp, "drawBack", &False, 1);
- DRW_shgroup_uniform_bool(grp, "drawSilhouette", &True, 1);
-
- return grp;
-}
-
-/* This Function setup the passes needed for the mode rendering.
- * The passes are populated by the rendering engines using the DRW_shgroup_* functions.
- * If a pass is not needed use NULL instead of the pass pointer */
-void DRW_mode_passes_setup(DRWPass **psl_wire_overlay,
- DRWPass **psl_wire_overlay_hidden_wire,
- DRWPass **psl_wire_outline,
- DRWPass **psl_non_meshes,
- DRWPass **psl_ob_center,
- DRWPass **psl_bone_solid,
- DRWPass **psl_bone_wire)
-{
-
-
- if (psl_wire_overlay) {
- /* This pass can draw mesh edges top of Shaded Meshes without any Z fighting */
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_BLEND;
- *psl_wire_overlay = DRW_pass_create("Wire Overlays Pass", state);
- }
-
- if (psl_wire_overlay_hidden_wire) {
- /* This pass can draw mesh edges top of Shaded Meshes without any Z fighting */
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_EQUAL | DRW_STATE_BLEND;
- *psl_wire_overlay_hidden_wire = DRW_pass_create("Wire Overlays Pass", state);
- }
-
- if (psl_wire_outline) {
- /* This pass can draw mesh outlines and/or fancy wireframe */
- /* Fancy wireframes are not meant to be occluded (without Z offset) */
- /* Outlines and Fancy Wires use the same VBO */
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND;
- *psl_wire_outline = DRW_pass_create("Wire + Outlines Pass", state);
- }
-
- if (psl_bone_solid) {
- /* Solid bones */
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS;
- *psl_bone_solid = DRW_pass_create("Bone Solid Pass", state);
- }
-
- if (psl_bone_wire) {
- /* Wire bones */
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND;
- *psl_bone_wire = DRW_pass_create("Bone Wire Pass", state);
- }
-
- if (psl_non_meshes) {
- /* Non Meshes Pass (Camera, empties, lamps ...) */
- struct Batch *geom;
-
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND | DRW_STATE_POINT;
- state |= DRW_STATE_WIRE;
- *psl_non_meshes = DRW_pass_create("Non Meshes Pass", state);
-
- /* Empties */
- geom = DRW_cache_plain_axes_get();
- plain_axes = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_cube_get();
- cube = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_circle_get();
- circle = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_empty_sphere_get();
- sphere = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_empty_cone_get();
- cone = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_arrow_get();
- single_arrow = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_line_get();
- single_arrow_line = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_arrows_get();
- arrows = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_axis_names_get();
- axis_names = shgroup_instance_axis_names(*psl_non_meshes, geom);
-
- /* Speaker */
- geom = DRW_cache_speaker_get();
- speaker = shgroup_instance(*psl_non_meshes, geom);
-
- /* Camera */
- geom = DRW_cache_camera_get();
- camera = shgroup_camera_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_camera_tria_get();
- camera_tria = shgroup_camera_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_plain_axes_get();
- camera_focus = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_line_get();
- camera_clip = shgroup_distance_lines_instance(*psl_non_meshes, geom);
- camera_mist = shgroup_distance_lines_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_line_endpoints_get();
- camera_clip_points = shgroup_distance_lines_instance(*psl_non_meshes, geom);
- camera_mist_points = shgroup_distance_lines_instance(*psl_non_meshes, geom);
-
- /* Lamps */
- /* TODO
- * for now we create multiple times the same VBO with only lamp center coordinates
- * but ideally we would only create it once */
-
- /* start with buflimit because we don't want stipples */
- geom = DRW_cache_single_line_get();
- lamp_buflimit = shgroup_distance_lines_instance(*psl_non_meshes, geom);
-
- lamp_center = shgroup_dynpoints_uniform_color(*psl_non_meshes, ts.colorLampNoAlpha, &ts.sizeLampCenter);
- lamp_center_group = shgroup_dynpoints_uniform_color(*psl_non_meshes, ts.colorGroup, &ts.sizeLampCenter);
-
- geom = DRW_cache_lamp_get();
- lamp_circle = shgroup_instance_screenspace(*psl_non_meshes, geom, &ts.sizeLampCircle);
- lamp_circle_shadow = shgroup_instance_screenspace(*psl_non_meshes, geom, &ts.sizeLampCircleShadow);
-
- geom = DRW_cache_lamp_sunrays_get();
- lamp_sunrays = shgroup_instance_screenspace(*psl_non_meshes, geom, &ts.sizeLampCircle);
-
- lamp_groundline = shgroup_groundlines_uniform_color(*psl_non_meshes, ts.colorLamp);
- lamp_groundpoint = shgroup_groundpoints_uniform_color(*psl_non_meshes, ts.colorLamp);
-
- geom = DRW_cache_lamp_area_get();
- lamp_area = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_lamp_hemi_get();
- lamp_hemi = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_line_get();
- lamp_distance = shgroup_distance_lines_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_single_line_endpoints_get();
- lamp_buflimit_points = shgroup_distance_lines_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_lamp_spot_get();
- lamp_spot_cone = shgroup_spot_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_circle_get();
- lamp_spot_blend = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_lamp_spot_square_get();
- lamp_spot_pyramid = shgroup_instance(*psl_non_meshes, geom);
-
- geom = DRW_cache_square_get();
- lamp_spot_blend_rect = shgroup_instance(*psl_non_meshes, geom);
-
- /* Relationship Lines */
- relationship_lines = shgroup_dynlines_uniform_color(*psl_non_meshes, ts.colorWire);
- DRW_shgroup_state_set(relationship_lines, DRW_STATE_STIPPLE_3);
- }
-
- if (psl_ob_center) {
- /* Object Center pass grouped by State */
- DRWShadingGroup *grp;
- static float outlineWidth, size;
-
- DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND | DRW_STATE_POINT;
- *psl_ob_center = DRW_pass_create("Obj Center Pass", state);
-
- outlineWidth = 1.0f * U.pixelsize;
- size = U.obcenter_dia * U.pixelsize + outlineWidth;
-
- GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_POINT_UNIFORM_SIZE_UNIFORM_COLOR_OUTLINE_AA);
-
- /* Active */
- grp = DRW_shgroup_point_batch_create(sh, *psl_ob_center);
- DRW_shgroup_uniform_float(grp, "size", &size, 1);
- DRW_shgroup_uniform_float(grp, "outlineWidth", &outlineWidth, 1);
- DRW_shgroup_uniform_vec4(grp, "color", ts.colorActive, 1);
- DRW_shgroup_uniform_vec4(grp, "outlineColor", ts.colorOutline, 1);
- center_active = grp;
-
- /* Select */
- grp = DRW_shgroup_point_batch_create(sh, *psl_ob_center);
- DRW_shgroup_uniform_vec4(grp, "color", ts.colorSelect, 1);
- center_selected = grp;
-
- /* Deselect */
- grp = DRW_shgroup_point_batch_create(sh, *psl_ob_center);
- DRW_shgroup_uniform_vec4(grp, "color", ts.colorDeselect, 1);
- center_deselected = grp;
- }
-
- /* Save passes refs */
- wire_overlay = (psl_wire_overlay) ? *psl_wire_overlay : NULL;
- wire_overlay_hidden_wire = (psl_wire_overlay_hidden_wire) ? *psl_wire_overlay_hidden_wire : NULL;
- wire_outline = (psl_wire_outline) ? *psl_wire_outline : NULL;
- non_meshes = (psl_non_meshes) ? *psl_non_meshes : NULL;
- ob_center = (psl_ob_center) ? *psl_ob_center : NULL;
- bone_solid = (psl_bone_solid) ? *psl_bone_solid : NULL;
- bone_wire = (psl_bone_wire) ? *psl_bone_wire : NULL;
-}
-
-/* ******************************************** WIRES *********************************************** */
-
-/* TODO FINISH */
-/* Get the wire color theme_id of an object based on it's state
- * **color is a way to get a pointer to the static color var associated */
-static int draw_object_wire_theme(Object *ob, float **color)
-{
- const bool is_edit = (ob->mode & OB_MODE_EDIT) != 0;
- /* confusing logic here, there are 2 methods of setting the color
- * 'colortab[colindex]' and 'theme_id', colindex overrides theme_id.
- *
- * note: no theme yet for 'colindex' */
- int theme_id = is_edit ? TH_WIRE_EDIT : TH_WIRE;
-
- if (//(scene->obedit == NULL) &&
- ((G.moving & G_TRANSFORM_OBJ) != 0) &&
- ((ob->base_flag & BASE_SELECTED) != 0))
- {
- theme_id = TH_TRANSFORM;
- }
- else {
- /* Sets the 'theme_id' or fallback to wire */
- if ((ob->flag & OB_FROMGROUP) != 0) {
- if ((ob->base_flag & BASE_SELECTED) != 0) {
- /* uses darker active color for non-active + selected */
- theme_id = TH_GROUP_ACTIVE;
-
- // if (scene->basact != base) {
- // theme_shade = -16;
- // }
- }
- else {
- theme_id = TH_GROUP;
- }
- }
- else {
- if ((ob->base_flag & BASE_SELECTED) != 0) {
- theme_id = //scene->basact == base ? TH_ACTIVE :
- TH_SELECT;
- }
- else {
- if (ob->type == OB_LAMP) theme_id = TH_LAMP;
- else if (ob->type == OB_SPEAKER) theme_id = TH_SPEAKER;
- else if (ob->type == OB_CAMERA) theme_id = TH_CAMERA;
- else if (ob->type == OB_EMPTY) theme_id = TH_EMPTY;
- /* fallback to TH_WIRE */
- }
- }
- }
-
- if (color != NULL) {
- switch (theme_id) {
- case TH_WIRE_EDIT: *color = ts.colorTransform; break;
- case TH_ACTIVE: *color = ts.colorActive; break;
- case TH_SELECT: *color = ts.colorSelect; break;
- case TH_GROUP: *color = ts.colorGroup; break;
- case TH_GROUP_ACTIVE: *color = ts.colorGroupActive; break;
- case TH_TRANSFORM: *color = ts.colorTransform; break;
- case OB_SPEAKER: *color = ts.colorSpeaker; break;
- case OB_CAMERA: *color = ts.colorCamera; break;
- case OB_EMPTY: *color = ts.colorEmpty; break;
- case OB_LAMP: *color = ts.colorLamp; break;
- default: *color = ts.colorWire; break;
- }
- }
-
- return theme_id;
-}
-
-void DRW_shgroup_wire_outline(Object *ob, const bool do_front, const bool do_back, const bool do_outline)
-{
- GPUShader *sh;
- struct Batch *geom = DRW_cache_wire_outline_get(ob);
-
- float *color;
- draw_object_wire_theme(ob, &color);
-
-#if 1 /* New wire */
-
- bool is_perps = DRW_viewport_is_persp_get();
- static bool bTrue = true;
- static bool bFalse = false;
-
- /* Note (TODO) : this requires cache to be discarded on ortho/perp switch
- * It may be preferable (or not depending on performance implication)
- * to introduce a shader uniform switch */
- if (is_perps) {
- sh = GPU_shader_get_builtin_shader(GPU_SHADER_EDGES_FRONT_BACK_PERSP);
- }
- else {
- sh = GPU_shader_get_builtin_shader(GPU_SHADER_EDGES_FRONT_BACK_ORTHO);
- }
-
- if (do_front || do_back) {
- bool *bFront = (do_front) ? &bTrue : &bFalse;
- bool *bBack = (do_back) ? &bTrue : &bFalse;
-
- DRWShadingGroup *grp = DRW_shgroup_create(sh, wire_outline);
- DRW_shgroup_state_set(grp, DRW_STATE_WIRE);
- DRW_shgroup_uniform_vec4(grp, "frontColor", color, 1);
- DRW_shgroup_uniform_vec4(grp, "backColor", color, 1);
- DRW_shgroup_uniform_bool(grp, "drawFront", bFront, 1);
- DRW_shgroup_uniform_bool(grp, "drawBack", bBack, 1);
- DRW_shgroup_uniform_bool(grp, "drawSilhouette", &bFalse, 1);
- DRW_shgroup_call_add(grp, geom, ob->obmat);
- }
-
- if (do_outline) {
- DRWShadingGroup *grp = DRW_shgroup_create(sh, wire_outline);
- DRW_shgroup_state_set(grp, DRW_STATE_WIRE_LARGE);
- DRW_shgroup_uniform_vec4(grp, "silhouetteColor", color, 1);
- DRW_shgroup_uniform_bool(grp, "drawFront", &bFalse, 1);
- DRW_shgroup_uniform_bool(grp, "drawBack", &bFalse, 1);
- DRW_shgroup_uniform_bool(grp, "drawSilhouette", &bTrue, 1);
-
- DRW_shgroup_call_add(grp, geom, ob->obmat);
- }
-
-#else /* Old (flat) wire */
-
- sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_UNIFORM_COLOR);
- DRWShadingGroup *grp = DRW_shgroup_create(sh, wire_outline);
- DRW_shgroup_state_set(grp, DRW_STATE_WIRE_LARGE);
- DRW_shgroup_uniform_vec4(grp, "color", frontcol, 1);
-
- DRW_shgroup_call_add(grp, geom, ob->obmat);
-#endif
-
-}
-
-/* ***************************** NON MESHES ********************** */
-
-void DRW_shgroup_lamp(Object *ob)
-{
- Lamp *la = ob->data;
- float *color;
- int theme_id = draw_object_wire_theme(ob, &color);
- static float zero = 0.0f;
-
- /* Don't draw the center if it's selected or active */
- if (theme_id == TH_GROUP)
- DRW_shgroup_dynamic_call_add(lamp_center_group, ob->obmat[3]);
- else if (theme_id == TH_LAMP)
- DRW_shgroup_dynamic_call_add(lamp_center, ob->obmat[3]);
-
- /* First circle */
- DRW_shgroup_dynamic_call_add(lamp_circle, ob->obmat[3], color);
-
- /* draw dashed outer circle if shadow is on. remember some lamps can't have certain shadows! */
- if (la->type != LA_HEMI) {
- if ((la->mode & LA_SHAD_RAY) || ((la->mode & LA_SHAD_BUF) && (la->type == LA_SPOT))) {
- DRW_shgroup_dynamic_call_add(lamp_circle_shadow, ob->obmat[3], color);
- }
- }
-
- /* Distance */
- if (ELEM(la->type, LA_HEMI, LA_SUN, LA_AREA)) {
- DRW_shgroup_dynamic_call_add(lamp_distance, color, &zero, &la->dist, ob->obmat);
- }
-
- copy_m4_m4(la->shapemat, ob->obmat);
-
- if (la->type == LA_SUN) {
- DRW_shgroup_dynamic_call_add(lamp_sunrays, ob->obmat[3], color);
- }
- else if (la->type == LA_SPOT) {
- float size[3], sizemat[4][4];
- static float one = 1.0f;
- float blend = 1.0f - pow2f(la->spotblend);
-
- size[0] = size[1] = sinf(la->spotsize * 0.5f) * la->dist;
- size[2] = cosf(la->spotsize * 0.5f) * la->dist;
-
- size_to_mat4(sizemat, size);
- mul_m4_m4m4(la->spotconemat, ob->obmat, sizemat);
-
- size[0] = size[1] = blend; size[2] = 1.0f;
- size_to_mat4(sizemat, size);
- translate_m4(sizemat, 0.0f, 0.0f, -1.0f);
- rotate_m4(sizemat, 'X', M_PI / 2.0f);
- mul_m4_m4m4(la->spotblendmat, la->spotconemat, sizemat);
-
- if (la->mode & LA_SQUARE) {
- DRW_shgroup_dynamic_call_add(lamp_spot_pyramid, color, &one, la->spotconemat);
-
- /* hide line if it is zero size or overlaps with outer border,
- * previously it adjusted to always to show it but that seems
- * confusing because it doesn't show the actual blend size */
- if (blend != 0.0f && blend != 1.0f) {
- DRW_shgroup_dynamic_call_add(lamp_spot_blend_rect, color, &one, la->spotblendmat);
- }
- }
- else {
- DRW_shgroup_dynamic_call_add(lamp_spot_cone, color, la->spotconemat);
-
- /* hide line if it is zero size or overlaps with outer border,
- * previously it adjusted to always to show it but that seems
- * confusing because it doesn't show the actual blend size */
- if (blend != 0.0f && blend != 1.0f) {
- DRW_shgroup_dynamic_call_add(lamp_spot_blend, color, &one, la->spotblendmat);
- }
- }
-
- normalize_m4(la->shapemat);
- DRW_shgroup_dynamic_call_add(lamp_buflimit, color, &la->clipsta, &la->clipend, ob->obmat);
- DRW_shgroup_dynamic_call_add(lamp_buflimit_points, color, &la->clipsta, &la->clipend, ob->obmat);
- }
- else if (la->type == LA_HEMI) {
- static float hemisize = 2.0f;
- DRW_shgroup_dynamic_call_add(lamp_hemi, color, &hemisize, la->shapemat);
- }
- else if (la->type == LA_AREA) {
- float size[3] = {1.0f, 1.0f, 1.0f}, sizemat[4][4];
-
- if (la->area_shape == LA_AREA_RECT) {
- size[1] = la->area_sizey / la->area_size;
- size_to_mat4(sizemat, size);
- mul_m4_m4m4(la->shapemat, la->shapemat, sizemat);
- }
-
- DRW_shgroup_dynamic_call_add(lamp_area, color, &la->area_size, la->shapemat);
- }
-
- /* Line and point going to the ground */
- DRW_shgroup_dynamic_call_add(lamp_groundline, ob->obmat[3]);
- DRW_shgroup_dynamic_call_add(lamp_groundpoint, ob->obmat[3]);
-}
-
-void DRW_shgroup_camera(Object *ob)
-{
- const struct bContext *C = DRW_get_context();
- View3D *v3d = CTX_wm_view3d(C);
- Scene *scene = CTX_data_scene(C);
-
- Camera *cam = ob->data;
- const bool is_active = (ob == v3d->camera);
- float *color;
- draw_object_wire_theme(ob, &color);
-
- float vec[4][3], asp[2], shift[2], scale[3], drawsize;
-
- scale[0] = 1.0f / len_v3(ob->obmat[0]);
- scale[1] = 1.0f / len_v3(ob->obmat[1]);
- scale[2] = 1.0f / len_v3(ob->obmat[2]);
-
- BKE_camera_view_frame_ex(scene, cam, cam->drawsize, false, scale,
- asp, shift, &drawsize, vec);
-
- // /* Frame coords */
- copy_v2_v2(cam->drwcorners[0], vec[0]);
- copy_v2_v2(cam->drwcorners[1], vec[1]);
- copy_v2_v2(cam->drwcorners[2], vec[2]);
- copy_v2_v2(cam->drwcorners[3], vec[3]);
-
- /* depth */
- cam->drwdepth = vec[0][2];
-
- /* tria */
- cam->drwtria[0][0] = shift[0] + ((0.7f * drawsize) * scale[0]);
- cam->drwtria[0][1] = shift[1] + ((drawsize * (asp[1] + 0.1f)) * scale[1]);
- cam->drwtria[1][0] = shift[0];
- cam->drwtria[1][1] = shift[1] + ((1.1f * drawsize * (asp[1] + 0.7f)) * scale[1]);
-
- DRW_shgroup_dynamic_call_add(camera, color, cam->drwcorners, &cam->drwdepth, cam->drwtria, ob->obmat);
-
- /* Active cam */
- if (is_active) {
- DRW_shgroup_dynamic_call_add(camera_tria, color, cam->drwcorners, &cam->drwdepth, cam->drwtria, ob->obmat);
- }
-
- /* draw the rest in normalize object space */
- copy_m4_m4(cam->drwnormalmat, ob->obmat);
- normalize_m4(cam->drwnormalmat);
-
- if (cam->flag & CAM_SHOWLIMITS) {
- static float col[3] = {0.5f, 0.5f, 0.25f}, col_hi[3] = {1.0f, 1.0f, 0.5f};
- float sizemat[4][4], size[3] = {1.0f, 1.0f, 0.0f};
- float focusdist = BKE_camera_object_dof_distance(ob);
-
- copy_m4_m4(cam->drwfocusmat, cam->drwnormalmat);
- translate_m4(cam->drwfocusmat, 0.0f, 0.0f, -focusdist);
- size_to_mat4(sizemat, size);
- mul_m4_m4m4(cam->drwfocusmat, cam->drwfocusmat, sizemat);
-
- DRW_shgroup_dynamic_call_add(camera_focus, (is_active ? col_hi : col), &cam->drawsize, cam->drwfocusmat);
-
- DRW_shgroup_dynamic_call_add(camera_clip, color, &cam->clipsta, &cam->clipend, cam->drwnormalmat);
- DRW_shgroup_dynamic_call_add(camera_clip_points, (is_active ? col_hi : col), &cam->clipsta, &cam->clipend, cam->drwnormalmat);
- }
-
- if (cam->flag & CAM_SHOWMIST) {
- World *world = scene->world;
-
- if (world) {
- static float col[3] = {0.5f, 0.5f, 0.5f}, col_hi[3] = {1.0f, 1.0f, 1.0f};
- world->mistend = world->miststa + world->mistdist;
- DRW_shgroup_dynamic_call_add(camera_mist, color, &world->miststa, &world->mistend, cam->drwnormalmat);
- DRW_shgroup_dynamic_call_add(camera_mist_points, (is_active ? col_hi : col), &world->miststa, &world->mistend, cam->drwnormalmat);
- }
- }
-}
-
-void DRW_shgroup_empty(Object *ob)
-{
- float *color;
- draw_object_wire_theme(ob, &color);
-
- switch (ob->empty_drawtype) {
- case OB_PLAINAXES:
- DRW_shgroup_dynamic_call_add(plain_axes, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_SINGLE_ARROW:
- DRW_shgroup_dynamic_call_add(single_arrow, color, &ob->empty_drawsize, ob->obmat);
- DRW_shgroup_dynamic_call_add(single_arrow_line, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_CUBE:
- DRW_shgroup_dynamic_call_add(cube, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_CIRCLE:
- DRW_shgroup_dynamic_call_add(circle, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_EMPTY_SPHERE:
- DRW_shgroup_dynamic_call_add(sphere, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_EMPTY_CONE:
- DRW_shgroup_dynamic_call_add(cone, color, &ob->empty_drawsize, ob->obmat);
- break;
- case OB_ARROWS:
- DRW_shgroup_dynamic_call_add(arrows, color, &ob->empty_drawsize, ob->obmat);
- DRW_shgroup_dynamic_call_add(axis_names, color, &ob->empty_drawsize, ob->obmat);
- break;
- }
-}
-
-void DRW_shgroup_speaker(Object *ob)
-{
- float *color;
- static float one = 1.0f;
- draw_object_wire_theme(ob, &color);
-
- DRW_shgroup_dynamic_call_add(speaker, color, &one, ob->obmat);
-}
-
-void DRW_shgroup_relationship_lines(Object *ob)
-{
- if (ob->parent) {
- DRW_shgroup_dynamic_call_add(relationship_lines, ob->obmat[3]);
- DRW_shgroup_dynamic_call_add(relationship_lines, ob->parent->obmat[3]);
- }
-}
-
-/* ***************************** COMMON **************************** */
-
-void DRW_shgroup_object_center(Object *ob)
-{
- if ((ob->base_flag & BASE_SELECTED) != 0) {
- DRW_shgroup_dynamic_call_add(center_selected, ob->obmat[3]);
- }
- else if (0) {
- DRW_shgroup_dynamic_call_add(center_deselected, ob->obmat[3]);
- }
-}
-
-/* *************************** ARMATURES ***************************** */
-
-static Object *current_armature;
-/* Reset when changing current_armature */
-static DRWShadingGroup *bone_octahedral_solid;
-static DRWShadingGroup *bone_octahedral_wire;
-static DRWShadingGroup *bone_point_solid;
-static DRWShadingGroup *bone_point_wire;
-static DRWShadingGroup *bone_axes;
-
-/* this function set the object space to use
- * for all subsequent DRW_shgroup_bone_*** calls */
-static void DRW_shgroup_armature(Object *ob)
-{
- current_armature = ob;
- bone_octahedral_solid = NULL;
- bone_octahedral_wire = NULL;
- bone_point_solid = NULL;
- bone_point_wire = NULL;
- bone_axes = NULL;
-}
-
-void DRW_shgroup_armature_object(Object *ob)
-{
- float *color;
- draw_object_wire_theme(ob, &color);
-
- DRW_shgroup_armature(ob);
- draw_armature_pose(ob, color);
-}
-
-void DRW_shgroup_armature_pose(Object *ob)
-{
- DRW_shgroup_armature(ob);
- draw_armature_pose(ob, NULL);
-}
-
-void DRW_shgroup_armature_edit(Object *ob)
-{
- DRW_shgroup_armature(ob);
- draw_armature_edit(ob);
-}
-
-/* Octahedral */
-void DRW_shgroup_bone_octahedral_solid(const float (*bone_mat)[4], const float color[4])
-{
- if (bone_octahedral_solid == NULL) {
- struct Batch *geom = DRW_cache_bone_octahedral_get();
- bone_octahedral_solid = shgroup_instance_objspace_solid(bone_solid, geom, current_armature->obmat);
- }
-
- DRW_shgroup_dynamic_call_add(bone_octahedral_solid, bone_mat, color);
-}
-
-void DRW_shgroup_bone_octahedral_wire(const float (*bone_mat)[4], const float color[4])
-{
- if (bone_octahedral_wire == NULL) {
- struct Batch *geom = DRW_cache_bone_octahedral_wire_outline_get();
- bone_octahedral_wire = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
- }
-
- DRW_shgroup_dynamic_call_add(bone_octahedral_wire, bone_mat, color);
-}
-
-/* Head and tail sphere */
-void DRW_shgroup_bone_point_solid(const float (*bone_mat)[4], const float color[4])
-{
- if (bone_point_solid == NULL) {
- struct Batch *geom = DRW_cache_bone_point_get();
- bone_point_solid = shgroup_instance_objspace_solid(bone_solid, geom, current_armature->obmat);
- }
-
- DRW_shgroup_dynamic_call_add(bone_point_solid, bone_mat, color);
-}
-
-void DRW_shgroup_bone_point_wire(const float (*bone_mat)[4], const float color[4])
-{
- if (bone_point_wire == NULL) {
- struct Batch *geom = DRW_cache_bone_point_wire_outline_get();
- bone_point_wire = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
- }
-
- DRW_shgroup_dynamic_call_add(bone_point_wire, bone_mat, color);
-}
-
-/* Axes */
-void DRW_shgroup_bone_axes(const float (*bone_mat)[4], const float color[4])
-{
- if (bone_axes == NULL) {
- struct Batch *geom = DRW_cache_bone_arrows_get();
- bone_axes = shgroup_instance_objspace_wire(bone_wire, geom, current_armature->obmat);
- }
-
- DRW_shgroup_dynamic_call_add(bone_axes, bone_mat, color);
-}
-
-
-void DRW_shgroup_bone_relationship_lines(const float head[3], const float tail[3])
-{
- DRW_shgroup_dynamic_call_add(relationship_lines, head);
- DRW_shgroup_dynamic_call_add(relationship_lines, tail);
-}
diff --git a/source/blender/draw/modes/object_mode.h b/source/blender/draw/modes/draw_mode_engines.h
index fda9096203d..01af249b736 100644
--- a/source/blender/draw/modes/object_mode.h
+++ b/source/blender/draw/modes/draw_mode_engines.h
@@ -19,19 +19,15 @@
*
*/
-/** \file blender/draw/modes/object_mode.h
+/** \file blender/draw/modes/draw_mode_engines.h
* \ingroup draw
*/
-#ifndef __OBJECT_MODE_H__
-#define __OBJECT_MODE_H__
+#ifndef __DRAW_MODES_ENGINES_H__
+#define __DRAW_MODES_ENGINES_H__
-struct Object;
+extern DrawEngineType draw_engine_object_type;
+extern DrawEngineType draw_engine_edit_mesh_type;
+extern DrawEngineType draw_engine_edit_armature_type;
-void OBJECT_cache_init(void);
-void OBJECT_cache_populate(struct Object *ob);
-void OBJECT_cache_finish(void);
-
-void OBJECT_draw(void);
-
-#endif /* __OBJECT_MODE_H__ */ \ No newline at end of file
+#endif /* __DRAW_MODES_ENGINES_H__ */ \ No newline at end of file
diff --git a/source/blender/draw/modes/edit_armature_mode.c b/source/blender/draw/modes/edit_armature_mode.c
index 5f1418340d1..f2f19eacf2d 100644
--- a/source/blender/draw/modes/edit_armature_mode.c
+++ b/source/blender/draw/modes/edit_armature_mode.c
@@ -28,85 +28,80 @@
#include "DNA_armature_types.h"
-#include "draw_mode_pass.h"
+#include "draw_common.h"
-#include "edit_armature_mode.h"
+#include "draw_mode_engines.h"
/* keep it under MAX_PASSES */
typedef struct EDIT_ARMATURE_PassList {
- struct DRWPass *non_meshes_pass;
- struct DRWPass *ob_center_pass;
- struct DRWPass *wire_outline_pass;
- struct DRWPass *bone_solid_pass;
- struct DRWPass *bone_wire_pass;
+ struct DRWPass *bone_solid;
+ struct DRWPass *bone_wire;
+ struct DRWPass *relationship;
} EDIT_ARMATURE_PassList;
-void EDIT_ARMATURE_cache_init(void)
+typedef struct EDIT_ARMATURE_Data {
+ char engine_name[32];
+ void *fbl;
+ void *txl;
+ EDIT_ARMATURE_PassList *psl;
+ void *stl;
+} EDIT_ARMATURE_Data;
+
+static DRWShadingGroup *relationship_lines;
+
+extern GlobalsUboStorage ts;
+
+static EDIT_ARMATURE_Data *vedata;
+
+static void EDIT_ARMATURE_cache_init(void)
{
- EDIT_ARMATURE_PassList *psl = DRW_mode_pass_list_get();
- static struct GPUShader *depth_sh;
+ vedata = DRW_viewport_engine_data_get("EditArmatureMode");
+ EDIT_ARMATURE_PassList *psl = vedata->psl;
- if (!depth_sh) {
- depth_sh = DRW_shader_create_3D_depth_only();
+ {
+ /* Solid bones */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS;
+ psl->bone_solid = DRW_pass_create("Bone Solid Pass", state);
}
- DRW_mode_passes_setup(NULL,
- NULL,
- &psl->wire_outline_pass,
- &psl->non_meshes_pass,
- &psl->ob_center_pass,
- &psl->bone_solid_pass,
- &psl->bone_wire_pass);
-}
+ {
+ /* Wire bones */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND;
+ psl->bone_wire = DRW_pass_create("Bone Wire Pass", state);
+ }
-void EDIT_ARMATURE_cache_populate(Object *ob)
-{
- bArmature *arm = ob->data;
+ {
+ /* Non Meshes Pass (Camera, empties, lamps ...) */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND | DRW_STATE_WIRE;
+ psl->relationship = DRW_pass_create("Bone Relationship Pass", state);
- switch (ob->type) {
- case OB_ARMATURE:
- /* detect Edit Armature mode */
- if (arm->edbo)
- DRW_shgroup_armature_edit(ob);
- else
- DRW_shgroup_armature_object(ob);
- break;
- case OB_MESH:
- break;
- case OB_LAMP:
- DRW_shgroup_lamp(ob);
- break;
- case OB_CAMERA:
- DRW_shgroup_camera(ob);
- break;
- case OB_EMPTY:
- DRW_shgroup_empty(ob);
- break;
- case OB_SPEAKER:
- DRW_shgroup_speaker(ob);
- break;
- default:
- break;
+ /* Relationship Lines */
+ relationship_lines = shgroup_dynlines_uniform_color(psl->relationship, ts.colorWire);
+ DRW_shgroup_state_set(relationship_lines, DRW_STATE_STIPPLE_3);
}
- DRW_shgroup_object_center(ob);
- DRW_shgroup_relationship_lines(ob);
}
-void EDIT_ARMATURE_cache_finish(void)
+static void EDIT_ARMATURE_cache_populate(Object *ob)
{
- /* Do nothing */
+ bArmature *arm = ob->data;
+ EDIT_ARMATURE_PassList *psl = vedata->psl;
+
+ if (ob->type == OB_ARMATURE) {
+ if (arm->edbo) {
+ DRW_shgroup_armature_edit(ob, psl->bone_solid, psl->bone_wire, relationship_lines);
+ }
+ }
}
-void EDIT_ARMATURE_draw(void)
+static void EDIT_ARMATURE_draw_scene(void)
{
- EDIT_ARMATURE_PassList *psl = DRW_mode_pass_list_get();
+ EDIT_ARMATURE_Data *ved = DRW_viewport_engine_data_get("EditArmatureMode");
+ EDIT_ARMATURE_PassList *psl = ved->psl;
- DRW_draw_pass(psl->bone_solid_pass);
- DRW_draw_pass(psl->bone_wire_pass);
- DRW_draw_pass(psl->wire_outline_pass);
- DRW_draw_pass(psl->non_meshes_pass);
- DRW_draw_pass(psl->ob_center_pass);
+ DRW_draw_pass(psl->bone_solid);
+ DRW_draw_pass(psl->bone_wire);
+ DRW_draw_pass(psl->relationship);
}
void EDIT_ARMATURE_collection_settings_create(CollectionEngineSettings *ces)
@@ -114,3 +109,15 @@ void EDIT_ARMATURE_collection_settings_create(CollectionEngineSettings *ces)
BLI_assert(ces);
//BKE_collection_engine_property_add_int(ces, "show_occlude_wire", false);
}
+
+DrawEngineType draw_engine_edit_armature_type = {
+ NULL, NULL,
+ N_("EditArmatureMode"),
+ NULL,
+ NULL,
+ &EDIT_ARMATURE_cache_init,
+ &EDIT_ARMATURE_cache_populate,
+ NULL,
+ NULL,
+ &EDIT_ARMATURE_draw_scene
+};
diff --git a/source/blender/draw/modes/edit_armature_mode.h b/source/blender/draw/modes/edit_armature_mode.h
deleted file mode 100644
index 89354cdf938..00000000000
--- a/source/blender/draw/modes/edit_armature_mode.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2016, Blender Foundation.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- * Contributor(s): Blender Institute
- *
- */
-
-/** \file blender/draw/modes/edit_armature_mode.h
- * \ingroup draw
- */
-
-#ifndef __EDIT_ARMATURE_MODE_H__
-#define __EDIT_ARMATURE_MODE_H__
-
-struct Object;
-
-void EDIT_ARMATURE_cache_init(void);
-void EDIT_ARMATURE_cache_populate(struct Object *ob);
-void EDIT_ARMATURE_cache_finish(void);
-
-void EDIT_ARMATURE_draw(void);
-
-#endif /* __EDIT_ARMATURE_MODE_H__ */ \ No newline at end of file
diff --git a/source/blender/draw/modes/edit_mesh_mode.c b/source/blender/draw/modes/edit_mesh_mode.c
index 3736369f396..e671e9f059b 100644
--- a/source/blender/draw/modes/edit_mesh_mode.c
+++ b/source/blender/draw/modes/edit_mesh_mode.c
@@ -27,18 +27,14 @@
#include "DRW_render.h"
#include "GPU_shader.h"
-#include "GPU_viewport.h"
#include "DNA_view3d_types.h"
-#include "draw_mode_pass.h"
+#include "draw_common.h"
-#include "edit_mesh_mode.h"
+#include "draw_mode_engines.h"
/* keep it under MAX_PASSES */
typedef struct EDIT_MESH_PassList {
- struct DRWPass *non_meshes_pass;
- struct DRWPass *ob_center_pass;
- struct DRWPass *wire_outline_pass;
struct DRWPass *depth_pass_hidden_wire;
struct DRWPass *edit_face_overlay_pass;
struct DRWPass *edit_face_occluded_pass;
@@ -57,6 +53,14 @@ typedef struct EDIT_MESH_TextureList {
struct GPUTexture *occlude_wire_color_tx;
} EDIT_MESH_TextureList;
+typedef struct EDIT_MESH_Data {
+ char engine_name[32];
+ EDIT_MESH_FramebufferList *fbl;
+ EDIT_MESH_TextureList *txl;
+ EDIT_MESH_PassList *psl;
+ void *stl;
+} EDIT_MESH_Data;
+
static DRWShadingGroup *depth_shgrp_hidden_wire;
static DRWShadingGroup *face_overlay_shgrp;
@@ -70,7 +74,7 @@ static DRWShadingGroup *lverts_occluded_shgrp;
static DRWShadingGroup *facedot_occluded_shgrp;
static DRWShadingGroup *facefill_occluded_shgrp;
-extern struct GPUUniformBuffer *globals_ubo; /* draw_mode_pass.c */
+extern struct GPUUniformBuffer *globals_ubo; /* draw_common.c */
static struct GPUShader *overlay_tri_sh = NULL;
static struct GPUShader *overlay_tri_fast_sh = NULL;
@@ -95,10 +99,11 @@ extern char datatoc_edit_overlay_mix_frag_glsl[];
extern char datatoc_edit_overlay_facefill_vert_glsl[];
extern char datatoc_edit_overlay_facefill_frag_glsl[];
-void EDIT_MESH_init(void)
+static void EDIT_MESH_engine_init(void)
{
- EDIT_MESH_TextureList *txl = DRW_mode_texture_list_get();
- EDIT_MESH_FramebufferList *fbl = DRW_mode_framebuffer_list_get();
+ EDIT_MESH_Data *vedata = DRW_viewport_engine_data_get("EditMeshMode");
+ EDIT_MESH_TextureList *txl = vedata->txl;
+ EDIT_MESH_FramebufferList *fbl = vedata->fbl;
float *viewport_size = DRW_viewport_size_get();
@@ -209,9 +214,13 @@ static DRWPass *edit_mesh_create_overlay_pass(DRWShadingGroup **face_shgrp, DRWS
static float backwire_opacity;
static float face_mod;
-void EDIT_MESH_cache_init(void)
+static void EDIT_MESH_cache_init(void)
{
- EDIT_MESH_PassList *psl = DRW_mode_pass_list_get();
+ EDIT_MESH_Data *vedata = DRW_viewport_engine_data_get("EditMeshMode");
+ EDIT_MESH_TextureList *txl = vedata->txl;
+ EDIT_MESH_PassList *psl = vedata->psl;
+ DefaultTextureList *dtxl = DRW_viewport_texture_list_get();
+
const struct bContext *C = DRW_get_context();
View3D *v3d = CTX_wm_view3d(C);
@@ -242,12 +251,9 @@ void EDIT_MESH_cache_init(void)
DRW_shgroup_uniform_block(facefill_occluded_shgrp, "globalsBlock", globals_ubo, 0);
/* we need a full screen pass to combine the result */
- EDIT_MESH_TextureList *txl = DRW_mode_texture_list_get();
- DefaultTextureList *dtxl = DRW_engine_texture_list_get();
struct Batch *quad = DRW_cache_fullscreen_quad_get();
static float mat[4][4]; /* not even used but avoid crash */
-
psl->mix_occlude_pass = DRW_pass_create("Mix Occluded Wires", DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND);
DRWShadingGroup *mix_shgrp = DRW_shgroup_create(overlay_mix_sh, psl->mix_occlude_pass);
DRW_shgroup_call_add(mix_shgrp, quad, mat);
@@ -256,14 +262,6 @@ void EDIT_MESH_cache_init(void)
DRW_shgroup_uniform_buffer(mix_shgrp, "wireDepth", &txl->occlude_wire_depth_tx, 2);
DRW_shgroup_uniform_buffer(mix_shgrp, "sceneDepth", &dtxl->depth, 3);
}
-
- DRW_mode_passes_setup(NULL,
- NULL,
- &psl->wire_outline_pass,
- &psl->non_meshes_pass,
- &psl->ob_center_pass,
- NULL,
- NULL);
}
static void edit_mesh_add_ob_to_pass(Scene *scene, Object *ob, DRWShadingGroup *face_shgrp, DRWShadingGroup *ledges_shgrp,
@@ -288,7 +286,7 @@ static void edit_mesh_add_ob_to_pass(Scene *scene, Object *ob, DRWShadingGroup *
}
}
-void EDIT_MESH_cache_populate(Object *ob)
+static void EDIT_MESH_cache_populate(Object *ob)
{
const struct bContext *C = DRW_get_context();
View3D *v3d = CTX_wm_view3d(C);
@@ -296,64 +294,38 @@ void EDIT_MESH_cache_populate(Object *ob)
Object *obedit = scene->obedit;
struct Batch *geom;
- CollectionEngineSettings *ces_mode_ed = BKE_object_collection_engine_get(ob, COLLECTION_MODE_EDIT, "");
- bool do_occlude_wire = BKE_collection_engine_property_value_get_bool(ces_mode_ed, "show_occlude_wire");
- backwire_opacity = BKE_collection_engine_property_value_get_float(ces_mode_ed, "backwire_opacity"); /* should be done only once */
-
- face_mod = (do_occlude_wire) ? 0.0f : 1.0f;
-
- switch (ob->type) {
- case OB_MESH:
- if (ob == obedit) {
- if (do_occlude_wire) {
- geom = DRW_cache_surface_get(ob);
- DRW_shgroup_call_add(depth_shgrp_hidden_wire, geom, ob->obmat);
- }
-
- if ((v3d->flag & V3D_ZBUF_SELECT) == 0) {
- edit_mesh_add_ob_to_pass(scene, ob, face_occluded_shgrp, ledges_occluded_shgrp,
- lverts_occluded_shgrp, facedot_occluded_shgrp, facefill_occluded_shgrp);
- }
- else {
- edit_mesh_add_ob_to_pass(scene, ob, face_overlay_shgrp, ledges_overlay_shgrp,
- lverts_overlay_shgrp, facedot_overlay_shgrp, NULL);
- }
- }
- break;
- case OB_LAMP:
- DRW_shgroup_lamp(ob);
- break;
- case OB_CAMERA:
- DRW_shgroup_camera(ob);
- break;
- case OB_EMPTY:
- DRW_shgroup_empty(ob);
- break;
- case OB_SPEAKER:
- DRW_shgroup_speaker(ob);
- break;
- case OB_ARMATURE:
- DRW_shgroup_armature_object(ob);
- break;
- default:
- break;
- }
+ if (ob->type == OB_MESH) {
+ if (ob == obedit) {
+ CollectionEngineSettings *ces_mode_ed = BKE_object_collection_engine_get(ob, COLLECTION_MODE_EDIT, "");
+ bool do_occlude_wire = BKE_collection_engine_property_value_get_bool(ces_mode_ed, "show_occlude_wire");
+ backwire_opacity = BKE_collection_engine_property_value_get_float(ces_mode_ed, "backwire_opacity"); /* should be done only once */
- DRW_shgroup_object_center(ob);
- DRW_shgroup_relationship_lines(ob);
-}
+ face_mod = (do_occlude_wire) ? 0.0f : 1.0f;
-void EDIT_MESH_cache_finish(void)
-{
- /* Do nothing */
+ if (do_occlude_wire) {
+ geom = DRW_cache_surface_get(ob);
+ DRW_shgroup_call_add(depth_shgrp_hidden_wire, geom, ob->obmat);
+ }
+
+ if ((v3d->flag & V3D_ZBUF_SELECT) == 0) {
+ edit_mesh_add_ob_to_pass(scene, ob, face_occluded_shgrp, ledges_occluded_shgrp,
+ lverts_occluded_shgrp, facedot_occluded_shgrp, facefill_occluded_shgrp);
+ }
+ else {
+ edit_mesh_add_ob_to_pass(scene, ob, face_overlay_shgrp, ledges_overlay_shgrp,
+ lverts_overlay_shgrp, facedot_overlay_shgrp, NULL);
+ }
+ }
+ }
}
-void EDIT_MESH_draw(void)
+static void EDIT_MESH_draw_scene(void)
{
- EDIT_MESH_PassList *psl = DRW_mode_pass_list_get();
- EDIT_MESH_FramebufferList *fbl = DRW_mode_framebuffer_list_get();
- DefaultFramebufferList *dfbl = DRW_engine_framebuffer_list_get();
- DefaultTextureList *dtxl = DRW_engine_texture_list_get();
+ EDIT_MESH_Data *vedata = DRW_viewport_engine_data_get("EditMeshMode");
+ EDIT_MESH_PassList *psl = vedata->psl;
+ EDIT_MESH_FramebufferList *fbl = vedata->fbl;
+ DefaultFramebufferList *dfbl = DRW_viewport_framebuffer_list_get();
+ DefaultTextureList *dtxl = DRW_viewport_texture_list_get();
DRW_draw_pass(psl->depth_pass_hidden_wire);
@@ -380,10 +352,6 @@ void EDIT_MESH_draw(void)
else {
DRW_draw_pass(psl->edit_face_overlay_pass);
}
-
- DRW_draw_pass(psl->wire_outline_pass);
- DRW_draw_pass(psl->non_meshes_pass);
- DRW_draw_pass(psl->ob_center_pass);
}
void EDIT_MESH_collection_settings_create(CollectionEngineSettings *ces)
@@ -393,7 +361,7 @@ void EDIT_MESH_collection_settings_create(CollectionEngineSettings *ces)
BKE_collection_engine_property_add_float(ces, "backwire_opacity", 0.5);
}
-void EDIT_MESH_engine_free(void)
+static void EDIT_MESH_engine_free(void)
{
if (overlay_tri_sh)
DRW_shader_free(overlay_tri_sh);
@@ -415,4 +383,16 @@ void EDIT_MESH_engine_free(void)
DRW_shader_free(overlay_mix_sh);
if (overlay_facefill_sh)
DRW_shader_free(overlay_facefill_sh);
-} \ No newline at end of file
+}
+
+DrawEngineType draw_engine_edit_mesh_type = {
+ NULL, NULL,
+ N_("EditMeshMode"),
+ &EDIT_MESH_engine_init,
+ &EDIT_MESH_engine_free,
+ &EDIT_MESH_cache_init,
+ &EDIT_MESH_cache_populate,
+ NULL,
+ NULL,
+ &EDIT_MESH_draw_scene
+};
diff --git a/source/blender/draw/modes/edit_mesh_mode.h b/source/blender/draw/modes/edit_mesh_mode.h
deleted file mode 100644
index 508685bd033..00000000000
--- a/source/blender/draw/modes/edit_mesh_mode.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2016, Blender Foundation.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- *
- * Contributor(s): Blender Institute
- *
- */
-
-/** \file blender/draw/modes/edit_mesh_mode.h
- * \ingroup draw
- */
-
-#ifndef __EDIT_MESH_MODE_H__
-#define __EDIT_MESH_MODE_H__
-
-struct Object;
-
-void EDIT_MESH_init(void);
-
-void EDIT_MESH_cache_init(void);
-void EDIT_MESH_cache_populate(struct Object *ob);
-void EDIT_MESH_cache_finish(void);
-
-void EDIT_MESH_draw(void);
-
-void EDIT_MESH_engine_free(void);
-
-#endif /* __EDIT_MESH_MODE_H__ */ \ No newline at end of file
diff --git a/source/blender/draw/modes/object_mode.c b/source/blender/draw/modes/object_mode.c
index 25c4bf932e4..ecfde38f5be 100644
--- a/source/blender/draw/modes/object_mode.c
+++ b/source/blender/draw/modes/object_mode.c
@@ -26,34 +26,543 @@
#include "DRW_engine.h"
#include "DRW_render.h"
-#include "draw_mode_pass.h"
+#include "DNA_userdef_types.h"
+#include "DNA_armature_types.h"
+#include "DNA_camera_types.h"
+#include "DNA_view3d_types.h"
+#include "DNA_world_types.h"
-#include "object_mode.h"
+#include "BKE_camera.h"
+#include "BKE_global.h"
+
+#include "GPU_shader.h"
+
+#include "UI_resources.h"
+
+#include "draw_mode_engines.h"
+#include "draw_common.h"
/* keep it under MAX_PASSES */
typedef struct OBJECT_PassList {
- struct DRWPass *non_meshes_pass;
- struct DRWPass *ob_center_pass;
- struct DRWPass *wire_outline_pass;
- struct DRWPass *bone_solid_pass;
- struct DRWPass *bone_wire_pass;
+ struct DRWPass *non_meshes;
+ struct DRWPass *ob_center;
+ struct DRWPass *wire_outline;
+ struct DRWPass *bone_solid;
+ struct DRWPass *bone_wire;
} OBJECT_PassList;
-void OBJECT_cache_init(void)
+typedef struct OBJECT_Data {
+ char engine_name[32];
+ void *fbl;
+ void *txl;
+ OBJECT_PassList *psl;
+ void *stl;
+} OBJECT_Data;
+
+/* Empties */
+static DRWShadingGroup *plain_axes;
+static DRWShadingGroup *cube;
+static DRWShadingGroup *circle;
+static DRWShadingGroup *sphere;
+static DRWShadingGroup *cone;
+static DRWShadingGroup *single_arrow;
+static DRWShadingGroup *single_arrow_line;
+static DRWShadingGroup *arrows;
+static DRWShadingGroup *axis_names;
+
+/* Speaker */
+static DRWShadingGroup *speaker;
+
+/* Lamps */
+static DRWShadingGroup *lamp_center;
+static DRWShadingGroup *lamp_center_group;
+static DRWShadingGroup *lamp_groundpoint;
+static DRWShadingGroup *lamp_groundline;
+static DRWShadingGroup *lamp_circle;
+static DRWShadingGroup *lamp_circle_shadow;
+static DRWShadingGroup *lamp_sunrays;
+static DRWShadingGroup *lamp_distance;
+static DRWShadingGroup *lamp_buflimit;
+static DRWShadingGroup *lamp_buflimit_points;
+static DRWShadingGroup *lamp_area;
+static DRWShadingGroup *lamp_hemi;
+static DRWShadingGroup *lamp_spot_cone;
+static DRWShadingGroup *lamp_spot_blend;
+static DRWShadingGroup *lamp_spot_pyramid;
+static DRWShadingGroup *lamp_spot_blend_rect;
+
+/* Helpers */
+static DRWShadingGroup *relationship_lines;
+
+/* Objects Centers */
+static DRWShadingGroup *center_active;
+static DRWShadingGroup *center_selected;
+static DRWShadingGroup *center_deselected;
+
+/* Camera */
+static DRWShadingGroup *camera;
+static DRWShadingGroup *camera_tria;
+static DRWShadingGroup *camera_focus;
+static DRWShadingGroup *camera_clip;
+static DRWShadingGroup *camera_clip_points;
+static DRWShadingGroup *camera_mist;
+static DRWShadingGroup *camera_mist_points;
+
+extern GlobalsUboStorage ts;
+
+static OBJECT_Data *vedata;
+
+static void OBJECT_cache_init(void)
+{
+ /* DRW_viewport_engine_data_get is rather slow, better not do it on every objects */
+ vedata = DRW_viewport_engine_data_get("ObjectMode");
+ OBJECT_PassList *psl = vedata->psl;
+
+ {
+ /* This pass can draw mesh outlines and/or fancy wireframe */
+ /* Fancy wireframes are not meant to be occluded (without Z offset) */
+ /* Outlines and Fancy Wires use the same VBO */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND;
+ psl->wire_outline = DRW_pass_create("Wire + Outlines Pass", state);
+ }
+
+ {
+ /* Solid bones */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS;
+ psl->bone_solid = DRW_pass_create("Bone Solid Pass", state);
+ }
+
+ {
+ /* Wire bones */
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND;
+ psl->bone_wire = DRW_pass_create("Bone Wire Pass", state);
+ }
+
+ {
+ /* Non Meshes Pass (Camera, empties, lamps ...) */
+ struct Batch *geom;
+
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | DRW_STATE_BLEND | DRW_STATE_POINT;
+ state |= DRW_STATE_WIRE;
+ psl->non_meshes = DRW_pass_create("Non Meshes Pass", state);
+
+ /* Empties */
+ geom = DRW_cache_plain_axes_get();
+ plain_axes = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_cube_get();
+ cube = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_circle_get();
+ circle = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_empty_sphere_get();
+ sphere = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_empty_cone_get();
+ cone = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_arrow_get();
+ single_arrow = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_line_get();
+ single_arrow_line = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_arrows_get();
+ arrows = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_axis_names_get();
+ axis_names = shgroup_instance_axis_names(psl->non_meshes, geom);
+
+ /* Speaker */
+ geom = DRW_cache_speaker_get();
+ speaker = shgroup_instance(psl->non_meshes, geom);
+
+ /* Camera */
+ geom = DRW_cache_camera_get();
+ camera = shgroup_camera_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_camera_tria_get();
+ camera_tria = shgroup_camera_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_plain_axes_get();
+ camera_focus = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_line_get();
+ camera_clip = shgroup_distance_lines_instance(psl->non_meshes, geom);
+ camera_mist = shgroup_distance_lines_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_line_endpoints_get();
+ camera_clip_points = shgroup_distance_lines_instance(psl->non_meshes, geom);
+ camera_mist_points = shgroup_distance_lines_instance(psl->non_meshes, geom);
+
+ /* Lamps */
+ /* TODO
+ * for now we create multiple times the same VBO with only lamp center coordinates
+ * but ideally we would only create it once */
+
+ /* start with buflimit because we don't want stipples */
+ geom = DRW_cache_single_line_get();
+ lamp_buflimit = shgroup_distance_lines_instance(psl->non_meshes, geom);
+
+ lamp_center = shgroup_dynpoints_uniform_color(psl->non_meshes, ts.colorLampNoAlpha, &ts.sizeLampCenter);
+ lamp_center_group = shgroup_dynpoints_uniform_color(psl->non_meshes, ts.colorGroup, &ts.sizeLampCenter);
+
+ geom = DRW_cache_lamp_get();
+ lamp_circle = shgroup_instance_screenspace(psl->non_meshes, geom, &ts.sizeLampCircle);
+ lamp_circle_shadow = shgroup_instance_screenspace(psl->non_meshes, geom, &ts.sizeLampCircleShadow);
+
+ geom = DRW_cache_lamp_sunrays_get();
+ lamp_sunrays = shgroup_instance_screenspace(psl->non_meshes, geom, &ts.sizeLampCircle);
+
+ lamp_groundline = shgroup_groundlines_uniform_color(psl->non_meshes, ts.colorLamp);
+ lamp_groundpoint = shgroup_groundpoints_uniform_color(psl->non_meshes, ts.colorLamp);
+
+ geom = DRW_cache_lamp_area_get();
+ lamp_area = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_lamp_hemi_get();
+ lamp_hemi = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_line_get();
+ lamp_distance = shgroup_distance_lines_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_single_line_endpoints_get();
+ lamp_buflimit_points = shgroup_distance_lines_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_lamp_spot_get();
+ lamp_spot_cone = shgroup_spot_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_circle_get();
+ lamp_spot_blend = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_lamp_spot_square_get();
+ lamp_spot_pyramid = shgroup_instance(psl->non_meshes, geom);
+
+ geom = DRW_cache_square_get();
+ lamp_spot_blend_rect = shgroup_instance(psl->non_meshes, geom);
+
+ /* Relationship Lines */
+ relationship_lines = shgroup_dynlines_uniform_color(psl->non_meshes, ts.colorWire);
+ DRW_shgroup_state_set(relationship_lines, DRW_STATE_STIPPLE_3);
+ }
+
+ {
+ /* Object Center pass grouped by State */
+ DRWShadingGroup *grp;
+ static float outlineWidth, size;
+
+ DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND | DRW_STATE_POINT;
+ psl->ob_center = DRW_pass_create("Obj Center Pass", state);
+
+ outlineWidth = 1.0f * U.pixelsize;
+ size = U.obcenter_dia * U.pixelsize + outlineWidth;
+
+ struct GPUShader *sh = GPU_shader_get_builtin_shader(GPU_SHADER_3D_POINT_UNIFORM_SIZE_UNIFORM_COLOR_OUTLINE_AA);
+
+ /* Active */
+ grp = DRW_shgroup_point_batch_create(sh, psl->ob_center);
+ DRW_shgroup_uniform_float(grp, "size", &size, 1);
+ DRW_shgroup_uniform_float(grp, "outlineWidth", &outlineWidth, 1);
+ DRW_shgroup_uniform_vec4(grp, "color", ts.colorActive, 1);
+ DRW_shgroup_uniform_vec4(grp, "outlineColor", ts.colorOutline, 1);
+ center_active = grp;
+
+ /* Select */
+ grp = DRW_shgroup_point_batch_create(sh, psl->ob_center);
+ DRW_shgroup_uniform_vec4(grp, "color", ts.colorSelect, 1);
+ center_selected = grp;
+
+ /* Deselect */
+ grp = DRW_shgroup_point_batch_create(sh, psl->ob_center);
+ DRW_shgroup_uniform_vec4(grp, "color", ts.colorDeselect, 1);
+ center_deselected = grp;
+ }
+}
+
+static void DRW_shgroup_wire_outline(Object *ob, const bool do_wire, const bool do_outline)
+{
+ struct GPUShader *sh;
+ OBJECT_PassList *psl = vedata->psl;
+ struct Batch *geom = DRW_cache_wire_outline_get(ob);
+
+ float *color;
+ DRW_object_wire_theme_get(ob, &color);
+
+ bool is_perps = DRW_viewport_is_persp_get();
+ static bool bTrue = true;
+ static bool bFalse = false;
+
+ /* Note (TODO) : this requires cache to be discarded on ortho/perp switch
+ * It may be preferable (or not depending on performance implication)
+ * to introduce a shader uniform switch */
+ if (is_perps) {
+ sh = GPU_shader_get_builtin_shader(GPU_SHADER_EDGES_FRONT_BACK_PERSP);
+ }
+ else {
+ sh = GPU_shader_get_builtin_shader(GPU_SHADER_EDGES_FRONT_BACK_ORTHO);
+ }
+
+ if (do_wire) {
+ bool *bFront = (do_wire) ? &bTrue : &bFalse;
+ bool *bBack = (do_wire) ? &bTrue : &bFalse;
+
+ DRWShadingGroup *grp = DRW_shgroup_create(sh, psl->wire_outline);
+ DRW_shgroup_state_set(grp, DRW_STATE_WIRE);
+ DRW_shgroup_uniform_vec4(grp, "frontColor", color, 1);
+ DRW_shgroup_uniform_vec4(grp, "backColor", color, 1);
+ DRW_shgroup_uniform_bool(grp, "drawFront", bFront, 1);
+ DRW_shgroup_uniform_bool(grp, "drawBack", bBack, 1);
+ DRW_shgroup_uniform_bool(grp, "drawSilhouette", &bFalse, 1);
+ DRW_shgroup_call_add(grp, geom, ob->obmat);
+ }
+
+ if (do_outline) {
+ DRWShadingGroup *grp = DRW_shgroup_create(sh, psl->wire_outline);
+ DRW_shgroup_state_set(grp, DRW_STATE_WIRE_LARGE);
+ DRW_shgroup_uniform_vec4(grp, "silhouetteColor", color, 1);
+ DRW_shgroup_uniform_bool(grp, "drawFront", &bFalse, 1);
+ DRW_shgroup_uniform_bool(grp, "drawBack", &bFalse, 1);
+ DRW_shgroup_uniform_bool(grp, "drawSilhouette", &bTrue, 1);
+
+ DRW_shgroup_call_add(grp, geom, ob->obmat);
+ }
+}
+
+static void DRW_shgroup_lamp(Object *ob)
{
- OBJECT_PassList *psl = DRW_mode_pass_list_get();
-
- DRW_mode_passes_setup(NULL,
- NULL,
- &psl->wire_outline_pass,
- &psl->non_meshes_pass,
- &psl->ob_center_pass,
- &psl->bone_solid_pass,
- &psl->bone_wire_pass);
+ Lamp *la = ob->data;
+ float *color;
+ int theme_id = DRW_object_wire_theme_get(ob, &color);
+ static float zero = 0.0f;
+
+ /* Don't draw the center if it's selected or active */
+ if (theme_id == TH_GROUP)
+ DRW_shgroup_dynamic_call_add(lamp_center_group, ob->obmat[3]);
+ else if (theme_id == TH_LAMP)
+ DRW_shgroup_dynamic_call_add(lamp_center, ob->obmat[3]);
+
+ /* First circle */
+ DRW_shgroup_dynamic_call_add(lamp_circle, ob->obmat[3], color);
+
+ /* draw dashed outer circle if shadow is on. remember some lamps can't have certain shadows! */
+ if (la->type != LA_HEMI) {
+ if ((la->mode & LA_SHAD_RAY) || ((la->mode & LA_SHAD_BUF) && (la->type == LA_SPOT))) {
+ DRW_shgroup_dynamic_call_add(lamp_circle_shadow, ob->obmat[3], color);
+ }
+ }
+
+ /* Distance */
+ if (ELEM(la->type, LA_HEMI, LA_SUN, LA_AREA)) {
+ DRW_shgroup_dynamic_call_add(lamp_distance, color, &zero, &la->dist, ob->obmat);
+ }
+
+ copy_m4_m4(la->shapemat, ob->obmat);
+
+ if (la->type == LA_SUN) {
+ DRW_shgroup_dynamic_call_add(lamp_sunrays, ob->obmat[3], color);
+ }
+ else if (la->type == LA_SPOT) {
+ float size[3], sizemat[4][4];
+ static float one = 1.0f;
+ float blend = 1.0f - pow2f(la->spotblend);
+
+ size[0] = size[1] = sinf(la->spotsize * 0.5f) * la->dist;
+ size[2] = cosf(la->spotsize * 0.5f) * la->dist;
+
+ size_to_mat4(sizemat, size);
+ mul_m4_m4m4(la->spotconemat, ob->obmat, sizemat);
+
+ size[0] = size[1] = blend; size[2] = 1.0f;
+ size_to_mat4(sizemat, size);
+ translate_m4(sizemat, 0.0f, 0.0f, -1.0f);
+ rotate_m4(sizemat, 'X', M_PI / 2.0f);
+ mul_m4_m4m4(la->spotblendmat, la->spotconemat, sizemat);
+
+ if (la->mode & LA_SQUARE) {
+ DRW_shgroup_dynamic_call_add(lamp_spot_pyramid, color, &one, la->spotconemat);
+
+ /* hide line if it is zero size or overlaps with outer border,
+ * previously it adjusted to always to show it but that seems
+ * confusing because it doesn't show the actual blend size */
+ if (blend != 0.0f && blend != 1.0f) {
+ DRW_shgroup_dynamic_call_add(lamp_spot_blend_rect, color, &one, la->spotblendmat);
+ }
+ }
+ else {
+ DRW_shgroup_dynamic_call_add(lamp_spot_cone, color, la->spotconemat);
+
+ /* hide line if it is zero size or overlaps with outer border,
+ * previously it adjusted to always to show it but that seems
+ * confusing because it doesn't show the actual blend size */
+ if (blend != 0.0f && blend != 1.0f) {
+ DRW_shgroup_dynamic_call_add(lamp_spot_blend, color, &one, la->spotblendmat);
+ }
+ }
+
+ normalize_m4(la->shapemat);
+ DRW_shgroup_dynamic_call_add(lamp_buflimit, color, &la->clipsta, &la->clipend, ob->obmat);
+ DRW_shgroup_dynamic_call_add(lamp_buflimit_points, color, &la->clipsta, &la->clipend, ob->obmat);
+ }
+ else if (la->type == LA_HEMI) {
+ static float hemisize = 2.0f;
+ DRW_shgroup_dynamic_call_add(lamp_hemi, color, &hemisize, la->shapemat);
+ }
+ else if (la->type == LA_AREA) {
+ float size[3] = {1.0f, 1.0f, 1.0f}, sizemat[4][4];
+
+ if (la->area_shape == LA_AREA_RECT) {
+ size[1] = la->area_sizey / la->area_size;
+ size_to_mat4(sizemat, size);
+ mul_m4_m4m4(la->shapemat, la->shapemat, sizemat);
+ }
+
+ DRW_shgroup_dynamic_call_add(lamp_area, color, &la->area_size, la->shapemat);
+ }
+
+ /* Line and point going to the ground */
+ DRW_shgroup_dynamic_call_add(lamp_groundline, ob->obmat[3]);
+ DRW_shgroup_dynamic_call_add(lamp_groundpoint, ob->obmat[3]);
}
-void OBJECT_cache_populate(Object *ob)
+static void DRW_shgroup_camera(Object *ob)
{
+ const struct bContext *C = DRW_get_context();
+ View3D *v3d = CTX_wm_view3d(C);
+ Scene *scene = CTX_data_scene(C);
+
+ Camera *cam = ob->data;
+ const bool is_active = (ob == v3d->camera);
+ float *color;
+ DRW_object_wire_theme_get(ob, &color);
+
+ float vec[4][3], asp[2], shift[2], scale[3], drawsize;
+
+ scale[0] = 1.0f / len_v3(ob->obmat[0]);
+ scale[1] = 1.0f / len_v3(ob->obmat[1]);
+ scale[2] = 1.0f / len_v3(ob->obmat[2]);
+
+ BKE_camera_view_frame_ex(scene, cam, cam->drawsize, false, scale,
+ asp, shift, &drawsize, vec);
+
+ // /* Frame coords */
+ copy_v2_v2(cam->drwcorners[0], vec[0]);
+ copy_v2_v2(cam->drwcorners[1], vec[1]);
+ copy_v2_v2(cam->drwcorners[2], vec[2]);
+ copy_v2_v2(cam->drwcorners[3], vec[3]);
+
+ /* depth */
+ cam->drwdepth = vec[0][2];
+
+ /* tria */
+ cam->drwtria[0][0] = shift[0] + ((0.7f * drawsize) * scale[0]);
+ cam->drwtria[0][1] = shift[1] + ((drawsize * (asp[1] + 0.1f)) * scale[1]);
+ cam->drwtria[1][0] = shift[0];
+ cam->drwtria[1][1] = shift[1] + ((1.1f * drawsize * (asp[1] + 0.7f)) * scale[1]);
+
+ DRW_shgroup_dynamic_call_add(camera, color, cam->drwcorners, &cam->drwdepth, cam->drwtria, ob->obmat);
+
+ /* Active cam */
+ if (is_active) {
+ DRW_shgroup_dynamic_call_add(camera_tria, color, cam->drwcorners, &cam->drwdepth, cam->drwtria, ob->obmat);
+ }
+
+ /* draw the rest in normalize object space */
+ copy_m4_m4(cam->drwnormalmat, ob->obmat);
+ normalize_m4(cam->drwnormalmat);
+
+ if (cam->flag & CAM_SHOWLIMITS) {
+ static float col[3] = {0.5f, 0.5f, 0.25f}, col_hi[3] = {1.0f, 1.0f, 0.5f};
+ float sizemat[4][4], size[3] = {1.0f, 1.0f, 0.0f};
+ float focusdist = BKE_camera_object_dof_distance(ob);
+
+ copy_m4_m4(cam->drwfocusmat, cam->drwnormalmat);
+ translate_m4(cam->drwfocusmat, 0.0f, 0.0f, -focusdist);
+ size_to_mat4(sizemat, size);
+ mul_m4_m4m4(cam->drwfocusmat, cam->drwfocusmat, sizemat);
+
+ DRW_shgroup_dynamic_call_add(camera_focus, (is_active ? col_hi : col), &cam->drawsize, cam->drwfocusmat);
+
+ DRW_shgroup_dynamic_call_add(camera_clip, color, &cam->clipsta, &cam->clipend, cam->drwnormalmat);
+ DRW_shgroup_dynamic_call_add(camera_clip_points, (is_active ? col_hi : col), &cam->clipsta, &cam->clipend, cam->drwnormalmat);
+ }
+
+ if (cam->flag & CAM_SHOWMIST) {
+ World *world = scene->world;
+
+ if (world) {
+ static float col[3] = {0.5f, 0.5f, 0.5f}, col_hi[3] = {1.0f, 1.0f, 1.0f};
+ world->mistend = world->miststa + world->mistdist;
+ DRW_shgroup_dynamic_call_add(camera_mist, color, &world->miststa, &world->mistend, cam->drwnormalmat);
+ DRW_shgroup_dynamic_call_add(camera_mist_points, (is_active ? col_hi : col), &world->miststa, &world->mistend, cam->drwnormalmat);
+ }
+ }
+}
+
+static void DRW_shgroup_empty(Object *ob)
+{
+ float *color;
+ DRW_object_wire_theme_get(ob, &color);
+
+ switch (ob->empty_drawtype) {
+ case OB_PLAINAXES:
+ DRW_shgroup_dynamic_call_add(plain_axes, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_SINGLE_ARROW:
+ DRW_shgroup_dynamic_call_add(single_arrow, color, &ob->empty_drawsize, ob->obmat);
+ DRW_shgroup_dynamic_call_add(single_arrow_line, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_CUBE:
+ DRW_shgroup_dynamic_call_add(cube, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_CIRCLE:
+ DRW_shgroup_dynamic_call_add(circle, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_EMPTY_SPHERE:
+ DRW_shgroup_dynamic_call_add(sphere, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_EMPTY_CONE:
+ DRW_shgroup_dynamic_call_add(cone, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ case OB_ARROWS:
+ DRW_shgroup_dynamic_call_add(arrows, color, &ob->empty_drawsize, ob->obmat);
+ DRW_shgroup_dynamic_call_add(axis_names, color, &ob->empty_drawsize, ob->obmat);
+ break;
+ }
+}
+
+static void DRW_shgroup_speaker(Object *ob)
+{
+ float *color;
+ static float one = 1.0f;
+ DRW_object_wire_theme_get(ob, &color);
+
+ DRW_shgroup_dynamic_call_add(speaker, color, &one, ob->obmat);
+}
+
+static void DRW_shgroup_relationship_lines(Object *ob)
+{
+ if (ob->parent) {
+ DRW_shgroup_dynamic_call_add(relationship_lines, ob->obmat[3]);
+ DRW_shgroup_dynamic_call_add(relationship_lines, ob->parent->obmat[3]);
+ }
+}
+
+static void DRW_shgroup_object_center(Object *ob)
+{
+ if ((ob->base_flag & BASE_SELECTED) != 0) {
+ DRW_shgroup_dynamic_call_add(center_selected, ob->obmat[3]);
+ }
+ else if (0) {
+ DRW_shgroup_dynamic_call_add(center_deselected, ob->obmat[3]);
+ }
+}
+
+static void OBJECT_cache_populate(Object *ob)
+{
+ const struct bContext *C = DRW_get_context();
+ Scene *scene = CTX_data_scene(C);
+
CollectionEngineSettings *ces_mode_ob = BKE_object_collection_engine_get(ob, COLLECTION_MODE_OBJECT, "");
bool do_wire = BKE_collection_engine_property_value_get_bool(ces_mode_ob, "show_wire");
@@ -61,7 +570,12 @@ void OBJECT_cache_populate(Object *ob)
switch (ob->type) {
case OB_MESH:
- DRW_shgroup_wire_outline(ob, do_wire, false, do_outlines);
+ {
+ Object *obedit = scene->obedit;
+ if (ob != obedit) {
+ DRW_shgroup_wire_outline(ob, do_wire, do_outlines);
+ }
+ }
break;
case OB_LAMP:
DRW_shgroup_lamp(ob);
@@ -76,7 +590,14 @@ void OBJECT_cache_populate(Object *ob)
DRW_shgroup_speaker(ob);
break;
case OB_ARMATURE:
- DRW_shgroup_armature_object(ob);
+ {
+ bArmature *arm = ob->data;
+ if (arm->edbo == NULL) {
+ DRW_shgroup_armature_object(ob, vedata->psl->bone_solid,
+ vedata->psl->bone_wire,
+ relationship_lines);
+ }
+ }
break;
default:
break;
@@ -86,20 +607,16 @@ void OBJECT_cache_populate(Object *ob)
DRW_shgroup_relationship_lines(ob);
}
-void OBJECT_cache_finish(void)
+static void OBJECT_draw_scene(void)
{
- /* Do nothing */
-}
-
-void OBJECT_draw(void)
-{
- OBJECT_PassList *psl = DRW_mode_pass_list_get();
+ OBJECT_Data *ved = DRW_viewport_engine_data_get("ObjectMode");
+ OBJECT_PassList *psl = ved->psl;
- DRW_draw_pass(psl->bone_wire_pass);
- DRW_draw_pass(psl->bone_solid_pass);
- DRW_draw_pass(psl->wire_outline_pass);
- DRW_draw_pass(psl->non_meshes_pass);
- DRW_draw_pass(psl->ob_center_pass);
+ DRW_draw_pass(psl->bone_wire);
+ DRW_draw_pass(psl->bone_solid);
+ DRW_draw_pass(psl->wire_outline);
+ DRW_draw_pass(psl->non_meshes);
+ DRW_draw_pass(psl->ob_center);
}
void OBJECT_collection_settings_create(CollectionEngineSettings *ces)
@@ -108,3 +625,15 @@ void OBJECT_collection_settings_create(CollectionEngineSettings *ces)
BKE_collection_engine_property_add_int(ces, "show_wire", false);
BKE_collection_engine_property_add_int(ces, "show_backface_culling", false);
}
+
+DrawEngineType draw_engine_object_type = {
+ NULL, NULL,
+ N_("ObjectMode"),
+ NULL,
+ NULL,
+ &OBJECT_cache_init,
+ &OBJECT_cache_populate,
+ NULL,
+ NULL,
+ &OBJECT_draw_scene
+};
diff --git a/source/blender/editors/space_view3d/CMakeLists.txt b/source/blender/editors/space_view3d/CMakeLists.txt
index f6d5cf6e5d2..34b68a80a0f 100644
--- a/source/blender/editors/space_view3d/CMakeLists.txt
+++ b/source/blender/editors/space_view3d/CMakeLists.txt
@@ -25,6 +25,7 @@ set(INC
../../blenlib
../../blentranslation
../../bmesh
+ ../../draw
../../gpu
../../imbuf
../../makesdna
diff --git a/source/blender/editors/space_view3d/view3d_draw.c b/source/blender/editors/space_view3d/view3d_draw.c
index f41d7d68288..21d07761cf5 100644
--- a/source/blender/editors/space_view3d/view3d_draw.c
+++ b/source/blender/editors/space_view3d/view3d_draw.c
@@ -60,6 +60,8 @@
#include "DNA_view3d_types.h"
#include "DNA_windowmanager_types.h"
+#include "DRW_engine.h"
+
#include "ED_keyframing.h"
#include "ED_armature.h"
#include "ED_keyframing.h"
@@ -2330,34 +2332,18 @@ static void view3d_draw_view(const bContext *C, ARegion *ar, DrawData *draw_data
#endif
}
-static void view3d_render_pass(const bContext *C, ARegion *UNUSED(ar))
-{
- Scene *scene = CTX_data_scene(C);
- RenderEngineType *type = RE_engines_find(scene->r.engine); /* In the future we should get that from Layers */
-
- if (type->flag & RE_USE_OGL_PIPELINE) {
- type->view_draw(NULL, C);
- }
- else {
- // Offline Render engine
- }
-}
-
static void view3d_draw_view_new(const bContext *C, ARegion *ar, DrawData *UNUSED(draw_data))
{
-
view3d_draw_setup_view(C, ar);
/* Only 100% compliant on new spec goes bellow */
- view3d_render_pass(C, ar);
+ DRW_draw_view(C);
}
-
void view3d_main_region_draw(const bContext *C, ARegion *ar)
{
Scene *scene = CTX_data_scene(C);
View3D *v3d = CTX_wm_view3d(C);
- int mode = CTX_data_mode_enum(C);
RegionView3D *rv3d = ar->regiondata;
/* TODO layers - In the future we should get RE from Layers */
RenderEngineType *type = RE_engines_find(scene->r.engine);
@@ -2370,21 +2356,19 @@ void view3d_main_region_draw(const bContext *C, ARegion *ar)
if (!rv3d->viewport)
rv3d->viewport = GPU_viewport_create();
- GPU_viewport_bind(rv3d->viewport, &ar->winrct, scene->r.engine, mode);
-
/* TODO viewport - there is so much to be done, in fact a lot will need to happen in the space_view3d.c
* before we even call the drawing routine, but let's move on for now (dfelinto)
* but this is a provisory way to start seeing things in the viewport */
DrawData draw_data;
view3d_draw_data_init(C, ar, rv3d, &draw_data);
+ GPU_viewport_bind(rv3d->viewport, &ar->winrct);
+
if (type->flag & RE_USE_OGL_PIPELINE)
view3d_draw_view_new(C, ar, &draw_data);
else
view3d_draw_view(C, ar, &draw_data);
- GPU_viewport_unbind(rv3d->viewport);
-
v3d->flag |= V3D_INVALID_BACKBUF;
}
diff --git a/source/blender/gpu/GPU_viewport.h b/source/blender/gpu/GPU_viewport.h
index f0e991fdac2..64f003badb7 100644
--- a/source/blender/gpu/GPU_viewport.h
+++ b/source/blender/gpu/GPU_viewport.h
@@ -63,28 +63,27 @@ typedef struct StorageList {
void *storage[MAX_STORAGE]; /* custom structs from the engine */
} StorageList;
-/* Buffer and textures used by the viewport by default */
-typedef struct DefaultFramebufferList {
- struct GPUFrameBuffer *default_fb;
-} DefaultFramebufferList;
+typedef struct ViewportEngineData {
+ char engine_name[32];
-typedef struct DefaultTextureList {
- struct GPUTexture *color;
- struct GPUTexture *depth;
-} DefaultTextureList;
-
-typedef struct DefaultPassList {
- struct DRWPass *non_meshes_pass;
- struct DRWPass *ob_center_pass;
-} DefaultPassList;
+ FramebufferList *fbl;
+ TextureList *txl;
+ PassList *psl;
+ StorageList *stl;
+} ViewportEngineData;
GPUViewport *GPU_viewport_create(void);
-void GPU_viewport_bind(GPUViewport *viewport, const rcti *rect, const char *engine, int mode);
+void GPU_viewport_bind(GPUViewport *viewport, const rcti *rect);
void GPU_viewport_unbind(GPUViewport *viewport);
void GPU_viewport_free(GPUViewport *viewport);
-void GPU_viewport_get_engine_data(GPUViewport *viewport, FramebufferList **fbs, TextureList **txs, PassList **pss, StorageList **str);
-void GPU_viewport_get_mode_data(GPUViewport *viewport, FramebufferList **fbs, TextureList **txs, PassList **pss, StorageList **str);
+void *GPU_viewport_engine_data_create(GPUViewport *viewport, const char *engine_name);
+void *GPU_viewport_engine_data_get(GPUViewport *viewport, const char *engine_name);
+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);
+
+bool GPU_viewport_cache_validate(GPUViewport *viewport, int hash);
/* debug */
bool GPU_viewport_debug_depth_create(GPUViewport *viewport, int width, int height, char err_out[256]);
diff --git a/source/blender/gpu/intern/gpu_viewport.c b/source/blender/gpu/intern/gpu_viewport.c
index c8e60c089d3..fc5c3ce3613 100644
--- a/source/blender/gpu/intern/gpu_viewport.c
+++ b/source/blender/gpu/intern/gpu_viewport.c
@@ -33,6 +33,7 @@
#include <string.h>
+#include "BLI_listbase.h"
#include "BLI_rect.h"
#include "BLI_string.h"
@@ -57,20 +58,11 @@ struct GPUViewport {
GPUTexture *debug_depth;
int size[2];
- /* Viewport Buffer Storage */
+ ListBase data; /* ViewportEngineData wrapped in LinkData */
+ int data_hash; /* If hash mismatch we free all ViewportEngineData in this viewport */
+
FramebufferList *fbl;
TextureList *txl;
- PassList *psl;
- StorageList *stl;
-
- char engine_name[32];
-
- /* Mode storage */
- FramebufferList *fbl_mode;
- TextureList *txl_mode;
- PassList *psl_mode;
- StorageList *stl_mode;
- int mode;
};
static void GPU_viewport_buffers_free(FramebufferList *fbl, TextureList *txl);
@@ -82,66 +74,118 @@ GPUViewport *GPU_viewport_create(void)
GPUViewport *viewport = MEM_callocN(sizeof(GPUViewport), "GPUViewport");
viewport->fbl = MEM_callocN(sizeof(FramebufferList), "FramebufferList");
viewport->txl = MEM_callocN(sizeof(TextureList), "TextureList");
- viewport->psl = MEM_callocN(sizeof(PassList), "PassList");
- viewport->stl = MEM_callocN(sizeof(StorageList), "StorageList");
- viewport->fbl_mode = MEM_callocN(sizeof(FramebufferList), "FramebufferList");
- viewport->txl_mode = MEM_callocN(sizeof(TextureList), "TextureList");
- viewport->psl_mode = MEM_callocN(sizeof(PassList), "PassList");
- viewport->stl_mode = MEM_callocN(sizeof(StorageList), "StorageList");
viewport->size[0] = viewport->size[1] = -1;
return viewport;
}
-void GPU_viewport_get_engine_data(GPUViewport *viewport, FramebufferList **fbs, TextureList **txs, PassList **pss, StorageList **str)
+void *GPU_viewport_engine_data_create(GPUViewport *viewport, const char *engine_name)
{
- *fbs = viewport->fbl;
- *txs = viewport->txl;
- *pss = viewport->psl;
- *str = viewport->stl;
+ LinkData *ld = MEM_callocN(sizeof(LinkData), "LinkData");
+ ViewportEngineData *data = MEM_callocN(sizeof(ViewportEngineData), "ViewportEngineData");
+ BLI_strncpy(data->engine_name, engine_name, 32);
+
+ data->fbl = MEM_callocN(sizeof(FramebufferList), "FramebufferList");
+ data->txl = MEM_callocN(sizeof(TextureList), "TextureList");
+ data->psl = MEM_callocN(sizeof(PassList), "PassList");
+ data->stl = MEM_callocN(sizeof(StorageList), "StorageList");
+
+ ld->data = data;
+ BLI_addtail(&viewport->data, ld);
+
+ return data;
}
-void GPU_viewport_get_mode_data(GPUViewport *viewport, FramebufferList **fbs, TextureList **txs, PassList **pss, StorageList **str)
+static void GPU_viewport_engines_data_free(GPUViewport *viewport)
{
- *fbs = viewport->fbl_mode;
- *txs = viewport->txl_mode;
- *pss = viewport->psl_mode;
- *str = viewport->stl_mode;
+ LinkData *next;
+ for (LinkData *link = viewport->data.first; link; link = next) {
+ next = link->next;
+ ViewportEngineData *data = link->data;
+
+ GPU_viewport_buffers_free(data->fbl, data->txl);
+ GPU_viewport_passes_free(data->psl);
+ GPU_viewport_storage_free(data->stl);
+
+ MEM_freeN(data->fbl);
+ MEM_freeN(data->txl);
+ MEM_freeN(data->psl);
+ MEM_freeN(data->stl);
+
+ MEM_freeN(data);
+
+ BLI_remlink(&viewport->data, link);
+ MEM_freeN(link);
+ }
}
-void GPU_viewport_bind(GPUViewport *viewport, const rcti *rect, const char *engine, int mode)
+void *GPU_viewport_engine_data_get(GPUViewport *viewport, const char *engine_name)
{
- DefaultFramebufferList *dfbl = (DefaultFramebufferList *)viewport->fbl;
- DefaultTextureList *dtxl = (DefaultTextureList *)viewport->txl;
+ for (LinkData *link = viewport->data.first; link; link = link->next) {
+ ViewportEngineData *vdata = link->data;
+ if (STREQ(engine_name, vdata->engine_name)) {
+ return vdata;
+ }
+ }
+ return NULL;
+}
- /* add one pixel because of scissor test */
- int rect_w = BLI_rcti_size_x(rect) + 1, rect_h = BLI_rcti_size_y(rect) + 1;
+void *GPU_viewport_framebuffer_list_get(GPUViewport *viewport)
+{
+ return viewport->fbl;
+}
+
+void *GPU_viewport_texture_list_get(GPUViewport *viewport)
+{
+ return viewport->txl;
+}
+
+void GPU_viewport_size_get(GPUViewport *viewport, int *size)
+{
+ size[0] = viewport->size[0];
+ size[1] = viewport->size[1];
+}
+bool GPU_viewport_cache_validate(GPUViewport *viewport, int hash)
+{
+ bool dirty = false;
+
+ /* TODO for testing only, we need proper cache invalidation */
if (G.debug_value != 666 && G.debug_value != 667) {
- /* TODO for testing only, we need proper cache invalidation */
- GPU_viewport_passes_free(viewport->psl);
- GPU_viewport_passes_free(viewport->psl_mode);
+ for (LinkData *link = viewport->data.first; link; link = link->next) {
+ ViewportEngineData *data = link->data;
+ GPU_viewport_passes_free(data->psl);
+ }
+ dirty = true;
}
- if (!STREQ(engine, viewport->engine_name)) {
- GPU_viewport_storage_free(viewport->stl);
- GPU_viewport_buffers_free(viewport->fbl, viewport->txl);
-
- BLI_strncpy(viewport->engine_name, engine, 32);
+ if (viewport->data_hash != hash) {
+ GPU_viewport_engines_data_free(viewport);
+ dirty = true;
}
- if (mode != viewport->mode) {
- GPU_viewport_buffers_free(viewport->fbl_mode, viewport->txl_mode);
- GPU_viewport_passes_free(viewport->psl_mode);
- GPU_viewport_storage_free(viewport->stl_mode);
+ viewport->data_hash = hash;
- viewport->mode = mode;
- }
+ return dirty;
+}
+
+void GPU_viewport_bind(GPUViewport *viewport, const rcti *rect)
+{
+ DefaultFramebufferList *dfbl = (DefaultFramebufferList *)viewport->fbl;
+ DefaultTextureList *dtxl = (DefaultTextureList *)viewport->txl;
+
+ /* add one pixel because of scissor test */
+ int rect_w = BLI_rcti_size_x(rect) + 1;
+ int rect_h = BLI_rcti_size_y(rect) + 1;
if (dfbl->default_fb) {
if (rect_w != viewport->size[0] || rect_h != viewport->size[1]) {
GPU_viewport_buffers_free(viewport->fbl, viewport->txl);
- GPU_viewport_buffers_free(viewport->fbl_mode, viewport->txl_mode);
+
+ for (LinkData *link = viewport->data.first; link; link = link->next) {
+ ViewportEngineData *data = link->data;
+ GPU_viewport_buffers_free(data->fbl, data->txl);
+ }
}
}
@@ -211,12 +255,11 @@ static void draw_ofs_to_screen(GPUViewport *viewport)
unsigned pos = add_attrib(format, "pos", GL_FLOAT, 2, KEEP_FLOAT);
immBindBuiltinProgram(GPU_SHADER_3D_IMAGE_MODULATE_ALPHA);
-
GPU_texture_bind(color, 0);
immUniform1i("image", 0); /* default GL_TEXTURE0 unit */
- immBegin(GL_QUADS, 4);
+ immBegin(GL_TRIANGLE_STRIP, 4);
immAttrib2f(texcoord, 0.0f, 0.0f);
immVertex2f(pos, 0.0f, 0.0f);
@@ -224,12 +267,12 @@ static void draw_ofs_to_screen(GPUViewport *viewport)
immAttrib2f(texcoord, 1.0f, 0.0f);
immVertex2f(pos, w, 0.0f);
- immAttrib2f(texcoord, 1.0f, 1.0f);
- immVertex2f(pos, w, h);
-
immAttrib2f(texcoord, 0.0f, 1.0f);
immVertex2f(pos, 0.0f, h);
+ immAttrib2f(texcoord, 1.0f, 1.0f);
+ immVertex2f(pos, w, h);
+
immEnd();
GPU_texture_unbind(color);
@@ -296,25 +339,13 @@ static void GPU_viewport_passes_free(PassList *psl)
void GPU_viewport_free(GPUViewport *viewport)
{
- GPU_viewport_debug_depth_free(viewport);
+ GPU_viewport_engines_data_free(viewport);
GPU_viewport_buffers_free(viewport->fbl, viewport->txl);
- GPU_viewport_passes_free(viewport->psl);
- GPU_viewport_storage_free(viewport->stl);
-
- GPU_viewport_buffers_free(viewport->fbl_mode, viewport->txl_mode);
- GPU_viewport_passes_free(viewport->psl_mode);
- GPU_viewport_storage_free(viewport->stl_mode);
-
MEM_freeN(viewport->fbl);
MEM_freeN(viewport->txl);
- MEM_freeN(viewport->psl);
- MEM_freeN(viewport->stl);
- MEM_freeN(viewport->fbl_mode);
- MEM_freeN(viewport->txl_mode);
- MEM_freeN(viewport->psl_mode);
- MEM_freeN(viewport->stl_mode);
+ GPU_viewport_debug_depth_free(viewport);
}
/****************** debug ********************/
@@ -360,7 +391,7 @@ void GPU_viewport_debug_depth_draw(GPUViewport *viewport, const float znear, con
immUniform1f("zfar", zfar);
immUniform1i("image", 0); /* default GL_TEXTURE0 unit */
- immBegin(GL_QUADS, 4);
+ immBegin(GL_TRIANGLE_STRIP, 4);
immAttrib2f(texcoord, 0.0f, 0.0f);
immVertex2f(pos, 0.0f, 0.0f);
@@ -368,12 +399,12 @@ void GPU_viewport_debug_depth_draw(GPUViewport *viewport, const float znear, con
immAttrib2f(texcoord, 1.0f, 0.0f);
immVertex2f(pos, w, 0.0f);
- immAttrib2f(texcoord, 1.0f, 1.0f);
- immVertex2f(pos, w, h);
-
immAttrib2f(texcoord, 0.0f, 1.0f);
immVertex2f(pos, 0.0f, h);
+ immAttrib2f(texcoord, 1.0f, 1.0f);
+ immVertex2f(pos, w, h);
+
immEnd();
GPU_texture_unbind(viewport->debug_depth);
diff --git a/source/blender/render/extern/include/RE_engine.h b/source/blender/render/extern/include/RE_engine.h
index f1b3534b40a..74d96ce69d1 100644
--- a/source/blender/render/extern/include/RE_engine.h
+++ b/source/blender/render/extern/include/RE_engine.h
@@ -102,6 +102,8 @@ typedef struct RenderEngineType {
void (*collection_settings_create)(struct RenderEngine *engine, struct CollectionEngineSettings *ces);
+ struct DrawEngineType *draw_engine;
+
/* RNA integration */
ExtensionRNA ext;
} RenderEngineType;
diff --git a/source/blender/render/intern/source/external_engine.c b/source/blender/render/intern/source/external_engine.c
index 1744d88a14f..8c1cdb3dc8a 100644
--- a/source/blender/render/intern/source/external_engine.c
+++ b/source/blender/render/intern/source/external_engine.c
@@ -71,7 +71,7 @@
static RenderEngineType internal_render_type = {
NULL, NULL,
"BLENDER_RENDER", N_("Blender Render"), RE_INTERNAL,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
{NULL, NULL, NULL}
};
@@ -80,7 +80,7 @@ static RenderEngineType internal_render_type = {
static RenderEngineType internal_game_type = {
NULL, NULL,
"BLENDER_GAME", N_("Blender Game"), RE_INTERNAL | RE_GAME,
- NULL, NULL, NULL, NULL, NULL, NULL, NULL,
+ NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
{NULL, NULL, NULL}
};
@@ -94,7 +94,7 @@ void RE_engines_init(void)
#ifdef WITH_GAMEENGINE
RE_engines_register(NULL, &internal_game_type);
#endif
- DRW_engines_init();
+ DRW_engines_register();
}
void RE_engines_exit(void)
@@ -121,6 +121,9 @@ void RE_engines_exit(void)
void RE_engines_register(Main *bmain, RenderEngineType *render_type)
{
+ if (render_type->draw_engine) {
+ DRW_engine_register(render_type->draw_engine);
+ }
if (render_type->collection_settings_create) {
BKE_layer_collection_engine_settings_callback_register(bmain, render_type->idname, render_type->collection_settings_create);
}