Mesh: Move vertex/edge crease to generic attributes

Store subdivision surface creases in two new named float attributes:
- `crease_vert`
- `crease_edge`
This is similar to 2a56403cb0.

The attributes are naming conventions, so their data type and domain
aren't enforced, and may be interpolated when necessary. Editing tools
and the subdivision surface modifier use the hard-coded name. It might
be best if these were edited as generic attributes in the future, but
in the meantime using generic attributes helps.

The attributes are visible in the list, which is how they're now meant
to be removed. They are now interchangeable with any tool that works
with the generic attribute system-- even tools like vertex paint can
affect creases now.

This is a breaking change. Forward compatibility isn't preserved for
versions before 3.6, and the `crease` property in RNA is removed in
favor of making a smaller API surface area with just the attribute API.
`Mesh.vertex_creases` and `Mesh.edge_creases` now just return the
matching attribute if possible, and are now implemented in Python.
New functions `*ensure` and `*remove` also replace the operators to
add and remove the layers for Python.

A few extrude node test files have to be updated because of different
(now generic) attribute interpolation behavior.

Pull Request: https://projects.blender.org/blender/blender/pulls/108089
This commit is contained in:
Hans Goudey
2023-06-13 20:23:39 +02:00
committed by Hans Goudey
parent f32bd8f804
commit e5ec04d73c
41 changed files with 344 additions and 617 deletions

View File

