diff options
Diffstat (limited to 'source/blender/nodes')
-rw-r--r-- | source/blender/nodes/CMakeLists.txt | 1 | ||||
-rw-r--r-- | source/blender/nodes/NOD_function.h | 1 | ||||
-rw-r--r-- | source/blender/nodes/NOD_static_types.h | 3 | ||||
-rw-r--r-- | source/blender/nodes/function/nodes/node_fn_rotate_euler.cc | 138 |
4 files changed, 142 insertions, 1 deletions
diff --git a/source/blender/nodes/CMakeLists.txt b/source/blender/nodes/CMakeLists.txt index 78b6ee1d7a6..903a30dd383 100644 --- a/source/blender/nodes/CMakeLists.txt +++ b/source/blender/nodes/CMakeLists.txt @@ -142,6 +142,7 @@ set(SRC function/nodes/node_fn_input_string.cc function/nodes/node_fn_input_vector.cc function/nodes/node_fn_random_value.cc + function/nodes/node_fn_rotate_euler.cc function/nodes/node_fn_string_length.cc function/nodes/node_fn_string_substring.cc function/nodes/node_fn_value_to_string.cc diff --git a/source/blender/nodes/NOD_function.h b/source/blender/nodes/NOD_function.h index 9aa4c04000e..450e999bea4 100644 --- a/source/blender/nodes/NOD_function.h +++ b/source/blender/nodes/NOD_function.h @@ -29,6 +29,7 @@ void register_node_type_fn_input_special_characters(void); void register_node_type_fn_input_string(void); void register_node_type_fn_input_vector(void); void register_node_type_fn_random_value(void); +void register_node_type_fn_rotate_euler(void); void register_node_type_fn_string_length(void); void register_node_type_fn_string_substring(void); void register_node_type_fn_value_to_string(void); diff --git a/source/blender/nodes/NOD_static_types.h b/source/blender/nodes/NOD_static_types.h index d328efe9cba..c13ab199691 100644 --- a/source/blender/nodes/NOD_static_types.h +++ b/source/blender/nodes/NOD_static_types.h @@ -272,9 +272,10 @@ DefNode(FunctionNode, FN_NODE_INPUT_SPECIAL_CHARACTERS, 0, "INPUT_SPECIAL_CHARAC DefNode(FunctionNode, FN_NODE_INPUT_STRING, def_fn_input_string, "INPUT_STRING", InputString, "String", "") DefNode(FunctionNode, FN_NODE_INPUT_VECTOR, def_fn_input_vector, "INPUT_VECTOR", InputVector, "Vector", "") DefNode(FunctionNode, FN_NODE_RANDOM_VALUE, def_fn_random_value, "RANDOM_VALUE", RandomValue, "Random Value", "") -DefNode(FunctionNode, FN_NODE_VALUE_TO_STRING, 0, "VALUE_TO_STRING", ValueToString, "Value to String", "") +DefNode(FunctionNode, FN_NODE_ROTATE_EULER, def_fn_rotate_euler, "ROTATE_EULER", RotateEuler, "Rotate Euler", "") DefNode(FunctionNode, FN_NODE_STRING_LENGTH, 0, "STRING_LENGTH", StringLength, "String Length", "") DefNode(FunctionNode, FN_NODE_STRING_SUBSTRING, 0, "STRING_SUBSTRING", StringSubstring, "String Substring", "") +DefNode(FunctionNode, FN_NODE_VALUE_TO_STRING, 0, "VALUE_TO_STRING", ValueToString, "Value to String", "") DefNode(GeometryNode, GEO_NODE_LEGACY_ALIGN_ROTATION_TO_VECTOR, def_geo_align_rotation_to_vector, "LEGACY_ALIGN_ROTATION_TO_VECTOR", LegacyAlignRotationToVector, "Align Rotation to Vector", "") DefNode(GeometryNode, GEO_NODE_LEGACY_ATTRIBUTE_CLAMP, def_geo_attribute_clamp, "LEGACY_ATTRIBUTE_CLAMP", LegacyAttributeClamp, "Attribute Clamp", "") diff --git a/source/blender/nodes/function/nodes/node_fn_rotate_euler.cc b/source/blender/nodes/function/nodes/node_fn_rotate_euler.cc new file mode 100644 index 00000000000..cbae1648663 --- /dev/null +++ b/source/blender/nodes/function/nodes/node_fn_rotate_euler.cc @@ -0,0 +1,138 @@ +/* + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + */ + +#include "BLI_listbase.h" +#include "BLI_string.h" + +#include "RNA_enum_types.h" + +#include "UI_interface.h" +#include "UI_resources.h" + +#include "node_function_util.hh" + +namespace blender::nodes { +static void fn_node_rotate_euler_declare(NodeDeclarationBuilder &b) +{ + b.is_function_node(); + b.add_input<decl::Vector>("Rotation").subtype(PROP_EULER).hide_value(); + b.add_input<decl::Vector>("Rotate By").subtype(PROP_EULER); + b.add_input<decl::Vector>("Axis").default_value({0.0, 0.0, 1.0}).subtype(PROP_XYZ); + b.add_input<decl::Float>("Angle").subtype(PROP_ANGLE); + b.add_output<decl::Vector>("Rotation"); +}; + +static void fn_node_rotate_euler_update(bNodeTree *UNUSED(ntree), bNode *node) +{ + bNodeSocket *rotate_by_socket = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 1)); + bNodeSocket *axis_socket = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 2)); + bNodeSocket *angle_socket = static_cast<bNodeSocket *>(BLI_findlink(&node->inputs, 3)); + + nodeSetSocketAvailability(rotate_by_socket, + ELEM(node->custom1, FN_NODE_ROTATE_EULER_TYPE_EULER)); + nodeSetSocketAvailability(axis_socket, + ELEM(node->custom1, FN_NODE_ROTATE_EULER_TYPE_AXIS_ANGLE)); + nodeSetSocketAvailability(angle_socket, + ELEM(node->custom1, FN_NODE_ROTATE_EULER_TYPE_AXIS_ANGLE)); +} + +static void fn_node_rotate_euler_layout(uiLayout *layout, bContext *UNUSED(C), PointerRNA *ptr) +{ + uiItemR(layout, ptr, "type", UI_ITEM_R_EXPAND, nullptr, ICON_NONE); + uiItemR(layout, ptr, "space", UI_ITEM_R_EXPAND, nullptr, ICON_NONE); +} + +static const fn::MultiFunction *get_multi_function(bNode &bnode) +{ + static fn::CustomMF_SI_SI_SO<float3, float3, float3> obj_euler_rot{ + "Rotate Euler by Euler/Object", [](const float3 &input, const float3 &rotation) { + float input_mat[3][3]; + eul_to_mat3(input_mat, input); + float rot_mat[3][3]; + eul_to_mat3(rot_mat, rotation); + float mat_res[3][3]; + mul_m3_m3m3(mat_res, rot_mat, input_mat); + float3 result; + mat3_to_eul(result, mat_res); + return result; + }}; + static fn::CustomMF_SI_SI_SI_SO<float3, float3, float, float3> obj_AA_rot{ + "Rotate Euler by AxisAngle/Object", + [](const float3 &input, const float3 &axis, float angle) { + float input_mat[3][3]; + eul_to_mat3(input_mat, input); + float rot_mat[3][3]; + axis_angle_to_mat3(rot_mat, axis, angle); + float mat_res[3][3]; + mul_m3_m3m3(mat_res, rot_mat, input_mat); + float3 result; + mat3_to_eul(result, mat_res); + return result; + }}; + static fn::CustomMF_SI_SI_SO<float3, float3, float3> point_euler_rot{ + "Rotate Euler by Euler/Point", [](const float3 &input, const float3 &rotation) { + float input_mat[3][3]; + eul_to_mat3(input_mat, input); + float rot_mat[3][3]; + eul_to_mat3(rot_mat, rotation); + float mat_res[3][3]; + mul_m3_m3m3(mat_res, input_mat, rot_mat); + float3 result; + mat3_to_eul(result, mat_res); + return result; + }}; + static fn::CustomMF_SI_SI_SI_SO<float3, float3, float, float3> point_AA_rot{ + "Rotate Euler by AxisAngle/Point", [](const float3 &input, const float3 &axis, float angle) { + float input_mat[3][3]; + eul_to_mat3(input_mat, input); + float rot_mat[3][3]; + axis_angle_to_mat3(rot_mat, axis, angle); + float mat_res[3][3]; + mul_m3_m3m3(mat_res, input_mat, rot_mat); + float3 result; + mat3_to_eul(result, mat_res); + return result; + }}; + short type = bnode.custom1; + short space = bnode.custom2; + if (type == FN_NODE_ROTATE_EULER_TYPE_AXIS_ANGLE) { + return space == FN_NODE_ROTATE_EULER_SPACE_OBJECT ? &obj_AA_rot : &point_AA_rot; + } + if (type == FN_NODE_ROTATE_EULER_TYPE_EULER) { + return space == FN_NODE_ROTATE_EULER_SPACE_OBJECT ? &obj_euler_rot : &point_euler_rot; + } + BLI_assert_unreachable(); + return nullptr; +} + +static void fn_node_rotate_euler_build_multi_function(NodeMultiFunctionBuilder &builder) +{ + const fn::MultiFunction *fn = get_multi_function(builder.node()); + builder.set_matching_fn(fn); +} + +} // namespace blender::nodes + +void register_node_type_fn_rotate_euler() +{ + static bNodeType ntype; + fn_node_type_base(&ntype, FN_NODE_ROTATE_EULER, "Rotate Euler", NODE_CLASS_CONVERTER, 0); + ntype.declare = blender::nodes::fn_node_rotate_euler_declare; + ntype.draw_buttons = blender::nodes::fn_node_rotate_euler_layout; + node_type_update(&ntype, blender::nodes::fn_node_rotate_euler_update); + ntype.build_multi_function = blender::nodes::fn_node_rotate_euler_build_multi_function; + nodeRegisterType(&ntype); +} |