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/nodes/shader/nodes/node_shader_curves.cc')
-rw-r--r--source/blender/nodes/shader/nodes/node_shader_curves.cc219
1 files changed, 157 insertions, 62 deletions
diff --git a/source/blender/nodes/shader/nodes/node_shader_curves.cc b/source/blender/nodes/shader/nodes/node_shader_curves.cc
index 887cc84bb76..bce59a60033 100644
--- a/source/blender/nodes/shader/nodes/node_shader_curves.cc
+++ b/source/blender/nodes/shader/nodes/node_shader_curves.cc
@@ -21,33 +21,16 @@
* \ingroup shdnodes
*/
-#include "node_shader_util.h"
+#include "node_shader_util.hh"
-namespace blender::nodes {
+namespace blender::nodes::node_shader_curves_cc {
static void sh_node_curve_vec_declare(NodeDeclarationBuilder &b)
{
b.is_function_node();
- b.add_input<decl::Float>("Fac").min(0.0f).max(1.0f).default_value(1.0f).subtype(PROP_FACTOR);
- b.add_input<decl::Vector>("Vector").min(-1.0f).max(1.0f);
- b.add_output<decl::Vector>("Vector");
-};
-
-} // namespace blender::nodes
-
-static void node_shader_exec_curve_vec(void *UNUSED(data),
- int UNUSED(thread),
- bNode *node,
- bNodeExecData *UNUSED(execdata),
- bNodeStack **in,
- bNodeStack **out)
-{
- float vec[3];
-
- /* stack order input: vec */
- /* stack order output: vec */
- nodestack_get_vec(vec, SOCK_VECTOR, in[1]);
- BKE_curvemapping_evaluate3F((CurveMapping *)node->storage, out[0]->vec, vec);
+ b.add_input<decl::Float>(N_("Fac")).min(0.0f).max(1.0f).default_value(1.0f).subtype(PROP_FACTOR);
+ b.add_input<decl::Vector>(N_("Vector")).min(-1.0f).max(1.0f);
+ b.add_output<decl::Vector>(N_("Vector"));
}
static void node_shader_init_curve_vec(bNodeTree *UNUSED(ntree), bNode *node)
@@ -152,53 +135,35 @@ static void sh_node_curve_vec_build_multi_function(
builder.construct_and_set_matching_fn<CurveVecFunction>(*cumap);
}
-void register_node_type_sh_curve_vec(void)
+} // namespace blender::nodes::node_shader_curves_cc
+
+void register_node_type_sh_curve_vec()
{
+ namespace file_ns = blender::nodes::node_shader_curves_cc;
+
static bNodeType ntype;
- sh_fn_node_type_base(&ntype, SH_NODE_CURVE_VEC, "Vector Curves", NODE_CLASS_OP_VECTOR, 0);
- ntype.declare = blender::nodes::sh_node_curve_vec_declare;
- node_type_init(&ntype, node_shader_init_curve_vec);
+ sh_fn_node_type_base(&ntype, SH_NODE_CURVE_VEC, "Vector Curves", NODE_CLASS_OP_VECTOR);
+ ntype.declare = file_ns::sh_node_curve_vec_declare;
+ node_type_init(&ntype, file_ns::node_shader_init_curve_vec);
node_type_size_preset(&ntype, NODE_SIZE_LARGE);
node_type_storage(&ntype, "CurveMapping", node_free_curves, node_copy_curves);
- node_type_exec(&ntype, node_initexec_curves, nullptr, node_shader_exec_curve_vec);
- node_type_gpu(&ntype, gpu_shader_curve_vec);
- ntype.build_multi_function = sh_node_curve_vec_build_multi_function;
+ node_type_gpu(&ntype, file_ns::gpu_shader_curve_vec);
+ ntype.build_multi_function = file_ns::sh_node_curve_vec_build_multi_function;
nodeRegisterType(&ntype);
}
/* **************** CURVE RGB ******************** */
-namespace blender::nodes {
+namespace blender::nodes::node_shader_curves_cc {
static void sh_node_curve_rgb_declare(NodeDeclarationBuilder &b)
{
- b.add_input<decl::Float>("Fac").min(0.0f).max(1.0f).default_value(1.0f).subtype(PROP_FACTOR);
- b.add_input<decl::Color>("Color").default_value({1.0f, 1.0f, 1.0f, 1.0f});
- b.add_output<decl::Color>("Color");
-};
-
-} // namespace blender::nodes
-
-static void node_shader_exec_curve_rgb(void *UNUSED(data),
- int UNUSED(thread),
- bNode *node,
- bNodeExecData *UNUSED(execdata),
- bNodeStack **in,
- bNodeStack **out)
-{
- float vec[3];
- float fac;
-
- /* stack order input: vec */
- /* stack order output: vec */
- nodestack_get_vec(&fac, SOCK_FLOAT, in[0]);
- nodestack_get_vec(vec, SOCK_VECTOR, in[1]);
- BKE_curvemapping_evaluateRGBF((CurveMapping *)node->storage, out[0]->vec, vec);
- if (fac != 1.0f) {
- interp_v3_v3v3(out[0]->vec, vec, out[0]->vec, fac);
- }
+ b.is_function_node();
+ b.add_input<decl::Float>(N_("Fac")).min(0.0f).max(1.0f).default_value(1.0f).subtype(PROP_FACTOR);
+ b.add_input<decl::Color>(N_("Color")).default_value({1.0f, 1.0f, 1.0f, 1.0f});
+ b.add_output<decl::Color>(N_("Color"));
}
static void node_shader_init_curve_rgb(bNodeTree *UNUSED(ntree), bNode *node)
@@ -328,18 +293,148 @@ static void sh_node_curve_rgb_build_multi_function(
builder.construct_and_set_matching_fn<CurveRGBFunction>(*cumap);
}
-void register_node_type_sh_curve_rgb(void)
+} // namespace blender::nodes::node_shader_curves_cc
+
+void register_node_type_sh_curve_rgb()
+{
+ namespace file_ns = blender::nodes::node_shader_curves_cc;
+
+ static bNodeType ntype;
+
+ sh_fn_node_type_base(&ntype, SH_NODE_CURVE_RGB, "RGB Curves", NODE_CLASS_OP_COLOR);
+ ntype.declare = file_ns::sh_node_curve_rgb_declare;
+ node_type_init(&ntype, file_ns::node_shader_init_curve_rgb);
+ node_type_size_preset(&ntype, NODE_SIZE_LARGE);
+ node_type_storage(&ntype, "CurveMapping", node_free_curves, node_copy_curves);
+ node_type_gpu(&ntype, file_ns::gpu_shader_curve_rgb);
+ ntype.build_multi_function = file_ns::sh_node_curve_rgb_build_multi_function;
+
+ nodeRegisterType(&ntype);
+}
+
+/* **************** CURVE FLOAT ******************** */
+
+namespace blender::nodes::node_shader_curves_cc {
+
+static void sh_node_curve_float_declare(NodeDeclarationBuilder &b)
+{
+ b.is_function_node();
+ b.add_input<decl::Float>(N_("Factor"))
+ .min(0.0f)
+ .max(1.0f)
+ .default_value(1.0f)
+ .subtype(PROP_FACTOR);
+ b.add_input<decl::Float>(N_("Value")).default_value(1.0f).is_default_link_socket();
+ b.add_output<decl::Float>(N_("Value"));
+}
+
+static void node_shader_init_curve_float(bNodeTree *UNUSED(ntree), bNode *node)
+{
+ node->storage = BKE_curvemapping_add(1, 0.0f, 0.0f, 1.0f, 1.0f);
+}
+
+static int gpu_shader_curve_float(GPUMaterial *mat,
+ bNode *node,
+ bNodeExecData *UNUSED(execdata),
+ GPUNodeStack *in,
+ GPUNodeStack *out)
+{
+ float *array, layer;
+ int size;
+
+ CurveMapping *cumap = (CurveMapping *)node->storage;
+
+ BKE_curvemapping_table_F(cumap, &array, &size);
+ GPUNodeLink *tex = GPU_color_band(mat, size, array, &layer);
+
+ float ext_xyz[4];
+ float range_x;
+
+ const CurveMap *cm = &cumap->cm[0];
+ ext_xyz[0] = cm->mintable;
+ ext_xyz[2] = cm->maxtable;
+ range_x = 1.0f / max_ff(1e-8f, cm->maxtable - cm->mintable);
+ /* Compute extrapolation gradients. */
+ if ((cumap->flag & CUMA_EXTEND_EXTRAPOLATE) != 0) {
+ ext_xyz[1] = (cm->ext_in[0] != 0.0f) ? (cm->ext_in[1] / (cm->ext_in[0] * range_x)) : 1e8f;
+ ext_xyz[3] = (cm->ext_out[0] != 0.0f) ? (cm->ext_out[1] / (cm->ext_out[0] * range_x)) : 1e8f;
+ }
+ else {
+ ext_xyz[1] = 0.0f;
+ ext_xyz[3] = 0.0f;
+ }
+ return GPU_stack_link(mat,
+ node,
+ "curve_float",
+ in,
+ out,
+ tex,
+ GPU_constant(&layer),
+ GPU_uniform(&range_x),
+ GPU_uniform(ext_xyz));
+}
+
+class CurveFloatFunction : public blender::fn::MultiFunction {
+ private:
+ const CurveMapping &cumap_;
+
+ public:
+ CurveFloatFunction(const CurveMapping &cumap) : cumap_(cumap)
+ {
+ static blender::fn::MFSignature signature = create_signature();
+ this->set_signature(&signature);
+ }
+
+ static blender::fn::MFSignature create_signature()
+ {
+ blender::fn::MFSignatureBuilder signature{"Curve Float"};
+ signature.single_input<float>("Factor");
+ signature.single_input<float>("Value");
+ signature.single_output<float>("Value");
+ return signature.build();
+ }
+
+ void call(blender::IndexMask mask,
+ blender::fn::MFParams params,
+ blender::fn::MFContext UNUSED(context)) const override
+ {
+ const blender::VArray<float> &fac = params.readonly_single_input<float>(0, "Factor");
+ const blender::VArray<float> &val_in = params.readonly_single_input<float>(1, "Value");
+ blender::MutableSpan<float> val_out = params.uninitialized_single_output<float>(2, "Value");
+
+ for (int64_t i : mask) {
+ val_out[i] = BKE_curvemapping_evaluateF(&cumap_, 0, val_in[i]);
+ if (fac[i] != 1.0f) {
+ val_out[i] = (1.0f - fac[i]) * val_in[i] + fac[i] * val_out[i];
+ }
+ }
+ }
+};
+
+static void sh_node_curve_float_build_multi_function(
+ blender::nodes::NodeMultiFunctionBuilder &builder)
+{
+ bNode &bnode = builder.node();
+ CurveMapping *cumap = (CurveMapping *)bnode.storage;
+ BKE_curvemapping_init(cumap);
+ builder.construct_and_set_matching_fn<CurveFloatFunction>(*cumap);
+}
+
+} // namespace blender::nodes::node_shader_curves_cc
+
+void register_node_type_sh_curve_float()
{
+ namespace file_ns = blender::nodes::node_shader_curves_cc;
+
static bNodeType ntype;
- sh_fn_node_type_base(&ntype, SH_NODE_CURVE_RGB, "RGB Curves", NODE_CLASS_OP_COLOR, 0);
- ntype.declare = blender::nodes::sh_node_curve_rgb_declare;
- node_type_init(&ntype, node_shader_init_curve_rgb);
+ sh_fn_node_type_base(&ntype, SH_NODE_CURVE_FLOAT, "Float Curve", NODE_CLASS_CONVERTER);
+ ntype.declare = file_ns::sh_node_curve_float_declare;
+ node_type_init(&ntype, file_ns::node_shader_init_curve_float);
node_type_size_preset(&ntype, NODE_SIZE_LARGE);
node_type_storage(&ntype, "CurveMapping", node_free_curves, node_copy_curves);
- node_type_exec(&ntype, node_initexec_curves, nullptr, node_shader_exec_curve_rgb);
- node_type_gpu(&ntype, gpu_shader_curve_rgb);
- ntype.build_multi_function = sh_node_curve_rgb_build_multi_function;
+ node_type_gpu(&ntype, file_ns::gpu_shader_curve_float);
+ ntype.build_multi_function = file_ns::sh_node_curve_float_build_multi_function;
nodeRegisterType(&ntype);
}