@@ -989,6 +989,48 @@ static const bool *find_sharp_face_attribute(BL::Mesh b_mesh)
return nullptr;
}
static const float *find_edge_crease_attribute(BL::Mesh b_mesh)
{
for (BL::Attribute &b_attribute : b_mesh.attributes) {
if (b_attribute.domain() != BL::Attribute::domain_EDGE) {
continue;
}
if (b_attribute.data_type() != BL::Attribute::data_type_FLOAT) {
continue;
}
if (b_attribute.name() != "crease_edge") {
continue;
}
BL::FloatAttribute b_float_attribute{b_attribute};
if (b_float_attribute.data.length() == 0) {
return nullptr;
}
return static_cast<const float *>(b_float_attribute.data[0].ptr.data);
}
return nullptr;
}
static const float *find_vert_crease_attribute(BL::Mesh b_mesh)
{
for (BL::Attribute &b_attribute : b_mesh.attributes) {
if (b_attribute.domain() != BL::Attribute::domain_POINT) {
continue;
}
if (b_attribute.data_type() != BL::Attribute::data_type_FLOAT) {
continue;
}
if (b_attribute.name() != "crease_vert") {
continue;
}
BL::FloatAttribute b_float_attribute{b_attribute};
if (b_float_attribute.data.length() == 0) {
return nullptr;
}
return static_cast<const float *>(b_float_attribute.data[0].ptr.data);
}
return nullptr;
}
static void create_mesh(Scene *scene,
Mesh *mesh,
BL::Mesh &b_mesh,
@@ -1226,11 +1268,12 @@ static void create_subd_mesh(Scene *scene,
create_mesh(scene, mesh, b_mesh, used_shaders, need_motion, motion_scale, true, subdivide_uvs);
const int verts_num = b_mesh.vertices.length();
const int edges_num = b_mesh.edges.length();
if (edges_num != 0 && b_mesh.edge_creases.length() > 0) {
const float *creases = static_cast<const float *>(b_mesh.edge_creases[0].data[0].ptr.data);
const float *creases = find_edge_crease_attribute(b_mesh);
if (edges_num != 0 && creases != nullptr) {
size_t num_creases = 0;
for (int i = 0; i < edges_num; i++) {
if (creases[i] != 0.0f) {
@@ -1250,11 +1293,10 @@ static void create_subd_mesh(Scene *scene,
}
}
for (BL::MeshVertexCreaseLayer &layer : b_mesh.vertex_creases) {
const float *creases = static_cast<const float *>(layer.data[0].ptr.data);
for (int i = 0; i < layer.data.length(); ++i) {
if (creases[i] != 0.0f) {
mesh->add_vertex_crease(i, creases[i]);
if (const float *vert_creases = find_vert_crease_attribute(b_mesh)) {
for (int i = 0; i < verts_num; i++) {
if (vert_creases[i] != 0.0f) {
mesh->add_vertex_crease(i, vert_creases[i]);
}
}
}

View File

@@ -531,6 +531,36 @@ def ord_ind(i1, i2):
return i2, i1
def _name_convention_attribute_get(attributes, name, domain, data_type):
try:
attribute = attributes[name]
except KeyError:
return None
if attribute.domain != domain:
return None
if attribute.data_type != data_type:
return None
return attribute
def _name_convention_attribute_ensure(attributes, name, domain, data_type):
try:
attribute = attributes[name]
except KeyError:
return attributes.new(name, data_type, domain)
if attribute.domain == domain and attribute.data_type == data_type:
return attribute
attributes.remove(attribute)
return attributes.new(name, data_type, domain)
def _name_convention_attribute_remove(attributes, name):
try:
attributes.remove(attributes[name])
except KeyError:
pass
class Mesh(bpy_types.ID):
__slots__ = ()
@@ -605,6 +635,32 @@ class Mesh(bpy_types.ID):
def edge_keys(self):
return [ed.key for ed in self.edges]
@property
def vertex_creases(self):
"""
Vertex crease values for subdivision surface, corresponding to the "crease_vert" attribute.
"""
return _name_convention_attribute_get(self.attributes, "crease_vert", 'POINT', 'FLOAT')
def vertex_creases_ensure(self):
return _name_convention_attribute_ensure(self.attributes, "crease_vert", 'POINT', 'FLOAT')
def vertex_creases_remove(self):
_name_convention_attribute_remove(self.attributes, "crease_vert")
@property
def edge_creases(self):
"""
Edge crease values for subdivision surface, corresponding to the "crease_edge" attribute.
"""
return _name_convention_attribute_get(self.attributes, "crease_edge", 'EDGE', 'FLOAT')
def edge_creases_ensure(self):
return _name_convention_attribute_ensure(self.attributes, "crease_edge", 'EDGE', 'FLOAT')
def edge_creases_remove(self):
_name_convention_attribute_remove(self.attributes, "crease_edge")
class MeshEdge(StructRNA):
__slots__ = ()

View File

@@ -441,16 +441,6 @@ class DATA_PT_customdata(MeshButtonsPanel, Panel):
else:
col.operator("mesh.customdata_custom_splitnormals_add", icon='ADD')
if me.has_crease_edge:
col.operator("mesh.customdata_crease_edge_clear", icon='X')
else:
col.operator("mesh.customdata_crease_edge_add", icon='ADD')
if me.has_crease_vertex:
col.operator("mesh.customdata_crease_vertex_clear", icon='X')
else:
col.operator("mesh.customdata_crease_vertex_add", icon='ADD')
class DATA_PT_custom_props_mesh(MeshButtonsPanel, PropertyPanel, Panel):
COMPAT_ENGINES = {'BLENDER_RENDER', 'BLENDER_EEVEE', 'BLENDER_WORKBENCH', 'BLENDER_WORKBENCH_NEXT'}

View File

@@ -27,7 +27,7 @@ extern "C" {
/* Blender file format version. */
#define BLENDER_FILE_VERSION BLENDER_VERSION
#define BLENDER_FILE_SUBVERSION 6
#define BLENDER_FILE_SUBVERSION 7
/* Minimum Blender version that supports reading file written with the current
* version. Older Blender versions will test this and show a warning if the file

View File

@@ -705,7 +705,8 @@ enum {
CD_FAKE_SHARP = CD_FAKE | 200, /* Sharp flag for edges, smooth flag for faces. */
CD_FAKE_BWEIGHT = CD_FAKE | 300, /* UV seam flag for edges. */
CD_FAKE_BWEIGHT = CD_FAKE | 300,
CD_FAKE_CREASE = CD_FAKE | 400,
};
enum {

View File

@@ -40,6 +40,7 @@ void BKE_mesh_legacy_face_set_to_generic(struct Mesh *mesh);
* Copy edge creases from edges to a separate layer.
*/
void BKE_mesh_legacy_edge_crease_to_layers(struct Mesh *mesh);
void BKE_mesh_legacy_crease_to_generic(struct Mesh *mesh);
/**
* Copy bevel weights from vertices and edges to separate layers.

View File

@@ -1766,10 +1766,10 @@ static const LayerTypeInfo LAYERTYPEINFO[CD_NUMTYPES] = {
{sizeof(int), "", 0, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr},
/* 28: CD_SHAPEKEY */
{sizeof(float[3]), "", 0, N_("ShapeKey"), nullptr, nullptr, layerInterp_shapekey},
/* 29: CD_BWEIGHT */ /* DEPRECATED*/
/* 29: CD_BWEIGHT */ /* DEPRECATED */
{sizeof(MFloatProperty), "MFloatProperty", 1},
/* 30: CD_CREASE */
{sizeof(float), "", 0, nullptr, nullptr, nullptr, layerInterp_propFloat},
/* 30: CD_CREASE */ /* DEPRECATED */
{sizeof(float), ""},
/* 31: CD_ORIGSPACE_MLOOP */
{sizeof(OrigSpaceLoop),
"OrigSpaceLoop",
@@ -2034,9 +2034,9 @@ const CustomData_MeshMasks CD_MASK_BAREMESH_ORIGINDEX = {
};
const CustomData_MeshMasks CD_MASK_MESH = {
/*vmask*/ (CD_MASK_PROP_FLOAT3 | CD_MASK_MDEFORMVERT | CD_MASK_MVERT_SKIN |
CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL | CD_MASK_CREASE),
CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL),
/*emask*/
(CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL | CD_MASK_CREASE),
(CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL),
/*fmask*/ 0,
/*pmask*/
(CD_MASK_FREESTYLE_FACE | CD_MASK_PROP_ALL),
@@ -2045,10 +2045,9 @@ const CustomData_MeshMasks CD_MASK_MESH = {
};
const CustomData_MeshMasks CD_MASK_DERIVEDMESH = {
/*vmask*/ (CD_MASK_ORIGINDEX | CD_MASK_MDEFORMVERT | CD_MASK_SHAPEKEY | CD_MASK_MVERT_SKIN |
CD_MASK_PAINT_MASK | CD_MASK_ORCO | CD_MASK_CLOTH_ORCO | CD_MASK_PROP_ALL |
CD_MASK_CREASE),
CD_MASK_PAINT_MASK | CD_MASK_ORCO | CD_MASK_CLOTH_ORCO | CD_MASK_PROP_ALL),
/*emask*/
(CD_MASK_ORIGINDEX | CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL | CD_MASK_CREASE),
(CD_MASK_ORIGINDEX | CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL),
/*fmask*/ (CD_MASK_ORIGINDEX | CD_MASK_ORIGSPACE | CD_MASK_PREVIEW_MCOL | CD_MASK_TANGENT),
/*pmask*/
(CD_MASK_ORIGINDEX | CD_MASK_FREESTYLE_FACE | CD_MASK_PROP_ALL),
@@ -2058,8 +2057,8 @@ const CustomData_MeshMasks CD_MASK_DERIVEDMESH = {
};
const CustomData_MeshMasks CD_MASK_BMESH = {
/*vmask*/ (CD_MASK_MDEFORMVERT | CD_MASK_MVERT_SKIN | CD_MASK_SHAPEKEY |
CD_MASK_SHAPE_KEYINDEX | CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL | CD_MASK_CREASE),
/*emask*/ (CD_MASK_CREASE | CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL),
CD_MASK_SHAPE_KEYINDEX | CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL),
/*emask*/ (CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL),
/*fmask*/ 0,
/*pmask*/
(CD_MASK_FREESTYLE_FACE | CD_MASK_PROP_ALL),
@@ -2069,10 +2068,9 @@ const CustomData_MeshMasks CD_MASK_BMESH = {
const CustomData_MeshMasks CD_MASK_EVERYTHING = {
/*vmask*/ (CD_MASK_BM_ELEM_PYPTR | CD_MASK_ORIGINDEX | CD_MASK_MDEFORMVERT |
CD_MASK_MVERT_SKIN | CD_MASK_ORCO | CD_MASK_CLOTH_ORCO | CD_MASK_SHAPEKEY |
CD_MASK_SHAPE_KEYINDEX | CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL | CD_MASK_CREASE),
CD_MASK_SHAPE_KEYINDEX | CD_MASK_PAINT_MASK | CD_MASK_PROP_ALL),
/*emask*/
(CD_MASK_BM_ELEM_PYPTR | CD_MASK_ORIGINDEX | CD_MASK_CREASE | CD_MASK_FREESTYLE_EDGE |
CD_MASK_PROP_ALL),
(CD_MASK_BM_ELEM_PYPTR | CD_MASK_ORIGINDEX | CD_MASK_FREESTYLE_EDGE | CD_MASK_PROP_ALL),
/*fmask*/
(CD_MASK_MFACE | CD_MASK_ORIGINDEX | CD_MASK_NORMAL | CD_MASK_MTFACE | CD_MASK_MCOL |
CD_MASK_ORIGSPACE | CD_MASK_TANGENT | CD_MASK_TESSLOOPNORMAL | CD_MASK_PREVIEW_MCOL |
@@ -5182,9 +5180,6 @@ void CustomData_blend_write(BlendWriter *writer,
case CD_PROP_BOOL:
BLO_write_raw(writer, sizeof(bool) * count, static_cast<const bool *>(layer.data));
break;
case CD_CREASE:
BLO_write_raw(writer, sizeof(float) * count, static_cast<const float *>(layer.data));
break;
default: {
const char *structname;
int structnum;

View File

@@ -199,7 +199,7 @@ int BKE_object_data_transfer_dttype_to_cdtype(const int dtdata_type)
case DT_TYPE_SEAM:
return CD_FAKE_SEAM;
case DT_TYPE_CREASE:
return CD_CREASE;
return CD_FAKE_CREASE;
case DT_TYPE_BWEIGHT_EDGE:
return CD_FAKE_BWEIGHT;
case DT_TYPE_FREESTYLE_EDGE:

View File

@@ -1195,20 +1195,6 @@ static ComponentAttributeProviders create_attribute_providers_for_mesh()
edge_access,
nullptr);
static const auto crease_clamp = mf::build::SI1_SO<float, float>(
"Crease Clamp",
[](float value) { return std::clamp(value, 0.0f, 1.0f); },
mf::build::exec_presets::AllSpanOrSingle());
static BuiltinCustomDataLayerProvider crease("crease",
ATTR_DOMAIN_EDGE,
CD_PROP_FLOAT,
CD_CREASE,
BuiltinAttributeProvider::Creatable,
BuiltinAttributeProvider::Deletable,
edge_access,
nullptr,
AttributeValidator{&crease_clamp});
static VertexGroupsAttributeProvider vertex_groups;
static CustomDataAttributeProvider corner_custom_data(ATTR_DOMAIN_CORNER, corner_access);
static CustomDataAttributeProvider point_custom_data(ATTR_DOMAIN_POINT, point_access);
@@ -1222,8 +1208,7 @@ static ComponentAttributeProviders create_attribute_providers_for_mesh()
&id,
&material_index,
&sharp_face,
&sharp_edge,
&crease},
&sharp_edge},
{&corner_custom_data,
&vertex_groups,
&point_custom_data,

View File

@@ -1369,53 +1369,44 @@ void BKE_mesh_legacy_bevel_weight_to_layers(Mesh *mesh)
}
}
void BKE_mesh_legacy_bevel_weight_to_generic(Mesh *mesh)
static void replace_custom_data_layer_with_named(CustomData &custom_data,
const eCustomDataType old_type,
const eCustomDataType new_type,
const int elems_num,
const char *new_name)
{
using namespace blender;
if (!mesh->attributes().contains("bevel_weight_vert")) {
void *data = nullptr;
const ImplicitSharingInfo *sharing_info = nullptr;
for (const int i : IndexRange(mesh->vdata.totlayer)) {
CustomDataLayer &layer = mesh->vdata.layers[i];
if (layer.type == CD_BWEIGHT) {
data = layer.data;
sharing_info = layer.sharing_info;
layer.data = nullptr;
layer.sharing_info = nullptr;
CustomData_free_layer(&mesh->vdata, CD_BWEIGHT, mesh->totvert, i);
break;
}
}
if (data != nullptr) {
CustomData_add_layer_named_with_data(
&mesh->vdata, CD_PROP_FLOAT, data, mesh->totvert, "bevel_weight_vert", sharing_info);
}
if (sharing_info != nullptr) {
sharing_info->remove_user_and_delete_if_last();
void *data = nullptr;
const ImplicitSharingInfo *sharing_info = nullptr;
for (const int i : IndexRange(custom_data.totlayer)) {
CustomDataLayer &layer = custom_data.layers[i];
if (layer.type == old_type) {
data = layer.data;
sharing_info = layer.sharing_info;
layer.data = nullptr;
layer.sharing_info = nullptr;
CustomData_free_layer(&custom_data, old_type, elems_num, i);
break;
}
}
if (data != nullptr) {
CustomData_add_layer_named_with_data(
&custom_data, new_type, data, elems_num, new_name, sharing_info);
}
if (sharing_info != nullptr) {
sharing_info->remove_user_and_delete_if_last();
}
}
void BKE_mesh_legacy_bevel_weight_to_generic(Mesh *mesh)
{
if (!mesh->attributes().contains("bevel_weight_vert")) {
replace_custom_data_layer_with_named(
mesh->vdata, CD_BWEIGHT, CD_PROP_FLOAT, mesh->totvert, "bevel_weight_vert");
}
if (!mesh->attributes().contains("bevel_weight_edge")) {
void *data = nullptr;
const ImplicitSharingInfo *sharing_info = nullptr;
for (const int i : IndexRange(mesh->edata.totlayer)) {
CustomDataLayer &layer = mesh->edata.layers[i];
if (layer.type == CD_BWEIGHT) {
data = layer.data;
sharing_info = layer.sharing_info;
layer.data = nullptr;
layer.sharing_info = nullptr;
CustomData_free_layer(&mesh->edata, CD_BWEIGHT, mesh->totedge, i);
break;
}
}
if (data != nullptr) {
CustomData_add_layer_named_with_data(
&mesh->edata, CD_PROP_FLOAT, data, mesh->totedge, "bevel_weight_edge", sharing_info);
}
if (sharing_info != nullptr) {
sharing_info->remove_user_and_delete_if_last();
}
replace_custom_data_layer_with_named(
mesh->edata, CD_BWEIGHT, CD_PROP_FLOAT, mesh->totedge, "bevel_weight_edge");
}
}
@@ -1441,6 +1432,18 @@ void BKE_mesh_legacy_edge_crease_to_layers(Mesh *mesh)
}
}
void BKE_mesh_legacy_crease_to_generic(Mesh *mesh)
{
if (!mesh->attributes().contains("crease_vert")) {
replace_custom_data_layer_with_named(
mesh->vdata, CD_CREASE, CD_PROP_FLOAT, mesh->totvert, "crease_vert");
}
if (!mesh->attributes().contains("crease_edge")) {
replace_custom_data_layer_with_named(
mesh->edata, CD_CREASE, CD_PROP_FLOAT, mesh->totedge, "crease_edge");
}
}
/** \} */
/* -------------------------------------------------------------------- */

View File

@@ -12,6 +12,7 @@
#include "BLI_offset_indices.hh"
#include "BLI_span.hh"
#include "BLI_sys_types.h"
#include "BLI_virtual_array.hh"
#include "BKE_multires.h"
@@ -100,10 +101,10 @@ struct MultiresReshapeContext {
* to that base face. */
int *face_ptex_offset;
/* Vertex crease custom data layer, null if none is present. */
const float *cd_vertex_crease;
/* Edge crease custom data layer, null if none is present. */
const float *cd_edge_crease;
/* Vertex crease custom data layer, empty if none is present. */
blender::VArraySpan<float> cd_vertex_crease;
/* Edge crease custom data layer, empty if none is present. */
blender::VArraySpan<float> cd_edge_crease;
};
/**

View File

@@ -491,8 +491,10 @@ static float get_effective_crease(const MultiresReshapeSmoothContext *reshape_sm
if (!is_crease_supported(reshape_smooth_context)) {
return 1.0f;
}
const float *creases = reshape_smooth_context->reshape_context->cd_edge_crease;
return creases ? creases[base_edge_index] : 0.0f;
if (reshape_smooth_context->reshape_context->cd_edge_crease.is_empty()) {
return 0.0f;
}
return reshape_smooth_context->reshape_context->cd_edge_crease[base_edge_index];
}
static float get_effective_crease_float(const MultiresReshapeSmoothContext *reshape_smooth_context,
@@ -617,12 +619,11 @@ static void foreach_single_vertex(const SubdivForeachContext *foreach_context,
}
const MultiresReshapeContext *reshape_context = reshape_smooth_context->reshape_context;
const float *cd_vertex_crease = reshape_context->cd_vertex_crease;
if (cd_vertex_crease == nullptr) {
if (reshape_context->cd_vertex_crease.is_empty()) {
return;
}
float crease = cd_vertex_crease[coarse_vertex_index];
float crease = reshape_context->cd_vertex_crease[coarse_vertex_index];
if (crease == 0.0f) {
return;
}

View File

@@ -18,6 +18,7 @@
#include "BLI_task.h"
#include "BKE_attribute.hh"
#include "BKE_customdata.h"
#include "BKE_mesh.hh"
#include "BKE_mesh_runtime.h"
@@ -184,6 +185,7 @@ bool multires_reshape_context_create_from_object(MultiresReshapeContext *reshape
Object *object,
MultiresModifierData *mmd)
{
using namespace blender;
context_zero(reshape_context);
const bool use_render_params = false;
@@ -212,10 +214,9 @@ bool multires_reshape_context_create_from_object(MultiresReshapeContext *reshape
reshape_context->top.level = mmd->totlvl;
reshape_context->top.grid_size = BKE_subdiv_grid_size_from_level(reshape_context->top.level);
reshape_context->cd_vertex_crease = static_cast<const float *>(
CustomData_get_layer(&base_mesh->vdata, CD_CREASE));
reshape_context->cd_edge_crease = static_cast<const float *>(
CustomData_get_layer(&base_mesh->edata, CD_CREASE));
const bke::AttributeAccessor attributes = base_mesh->attributes();
reshape_context->cd_vertex_crease = *attributes.lookup<float>("crease_vert", ATTR_DOMAIN_POINT);
reshape_context->cd_edge_crease = *attributes.lookup<float>("crease_edge", ATTR_DOMAIN_EDGE);
context_init_commoon(reshape_context);
@@ -272,6 +273,7 @@ bool multires_reshape_context_create_from_subdiv(MultiresReshapeContext *reshape
Subdiv *subdiv,
int top_level)
{
using namespace blender;
context_zero(reshape_context);
Mesh *base_mesh = (Mesh *)object->data;
@@ -283,8 +285,9 @@ bool multires_reshape_context_create_from_subdiv(MultiresReshapeContext *reshape
reshape_context->base_polys = base_mesh->polys();
reshape_context->base_corner_verts = base_mesh->corner_verts();
reshape_context->base_corner_edges = base_mesh->corner_edges();
reshape_context->cd_vertex_crease = (const float *)CustomData_get_layer(&base_mesh->edata,
CD_CREASE);
const bke::AttributeAccessor attributes = base_mesh->attributes();
reshape_context->cd_vertex_crease = *attributes.lookup<float>("crease_vert", ATTR_DOMAIN_POINT);
reshape_context->subdiv = subdiv;
reshape_context->need_free_subdiv = false;

View File

@@ -149,8 +149,8 @@ void BKE_object_handle_data_update(Depsgraph *depsgraph, Scene *scene, Object *o
/* Custom attributes should not be removed automatically. They might be used by the render
* engine or scripts. They can still be removed explicitly using geometry nodes. Crease and
* vertex groups can be used in arbitrary situations with geometry nodes as well. */
cddata_masks.vmask |= CD_MASK_PROP_ALL | CD_MASK_CREASE | CD_MASK_MDEFORMVERT;
cddata_masks.emask |= CD_MASK_PROP_ALL | CD_MASK_CREASE;
cddata_masks.vmask |= CD_MASK_PROP_ALL | CD_MASK_MDEFORMVERT;
cddata_masks.emask |= CD_MASK_PROP_ALL;
cddata_masks.fmask |= CD_MASK_PROP_ALL;
cddata_masks.pmask |= CD_MASK_PROP_ALL;
cddata_masks.lmask |= CD_MASK_PROP_ALL;

View File

@@ -15,7 +15,7 @@
#include "BLI_utildefines.h"
#include "BKE_customdata.h"
#include "BKE_attribute.hh"
#include "BKE_mesh.hh"
#include "BKE_mesh_mapping.h"
#include "BKE_subdiv.h"
@@ -41,9 +41,9 @@ struct ConverterStorage {
blender::Span<int> corner_edges;
/* CustomData layer for vertex sharpnesses. */
const float *cd_vertex_crease;
blender::VArraySpan<float> cd_vertex_crease;
/* CustomData layer for edge sharpness. */
const float *cd_edge_crease;
blender::VArraySpan<float> cd_edge_crease;
/* Indexed by loop index, value denotes index of face-varying vertex
* which corresponds to the UV coordinate.
*/
@@ -161,7 +161,7 @@ static float get_edge_sharpness(const OpenSubdiv_Converter *converter, int manif
return 10.0f;
}
#endif
if (storage->cd_edge_crease == nullptr) {
if (storage->cd_edge_crease.is_empty()) {
return 0.0f;
}
const int edge_index = storage->manifold_edge_index_reverse[manifold_edge_index];
@@ -187,7 +187,7 @@ static bool is_infinite_sharp_vertex(const OpenSubdiv_Converter *converter,
static float get_vertex_sharpness(const OpenSubdiv_Converter *converter, int manifold_vertex_index)
{
ConverterStorage *storage = static_cast<ConverterStorage *>(converter->user_data);
if (storage->cd_vertex_crease == nullptr) {
if (storage->cd_vertex_crease.is_empty()) {
return 0.0f;
}
const int vertex_index = storage->manifold_vertex_index_reverse[manifold_vertex_index];
@@ -382,6 +382,7 @@ static void init_user_data(OpenSubdiv_Converter *converter,
const SubdivSettings *settings,
const Mesh *mesh)
{
using namespace blender;
ConverterStorage *user_data = MEM_new<ConverterStorage>(__func__);
user_data->settings = *settings;
user_data->mesh = mesh;
@@ -391,10 +392,9 @@ static void init_user_data(OpenSubdiv_Converter *converter,
user_data->corner_verts = mesh->corner_verts();
user_data->corner_edges = mesh->corner_edges();
if (settings->use_creases) {
user_data->cd_vertex_crease = static_cast<const float *>(
CustomData_get_layer(&mesh->vdata, CD_CREASE));
user_data->cd_edge_crease = static_cast<const float *>(
CustomData_get_layer(&mesh->edata, CD_CREASE));
const bke::AttributeAccessor attributes = mesh->attributes();
user_data->cd_vertex_crease = *attributes.lookup<float>("crease_vert", ATTR_DOMAIN_POINT);
user_data->cd_edge_crease = *attributes.lookup<float>("crease_edge", ATTR_DOMAIN_EDGE);
}
user_data->loop_uv_indices = nullptr;
initialize_manifold_indices(user_data);

View File

@@ -525,10 +525,6 @@ static bool subdiv_mesh_topology_info(const SubdivForeachContext *foreach_contex
* so don't try to preserve it and use memory. Crease values should also not be interpolated. */
CustomData_MeshMasks mask = CD_MASK_EVERYTHING;
mask.lmask &= ~CD_MASK_MULTIRES_GRIDS;
/* Propagate edge creases so they can be used in another subdivision modifier (maintaining
* existing behavior), but don't propagate vertex creases to avoid extra work when the result
* isn't useful anyway. */
mask.vmask &= ~CD_MASK_CREASE;
SubdivMeshContext *subdiv_context = static_cast<SubdivMeshContext *>(foreach_context->user_data);
subdiv_context->subdiv_mesh = BKE_mesh_new_nomain_from_template_ex(

View File

@@ -566,7 +566,8 @@ static void ss_sync_ccg_from_derivedmesh(CCGSubSurf *ss,
}
index = (int *)dm->getEdgeDataArray(dm, CD_ORIGINDEX);
const float *creases = (const float *)dm->getEdgeDataArray(dm, CD_CREASE);
const float *creases = (const float *)CustomData_get_layer_named(
&dm->edgeData, CD_PROP_FLOAT, "crease_edge");
for (i = 0; i < totedge; i++) {
CCGEdge *e;
float crease;

View File

@@ -10,15 +10,19 @@
#include "CLG_log.h"
#include "DNA_modifier_types.h"
#include "DNA_movieclip_types.h"
#include "BLI_assert.h"
#include "BLI_listbase.h"
#include "BLI_set.hh"
#include "BLI_string_ref.hh"
#include "BKE_idprop.hh"
#include "BKE_main.h"
#include "BKE_mesh_legacy_convert.h"
#include "BKE_node.hh"
#include "BKE_node_runtime.hh"
#include "BKE_tracking.h"
#include "BLO_readfile.h"
@@ -115,6 +119,45 @@ static void version_geometry_nodes_add_realize_instance_nodes(bNodeTree *ntree)
}
}
static void version_mesh_crease_generic(Main &bmain)
{
LISTBASE_FOREACH (Mesh *, mesh, &bmain.meshes) {
BKE_mesh_legacy_crease_to_generic(mesh);
}
LISTBASE_FOREACH (bNodeTree *, ntree, &bmain.nodetrees) {
if (ntree->type == NTREE_GEOMETRY) {
LISTBASE_FOREACH (bNode *, node, &ntree->nodes) {
if (STR_ELEM(node->idname,
"GeometryNodeStoreNamedAttribute",
"GeometryNodeInputNamedAttribute")) {
bNodeSocket *socket = nodeFindSocket(node, SOCK_IN, "Name");
if (STREQ(socket->default_value_typed<bNodeSocketValueString>()->value, "crease")) {
STRNCPY(socket->default_value_typed<bNodeSocketValueString>()->value, "crease_edge");
}
}
}
}
}
LISTBASE_FOREACH (Object *, object, &bmain.objects) {
LISTBASE_FOREACH (ModifierData *, md, &object->modifiers) {
if (md->type != eModifierType_Nodes) {
continue;
}
if (IDProperty *settings = reinterpret_cast<NodesModifierData *>(md)->settings.properties) {
LISTBASE_FOREACH (IDProperty *, prop, &settings->data.group) {
if (blender::StringRef(prop->name).endswith("_attribute_name")) {
if (STREQ(IDP_String(prop), "crease")) {
IDP_AssignString(prop, "crease_edge");
}
}
}
}
}
}
}
static void versioning_replace_legacy_glossy_node(bNodeTree *ntree)
{
LISTBASE_FOREACH (bNode *, node, &ntree->nodes) {
@@ -206,6 +249,12 @@ void blo_do_versions_400(FileData * /*fd*/, Library * /*lib*/, Main *bmain)
FOREACH_NODETREE_END;
}
if (!MAIN_VERSION_ATLEAST(bmain, 400, 7)) {
LISTBASE_FOREACH (Mesh *, mesh, &bmain->meshes) {
version_mesh_crease_generic(*bmain);
}
}
/**
* Versioning code until next subversion bump goes here.
*

View File

@@ -161,7 +161,9 @@ void BM_mesh_wireframe(BMesh *bm,
const float ofs_new = offset + ofs_orig;
const float ofs_mid = (ofs_orig + ofs_new) / 2.0f;
const float inset = offset / 2.0f;
int cd_edge_crease_offset = use_crease ? CustomData_get_offset(&bm->edata, CD_CREASE) : -1;
int cd_edge_crease_offset = use_crease ? CustomData_get_offset_named(
&bm->edata, CD_PROP_FLOAT, "crease_edge") :
-1;
const int cd_dvert_offset = (defgrp_index != -1) ?
CustomData_get_offset(&bm->vdata, CD_MDEFORMVERT) :
-1;
@@ -200,8 +202,8 @@ void BM_mesh_wireframe(BMesh *bm,
int i;
if (use_crease && cd_edge_crease_offset == -1) {
BM_data_layer_add(bm, &bm->edata, CD_CREASE);
cd_edge_crease_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
BM_data_layer_add_named(bm, &bm->edata, CD_PROP_FLOAT, "crease_edge");
cd_edge_crease_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
}
BM_ITER_MESH_INDEX (v_src, &iter, bm, BM_VERTS_OF_MESH, i) {

View File

@@ -453,8 +453,10 @@ MeshRenderData *mesh_render_data_create(Object *object,
mr->eed_act = BM_mesh_active_edge_get(mr->bm);
mr->eve_act = BM_mesh_active_vert_get(mr->bm);
mr->vert_crease_ofs = CustomData_get_offset(&mr->bm->vdata, CD_CREASE);
mr->edge_crease_ofs = CustomData_get_offset(&mr->bm->edata, CD_CREASE);
mr->vert_crease_ofs = CustomData_get_offset_named(
&mr->bm->vdata, CD_PROP_FLOAT, "crease_vert");
mr->edge_crease_ofs = CustomData_get_offset_named(
&mr->bm->edata, CD_PROP_FLOAT, "crease_edge");
mr->bweight_ofs = CustomData_get_offset_named(
&mr->bm->edata, CD_PROP_FLOAT, "bevel_weight_edge");
#ifdef WITH_FREESTYLE

View File

@@ -194,7 +194,7 @@ static void mouse_mesh_shortest_path_vert(Scene *UNUSED(scene),
#endif
break;
case EDGE_MODE_TAG_CREASE:
cd_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
break;
case EDGE_MODE_TAG_BEVEL:
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "bevel_weight_edge");
@@ -363,8 +363,8 @@ static void edgetag_ensure_cd_flag(Mesh *me, const char edge_mode)
switch (edge_mode) {
case EDGE_MODE_TAG_CREASE:
if (!CustomData_has_layer(&bm->edata, CD_CREASE)) {
BM_data_layer_add(bm, &bm->edata, CD_CREASE);
if (!CustomData_has_layer_named(&bm->edata, CD_PROP_FLOAT, "crease_edge")) {
BM_data_layer_add_named(bm, &bm->edata, CD_PROP_FLOAT, "crease_edge");
}
break;
case EDGE_MODE_TAG_BEVEL:
@@ -406,7 +406,7 @@ static void mouse_mesh_shortest_path_edge(Scene *scene,
#endif
break;
case EDGE_MODE_TAG_CREASE:
cd_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
break;
case EDGE_MODE_TAG_BEVEL:
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "bevel_weight_edge");
@@ -559,7 +559,7 @@ static void mouse_mesh_shortest_path_face(Scene *UNUSED(scene),
#endif
break;
case EDGE_MODE_TAG_CREASE:
cd_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
break;
case EDGE_MODE_TAG_BEVEL:
cd_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "bevel_weight_edge");

View File

@@ -641,7 +641,7 @@ static int similar_edge_select_exec(bContext *C, wmOperator *op)
break;
}
case SIMEDGE_CREASE: {
if (!CustomData_has_layer(&bm->edata, CD_CREASE)) {
if (!CustomData_has_layer_named(&bm->edata, CD_PROP_FLOAT, "crease_edge")) {
BLI_kdtree_1d_insert(tree_1d, tree_index++, (float[1]){0.0f});
continue;
}
@@ -659,7 +659,7 @@ static int similar_edge_select_exec(bContext *C, wmOperator *op)
int custom_data_offset;
switch (type) {
case SIMEDGE_CREASE:
custom_data_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
custom_data_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
break;
case SIMEDGE_BEVEL:
custom_data_offset = CustomData_get_offset_named(
@@ -760,7 +760,8 @@ static int similar_edge_select_exec(bContext *C, wmOperator *op)
break;
}
case SIMEDGE_CREASE: {
has_custom_data_layer = CustomData_has_layer(&bm->edata, CD_CREASE);
has_custom_data_layer = CustomData_has_layer_named(
&bm->edata, CD_PROP_FLOAT, "crease_edge");
ATTR_FALLTHROUGH;
}
case SIMEDGE_BEVEL: {
@@ -784,7 +785,7 @@ static int similar_edge_select_exec(bContext *C, wmOperator *op)
int custom_data_offset;
switch (type) {
case SIMEDGE_CREASE:
custom_data_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
custom_data_offset = CustomData_get_offset_named(&bm->edata, CD_PROP_FLOAT, "crease_edge");
break;
case SIMEDGE_BEVEL:
custom_data_offset = CustomData_get_offset_named(
@@ -1002,6 +1003,7 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
BMEditMesh *em = BKE_editmesh_from_object(ob);
BMesh *bm = em->bm;
int cd_dvert_offset = -1;
int cd_crease_offset = -1;
BLI_bitmap *defbase_selected = NULL;
int defbase_len = 0;
@@ -1023,11 +1025,14 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
defbase_selected = BLI_BITMAP_NEW(defbase_len, __func__);
}
else if (type == SIMVERT_CREASE) {
if (!CustomData_has_layer(&bm->vdata, CD_CREASE)) {
if (!CustomData_has_layer_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert")) {
BLI_kdtree_1d_insert(tree_1d, tree_1d_index++, (float[1]){0.0f});
continue;
}
}
else if (type == SIMVERT_CREASE) {
cd_crease_offset = CustomData_get_offset_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert");
}
BMVert *vert; /* Mesh vertex. */
BMIter iter; /* Selected verts iterator. */
@@ -1064,7 +1069,7 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
break;
}
case SIMVERT_CREASE: {
const float *value = CustomData_bmesh_get(&bm->vdata, vert->head.data, CD_CREASE);
const float *value = BM_ELEM_CD_GET_FLOAT_P(vert, cd_crease_offset);
BLI_kdtree_1d_insert(tree_1d, tree_1d_index++, value);
break;
}
@@ -1113,6 +1118,7 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
bool changed = false;
bool has_crease_layer = false;
int cd_dvert_offset = -1;
int cd_crease_offset = -1;
BLI_bitmap *defbase_selected = NULL;
int defbase_len = 0;
@@ -1147,7 +1153,8 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
}
}
else if (type == SIMVERT_CREASE) {
has_crease_layer = CustomData_has_layer(&bm->vdata, CD_CREASE);
cd_crease_offset = CustomData_get_offset_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert");
has_crease_layer = CustomData_has_layer_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert");
if (!has_crease_layer) {
/* Proceed only if we have to select all the vertices that have custom data value of 0.0f.
* In this case we will just select all the vertices.
@@ -1228,7 +1235,7 @@ static int similar_vert_select_exec(bContext *C, wmOperator *op)
select = true;
break;
}
const float *value = CustomData_bmesh_get(&bm->vdata, vert->head.data, CD_CREASE);
const float *value = BM_ELEM_CD_GET_FLOAT_P(vert, cd_crease_offset);
if (ED_select_similar_compare_float_tree(tree_1d, *value, thresh, compare)) {
select = true;
}

View File

@@ -583,28 +583,6 @@ static int mesh_customdata_clear_exec__internal(bContext *C,
return OPERATOR_CANCELLED;
}
static int mesh_customdata_add_exec__internal(bContext *C, char htype, const eCustomDataType type)
{
Mesh *mesh = ED_mesh_context(C);
int tot;
CustomData *data = mesh_customdata_get_type(mesh, htype, &tot);
BLI_assert(CustomData_layertype_is_singleton(type) == true);
if (mesh->edit_mesh) {
BM_data_layer_add(mesh->edit_mesh->bm, data, type);
}
else {
CustomData_add_layer(data, eCustomDataType(type), CD_SET_DEFAULT, tot);
}
DEG_id_tag_update(&mesh->id, 0);
WM_event_add_notifier(C, NC_GEOM | ND_DATA, mesh);
return CustomData_has_layer(data, type) ? OPERATOR_FINISHED : OPERATOR_CANCELLED;
}
/* Clear Mask */
static bool mesh_customdata_mask_clear_poll(bContext *C)
{
@@ -825,128 +803,6 @@ void MESH_OT_customdata_custom_splitnormals_clear(wmOperatorType *ot)
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
/* Edge crease. */
static int mesh_customdata_crease_edge_state(bContext *C)
{
const Object *ob = ED_object_context(C);
if (ob && ob->type == OB_MESH) {
const Mesh *mesh = static_cast<Mesh *>(ob->data);
if (!ID_IS_LINKED(mesh)) {
const CustomData *data = GET_CD_DATA(mesh, edata);
return CustomData_has_layer(data, CD_CREASE);
}
}
return -1;
}
static bool mesh_customdata_crease_edge_add_poll(bContext *C)
{
return mesh_customdata_crease_edge_state(C) == 0;
}
static int mesh_customdata_crease_edge_add_exec(bContext *C, wmOperator * /*op*/)
{
return mesh_customdata_add_exec__internal(C, BM_EDGE, CD_CREASE);
}
void MESH_OT_customdata_crease_edge_add(wmOperatorType *ot)
{
ot->name = "Add Edge Crease";
ot->idname = "MESH_OT_customdata_crease_edge_add";
ot->description = "Add an edge crease layer";
ot->exec = mesh_customdata_crease_edge_add_exec;
ot->poll = mesh_customdata_crease_edge_add_poll;
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
static bool mesh_customdata_crease_edge_clear_poll(bContext *C)
{
return mesh_customdata_crease_edge_state(C) == 1;
}
static int mesh_customdata_crease_edge_clear_exec(bContext *C, wmOperator * /*op*/)
{
return mesh_customdata_clear_exec__internal(C, BM_EDGE, CD_CREASE);
}
void MESH_OT_customdata_crease_edge_clear(wmOperatorType *ot)
{
ot->name = "Clear Edge Crease";
ot->idname = "MESH_OT_customdata_crease_edge_clear";
ot->description = "Clear the edge crease layer";
ot->exec = mesh_customdata_crease_edge_clear_exec;
ot->poll = mesh_customdata_crease_edge_clear_poll;
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
/* Vertex crease. */
static int mesh_customdata_crease_vertex_state(bContext *C)
{
const Object *object = ED_object_context(C);
if (object && object->type == OB_MESH) {
const Mesh *mesh = static_cast<Mesh *>(object->data);
if (!ID_IS_LINKED(mesh)) {
const CustomData *data = GET_CD_DATA(mesh, vdata);
return CustomData_has_layer(data, CD_CREASE);
}
}
return -1;
}
static bool mesh_customdata_crease_vertex_add_poll(bContext *C)
{
return mesh_customdata_crease_vertex_state(C) == 0;
}
static int mesh_customdata_crease_vertex_add_exec(bContext *C, wmOperator * /*op*/)
{
return mesh_customdata_add_exec__internal(C, BM_VERT, CD_CREASE);
}
void MESH_OT_customdata_crease_vertex_add(wmOperatorType *ot)
{
ot->name = "Add Vertex Crease";
ot->idname = "MESH_OT_customdata_crease_vertex_add";
ot->description = "Add a vertex crease layer";
ot->exec = mesh_customdata_crease_vertex_add_exec;
ot->poll = mesh_customdata_crease_vertex_add_poll;
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
static bool mesh_customdata_crease_vertex_clear_poll(bContext *C)
{
return (mesh_customdata_crease_vertex_state(C) == 1);
}
static int mesh_customdata_crease_vertex_clear_exec(bContext *C, wmOperator * /*op*/)
{
return mesh_customdata_clear_exec__internal(C, BM_VERT, CD_CREASE);
}
void MESH_OT_customdata_crease_vertex_clear(wmOperatorType *ot)
{
ot->name = "Clear Vertex Crease";
ot->idname = "MESH_OT_customdata_crease_vertex_clear";
ot->description = "Clear the vertex crease layer";
ot->exec = mesh_customdata_crease_vertex_clear_exec;
ot->poll = mesh_customdata_crease_vertex_clear_poll;
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
}
/************************** Add Geometry Layers *************************/
void ED_mesh_update(Mesh *mesh, bContext *C, bool calc_edges, bool calc_edges_loose)
{
if (calc_edges || ((mesh->totpoly || mesh->totface) && mesh->totedge == 0)) {

View File

@@ -325,10 +325,6 @@ void MESH_OT_customdata_skin_add(struct wmOperatorType *ot);
void MESH_OT_customdata_skin_clear(struct wmOperatorType *ot);
void MESH_OT_customdata_custom_splitnormals_add(struct wmOperatorType *ot);
void MESH_OT_customdata_custom_splitnormals_clear(struct wmOperatorType *ot);
void MESH_OT_customdata_crease_vertex_add(struct wmOperatorType *ot);
void MESH_OT_customdata_crease_vertex_clear(struct wmOperatorType *ot);
void MESH_OT_customdata_crease_edge_add(struct wmOperatorType *ot);
void MESH_OT_customdata_crease_edge_clear(struct wmOperatorType *ot);
#ifdef __cplusplus
}

View File

@@ -142,10 +142,6 @@ void ED_operatortypes_mesh(void)
WM_operatortype_append(MESH_OT_customdata_skin_clear);
WM_operatortype_append(MESH_OT_customdata_custom_splitnormals_add);
WM_operatortype_append(MESH_OT_customdata_custom_splitnormals_clear);
WM_operatortype_append(MESH_OT_customdata_crease_vertex_add);
WM_operatortype_append(MESH_OT_customdata_crease_vertex_clear);
WM_operatortype_append(MESH_OT_customdata_crease_edge_add);
WM_operatortype_append(MESH_OT_customdata_crease_edge_clear);
WM_operatortype_append(MESH_OT_edgering_select);
WM_operatortype_append(MESH_OT_loopcut);

View File

@@ -672,7 +672,7 @@ static int sculpt_face_set_init_exec(bContext *C, wmOperator *op)
}
case SCULPT_FACE_SETS_FROM_CREASES: {
const float *creases = static_cast<const float *>(
CustomData_get_layer(&mesh->edata, CD_CREASE));
CustomData_get_layer_named(&mesh->edata, CD_PROP_FLOAT, "crease_edge"));
sculpt_face_sets_init_flood_fill(
ob, [&](const int /*from_face*/, const int edge, const int /*to_face*/) -> bool {
return creases ? creases[edge] < threshold : true;

View File

@@ -308,11 +308,13 @@ static void v3d_editvertex_buts(uiLayout *layout, View3D *v3d, Object *ob, float
const int cd_vert_bweight_offset = CustomData_get_offset_named(
&bm->vdata, CD_PROP_FLOAT, "bevel_weight_vert");
const int cd_vert_crease_offset = CustomData_get_offset(&bm->vdata, CD_CREASE);
const int cd_vert_crease_offset = CustomData_get_offset_named(
&bm->vdata, CD_PROP_FLOAT, "crease_vert");
const int cd_vert_skin_offset = CustomData_get_offset(&bm->vdata, CD_MVERT_SKIN);
const int cd_edge_bweight_offset = CustomData_get_offset_named(
&bm->edata, CD_PROP_FLOAT, "bevel_weight_edge");
const int cd_edge_crease_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
const int cd_edge_crease_offset = CustomData_get_offset_named(
&bm->edata, CD_PROP_FLOAT, "crease_edge");
has_skinradius = (cd_vert_skin_offset != -1);
@@ -1011,10 +1013,11 @@ static void v3d_editvertex_buts(uiLayout *layout, View3D *v3d, Object *ob, float
}
if (median->v_crease) {
if (!CustomData_has_layer(&bm->vdata, CD_CREASE)) {
BM_data_layer_add(bm, &bm->vdata, CD_CREASE);
if (!CustomData_has_layer_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert")) {
BM_data_layer_add_named(bm, &bm->vdata, CD_PROP_FLOAT, "crease_vert");
}
cd_vert_crease_offset = CustomData_get_offset(&bm->vdata, CD_CREASE);
cd_vert_crease_offset = CustomData_get_offset_named(
&bm->vdata, CD_PROP_FLOAT, "crease_vert");
BLI_assert(cd_vert_crease_offset != -1);
scale_v_crease = compute_scale_factor(ve_median->v_crease, median->v_crease);
@@ -1082,10 +1085,11 @@ static void v3d_editvertex_buts(uiLayout *layout, View3D *v3d, Object *ob, float
}
if (median->e_crease) {
if (!CustomData_has_layer(&bm->edata, CD_CREASE)) {
BM_data_layer_add(bm, &bm->edata, CD_CREASE);
if (!CustomData_has_layer_named(&bm->edata, CD_PROP_FLOAT, "crease_edge")) {
BM_data_layer_add_named(bm, &bm->edata, CD_PROP_FLOAT, "crease_edge");
}
cd_edge_crease_offset = CustomData_get_offset(&bm->edata, CD_CREASE);
cd_edge_crease_offset = CustomData_get_offset_named(
&bm->edata, CD_PROP_FLOAT, "crease_edge");
BLI_assert(cd_edge_crease_offset != -1);
scale_e_crease = compute_scale_factor(ve_median->e_crease, median->e_crease);

View File

@@ -76,10 +76,11 @@ static void createTransEdge(bContext *UNUSED(C), TransInfo *t)
}
else { /* if (t->mode == TFM_EDGE_CREASE) { */
BLI_assert(t->mode == TFM_EDGE_CREASE);
if (!CustomData_has_layer(&em->bm->edata, CD_CREASE)) {
BM_data_layer_add(em->bm, &em->bm->edata, CD_CREASE);
if (!CustomData_has_layer_named(&em->bm->edata, CD_PROP_FLOAT, "crease_edge")) {
BM_data_layer_add_named(em->bm, &em->bm->edata, CD_PROP_FLOAT, "crease_edge");
}
cd_edge_float_offset = CustomData_get_offset(&em->bm->edata, CD_CREASE);
cd_edge_float_offset = CustomData_get_offset_named(
&em->bm->edata, CD_PROP_FLOAT, "crease_edge");
}
BLI_assert(cd_edge_float_offset != -1);

View File

@@ -29,7 +29,7 @@
#include "transform_convert.h"
/* -------------------------------------------------------------------- */
/** \name Edit Mesh Bevel Weight and #CD_CREASE Transform Creation
/** \name Edit Mesh Bevel Weight and Crease Transform Creation
* \{ */
static float *tc_mesh_cdata_transdata_center(const struct TransIslandData *island_data,
@@ -92,10 +92,10 @@ static void createTransMeshVertCData(bContext *UNUSED(C), TransInfo *t)
cd_offset = CustomData_get_offset_named(&bm->vdata, CD_PROP_FLOAT, "bevel_weight_vert");
}
else {
if (!CustomData_has_layer(&bm->vdata, CD_CREASE)) {
BM_data_layer_add(bm, &bm->vdata, CD_CREASE);
if (!CustomData_has_layer_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert")) {
BM_data_layer_add_named(bm, &bm->vdata, CD_PROP_FLOAT, "crease_vert");
}
cd_offset = CustomData_get_offset(&bm->vdata, CD_CREASE);
cd_offset = CustomData_get_offset_named(&bm->vdata, CD_PROP_FLOAT, "crease_vert");
}
if (cd_offset == -1) {

View File

@@ -489,10 +489,12 @@ static void get_edge_creases(Mesh *mesh,
lengths.clear();
sharpnesses.clear();
const float *creases = static_cast<const float *>(CustomData_get_layer(&mesh->edata, CD_CREASE));
if (!creases) {
const bke::AttributeAccessor attributes = mesh->attributes();
const bke::AttributeReader attribute = attributes.lookup<float>("crease_edge", ATTR_DOMAIN_EDGE);
if (!attribute) {
return;
}
const VArraySpan creases(*attribute);
const Span<int2> edges = mesh->edges();
for (const int i : edges.index_range()) {
const float sharpness = creases[i];
@@ -514,13 +516,14 @@ static void get_vert_creases(Mesh *mesh,
indices.clear();
sharpnesses.clear();
const float *creases = static_cast<const float *>(CustomData_get_layer(&mesh->vdata, CD_CREASE));
if (!creases) {
const bke::AttributeAccessor attributes = mesh->attributes();
const bke::AttributeReader attribute = attributes.lookup<float>("crease_vert",
ATTR_DOMAIN_POINT);
if (!attribute) {
return;
}
for (int i = 0, v = mesh->totvert; i < v; i++) {
const VArraySpan creases(*attribute);
for (const int i : creases.index_range()) {
const float sharpness = creases[i];
if (sharpness != 0.0f) {

View File

@@ -892,8 +892,8 @@ static void read_vertex_creases(Mesh *mesh,
return;
}
float *vertex_crease_data = (float *)CustomData_add_layer(
&mesh->vdata, CD_CREASE, CD_SET_DEFAULT, mesh->totvert);
float *vertex_crease_data = (float *)CustomData_add_layer_named(
&mesh->vdata, CD_PROP_FLOAT, CD_SET_DEFAULT, mesh->totvert, "crease_vert");
const int totvert = mesh->totvert;
for (int i = 0, v = indices->size(); i < v; ++i) {
@@ -918,8 +918,8 @@ static void read_edge_creases(Mesh *mesh,
MutableSpan<int2> edges = mesh->edges_for_write();
EdgeHash *edge_hash = BLI_edgehash_new_ex(__func__, edges.size());
float *creases = static_cast<float *>(
CustomData_add_layer(&mesh->edata, CD_CREASE, CD_SET_DEFAULT, edges.size()));
float *creases = static_cast<float *>(CustomData_add_layer_named(
&mesh->edata, CD_PROP_FLOAT, CD_SET_DEFAULT, edges.size(), "crease_edge"));
for (const int i : edges.index_range()) {
int2 &edge = edges[i];

View File

@@ -630,12 +630,14 @@ void USDMeshReader::read_vertex_creases(Mesh *mesh, const double motionSampleTim
return;
}
float *creases = static_cast<float *>(
CustomData_add_layer(&mesh->vdata, CD_CREASE, CD_SET_DEFAULT, mesh->totvert));
bke::MutableAttributeAccessor attributes = mesh->attributes_for_write();
bke::SpanAttributeWriter creases = attributes.lookup_or_add_for_write_span<float>(
"crease_vert", ATTR_DOMAIN_POINT);
for (size_t i = 0; i < corner_indices.size(); i++) {
creases[corner_indices[i]] = corner_sharpnesses[i];
creases.span[corner_indices[i]] = corner_sharpnesses[i];
}
creases.finish();
}
void USDMeshReader::process_normals_vertex_varying(Mesh *mesh)

View File

@@ -374,11 +374,12 @@ static void get_loops_polys(const Mesh *mesh, USDMeshData &usd_mesh_data)
static void get_edge_creases(const Mesh *mesh, USDMeshData &usd_mesh_data)
{
const float *creases = static_cast<const float *>(CustomData_get_layer(&mesh->edata, CD_CREASE));
if (!creases) {
const bke::AttributeAccessor attributes = mesh->attributes();
const bke::AttributeReader attribute = attributes.lookup<float>("crease_edge", ATTR_DOMAIN_EDGE);
if (!attribute) {
return;
}
const VArraySpan creases(*attribute);
const Span<int2> edges = mesh->edges();
for (const int i : edges.index_range()) {
const float crease = creases[i];
@@ -397,13 +398,14 @@ static void get_edge_creases(const Mesh *mesh, USDMeshData &usd_mesh_data)
static void get_vert_creases(const Mesh *mesh, USDMeshData &usd_mesh_data)
{
const float *creases = static_cast<const float *>(CustomData_get_layer(&mesh->vdata, CD_CREASE));
if (!creases) {
const bke::AttributeAccessor attributes = mesh->attributes();
const bke::AttributeReader attribute = attributes.lookup<float>("crease_vert",
ATTR_DOMAIN_POINT);
if (!attribute) {
return;
}
for (int i = 0, v = mesh->totvert; i < v; i++) {
const VArraySpan creases(*attribute);
for (const int i : creases.index_range()) {
const float sharpness = creases[i];
if (sharpness != 0.0f) {

View File

@@ -149,9 +149,8 @@ typedef enum eCustomDataType {
CD_SHAPEKEY = 28,
#ifdef DNA_DEPRECATED_ALLOW
CD_BWEIGHT = 29,
#endif
/** Subdivision sharpness data per edge or per vertex. */
CD_CREASE = 30,
#endif
CD_ORIGSPACE_MLOOP = 31,
CD_PREVIEW_MLOOPCOL = 32,
CD_BM_ELEM_PYPTR = 33,
@@ -205,7 +204,6 @@ typedef enum eCustomDataType {
#define CD_MASK_SHAPE_KEYINDEX (1 << CD_SHAPE_KEYINDEX)
#define CD_MASK_SHAPEKEY (1 << CD_SHAPEKEY)
#define CD_MASK_CREASE (1 << CD_CREASE)
#define CD_MASK_ORIGSPACE_MLOOP (1LL << CD_ORIGSPACE_MLOOP)
#define CD_MASK_PREVIEW_MLOOPCOL (1LL << CD_PREVIEW_MLOOPCOL)
#define CD_MASK_BM_ELEM_PYPTR (1LL << CD_BM_ELEM_PYPTR)

View File

@@ -359,7 +359,7 @@ enum {
typedef struct MEdge {
/** Un-ordered vertex indices (cannot match). */
unsigned int v1, v2;
/** Deprecated edge crease, now located in #CD_CREASE, except for file read and write. */
/** Deprecated edge crease, now located in `edge_crease`, except for file read and write. */
char crease_legacy;
/**
* Deprecated bevel weight storage, now located in #CD_BWEIGHT, except for file read and write.

View File

@@ -81,11 +81,6 @@ static CustomData *rna_mesh_vdata_helper(Mesh *me)
return (me->edit_mesh) ? &me->edit_mesh->bm->vdata : &me->vdata;
}
static CustomData *rna_mesh_edata_helper(Mesh *me)
{
return (me->edit_mesh) ? &me->edit_mesh->bm->edata : &me->edata;
}
static CustomData *rna_mesh_ldata_helper(Mesh *me)
{
return (me->edit_mesh) ? &me->edit_mesh->bm->ldata : &me->ldata;
@@ -96,12 +91,6 @@ static CustomData *rna_mesh_vdata(const PointerRNA *ptr)
Mesh *me = rna_mesh(ptr);
return rna_mesh_vdata_helper(me);
}
static CustomData *rna_mesh_edata(const PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
return rna_mesh_edata_helper(me);
}
static CustomData *rna_mesh_ldata(const PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
@@ -162,16 +151,6 @@ static bool rna_Mesh_has_custom_normals_get(PointerRNA *ptr)
return BKE_mesh_has_custom_loop_normals(me);
}
static bool rna_Mesh_has_edge_crease_get(PointerRNA *ptr)
{
return CustomData_has_layer(rna_mesh_edata(ptr), CD_CREASE);
}
static bool rna_Mesh_has_vertex_crease_get(PointerRNA *ptr)
{
return CustomData_has_layer(rna_mesh_vdata(ptr), CD_CREASE);
}
/** \} */
/* -------------------------------------------------------------------- */
@@ -466,23 +445,6 @@ static void rna_MeshVertex_select_set(PointerRNA *ptr, bool value)
select_vert[index] = value;
}
static float rna_MEdge_crease_get(PointerRNA *ptr)
{
const Mesh *mesh = rna_mesh(ptr);
const int index = rna_MeshEdge_index_get(ptr);
const float *values = (const float *)CustomData_get_layer(&mesh->edata, CD_CREASE);
return values == NULL ? 0.0f : values[index];
}
static void rna_MEdge_crease_set(PointerRNA *ptr, float value)
{
Mesh *mesh = rna_mesh(ptr);
const int index = rna_MeshEdge_index_get(ptr);
float *values = (float *)CustomData_add_layer(
&mesh->edata, CD_CREASE, CD_SET_DEFAULT, mesh->totedge);
values[index] = clamp_f(value, 0.0f, 1.0f);
}
static int rna_MeshLoop_vertex_index_get(PointerRNA *ptr)
{
return *(int *)ptr->data;
@@ -1255,54 +1217,6 @@ static int rna_MeshSkinVertexLayer_data_length(PointerRNA *ptr)
/* End skin vertices */
/* Vertex creases */
DEFINE_CUSTOMDATA_LAYER_COLLECTION(vertex_crease, vdata, CD_CREASE)
static char *rna_MeshVertexCreaseLayer_path(const PointerRNA *ptr)
{
return rna_VertCustomData_data_path(ptr, "vertex_creases", CD_CREASE);
}
static void rna_MeshVertexCreaseLayer_data_begin(CollectionPropertyIterator *iter, PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
CustomDataLayer *layer = (CustomDataLayer *)ptr->data;
rna_iterator_array_begin(iter, layer->data, sizeof(float), me->totvert, 0, NULL);
}
static int rna_MeshVertexCreaseLayer_data_length(PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
return me->totvert;
}
/* End vertex creases */
/* Edge creases */
DEFINE_CUSTOMDATA_LAYER_COLLECTION(edge_crease, edata, CD_CREASE)
static char *rna_EdgeCustomData_data_path(const PointerRNA *ptr, const char *collection, int type);
static char *rna_MeshEdgeCreaseLayer_path(const PointerRNA *ptr)
{
return rna_EdgeCustomData_data_path(ptr, "edge_creases", CD_CREASE);
}
static void rna_MeshEdgeCreaseLayer_data_begin(CollectionPropertyIterator *iter, PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
CustomDataLayer *layer = (CustomDataLayer *)ptr->data;
rna_iterator_array_begin(iter, layer->data, sizeof(float), me->totedge, 0, NULL);
}
static int rna_MeshEdgeCreaseLayer_data_length(PointerRNA *ptr)
{
Mesh *me = rna_mesh(ptr);
return me->totedge;
}
/* End edge creases */
/* Paint mask */
DEFINE_CUSTOMDATA_LAYER_COLLECTION(vertex_paint_mask, vdata, CD_PAINT_MASK)
@@ -1588,27 +1502,6 @@ static char *rna_VertCustomData_data_path(const PointerRNA *ptr, const char *col
return NULL;
}
static char *rna_EdgeCustomData_data_path(const PointerRNA *ptr, const char *collection, int type)
{
const CustomDataLayer *cdl;
const Mesh *me = rna_mesh(ptr);
const CustomData *edata = rna_mesh_edata(ptr);
int a, b, totedge = (me->edit_mesh) ? 0 : me->totedge;
for (cdl = edata->layers, a = 0; a < edata->totlayer; cdl++, a++) {
if (cdl->type == type) {
b = ((char *)ptr->data - ((char *)cdl->data)) / CustomData_sizeof(type);
if (b >= 0 && b < totedge) {
char name_esc[sizeof(cdl->name) * 2];
BLI_str_escape(name_esc, cdl->name, sizeof(name_esc));
return BLI_sprintfN("%s[\"%s\"].data[%d]", collection, name_esc, b);
}
}
}
return NULL;
}
static char *rna_LoopCustomData_data_path(const PointerRNA *ptr, const char *collection, int type)
{
const CustomDataLayer *cdl;
@@ -2034,8 +1927,6 @@ static void UNUSED_FUNCTION(rna_mesh_unused)(void)
(void)rna_Mesh_uv_layer_render_index_get;
(void)rna_Mesh_uv_layer_render_index_set;
(void)rna_Mesh_uv_layer_render_set;
(void)rna_Mesh_vertex_crease_index_range;
(void)rna_Mesh_edge_crease_index_range;
/* end unused function block */
}
@@ -2202,12 +2093,6 @@ static void rna_def_medge(BlenderRNA *brna)
RNA_def_property_ui_text(prop, "Vertices", "Vertex indices");
/* XXX allows creating invalid meshes */
prop = RNA_def_property(srna, "crease", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_funcs(prop, "rna_MEdge_crease_get", "rna_MEdge_crease_set", NULL);
RNA_def_property_ui_text(
prop, "Crease", "Weight used by the Subdivision Surface modifier for creasing");
RNA_def_property_update(prop, 0, "rna_Mesh_update_data_legacy_deg_tag_all");
prop = RNA_def_property(srna, "select", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_boolean_funcs(prop, "rna_MeshEdge_select_get", "rna_MeshEdge_select_set");
RNA_def_property_ui_text(prop, "Select", "");
@@ -2999,76 +2884,6 @@ static void rna_def_skin_vertices(BlenderRNA *brna, PropertyRNA *UNUSED(cprop))
RNA_def_property_update(prop, 0, "rna_Mesh_update_data_legacy_deg_tag_all");
}
static void rna_def_vertex_creases(BlenderRNA *brna)
{
StructRNA *srna;
PropertyRNA *prop;
srna = RNA_def_struct(brna, "MeshVertexCreaseLayer", NULL);
RNA_def_struct_ui_text(srna, "Mesh Vertex Crease Layer", "Per-vertex crease");
RNA_def_struct_sdna(srna, "CustomDataLayer");
RNA_def_struct_path_func(srna, "rna_MeshVertexCreaseLayer_path");
prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
RNA_def_property_struct_type(prop, "MeshVertexCrease");
RNA_def_property_ui_text(prop, "Data", "");
RNA_def_property_override_flag(prop, PROPOVERRIDE_IGNORE);
RNA_def_property_collection_funcs(prop,
"rna_MeshVertexCreaseLayer_data_begin",
"rna_iterator_array_next",
"rna_iterator_array_end",
"rna_iterator_array_get",
"rna_MeshVertexCreaseLayer_data_length",
NULL,
NULL,
NULL);
/* VertexCrease struct */
srna = RNA_def_struct(brna, "MeshVertexCrease", NULL);
RNA_def_struct_sdna(srna, "MFloatProperty");
RNA_def_struct_ui_text(srna, "Float Property", "");
prop = RNA_def_property(srna, "value", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_sdna(prop, NULL, "f");
RNA_def_property_ui_text(prop, "Value", "");
RNA_def_property_update(prop, 0, "rna_Mesh_update_data_legacy_deg_tag_all");
}
static void rna_def_edge_creases(BlenderRNA *brna)
{
StructRNA *srna;
PropertyRNA *prop;
srna = RNA_def_struct(brna, "MeshEdgeCreaseLayer", NULL);
RNA_def_struct_ui_text(srna, "Mesh Edge Crease Layer", "Per-edge crease");
RNA_def_struct_sdna(srna, "CustomDataLayer");
RNA_def_struct_path_func(srna, "rna_MeshEdgeCreaseLayer_path");
prop = RNA_def_property(srna, "data", PROP_COLLECTION, PROP_NONE);
RNA_def_property_struct_type(prop, "MeshEdgeCrease");
RNA_def_property_ui_text(prop, "Data", "");
RNA_def_property_override_flag(prop, PROPOVERRIDE_IGNORE);
RNA_def_property_collection_funcs(prop,
"rna_MeshEdgeCreaseLayer_data_begin",
"rna_iterator_array_next",
"rna_iterator_array_end",
"rna_iterator_array_get",
"rna_MeshEdgeCreaseLayer_data_length",
NULL,
NULL,
NULL);
/* EdgeCrease struct */
srna = RNA_def_struct(brna, "MeshEdgeCrease", NULL);
RNA_def_struct_sdna(srna, "MFloatProperty");
RNA_def_struct_ui_text(srna, "Float Property", "");
prop = RNA_def_property(srna, "value", PROP_FLOAT, PROP_NONE);
RNA_def_property_float_sdna(prop, NULL, "f");
RNA_def_property_ui_text(prop, "Value", "");
RNA_def_property_update(prop, 0, "rna_Mesh_update_data_legacy_deg_tag_all");
}
static void rna_def_paint_mask(BlenderRNA *brna, PropertyRNA *UNUSED(cprop))
{
StructRNA *srna;
@@ -3368,42 +3183,6 @@ static void rna_def_mesh(BlenderRNA *brna)
rna_def_skin_vertices(brna, prop);
/* End skin vertices */
/* Vertex Crease */
prop = RNA_def_property(srna, "vertex_creases", PROP_COLLECTION, PROP_NONE);
RNA_def_property_struct_type(prop, "MeshVertexCreaseLayer");
RNA_def_property_collection_sdna(prop, NULL, "vdata.layers", "vdata.totlayer");
RNA_def_property_collection_funcs(prop,
"rna_Mesh_vertex_creases_begin",
NULL,
NULL,
NULL,
"rna_Mesh_vertex_creases_length",
NULL,
NULL,
NULL);
RNA_def_property_override_flag(prop, PROPOVERRIDE_IGNORE);
RNA_def_property_ui_text(prop, "Vertex Creases", "Sharpness of the vertices");
rna_def_vertex_creases(brna);
/* End vertex crease */
/* Vertex Crease */
prop = RNA_def_property(srna, "edge_creases", PROP_COLLECTION, PROP_NONE);
RNA_def_property_struct_type(prop, "MeshEdgeCreaseLayer");
RNA_def_property_collection_sdna(prop, NULL, "edata.layers", "edata.totlayer");
RNA_def_property_collection_funcs(prop,
"rna_Mesh_edge_creases_begin",
NULL,
NULL,
NULL,
"rna_Mesh_edge_creases_length",
NULL,
NULL,
NULL);
RNA_def_property_override_flag(prop, PROPOVERRIDE_IGNORE);
RNA_def_property_ui_text(prop, "Edge Creases", "Sharpness of the edges for subdivision");
rna_def_edge_creases(brna);
/* End edge crease */
/* Paint mask */
prop = RNA_def_property(srna, "vertex_paint_masks", PROP_COLLECTION, PROP_NONE);
RNA_def_property_collection_sdna(prop, NULL, "vdata.layers", "vdata.totlayer");
@@ -3545,17 +3324,6 @@ static void rna_def_mesh(BlenderRNA *brna)
RNA_def_property_boolean_funcs(prop, "rna_Mesh_has_custom_normals_get", NULL);
RNA_define_verify_sdna(true);
prop = RNA_def_property(srna, "has_crease_edge", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_clear_flag(prop, PROP_EDITABLE);
RNA_def_property_ui_text(prop, "Has Edge Crease", "True if the mesh has an edge crease layer");
RNA_def_property_boolean_funcs(prop, "rna_Mesh_has_edge_crease_get", NULL);
prop = RNA_def_property(srna, "has_crease_vertex", PROP_BOOLEAN, PROP_NONE);
RNA_def_property_clear_flag(prop, PROP_EDITABLE);
RNA_def_property_ui_text(
prop, "Has Vertex Crease", "True if the mesh has an vertex crease layer");
RNA_def_property_boolean_funcs(prop, "rna_Mesh_has_vertex_crease_get", NULL);
prop = RNA_def_property(srna, "texco_mesh", PROP_POINTER, PROP_NONE);
RNA_def_property_pointer_sdna(prop, NULL, "texcomesh");
RNA_def_property_flag(prop, PROP_EDITABLE);

View File

@@ -1044,8 +1044,8 @@ Mesh *MOD_solidify_extrude_modifyMesh(ModifierData *md, const ModifierEvalContex
float *result_edge_crease = nullptr;
if (crease_rim || crease_outer || crease_inner) {
result_edge_crease = (float *)CustomData_add_layer(
&result->edata, CD_CREASE, CD_SET_DEFAULT, result->totedge);
result_edge_crease = (float *)CustomData_add_layer_named(
&result->edata, CD_PROP_FLOAT, CD_SET_DEFAULT, result->totedge, "crease_edge");
}
/* add faces & edges */

View File

@@ -197,7 +197,7 @@ Mesh *MOD_solidify_nonmanifold_modifyMesh(ModifierData *md,
const float *orig_edge_bweight = static_cast<const float *>(
CustomData_get_layer_named(&mesh->edata, CD_PROP_FLOAT, "bevel_weight_edge"));
const float *orig_edge_crease = static_cast<const float *>(
CustomData_get_layer(&mesh->edata, CD_CREASE));
CustomData_get_layer_named(&mesh->edata, CD_PROP_FLOAT, "crease_edge"));
uint new_verts_num = 0;
uint new_edges_num = 0;
@@ -2019,14 +2019,14 @@ Mesh *MOD_solidify_nonmanifold_modifyMesh(ModifierData *md,
/* Get vertex crease layer and ensure edge creases are active if vertex creases are found, since
* they will introduce edge creases in the used custom interpolation method. */
const float *vertex_crease = static_cast<const float *>(
CustomData_get_layer(&mesh->vdata, CD_CREASE));
CustomData_get_layer_named(&mesh->vdata, CD_PROP_FLOAT, "crease_vert"));
float *result_edge_crease = nullptr;
if (vertex_crease) {
result_edge_crease = (float *)CustomData_add_layer(
&result->edata, CD_CREASE, CD_SET_DEFAULT, result->totedge);
result_edge_crease = (float *)CustomData_add_layer_named(
&result->edata, CD_PROP_FLOAT, CD_SET_DEFAULT, result->totedge, "crease_edge");
/* delete all vertex creases in the result if a rim is used. */
if (do_rim) {
CustomData_free_layers(&result->vdata, CD_CREASE, result->totvert);
CustomData_free_layer_named(&result->vdata, "crease_vert", result->totvert);
}
}

View File

@@ -69,9 +69,6 @@ static void requiredDataMask(ModifierData *md, CustomData_MeshMasks *r_cddata_ma
r_cddata_masks->lmask |= CD_MASK_NORMAL;
r_cddata_masks->lmask |= CD_MASK_CUSTOMLOOPNORMAL;
}
if (smd->flags & eSubsurfModifierFlag_UseCrease) {
r_cddata_masks->vmask |= CD_MASK_CREASE;
}
}
static bool dependsOnNormals(ModifierData *md)

View File

@@ -59,17 +59,16 @@ static void node_init(bNodeTree * /*tree*/, bNode *node)
static void write_vert_creases(Mesh &mesh, const VArray<float> &creases)
{
CustomData_free_layers(&mesh.vdata, CD_CREASE, mesh.totvert);
float *layer = static_cast<float *>(
CustomData_add_layer(&mesh.vdata, CD_CREASE, CD_CONSTRUCT, mesh.totvert));
array_utils::copy(creases, {layer, mesh.totvert});
bke::MutableAttributeAccessor attributes = mesh.attributes_for_write();
attributes.remove("crease_vert");
attributes.add<float>("crease_vert", ATTR_DOMAIN_POINT, bke::AttributeInitVArray(creases));
}
static void write_edge_creases(Mesh &mesh, const VArray<float> &creases)
{
bke::MutableAttributeAccessor attributes = mesh.attributes_for_write();
attributes.remove("crease");
attributes.add<float>("crease", ATTR_DOMAIN_EDGE, bke::AttributeInitVArray(creases));
attributes.remove("crease_edge");
attributes.add<float>("crease_edge", ATTR_DOMAIN_EDGE, bke::AttributeInitVArray(creases));
}
static bool varray_is_single_zero(const VArray<float> &varray)
@@ -146,9 +145,10 @@ static Mesh *mesh_subsurf_calc(const Mesh *mesh,
if (use_creases) {
/* Remove the layer in case it was created by the node from the field input. The fact
* that this node uses #CD_CREASE to input creases to the subdivision code is meant to be
* that this node uses attributes to input creases to the subdivision code is meant to be
* an implementation detail ideally. */
CustomData_free_layers(&result->edata, CD_CREASE, result->totedge);
result->attributes_for_write().remove("crease_vert");
result->attributes_for_write().remove("crease_edge");
}
if (mesh_copy) {

View File

@@ -88,9 +88,6 @@ PyDoc_STRVAR(bpy_bmlayeraccess_collection__deform_doc,
PyDoc_STRVAR(
bpy_bmlayeraccess_collection__shape_doc,
"Vertex shapekey absolute location (as a 3D Vector).\n\n:type: :class:`BMLayerCollection`");
PyDoc_STRVAR(bpy_bmlayeraccess_collection__crease_doc,
"Crease for subdivision surface - float in [0 - 1].\n\n:type: "
":class:`BMLayerCollection`");
PyDoc_STRVAR(
bpy_bmlayeraccess_collection__uv_doc,
"Accessor for :class:`BMLoopUV` UV (as a 2D Vector).\n\ntype: :class:`BMLayerCollection`");
@@ -202,11 +199,6 @@ static PyGetSetDef bpy_bmlayeraccess_vert_getseters[] = {
(setter)NULL,
bpy_bmlayeraccess_collection__shape_doc,
(void *)CD_SHAPEKEY},
{"crease",
(getter)bpy_bmlayeraccess_collection_get,
(setter)NULL,
bpy_bmlayeraccess_collection__crease_doc,
(void *)CD_CREASE},
{"skin",
(getter)bpy_bmlayeraccess_collection_get,
(setter)NULL,
@@ -252,12 +244,6 @@ static PyGetSetDef bpy_bmlayeraccess_edge_getseters[] = {
(setter)NULL,
bpy_bmlayeraccess_collection__string_doc,
(void *)CD_PROP_STRING},
{"crease",
(getter)bpy_bmlayeraccess_collection_get,
(setter)NULL,
bpy_bmlayeraccess_collection__crease_doc,
(void *)CD_CREASE},
#ifdef WITH_FREESTYLE
{"freestyle",
(getter)bpy_bmlayeraccess_collection_get,
@@ -265,7 +251,6 @@ static PyGetSetDef bpy_bmlayeraccess_edge_getseters[] = {
bpy_bmlayeraccess_collection__freestyle_edge_doc,
(void *)CD_FREESTYLE_EDGE},
#endif
{NULL, NULL, NULL, NULL, NULL} /* Sentinel */
};
@@ -1141,10 +1126,6 @@ PyObject *BPy_BMLayerItem_GetItem(BPy_BMElem *py_ele, BPy_BMLayerItem *py_layer)
ret = Vector_CreatePyObject_wrap((float *)value, 3, NULL);
break;
}
case CD_CREASE: {
ret = PyFloat_FromDouble(*(float *)value);
break;
}
case CD_MVERT_SKIN: {
ret = BPy_BMVertSkin_CreatePyObject(value);
break;
@@ -1251,18 +1232,6 @@ int BPy_BMLayerItem_SetItem(BPy_BMElem *py_ele, BPy_BMLayerItem *py_layer, PyObj
}
break;
}
case CD_CREASE: {
const float tmp_val = PyFloat_AsDouble(py_value);
if (UNLIKELY(tmp_val == -1 && PyErr_Occurred())) {
PyErr_Format(
PyExc_TypeError, "expected a float, not a %.200s", Py_TYPE(py_value)->tp_name);
ret = -1;
}
else {
*(float *)value = clamp_f(tmp_val, 0.0f, 1.0f);
}
break;
}
case CD_MVERT_SKIN: {
ret = BPy_BMVertSkin_AssignPyObject(value, py_value);
break;