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:
Diffstat (limited to 'source/blender/draw')
-rw-r--r--source/blender/draw/CMakeLists.txt7
-rw-r--r--source/blender/draw/engines/overlay/overlay_engine.cc18
-rw-r--r--source/blender/draw/engines/overlay/overlay_private.hh16
-rw-r--r--source/blender/draw/engines/overlay/overlay_shader.cc66
-rw-r--r--source/blender/draw/engines/overlay/overlay_viewer_attribute.cc181
-rw-r--r--source/blender/draw/engines/overlay/shaders/infos/overlay_edit_mode_info.hh12
-rw-r--r--source/blender/draw/engines/overlay/shaders/infos/overlay_viewer_attribute_info.hh62
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_pointcloud_only_vert.glsl9
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curve_vert.glsl9
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curves_vert.glsl28
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_frag.glsl6
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_mesh_vert.glsl9
-rw-r--r--source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_pointcloud_vert.glsl10
-rw-r--r--source/blender/draw/intern/draw_cache.c19
-rw-r--r--source/blender/draw/intern/draw_cache.h3
-rw-r--r--source/blender/draw/intern/draw_cache_extract.hh3
-rw-r--r--source/blender/draw/intern/draw_cache_extract_mesh.cc1
-rw-r--r--source/blender/draw/intern/draw_cache_impl.h3
-rw-r--r--source/blender/draw/intern/draw_cache_impl_curve.cc45
-rw-r--r--source/blender/draw/intern/draw_cache_impl_mesh.cc27
-rw-r--r--source/blender/draw/intern/draw_cache_impl_pointcloud.cc47
-rw-r--r--source/blender/draw/intern/draw_manager.c10
-rw-r--r--source/blender/draw/intern/mesh_extractors/extract_mesh.hh1
-rw-r--r--source/blender/draw/intern/mesh_extractors/extract_mesh_vbo_attributes.cc38
-rw-r--r--source/blender/draw/tests/shaders_test.cc5
25 files changed, 632 insertions, 3 deletions
diff --git a/source/blender/draw/CMakeLists.txt b/source/blender/draw/CMakeLists.txt
index 540041ed02a..45a7e3410eb 100644
--- a/source/blender/draw/CMakeLists.txt
+++ b/source/blender/draw/CMakeLists.txt
@@ -201,6 +201,7 @@ set(SRC
engines/overlay/overlay_sculpt.cc
engines/overlay/overlay_sculpt_curves.cc
engines/overlay/overlay_shader.cc
+ engines/overlay/overlay_viewer_attribute.cc
engines/overlay/overlay_volume.cc
engines/overlay/overlay_wireframe.cc
@@ -645,12 +646,18 @@ set(GLSL_SRC
engines/overlay/shaders/overlay_particle_vert.glsl
engines/overlay/shaders/overlay_point_varying_color_frag.glsl
engines/overlay/shaders/overlay_point_varying_color_varying_outline_aa_frag.glsl
+ engines/overlay/shaders/overlay_pointcloud_only_vert.glsl
engines/overlay/shaders/overlay_sculpt_curves_selection_frag.glsl
engines/overlay/shaders/overlay_sculpt_curves_selection_vert.glsl
engines/overlay/shaders/overlay_sculpt_mask_frag.glsl
engines/overlay/shaders/overlay_sculpt_mask_vert.glsl
engines/overlay/shaders/overlay_uniform_color_frag.glsl
engines/overlay/shaders/overlay_varying_color.glsl
+ engines/overlay/shaders/overlay_viewer_attribute_curve_vert.glsl
+ engines/overlay/shaders/overlay_viewer_attribute_curves_vert.glsl
+ engines/overlay/shaders/overlay_viewer_attribute_frag.glsl
+ engines/overlay/shaders/overlay_viewer_attribute_mesh_vert.glsl
+ engines/overlay/shaders/overlay_viewer_attribute_pointcloud_vert.glsl
engines/overlay/shaders/overlay_volume_gridlines_vert.glsl
engines/overlay/shaders/overlay_volume_velocity_vert.glsl
engines/overlay/shaders/overlay_wireframe_frag.glsl
diff --git a/source/blender/draw/engines/overlay/overlay_engine.cc b/source/blender/draw/engines/overlay/overlay_engine.cc
index bbcae92561d..c2c4706138f 100644
--- a/source/blender/draw/engines/overlay/overlay_engine.cc
+++ b/source/blender/draw/engines/overlay/overlay_engine.cc
@@ -16,6 +16,7 @@
#include "UI_interface.h"
+#include "BKE_duplilist.h"
#include "BKE_object.h"
#include "BKE_paint.h"
@@ -204,6 +205,7 @@ static void OVERLAY_cache_init(void *vedata)
}
OVERLAY_antialiasing_cache_init(data);
OVERLAY_armature_cache_init(data);
+ OVERLAY_viewer_attribute_cache_init(data);
OVERLAY_background_cache_init(data);
OVERLAY_fade_cache_init(data);
OVERLAY_mode_transfer_cache_init(data);
@@ -300,8 +302,12 @@ static void OVERLAY_cache_populate(void *vedata, Object *ob)
}
const DRWContextState *draw_ctx = DRW_context_state_get();
+ DupliObject *dupli_object = DRW_object_get_dupli(ob);
+ Object *dupli_parent = DRW_object_get_dupli_parent(ob);
const bool is_select = DRW_state_is_select();
const bool renderable = DRW_object_is_renderable(ob);
+ const bool is_preview = dupli_object != nullptr &&
+ dupli_object->preview_base_geometry != nullptr;
const bool in_pose_mode = ob->type == OB_ARMATURE && OVERLAY_armature_is_pose_mode(ob, draw_ctx);
const bool in_edit_mode = overlay_object_is_edit_mode(pd, ob);
const bool is_instance = (ob->base_flag & BASE_FROM_DUPLI);
@@ -313,7 +319,8 @@ static void OVERLAY_cache_populate(void *vedata, Object *ob)
(pd->ctx_mode == CTX_MODE_PARTICLE);
const bool in_paint_mode = (ob == draw_ctx->obact) &&
(draw_ctx->object_mode & OB_MODE_ALL_PAINT);
- const bool in_sculpt_curve_mode = (ob == draw_ctx->obact) &&
+ const bool in_sculpt_curve_mode = (ob == draw_ctx->obact ||
+ (is_preview && dupli_parent == draw_ctx->obact)) &&
(draw_ctx->object_mode & OB_MODE_SCULPT_CURVES);
const bool in_sculpt_mode = (ob == draw_ctx->obact) && (ob->sculpt != nullptr) &&
(ob->sculpt->mode_type == OB_MODE_SCULPT);
@@ -374,6 +381,12 @@ static void OVERLAY_cache_populate(void *vedata, Object *ob)
OVERLAY_pose_cache_populate(data, ob);
}
+ if (pd->overlay.flag & V3D_OVERLAY_VIEWER_ATTRIBUTE) {
+ if (is_preview) {
+ OVERLAY_viewer_attribute_cache_populate(data, ob);
+ }
+ }
+
if (ob->type == OB_VOLUME) {
OVERLAY_volume_cache_populate(data, ob);
}
@@ -627,6 +640,9 @@ static void OVERLAY_draw_scene(void *vedata)
OVERLAY_metaball_draw(data);
OVERLAY_gpencil_draw(data);
OVERLAY_extra_draw(data);
+ if (pd->overlay.flag & V3D_OVERLAY_VIEWER_ATTRIBUTE) {
+ OVERLAY_viewer_attribute_draw(data);
+ }
if (DRW_state_is_fbo()) {
GPU_framebuffer_bind(fbl->overlay_color_only_fb);
diff --git a/source/blender/draw/engines/overlay/overlay_private.hh b/source/blender/draw/engines/overlay/overlay_private.hh
index 0a783c44029..b1118e084a6 100644
--- a/source/blender/draw/engines/overlay/overlay_private.hh
+++ b/source/blender/draw/engines/overlay/overlay_private.hh
@@ -61,6 +61,7 @@ typedef struct OVERLAY_PassList {
DRWPass *armature_ps[2];
DRWPass *armature_bone_select_ps;
DRWPass *armature_transp_ps[2];
+ DRWPass *attribute_ps;
DRWPass *background_ps;
DRWPass *clipping_frustum_ps;
DRWPass *edit_curve_wire_ps[2];
@@ -284,6 +285,12 @@ typedef struct OVERLAY_PrivateData {
DRWShadingGroup *pointcloud_dots_grp;
DRWShadingGroup *sculpt_mask_grp;
DRWShadingGroup *sculpt_curves_selection_grp;
+ DRWShadingGroup *viewer_attribute_curve_grp;
+ DRWShadingGroup *viewer_attribute_curves_grp;
+ DRWShadingGroup *viewer_attribute_mesh_grp;
+ DRWShadingGroup *viewer_attribute_pointcloud_grp;
+ DRWShadingGroup *viewer_attribute_instance_grp;
+ DRWShadingGroup *viewer_attribute_instance_pointcloud_grp;
DRWShadingGroup *volume_selection_surface_grp;
DRWShadingGroup *wires_grp[2][2]; /* With and without coloring. */
DRWShadingGroup *wires_all_grp[2][2]; /* With and without coloring. */
@@ -678,6 +685,10 @@ void OVERLAY_sculpt_curves_cache_init(OVERLAY_Data *vedata);
void OVERLAY_sculpt_curves_cache_populate(OVERLAY_Data *vedata, Object *ob);
void OVERLAY_sculpt_curves_draw(OVERLAY_Data *vedata);
+void OVERLAY_viewer_attribute_cache_init(OVERLAY_Data *vedata);
+void OVERLAY_viewer_attribute_cache_populate(OVERLAY_Data *vedata, Object *object);
+void OVERLAY_viewer_attribute_draw(OVERLAY_Data *vedata);
+
void OVERLAY_wireframe_init(OVERLAY_Data *vedata);
void OVERLAY_wireframe_cache_init(OVERLAY_Data *vedata);
void OVERLAY_wireframe_cache_populate(OVERLAY_Data *vedata,
@@ -745,6 +756,7 @@ GPUShader *OVERLAY_shader_image(void);
GPUShader *OVERLAY_shader_motion_path_line(void);
GPUShader *OVERLAY_shader_motion_path_vert(void);
GPUShader *OVERLAY_shader_uniform_color(void);
+GPUShader *OVERLAY_shader_uniform_color_pointcloud(void);
GPUShader *OVERLAY_shader_outline_prepass(bool use_wire);
GPUShader *OVERLAY_shader_outline_prepass_curves(void);
GPUShader *OVERLAY_shader_outline_prepass_gpencil(void);
@@ -761,6 +773,10 @@ GPUShader *OVERLAY_shader_particle_dot(void);
GPUShader *OVERLAY_shader_particle_shape(void);
GPUShader *OVERLAY_shader_sculpt_mask(void);
GPUShader *OVERLAY_shader_sculpt_curves_selection(void);
+GPUShader *OVERLAY_shader_viewer_attribute_curve(void);
+GPUShader *OVERLAY_shader_viewer_attribute_curves(void);
+GPUShader *OVERLAY_shader_viewer_attribute_mesh(void);
+GPUShader *OVERLAY_shader_viewer_attribute_pointcloud(void);
GPUShader *OVERLAY_shader_volume_velocity(bool use_needle, bool use_mac);
GPUShader *OVERLAY_shader_volume_gridlines(bool color_with_flags, bool color_range);
GPUShader *OVERLAY_shader_wireframe(bool custom_bias);
diff --git a/source/blender/draw/engines/overlay/overlay_shader.cc b/source/blender/draw/engines/overlay/overlay_shader.cc
index b0a6926a57f..b7e5e8c56b7 100644
--- a/source/blender/draw/engines/overlay/overlay_shader.cc
+++ b/source/blender/draw/engines/overlay/overlay_shader.cc
@@ -93,6 +93,11 @@ typedef struct OVERLAY_Shaders {
GPUShader *sculpt_mask;
GPUShader *sculpt_curves_selection;
GPUShader *uniform_color;
+ GPUShader *uniform_color_pointcloud;
+ GPUShader *viewer_attribute_mesh;
+ GPUShader *viewer_attribute_pointcloud;
+ GPUShader *viewer_attribute_curve;
+ GPUShader *viewer_attribute_curves;
GPUShader *volume_velocity_needle_sh;
GPUShader *volume_velocity_mac_sh;
GPUShader *volume_velocity_sh;
@@ -818,6 +823,55 @@ GPUShader *OVERLAY_shader_sculpt_curves_selection(void)
return sh_data->sculpt_curves_selection;
}
+GPUShader *OVERLAY_shader_viewer_attribute_mesh(void)
+{
+ const DRWContextState *draw_ctx = DRW_context_state_get();
+ OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg];
+ if (!sh_data->viewer_attribute_mesh) {
+ sh_data->viewer_attribute_mesh = GPU_shader_create_from_info_name(
+ draw_ctx->sh_cfg == GPU_SHADER_CFG_CLIPPED ? "overlay_viewer_attribute_mesh_clipped" :
+ "overlay_viewer_attribute_mesh");
+ }
+ return sh_data->viewer_attribute_mesh;
+}
+
+GPUShader *OVERLAY_shader_viewer_attribute_pointcloud(void)
+{
+ const DRWContextState *draw_ctx = DRW_context_state_get();
+ OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg];
+ if (!sh_data->viewer_attribute_pointcloud) {
+ sh_data->viewer_attribute_pointcloud = GPU_shader_create_from_info_name(
+ draw_ctx->sh_cfg == GPU_SHADER_CFG_CLIPPED ?
+ "overlay_viewer_attribute_pointcloud_clipped" :
+ "overlay_viewer_attribute_pointcloud");
+ }
+ return sh_data->viewer_attribute_pointcloud;
+}
+
+GPUShader *OVERLAY_shader_viewer_attribute_curve(void)
+{
+ const DRWContextState *draw_ctx = DRW_context_state_get();
+ OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg];
+ if (!sh_data->viewer_attribute_curve) {
+ sh_data->viewer_attribute_curve = GPU_shader_create_from_info_name(
+ draw_ctx->sh_cfg == GPU_SHADER_CFG_CLIPPED ? "overlay_viewer_attribute_curve_clipped" :
+ "overlay_viewer_attribute_curve");
+ }
+ return sh_data->viewer_attribute_curve;
+}
+
+GPUShader *OVERLAY_shader_viewer_attribute_curves(void)
+{
+ const DRWContextState *draw_ctx = DRW_context_state_get();
+ OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg];
+ if (!sh_data->viewer_attribute_curves) {
+ sh_data->viewer_attribute_curves = GPU_shader_create_from_info_name(
+ draw_ctx->sh_cfg == GPU_SHADER_CFG_CLIPPED ? "overlay_viewer_attribute_curves_clipped" :
+ "overlay_viewer_attribute_curves");
+ }
+ return sh_data->viewer_attribute_curves;
+}
+
struct GPUShader *OVERLAY_shader_uniform_color(void)
{
const DRWContextState *draw_ctx = DRW_context_state_get();
@@ -829,6 +883,18 @@ struct GPUShader *OVERLAY_shader_uniform_color(void)
return sh_data->uniform_color;
}
+struct GPUShader *OVERLAY_shader_uniform_color_pointcloud()
+{
+ const DRWContextState *draw_ctx = DRW_context_state_get();
+ OVERLAY_Shaders *sh_data = &e_data.sh_data[draw_ctx->sh_cfg];
+ if (!sh_data->uniform_color_pointcloud) {
+ sh_data->uniform_color_pointcloud = GPU_shader_create_from_info_name(
+ draw_ctx->sh_cfg ? "overlay_uniform_color_pointcloud_clipped" :
+ "overlay_uniform_color_pointcloud");
+ }
+ return sh_data->uniform_color_pointcloud;
+}
+
struct GPUShader *OVERLAY_shader_volume_velocity(bool use_needle, bool use_mac)
{
OVERLAY_Shaders *sh_data = &e_data.sh_data[0];
diff --git a/source/blender/draw/engines/overlay/overlay_viewer_attribute.cc b/source/blender/draw/engines/overlay/overlay_viewer_attribute.cc
new file mode 100644
index 00000000000..7e1949c5261
--- /dev/null
+++ b/source/blender/draw/engines/overlay/overlay_viewer_attribute.cc
@@ -0,0 +1,181 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+
+/** \file
+ * \ingroup draw_engine
+ */
+
+#include "DRW_render.h"
+
+#include "DNA_mesh_types.h"
+#include "DNA_pointcloud_types.h"
+
+#include "BLI_math_vector.hh"
+#include "BLI_span.hh"
+
+#include "GPU_batch.h"
+
+#include "BKE_attribute.hh"
+#include "BKE_curves.hh"
+#include "BKE_duplilist.h"
+#include "BKE_geometry_set.hh"
+
+#include "draw_cache_extract.hh"
+#include "draw_cache_impl.h"
+#include "overlay_private.hh"
+
+void OVERLAY_viewer_attribute_cache_init(OVERLAY_Data *vedata)
+{
+ OVERLAY_PassList *psl = vedata->psl;
+ OVERLAY_PrivateData *pd = vedata->stl->pd;
+
+ const DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_DEPTH_LESS_EQUAL |
+ DRW_STATE_BLEND_ALPHA;
+ DRW_PASS_CREATE(psl->attribute_ps, state | pd->clipping_state);
+
+ GPUShader *mesh_sh = OVERLAY_shader_viewer_attribute_mesh();
+ GPUShader *pointcloud_sh = OVERLAY_shader_viewer_attribute_pointcloud();
+ GPUShader *curve_sh = OVERLAY_shader_viewer_attribute_curve();
+ GPUShader *curves_sh = OVERLAY_shader_viewer_attribute_curves();
+ GPUShader *uniform_sh = OVERLAY_shader_uniform_color();
+ GPUShader *uniform_pointcloud_sh = OVERLAY_shader_uniform_color_pointcloud();
+ pd->viewer_attribute_mesh_grp = DRW_shgroup_create(mesh_sh, psl->attribute_ps);
+ pd->viewer_attribute_pointcloud_grp = DRW_shgroup_create(pointcloud_sh, psl->attribute_ps);
+ pd->viewer_attribute_curve_grp = DRW_shgroup_create(curve_sh, psl->attribute_ps);
+ pd->viewer_attribute_curves_grp = DRW_shgroup_create(curves_sh, psl->attribute_ps);
+ pd->viewer_attribute_instance_grp = DRW_shgroup_create(uniform_sh, psl->attribute_ps);
+ pd->viewer_attribute_instance_pointcloud_grp = DRW_shgroup_create(uniform_pointcloud_sh,
+ psl->attribute_ps);
+}
+
+static void populate_cache_for_instance(Object &object,
+ OVERLAY_PrivateData &pd,
+ const DupliObject &dupli_object,
+ const float opacity)
+{
+ using namespace blender;
+ using namespace blender::bke;
+
+ const GeometrySet &base_geometry = *dupli_object.preview_base_geometry;
+ const InstancesComponent &instances =
+ *base_geometry.get_component_for_read<InstancesComponent>();
+ const AttributeAccessor instance_attributes = *instances.attributes();
+ const VArray attribute = instance_attributes.lookup<ColorGeometry4f>(".viewer");
+ if (!attribute) {
+ return;
+ }
+ ColorGeometry4f color = attribute.get(dupli_object.preview_instance_index);
+ color.a *= opacity;
+ switch (object.type) {
+ case OB_MESH: {
+ {
+ DRWShadingGroup *sub_grp = DRW_shgroup_create_sub(pd.viewer_attribute_instance_grp);
+ DRW_shgroup_uniform_vec4_copy(sub_grp, "ucolor", color);
+ GPUBatch *batch = DRW_cache_mesh_surface_get(&object);
+ DRW_shgroup_call(sub_grp, batch, &object);
+ }
+ if (GPUBatch *batch = DRW_cache_mesh_loose_edges_get(&object)) {
+ DRWShadingGroup *sub_grp = DRW_shgroup_create_sub(pd.viewer_attribute_instance_grp);
+ DRW_shgroup_uniform_vec4_copy(sub_grp, "ucolor", color);
+ DRW_shgroup_call(sub_grp, batch, &object);
+ }
+ break;
+ }
+ case OB_POINTCLOUD: {
+ DRWShadingGroup *sub_grp = DRW_shgroup_create_sub(
+ pd.viewer_attribute_instance_pointcloud_grp);
+ DRW_shgroup_uniform_vec4_copy(sub_grp, "ucolor", color);
+ GPUBatch *batch = DRW_cache_pointcloud_surface_get(&object);
+ DRW_shgroup_call_instance_range(sub_grp, &object, batch, 0, 0);
+ break;
+ }
+ case OB_CURVES_LEGACY: {
+ DRWShadingGroup *sub_grp = DRW_shgroup_create_sub(pd.viewer_attribute_instance_grp);
+ DRW_shgroup_uniform_vec4_copy(sub_grp, "ucolor", color);
+ GPUBatch *batch = DRW_cache_curve_edge_wire_get(&object);
+ DRW_shgroup_call(sub_grp, batch, &object);
+ break;
+ }
+ case OB_CURVES: {
+ /* Not supported yet because instances of this type are currently drawn as legacy curves.
+ */
+ break;
+ }
+ }
+}
+
+static void populate_cache_for_geometry(Object &object,
+ OVERLAY_PrivateData &pd,
+ const float opacity)
+{
+ using namespace blender;
+ using namespace blender::bke;
+
+ switch (object.type) {
+ case OB_MESH: {
+ Mesh *mesh = static_cast<Mesh *>(object.data);
+ if (mesh->attributes().contains(".viewer")) {
+ GPUBatch *batch = DRW_cache_mesh_surface_viewer_attribute_get(&object);
+ DRW_shgroup_uniform_float_copy(pd.viewer_attribute_mesh_grp, "opacity", opacity);
+ DRW_shgroup_call(pd.viewer_attribute_mesh_grp, batch, &object);
+ }
+ break;
+ }
+ case OB_POINTCLOUD: {
+ PointCloud *pointcloud = static_cast<PointCloud *>(object.data);
+ if (pointcloud->attributes().contains(".viewer")) {
+ GPUBatch *batch = DRW_cache_pointcloud_surface_viewer_attribute_get(&object);
+ DRW_shgroup_uniform_float_copy(pd.viewer_attribute_pointcloud_grp, "opacity", opacity);
+ DRW_shgroup_call_instance_range(pd.viewer_attribute_pointcloud_grp, &object, batch, 0, 0);
+ }
+ break;
+ }
+ case OB_CURVES_LEGACY: {
+ Curve *curve = static_cast<Curve *>(object.data);
+ const bke::CurvesGeometry &curves = bke::CurvesGeometry::wrap(curve->curve_eval->geometry);
+ if (curves.attributes().contains(".viewer")) {
+ GPUBatch *batch = DRW_cache_curve_edge_wire_viewer_attribute_get(&object);
+ DRW_shgroup_uniform_float_copy(pd.viewer_attribute_curve_grp, "opacity", opacity);
+ DRW_shgroup_call(pd.viewer_attribute_curve_grp, batch, &object);
+ }
+ break;
+ }
+ case OB_CURVES: {
+ Curves *curves_id = static_cast<Curves *>(object.data);
+ const bke::CurvesGeometry &curves = bke::CurvesGeometry::wrap(curves_id->geometry);
+ if (curves.attributes().contains(".viewer")) {
+ bool is_point_domain;
+ GPUTexture **texture = DRW_curves_texture_for_evaluated_attribute(
+ curves_id, ".viewer", &is_point_domain);
+ DRWShadingGroup *grp = DRW_shgroup_curves_create_sub(
+ &object, pd.viewer_attribute_curves_grp, nullptr);
+ DRW_shgroup_uniform_float_copy(pd.viewer_attribute_curves_grp, "opacity", opacity);
+ DRW_shgroup_uniform_bool_copy(grp, "is_point_domain", is_point_domain);
+ DRW_shgroup_uniform_texture(grp, "color_tx", *texture);
+ }
+ break;
+ }
+ }
+}
+
+void OVERLAY_viewer_attribute_cache_populate(OVERLAY_Data *vedata, Object *object)
+{
+ OVERLAY_PrivateData *pd = vedata->stl->pd;
+ const float opacity = vedata->stl->pd->overlay.viewer_attribute_opacity;
+ DupliObject *dupli_object = DRW_object_get_dupli(object);
+
+ if (dupli_object->preview_instance_index >= 0) {
+ const InstancesComponent &instances =
+ *dupli_object->preview_base_geometry->get_component_for_read<InstancesComponent>();
+ if (instances.attributes()->contains(".viewer")) {
+ populate_cache_for_instance(*object, *pd, *dupli_object, opacity);
+ return;
+ }
+ }
+ populate_cache_for_geometry(*object, *pd, opacity);
+}
+
+void OVERLAY_viewer_attribute_draw(OVERLAY_Data *vedata)
+{
+ OVERLAY_PassList *psl = vedata->psl;
+ DRW_draw_pass(psl->attribute_ps);
+}
diff --git a/source/blender/draw/engines/overlay/shaders/infos/overlay_edit_mode_info.hh b/source/blender/draw/engines/overlay/shaders/infos/overlay_edit_mode_info.hh
index 8c9c943393f..40b7249a997 100644
--- a/source/blender/draw/engines/overlay/shaders/infos/overlay_edit_mode_info.hh
+++ b/source/blender/draw/engines/overlay/shaders/infos/overlay_edit_mode_info.hh
@@ -587,8 +587,20 @@ GPU_SHADER_CREATE_INFO(overlay_uniform_color)
.fragment_source("overlay_uniform_color_frag.glsl")
.additional_info("draw_mesh");
+GPU_SHADER_CREATE_INFO(overlay_uniform_color_pointcloud)
+ .do_static_compilation(true)
+ .push_constant(Type::VEC4, "ucolor")
+ .fragment_out(0, Type::VEC4, "fragColor")
+ .vertex_source("overlay_pointcloud_only_vert.glsl")
+ .fragment_source("overlay_uniform_color_frag.glsl")
+ .additional_info("draw_pointcloud");
+
GPU_SHADER_CREATE_INFO(overlay_uniform_color_clipped)
.do_static_compilation(true)
.additional_info("overlay_depth_only", "drw_clipped");
+GPU_SHADER_CREATE_INFO(overlay_uniform_color_pointcloud_clipped)
+ .do_static_compilation(true)
+ .additional_info("overlay_uniform_color_pointcloud", "drw_clipped");
+
/** \} */
diff --git a/source/blender/draw/engines/overlay/shaders/infos/overlay_viewer_attribute_info.hh b/source/blender/draw/engines/overlay/shaders/infos/overlay_viewer_attribute_info.hh
new file mode 100644
index 00000000000..aca80992622
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/infos/overlay_viewer_attribute_info.hh
@@ -0,0 +1,62 @@
+/* SPDX-License-Identifier: GPL-2.0-or-later */
+
+#include "gpu_shader_create_info.hh"
+
+GPU_SHADER_INTERFACE_INFO(overlay_viewer_attribute_iface, "").smooth(Type::VEC4, "finalColor");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_common).push_constant(Type::FLOAT, "opacity");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_mesh)
+ .do_static_compilation(true)
+ .vertex_source("overlay_viewer_attribute_mesh_vert.glsl")
+ .fragment_source("overlay_viewer_attribute_frag.glsl")
+ .fragment_out(0, Type::VEC4, "out_color")
+ .vertex_in(0, Type::VEC3, "pos")
+ .vertex_in(1, Type::VEC4, "attribute_value")
+ .vertex_out(overlay_viewer_attribute_iface)
+ .additional_info("overlay_viewer_attribute_common", "draw_mesh");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_mesh_clipped)
+ .do_static_compilation(true)
+ .additional_info("overlay_viewer_attribute_mesh", "drw_clipped");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_pointcloud)
+ .do_static_compilation(true)
+ .vertex_source("overlay_viewer_attribute_pointcloud_vert.glsl")
+ .fragment_source("overlay_viewer_attribute_frag.glsl")
+ .fragment_out(0, Type::VEC4, "out_color")
+ .vertex_in(3, Type::VEC4, "attribute_value")
+ .vertex_out(overlay_viewer_attribute_iface)
+ .additional_info("overlay_viewer_attribute_common", "draw_pointcloud");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_pointcloud_clipped)
+ .do_static_compilation(true)
+ .additional_info("overlay_viewer_attribute_pointcloud", "drw_clipped");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_curve)
+ .do_static_compilation(true)
+ .vertex_source("overlay_viewer_attribute_curve_vert.glsl")
+ .fragment_source("overlay_viewer_attribute_frag.glsl")
+ .fragment_out(0, Type::VEC4, "out_color")
+ .vertex_in(0, Type::VEC3, "pos")
+ .vertex_in(1, Type::VEC4, "attribute_value")
+ .vertex_out(overlay_viewer_attribute_iface)
+ .additional_info("overlay_viewer_attribute_common", "draw_modelmat", "draw_resource_id");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_curve_clipped)
+ .do_static_compilation(true)
+ .additional_info("overlay_viewer_attribute_curve", "drw_clipped");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_curves)
+ .do_static_compilation(true)
+ .vertex_source("overlay_viewer_attribute_curves_vert.glsl")
+ .fragment_source("overlay_viewer_attribute_frag.glsl")
+ .fragment_out(0, Type::VEC4, "out_color")
+ .sampler(0, ImageType::FLOAT_BUFFER, "color_tx")
+ .push_constant(Type::BOOL, "is_point_domain")
+ .vertex_out(overlay_viewer_attribute_iface)
+ .additional_info("overlay_viewer_attribute_common", "draw_hair");
+
+GPU_SHADER_CREATE_INFO(overlay_viewer_attribute_curves_clipped)
+ .do_static_compilation(true)
+ .additional_info("overlay_viewer_attribute_curves", "drw_clipped");
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_pointcloud_only_vert.glsl b/source/blender/draw/engines/overlay/shaders/overlay_pointcloud_only_vert.glsl
new file mode 100644
index 00000000000..8a7e81028d3
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_pointcloud_only_vert.glsl
@@ -0,0 +1,9 @@
+#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl)
+#pragma BLENDER_REQUIRE(common_view_lib.glsl)
+#pragma BLENDER_REQUIRE(common_pointcloud_lib.glsl)
+
+void main()
+{
+ vec3 world_pos = pointcloud_get_pos();
+ gl_Position = point_world_to_ndc(world_pos);
+}
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curve_vert.glsl b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curve_vert.glsl
new file mode 100644
index 00000000000..7c2c386b2f5
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curve_vert.glsl
@@ -0,0 +1,9 @@
+#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl)
+#pragma BLENDER_REQUIRE(common_view_lib.glsl)
+
+void main()
+{
+ vec3 world_pos = point_object_to_world(pos);
+ gl_Position = point_world_to_ndc(world_pos);
+ finalColor = attribute_value;
+}
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curves_vert.glsl b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curves_vert.glsl
new file mode 100644
index 00000000000..23d313e036f
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_curves_vert.glsl
@@ -0,0 +1,28 @@
+#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl)
+#pragma BLENDER_REQUIRE(common_view_lib.glsl)
+#pragma BLENDER_REQUIRE(common_hair_lib.glsl)
+
+void main()
+{
+ bool is_persp = (ProjectionMatrix[3][3] == 0.0);
+ float time, thick_time, thickness;
+ vec3 world_pos, tan, binor;
+ hair_get_pos_tan_binor_time(is_persp,
+ ModelMatrixInverse,
+ ViewMatrixInverse[3].xyz,
+ ViewMatrixInverse[2].xyz,
+ world_pos,
+ tan,
+ binor,
+ time,
+ thickness,
+ thick_time);
+ gl_Position = point_world_to_ndc(world_pos);
+
+ if (is_point_domain) {
+ finalColor = texelFetch(color_tx, hair_get_base_id());
+ }
+ else {
+ finalColor = texelFetch(color_tx, hair_get_strand_id());
+ }
+}
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_frag.glsl b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_frag.glsl
new file mode 100644
index 00000000000..6176a6b96ba
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_frag.glsl
@@ -0,0 +1,6 @@
+
+void main()
+{
+ out_color = finalColor;
+ out_color.a *= opacity;
+}
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_mesh_vert.glsl b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_mesh_vert.glsl
new file mode 100644
index 00000000000..7c2c386b2f5
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_mesh_vert.glsl
@@ -0,0 +1,9 @@
+#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl)
+#pragma BLENDER_REQUIRE(common_view_lib.glsl)
+
+void main()
+{
+ vec3 world_pos = point_object_to_world(pos);
+ gl_Position = point_world_to_ndc(world_pos);
+ finalColor = attribute_value;
+}
diff --git a/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_pointcloud_vert.glsl b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_pointcloud_vert.glsl
new file mode 100644
index 00000000000..e706e8f9033
--- /dev/null
+++ b/source/blender/draw/engines/overlay/shaders/overlay_viewer_attribute_pointcloud_vert.glsl
@@ -0,0 +1,10 @@
+#pragma BLENDER_REQUIRE(common_view_clipping_lib.glsl)
+#pragma BLENDER_REQUIRE(common_view_lib.glsl)
+#pragma BLENDER_REQUIRE(common_pointcloud_lib.glsl)
+
+void main()
+{
+ vec3 world_pos = pointcloud_get_pos();
+ gl_Position = point_world_to_ndc(world_pos);
+ finalColor = attribute_value;
+}
diff --git a/source/blender/draw/intern/draw_cache.c b/source/blender/draw/intern/draw_cache.c
index 6537490c06c..6da22039c2f 100644
--- a/source/blender/draw/intern/draw_cache.c
+++ b/source/blender/draw/intern/draw_cache.c
@@ -2889,6 +2889,12 @@ GPUBatch *DRW_cache_mesh_surface_mesh_analysis_get(Object *ob)
return DRW_mesh_batch_cache_get_edit_mesh_analysis(ob->data);
}
+GPUBatch *DRW_cache_mesh_surface_viewer_attribute_get(Object *ob)
+{
+ BLI_assert(ob->type == OB_MESH);
+ return DRW_mesh_batch_cache_get_surface_viewer_attribute(ob->data);
+}
+
/** \} */
/* -------------------------------------------------------------------- */
@@ -2902,6 +2908,13 @@ GPUBatch *DRW_cache_curve_edge_wire_get(Object *ob)
return DRW_curve_batch_cache_get_wire_edge(cu);
}
+GPUBatch *DRW_cache_curve_edge_wire_viewer_attribute_get(Object *ob)
+{
+ BLI_assert(ob->type == OB_CURVES_LEGACY);
+ struct Curve *cu = ob->data;
+ return DRW_curve_batch_cache_get_wire_edge_viewer_attribute(cu);
+}
+
GPUBatch *DRW_cache_curve_edge_normal_get(Object *ob)
{
BLI_assert(ob->type == OB_CURVES_LEGACY);
@@ -3005,6 +3018,12 @@ GPUBatch *DRW_cache_pointcloud_surface_get(Object *object)
return DRW_pointcloud_batch_cache_get_surface(object);
}
+GPUBatch *DRW_cache_pointcloud_surface_viewer_attribute_get(Object *object)
+{
+ BLI_assert(object->type == OB_POINTCLOUD);
+ return DRW_pointcloud_batch_cache_get_surface_viewer_attribute(object);
+}
+
/** \} */
/* -------------------------------------------------------------------- */
diff --git a/source/blender/draw/intern/draw_cache.h b/source/blender/draw/intern/draw_cache.h
index 4e8788ada08..058f28f094d 100644
--- a/source/blender/draw/intern/draw_cache.h
+++ b/source/blender/draw/intern/draw_cache.h
@@ -170,10 +170,12 @@ struct GPUBatch *DRW_cache_mesh_surface_sculptcolors_get(struct Object *ob);
struct GPUBatch *DRW_cache_mesh_surface_weights_get(struct Object *ob);
struct GPUBatch *DRW_cache_mesh_surface_mesh_analysis_get(struct Object *ob);
struct GPUBatch *DRW_cache_mesh_face_wireframe_get(struct Object *ob);
+struct GPUBatch *DRW_cache_mesh_surface_viewer_attribute_get(struct Object *ob);
/* Curve */
struct GPUBatch *DRW_cache_curve_edge_wire_get(struct Object *ob);
+struct GPUBatch *DRW_cache_curve_edge_wire_viewer_attribute_get(struct Object *ob);
/* edit-mode */
@@ -226,6 +228,7 @@ struct GPUBatch *DRW_cache_curves_edge_detection_get(struct Object *ob, bool *r_
struct GPUBatch *DRW_cache_pointcloud_get_dots(struct Object *obj);
struct GPUBatch *DRW_cache_pointcloud_surface_get(struct Object *obj);
+struct GPUBatch *DRW_cache_pointcloud_surface_viewer_attribute_get(struct Object *obj);
/* Volume */
diff --git a/source/blender/draw/intern/draw_cache_extract.hh b/source/blender/draw/intern/draw_cache_extract.hh
index 203da22406c..6f4a652ce24 100644
--- a/source/blender/draw/intern/draw_cache_extract.hh
+++ b/source/blender/draw/intern/draw_cache_extract.hh
@@ -130,6 +130,7 @@ struct MeshBufferList {
GPUVertBuf *poly_idx;
GPUVertBuf *fdot_idx;
GPUVertBuf *attr[GPU_MAX_ATTR];
+ GPUVertBuf *attr_viewer;
} vbo;
/* Index Buffers:
* Only need to be updated when topology changes. */
@@ -191,6 +192,7 @@ struct MeshBatchList {
/* Same as wire_loops but only has uvs. */
GPUBatch *wire_loops_uvs;
GPUBatch *sculpt_overlays;
+ GPUBatch *surface_viewer_attribute;
};
#define MBC_BATCH_LEN (sizeof(MeshBatchList) / sizeof(void *))
@@ -228,6 +230,7 @@ enum DRWBatchFlag {
MBC_WIRE_LOOPS = (1u << MBC_BATCH_INDEX(wire_loops)),
MBC_WIRE_LOOPS_UVS = (1u << MBC_BATCH_INDEX(wire_loops_uvs)),
MBC_SCULPT_OVERLAYS = (1u << MBC_BATCH_INDEX(sculpt_overlays)),
+ MBC_VIEWER_ATTRIBUTE_OVERLAY = (1u << MBC_BATCH_INDEX(surface_viewer_attribute)),
MBC_SURFACE_PER_MAT = (1u << MBC_BATCH_LEN),
};
ENUM_OPERATORS(DRWBatchFlag, MBC_SURFACE_PER_MAT);
diff --git a/source/blender/draw/intern/draw_cache_extract_mesh.cc b/source/blender/draw/intern/draw_cache_extract_mesh.cc
index fd00059bac6..d3170f4c776 100644
--- a/source/blender/draw/intern/draw_cache_extract_mesh.cc
+++ b/source/blender/draw/intern/draw_cache_extract_mesh.cc
@@ -640,6 +640,7 @@ void mesh_buffer_cache_create_requested(struct TaskGraph *task_graph,
for (int i = 0; i < GPU_MAX_ATTR; i++) {
EXTRACT_ADD_REQUESTED(vbo, attr[i]);
}
+ EXTRACT_ADD_REQUESTED(vbo, attr_viewer);
EXTRACT_ADD_REQUESTED(ibo, tris);
if (DRW_ibo_requested(mbuflist->ibo.lines_loose)) {
diff --git a/source/blender/draw/intern/draw_cache_impl.h b/source/blender/draw/intern/draw_cache_impl.h
index 7f7d0a7613f..89432b0da83 100644
--- a/source/blender/draw/intern/draw_cache_impl.h
+++ b/source/blender/draw/intern/draw_cache_impl.h
@@ -100,6 +100,7 @@ void DRW_curve_batch_cache_create_requested(struct Object *ob, const struct Scen
int DRW_curve_material_count_get(struct Curve *cu);
struct GPUBatch *DRW_curve_batch_cache_get_wire_edge(struct Curve *cu);
+struct GPUBatch *DRW_curve_batch_cache_get_wire_edge_viewer_attribute(struct Curve *cu);
struct GPUBatch *DRW_curve_batch_cache_get_normal_edge(struct Curve *cu);
struct GPUBatch *DRW_curve_batch_cache_get_edit_edges(struct Curve *cu);
struct GPUBatch *DRW_curve_batch_cache_get_edit_verts(struct Curve *cu);
@@ -148,6 +149,7 @@ int DRW_pointcloud_material_count_get(struct PointCloud *pointcloud);
struct GPUBatch *DRW_pointcloud_batch_cache_get_dots(struct Object *ob);
struct GPUBatch *DRW_pointcloud_batch_cache_get_surface(struct Object *ob);
+struct GPUBatch *DRW_pointcloud_batch_cache_get_surface_viewer_attribute(struct Object *ob);
struct GPUBatch **DRW_cache_pointcloud_surface_shaded_get(struct Object *ob,
struct GPUMaterial **gpumat_array,
uint gpumat_array_len);
@@ -198,6 +200,7 @@ struct GPUBatch *DRW_mesh_batch_cache_get_surface_vertpaint(struct Object *objec
struct GPUBatch *DRW_mesh_batch_cache_get_surface_sculpt(struct Object *object, struct Mesh *me);
struct GPUBatch *DRW_mesh_batch_cache_get_surface_weights(struct Mesh *me);
struct GPUBatch *DRW_mesh_batch_cache_get_sculpt_overlays(struct Mesh *me);
+struct GPUBatch *DRW_mesh_batch_cache_get_surface_viewer_attribute(struct Mesh *me);
/** \} */
diff --git a/source/blender/draw/intern/draw_cache_impl_curve.cc b/source/blender/draw/intern/draw_cache_impl_curve.cc
index 695c348d8e2..6188b1e0544 100644
--- a/source/blender/draw/intern/draw_cache_impl_curve.cc
+++ b/source/blender/draw/intern/draw_cache_impl_curve.cc
@@ -10,6 +10,7 @@
#include "MEM_guardedalloc.h"
#include "BLI_array.hh"
+#include "BLI_color.hh"
#include "BLI_listbase.h"
#include "BLI_math_vec_types.hh"
#include "BLI_math_vector.h"
@@ -38,6 +39,7 @@
#include "draw_cache_impl.h" /* own include */
using blender::Array;
+using blender::ColorGeometry4f;
using blender::float3;
using blender::IndexRange;
using blender::Span;
@@ -296,6 +298,7 @@ static int curve_render_data_normal_len_get(const CurveRenderData *rdata)
struct CurveBatchCache {
struct {
GPUVertBuf *curves_pos;
+ GPUVertBuf *attr_viewer;
} ordered;
struct {
@@ -314,6 +317,7 @@ struct CurveBatchCache {
struct {
GPUBatch *curves;
+ GPUBatch *curves_viewer_attribute;
/* control handles and vertices */
GPUBatch *edit_edges;
GPUBatch *edit_verts;
@@ -474,6 +478,31 @@ static void curve_create_curves_pos(CurveRenderData *rdata, GPUVertBuf *vbo_curv
GPU_vertbuf_attr_fill(vbo_curves_pos, attr_id.pos, positions.data());
}
+static void curve_create_attribute(CurveRenderData *rdata, GPUVertBuf *vbo_attr)
+{
+ if (rdata->curve_eval == nullptr) {
+ return;
+ }
+
+ static GPUVertFormat format = {0};
+ if (format.attr_len == 0) {
+ GPU_vertformat_attr_add(&format, "attribute_value", GPU_COMP_F32, 4, GPU_FETCH_FLOAT);
+ }
+
+ const int vert_len = curve_render_data_wire_verts_len_get(rdata);
+ GPU_vertbuf_init_with_format(vbo_attr, &format);
+ GPU_vertbuf_data_alloc(vbo_attr, vert_len);
+
+ const blender::bke::CurvesGeometry &curves = blender::bke::CurvesGeometry::wrap(
+ rdata->curve_eval->geometry);
+ curves.ensure_can_interpolate_to_evaluated();
+ const blender::VArraySpan<ColorGeometry4f> colors = curves.attributes().lookup<ColorGeometry4f>(
+ ".viewer", ATTR_DOMAIN_POINT);
+ ColorGeometry4f *vbo_data = static_cast<ColorGeometry4f *>(GPU_vertbuf_get_data(vbo_attr));
+ curves.interpolate_to_evaluated(colors,
+ blender::MutableSpan<ColorGeometry4f>{vbo_data, vert_len});
+}
+
static void curve_create_curves_lines(CurveRenderData *rdata, GPUIndexBuf *ibo_curve_lines)
{
if (rdata->curve_eval == nullptr) {
@@ -769,6 +798,12 @@ GPUBatch *DRW_curve_batch_cache_get_wire_edge(Curve *cu)
return DRW_batch_request(&cache->batch.curves);
}
+GPUBatch *DRW_curve_batch_cache_get_wire_edge_viewer_attribute(Curve *cu)
+{
+ CurveBatchCache *cache = curve_batch_cache_get(cu);
+ return DRW_batch_request(&cache->batch.curves_viewer_attribute);
+}
+
GPUBatch *DRW_curve_batch_cache_get_normal_edge(Curve *cu)
{
CurveBatchCache *cache = curve_batch_cache_get(cu);
@@ -810,6 +845,11 @@ void DRW_curve_batch_cache_create_requested(Object *ob, const struct Scene *scen
DRW_ibo_request(cache->batch.curves, &cache->ibo.curves_lines);
DRW_vbo_request(cache->batch.curves, &cache->ordered.curves_pos);
}
+ if (DRW_batch_requested(cache->batch.curves_viewer_attribute, GPU_PRIM_LINE_STRIP)) {
+ DRW_ibo_request(cache->batch.curves_viewer_attribute, &cache->ibo.curves_lines);
+ DRW_vbo_request(cache->batch.curves_viewer_attribute, &cache->ordered.curves_pos);
+ DRW_vbo_request(cache->batch.curves_viewer_attribute, &cache->ordered.attr_viewer);
+ }
/* Edit mode */
if (DRW_batch_requested(cache->batch.edit_edges, GPU_PRIM_LINES)) {
@@ -833,6 +873,8 @@ void DRW_curve_batch_cache_create_requested(Object *ob, const struct Scene *scen
/* Generate MeshRenderData flags */
int mr_flag = 0;
DRW_ADD_FLAG_FROM_VBO_REQUEST(mr_flag, cache->ordered.curves_pos, CU_DATATYPE_WIRE);
+ DRW_ADD_FLAG_FROM_VBO_REQUEST(
+ mr_flag, cache->ordered.attr_viewer, CU_DATATYPE_WIRE | CU_DATATYPE_OVERLAY);
DRW_ADD_FLAG_FROM_IBO_REQUEST(mr_flag, cache->ibo.curves_lines, CU_DATATYPE_WIRE);
DRW_ADD_FLAG_FROM_VBO_REQUEST(mr_flag, cache->edit.pos, CU_DATATYPE_OVERLAY);
@@ -851,6 +893,9 @@ void DRW_curve_batch_cache_create_requested(Object *ob, const struct Scene *scen
if (DRW_vbo_requested(cache->ordered.curves_pos)) {
curve_create_curves_pos(rdata, cache->ordered.curves_pos);
}
+ if (DRW_vbo_requested(cache->ordered.attr_viewer)) {
+ curve_create_attribute(rdata, cache->ordered.attr_viewer);
+ }
if (DRW_ibo_requested(cache->ibo.curves_lines)) {
curve_create_curves_lines(rdata, cache->ibo.curves_lines);
}
diff --git a/source/blender/draw/intern/draw_cache_impl_mesh.cc b/source/blender/draw/intern/draw_cache_impl_mesh.cc
index c22382b3e09..ed78cbbda39 100644
--- a/source/blender/draw/intern/draw_cache_impl_mesh.cc
+++ b/source/blender/draw/intern/draw_cache_impl_mesh.cc
@@ -104,7 +104,8 @@ static constexpr DRWBatchFlag batches_that_use_buffer(const int buffer_index)
MBC_EDIT_EDGES | MBC_EDIT_VNOR | MBC_EDIT_LNOR | MBC_EDIT_MESH_ANALYSIS |
MBC_EDIT_SELECTION_VERTS | MBC_EDIT_SELECTION_EDGES | MBC_EDIT_SELECTION_FACES |
MBC_ALL_VERTS | MBC_ALL_EDGES | MBC_LOOSE_EDGES | MBC_EDGE_DETECTION |
- MBC_WIRE_EDGES | MBC_WIRE_LOOPS | MBC_SCULPT_OVERLAYS | MBC_SURFACE_PER_MAT;
+ MBC_WIRE_EDGES | MBC_WIRE_LOOPS | MBC_SCULPT_OVERLAYS | MBC_VIEWER_ATTRIBUTE_OVERLAY |
+ MBC_SURFACE_PER_MAT;
case BUFFER_INDEX(vbo.lnor):
return MBC_SURFACE | MBC_EDIT_LNOR | MBC_WIRE_LOOPS | MBC_SURFACE_PER_MAT;
case BUFFER_INDEX(vbo.edge_fac):
@@ -166,9 +167,12 @@ static constexpr DRWBatchFlag batches_that_use_buffer(const int buffer_index)
case BUFFER_INDEX(vbo.attr[13]):
case BUFFER_INDEX(vbo.attr[14]):
return MBC_SURFACE | MBC_SURFACE_PER_MAT;
+ case BUFFER_INDEX(vbo.attr_viewer):
+ return MBC_VIEWER_ATTRIBUTE_OVERLAY;
case BUFFER_INDEX(ibo.tris):
return MBC_SURFACE | MBC_SURFACE_WEIGHTS | MBC_EDIT_TRIANGLES | MBC_EDIT_LNOR |
- MBC_EDIT_MESH_ANALYSIS | MBC_EDIT_SELECTION_FACES | MBC_SCULPT_OVERLAYS;
+ MBC_EDIT_MESH_ANALYSIS | MBC_EDIT_SELECTION_FACES | MBC_SCULPT_OVERLAYS |
+ MBC_VIEWER_ATTRIBUTE_OVERLAY;
case BUFFER_INDEX(ibo.lines):
return MBC_EDIT_EDGES | MBC_EDIT_SELECTION_EDGES | MBC_ALL_EDGES | MBC_WIRE_EDGES;
case BUFFER_INDEX(ibo.lines_loose):
@@ -1057,6 +1061,16 @@ GPUBatch *DRW_mesh_batch_cache_get_sculpt_overlays(Mesh *me)
return cache->batch.sculpt_overlays;
}
+GPUBatch *DRW_mesh_batch_cache_get_surface_viewer_attribute(Mesh *me)
+{
+ MeshBatchCache *cache = mesh_batch_cache_get(me);
+
+ mesh_batch_cache_add_request(cache, MBC_VIEWER_ATTRIBUTE_OVERLAY);
+ DRW_batch_request(&cache->batch.surface_viewer_attribute);
+
+ return cache->batch.surface_viewer_attribute;
+}
+
/** \} */
/* ---------------------------------------------------------------------- */
@@ -1802,6 +1816,14 @@ void DRW_mesh_batch_cache_create_requested(struct TaskGraph *task_graph,
DRW_vbo_request(cache->batch.edituv_fdots, &mbuflist->vbo.fdots_uv);
DRW_vbo_request(cache->batch.edituv_fdots, &mbuflist->vbo.fdots_edituv_data);
}
+ assert_deps_valid(
+ MBC_VIEWER_ATTRIBUTE_OVERLAY,
+ {BUFFER_INDEX(ibo.tris), BUFFER_INDEX(vbo.pos_nor), BUFFER_INDEX(vbo.attr_viewer)});
+ if (DRW_batch_requested(cache->batch.surface_viewer_attribute, GPU_PRIM_TRIS)) {
+ DRW_ibo_request(cache->batch.surface_viewer_attribute, &mbuflist->ibo.tris);
+ DRW_vbo_request(cache->batch.surface_viewer_attribute, &mbuflist->vbo.pos_nor);
+ DRW_vbo_request(cache->batch.surface_viewer_attribute, &mbuflist->vbo.attr_viewer);
+ }
#ifdef DEBUG
auto assert_final_deps_valid = [&](const int buffer_index) {
@@ -1833,6 +1855,7 @@ void DRW_mesh_batch_cache_create_requested(struct TaskGraph *task_graph,
for (const int i : IndexRange(GPU_MAX_ATTR)) {
assert_final_deps_valid(BUFFER_INDEX(vbo.attr[i]));
}
+ assert_final_deps_valid(BUFFER_INDEX(vbo.attr_viewer));
assert_final_deps_valid(BUFFER_INDEX(ibo.tris));
assert_final_deps_valid(BUFFER_INDEX(ibo.lines));
diff --git a/source/blender/draw/intern/draw_cache_impl_pointcloud.cc b/source/blender/draw/intern/draw_cache_impl_pointcloud.cc
index a43b23c8969..72be5b37652 100644
--- a/source/blender/draw/intern/draw_cache_impl_pointcloud.cc
+++ b/source/blender/draw/intern/draw_cache_impl_pointcloud.cc
@@ -32,11 +32,13 @@
struct PointCloudBatchCache {
GPUVertBuf *pos; /* Position and radius. */
GPUVertBuf *geom; /* Instanced geometry for each point in the cloud (small sphere). */
+ GPUVertBuf *attr_viewer;
GPUIndexBuf *geom_indices;
GPUBatch *dots;
GPUBatch *surface;
GPUBatch **surface_per_mat;
+ GPUBatch *surface_viewer_attribute;
/* settings to determine if cache is invalid */
bool is_dirty;
@@ -109,6 +111,7 @@ static void pointcloud_batch_cache_clear(PointCloud &pointcloud)
GPU_BATCH_DISCARD_SAFE(cache->surface);
GPU_VERTBUF_DISCARD_SAFE(cache->pos);
GPU_VERTBUF_DISCARD_SAFE(cache->geom);
+ GPU_VERTBUF_DISCARD_SAFE(cache->attr_viewer);
GPU_INDEXBUF_DISCARD_SAFE(cache->geom_indices);
if (cache->surface_per_mat) {
@@ -116,6 +119,7 @@ static void pointcloud_batch_cache_clear(PointCloud &pointcloud)
GPU_BATCH_DISCARD_SAFE(cache->surface_per_mat[i]);
}
}
+ GPU_BATCH_DISCARD_SAFE(cache->surface_viewer_attribute);
MEM_SAFE_FREE(cache->surface_per_mat);
}
@@ -227,6 +231,30 @@ static void pointcloud_batch_cache_ensure_geom(PointCloudBatchCache &cache)
cache.geom_indices = GPU_indexbuf_build(&builder);
}
+static void pointcloud_batch_cache_ensure_attribute_overlay(const PointCloud &pointcloud,
+ PointCloudBatchCache &cache)
+{
+ using namespace blender;
+ if (cache.attr_viewer != nullptr) {
+ return;
+ }
+
+ const bke::AttributeAccessor attributes = pointcloud.attributes();
+ const VArray<ColorGeometry4f> colors = attributes.lookup_or_default<ColorGeometry4f>(
+ ".viewer", ATTR_DOMAIN_POINT, {1.0f, 0.0f, 1.0f, 1.0f});
+
+ static GPUVertFormat format = {0};
+ if (format.attr_len == 0) {
+ GPU_vertformat_attr_add(&format, "attribute_value", GPU_COMP_F32, 4, GPU_FETCH_FLOAT);
+ }
+ cache.attr_viewer = GPU_vertbuf_create_with_format(&format);
+ GPU_vertbuf_data_alloc(cache.attr_viewer, pointcloud.totpoint);
+ MutableSpan<ColorGeometry4f> vbo_data{
+ static_cast<ColorGeometry4f *>(GPU_vertbuf_get_data(cache.attr_viewer)),
+ pointcloud.totpoint};
+ colors.materialize(vbo_data);
+}
+
GPUBatch *DRW_pointcloud_batch_cache_get_dots(Object *ob)
{
PointCloud &pointcloud = *static_cast<PointCloud *>(ob->data);
@@ -256,6 +284,25 @@ GPUBatch *DRW_pointcloud_batch_cache_get_surface(Object *ob)
return cache->surface;
}
+GPUBatch *DRW_pointcloud_batch_cache_get_surface_viewer_attribute(Object *ob)
+{
+ PointCloud &pointcloud = *static_cast<PointCloud *>(ob->data);
+ PointCloudBatchCache *cache = pointcloud_batch_cache_get(pointcloud);
+
+ if (cache->surface_viewer_attribute == nullptr) {
+ pointcloud_batch_cache_ensure_pos(pointcloud, *cache);
+ pointcloud_batch_cache_ensure_geom(*cache);
+ pointcloud_batch_cache_ensure_attribute_overlay(pointcloud, *cache);
+
+ cache->surface_viewer_attribute = GPU_batch_create(
+ GPU_PRIM_TRIS, cache->geom, cache->geom_indices);
+ GPU_batch_instbuf_add_ex(cache->surface_viewer_attribute, cache->attr_viewer, false);
+ GPU_batch_instbuf_add_ex(cache->surface_viewer_attribute, cache->pos, false);
+ }
+
+ return cache->surface_viewer_attribute;
+}
+
GPUBatch **DRW_cache_pointcloud_surface_shaded_get(Object *ob,
struct GPUMaterial **UNUSED(gpumat_array),
uint gpumat_array_len)
diff --git a/source/blender/draw/intern/draw_manager.c b/source/blender/draw/intern/draw_manager.c
index 51762e29506..99f75581a47 100644
--- a/source/blender/draw/intern/draw_manager.c
+++ b/source/blender/draw/intern/draw_manager.c
@@ -38,6 +38,7 @@
#include "BKE_pointcloud.h"
#include "BKE_screen.h"
#include "BKE_subdiv_modifier.h"
+#include "BKE_viewer_path.h"
#include "BKE_volume.h"
#include "DNA_camera_types.h"
@@ -1695,6 +1696,9 @@ void DRW_draw_render_loop_ex(struct Depsgraph *depsgraph,
DEGObjectIterSettings deg_iter_settings = {0};
deg_iter_settings.depsgraph = depsgraph;
deg_iter_settings.flags = DEG_OBJECT_ITER_FOR_RENDER_ENGINE_FLAGS;
+ if (v3d->flag2 & V3D_SHOW_VIEWER) {
+ deg_iter_settings.viewer_path = &v3d->viewer_path;
+ }
DEG_OBJECT_ITER_BEGIN (&deg_iter_settings, ob) {
if ((object_type_exclude_viewport & (1 << ob->type)) != 0) {
continue;
@@ -2497,6 +2501,9 @@ void DRW_draw_select_loop(struct Depsgraph *depsgraph,
DEGObjectIterSettings deg_iter_settings = {0};
deg_iter_settings.depsgraph = depsgraph;
deg_iter_settings.flags = DEG_OBJECT_ITER_FOR_RENDER_ENGINE_FLAGS;
+ if (v3d->flag2 & V3D_SHOW_VIEWER) {
+ deg_iter_settings.viewer_path = &v3d->viewer_path;
+ }
DEG_OBJECT_ITER_BEGIN (&deg_iter_settings, ob) {
if (!BKE_object_is_visible_in_viewport(v3d, ob)) {
continue;
@@ -2662,6 +2669,9 @@ static void drw_draw_depth_loop_impl(struct Depsgraph *depsgraph,
DEGObjectIterSettings deg_iter_settings = {0};
deg_iter_settings.depsgraph = DST.draw_ctx.depsgraph;
deg_iter_settings.flags = DEG_OBJECT_ITER_FOR_RENDER_ENGINE_FLAGS;
+ if (v3d->flag2 & V3D_SHOW_VIEWER) {
+ deg_iter_settings.viewer_path = &v3d->viewer_path;
+ }
DEG_OBJECT_ITER_BEGIN (&deg_iter_settings, ob) {
if ((object_type_exclude_viewport & (1 << ob->type)) != 0) {
continue;
diff --git a/source/blender/draw/intern/mesh_extractors/extract_mesh.hh b/source/blender/draw/intern/mesh_extractors/extract_mesh.hh
index 0bce05577b2..d9bb8d1d2b4 100644
--- a/source/blender/draw/intern/mesh_extractors/extract_mesh.hh
+++ b/source/blender/draw/intern/mesh_extractors/extract_mesh.hh
@@ -440,3 +440,4 @@ extern const MeshExtract extract_edge_idx;
extern const MeshExtract extract_vert_idx;
extern const MeshExtract extract_fdot_idx;
extern const MeshExtract extract_attr[GPU_MAX_ATTR];
+extern const MeshExtract extract_attr_viewer;
diff --git a/source/blender/draw/intern/mesh_extractors/extract_mesh_vbo_attributes.cc b/source/blender/draw/intern/mesh_extractors/extract_mesh_vbo_attributes.cc
index 240e9b4fa60..c602b768df9 100644
--- a/source/blender/draw/intern/mesh_extractors/extract_mesh_vbo_attributes.cc
+++ b/source/blender/draw/intern/mesh_extractors/extract_mesh_vbo_attributes.cc
@@ -14,6 +14,8 @@
#include "BLI_string.h"
#include "BKE_attribute.h"
+#include "BKE_attribute.hh"
+#include "BKE_mesh.h"
#include "draw_attributes.h"
#include "draw_subdivision.h"
@@ -432,6 +434,40 @@ constexpr MeshExtract create_extractor_attr(ExtractInitFn fn, ExtractInitSubdivF
return extractor;
}
+static void extract_mesh_attr_viewer_init(const MeshRenderData *mr,
+ MeshBatchCache *UNUSED(cache),
+ void *buf,
+ void *UNUSED(tls_data))
+{
+ GPUVertBuf *vbo = static_cast<GPUVertBuf *>(buf);
+ static GPUVertFormat format = {0};
+ if (format.attr_len == 0) {
+ GPU_vertformat_attr_add(&format, "attribute_value", GPU_COMP_F32, 4, GPU_FETCH_FLOAT);
+ }
+
+ GPU_vertbuf_init_with_format(vbo, &format);
+ GPU_vertbuf_data_alloc(vbo, mr->loop_len);
+ MutableSpan<ColorGeometry4f> attr{static_cast<ColorGeometry4f *>(GPU_vertbuf_get_data(vbo)),
+ mr->loop_len};
+
+ const StringRefNull attr_name = ".viewer";
+ const bke::AttributeAccessor attributes = mr->me->attributes();
+ attributes
+ .lookup_or_default<ColorGeometry4f>(attr_name, ATTR_DOMAIN_CORNER, {1.0f, 0.0f, 1.0f, 1.0f})
+ .materialize(attr);
+}
+
+constexpr MeshExtract create_extractor_attr_viewer()
+{
+ MeshExtract extractor = {nullptr};
+ extractor.init = extract_mesh_attr_viewer_init;
+ extractor.data_type = MR_DATA_NONE;
+ extractor.data_size = 0;
+ extractor.use_threading = false;
+ extractor.mesh_buffer_offset = offsetof(MeshBufferList, vbo.attr_viewer);
+ return extractor;
+}
+
/** \} */
} // namespace blender::draw
@@ -457,3 +493,5 @@ const MeshExtract extract_attr[GPU_MAX_ATTR] = {
CREATE_EXTRACTOR_ATTR(13),
CREATE_EXTRACTOR_ATTR(14),
};
+
+const MeshExtract extract_attr_viewer = blender::draw::create_extractor_attr_viewer();
diff --git a/source/blender/draw/tests/shaders_test.cc b/source/blender/draw/tests/shaders_test.cc
index dc631483857..f238c7e25b1 100644
--- a/source/blender/draw/tests/shaders_test.cc
+++ b/source/blender/draw/tests/shaders_test.cc
@@ -254,6 +254,7 @@ static void test_overlay_glsl_shaders()
EXPECT_NE(OVERLAY_shader_motion_path_line(), nullptr);
EXPECT_NE(OVERLAY_shader_motion_path_vert(), nullptr);
EXPECT_NE(OVERLAY_shader_uniform_color(), nullptr);
+ EXPECT_NE(OVERLAY_shader_uniform_color_pointcloud(), nullptr);
EXPECT_NE(OVERLAY_shader_outline_prepass(false), nullptr);
EXPECT_NE(OVERLAY_shader_outline_prepass(true), nullptr);
EXPECT_NE(OVERLAY_shader_outline_prepass_curves(), nullptr);
@@ -272,6 +273,10 @@ static void test_overlay_glsl_shaders()
EXPECT_NE(OVERLAY_shader_particle_shape(), nullptr);
EXPECT_NE(OVERLAY_shader_sculpt_mask(), nullptr);
EXPECT_NE(OVERLAY_shader_sculpt_curves_selection(), nullptr);
+ EXPECT_NE(OVERLAY_shader_viewer_attribute_curve(), nullptr);
+ EXPECT_NE(OVERLAY_shader_viewer_attribute_curves(), nullptr);
+ EXPECT_NE(OVERLAY_shader_viewer_attribute_mesh(), nullptr);
+ EXPECT_NE(OVERLAY_shader_viewer_attribute_pointcloud(), nullptr);
EXPECT_NE(OVERLAY_shader_volume_velocity(false, false), nullptr);
EXPECT_NE(OVERLAY_shader_volume_velocity(false, true), nullptr);
EXPECT_NE(OVERLAY_shader_volume_velocity(true, false), nullptr);