Adds UVFunc
for panning/scaling on UV's to VisualShader's.
This commit is contained in:
parent
34fc33d192
commit
b2d2822a39
8 changed files with 274 additions and 0 deletions
|
@ -9,6 +9,13 @@
|
|||
<link title="VisualShaders">https://docs.godotengine.org/en/latest/tutorials/shading/visual_shaders.html</link>
|
||||
</tutorials>
|
||||
<methods>
|
||||
<method name="clear_default_input_values">
|
||||
<return type="void">
|
||||
</return>
|
||||
<description>
|
||||
Clears the default input ports value.
|
||||
</description>
|
||||
</method>
|
||||
<method name="get_default_input_values" qualifiers="const">
|
||||
<return type="Array">
|
||||
</return>
|
||||
|
@ -25,6 +32,15 @@
|
|||
Returns the default value of the input [code]port[/code].
|
||||
</description>
|
||||
</method>
|
||||
<method name="remove_input_port_default_value">
|
||||
<return type="void">
|
||||
</return>
|
||||
<argument index="0" name="port" type="int">
|
||||
</argument>
|
||||
<description>
|
||||
Removes the default value of the input [code]port[/code].
|
||||
</description>
|
||||
</method>
|
||||
<method name="set_default_input_values">
|
||||
<return type="void">
|
||||
</return>
|
||||
|
|
28
doc/classes/VisualShaderNodeUVFunc.xml
Normal file
28
doc/classes/VisualShaderNodeUVFunc.xml
Normal file
|
@ -0,0 +1,28 @@
|
|||
<?xml version="1.0" encoding="UTF-8" ?>
|
||||
<class name="VisualShaderNodeUVFunc" inherits="VisualShaderNode" version="4.0">
|
||||
<brief_description>
|
||||
Contains functions to modify texture coordinates ([code]uv[/code]) to be used within the visual shader graph.
|
||||
</brief_description>
|
||||
<description>
|
||||
</description>
|
||||
<tutorials>
|
||||
</tutorials>
|
||||
<methods>
|
||||
</methods>
|
||||
<members>
|
||||
<member name="function" type="int" setter="set_function" getter="get_function" enum="VisualShaderNodeUVFunc.Function" default="0">
|
||||
A function to be applied to the texture coordinates. See [enum Function] for options.
|
||||
</member>
|
||||
</members>
|
||||
<constants>
|
||||
<constant name="FUNC_PANNING" value="0" enum="Function">
|
||||
Translates [code]uv[/code] by using [code]scale[/code] and [code]offset[/code] values using the following formula: [code]uv = uv + offset * scale[/code]. [code]uv[/code] port is connected to [code]UV[/code] built-in by default.
|
||||
</constant>
|
||||
<constant name="FUNC_SCALING" value="1" enum="Function">
|
||||
Scales [code]uv[/uv] by using [code]scale[/code] and [code]pivot[/code] values using the following formula: [code]uv = (uv - pivot) * scale + pivot[/code]. [code]uv[/code] port is connected to [code]UV[/code] built-in by default.
|
||||
</constant>
|
||||
<constant name="FUNC_MAX" value="2" enum="Function">
|
||||
Represents the size of the [enum Function] enum.
|
||||
</constant>
|
||||
</constants>
|
||||
</class>
|
|
@ -2081,6 +2081,16 @@ void VisualShaderEditor::_setup_node(VisualShaderNode *p_node, int p_op_idx) {
|
|||
}
|
||||
}
|
||||
|
||||
//UV_FUNC
|
||||
{
|
||||
VisualShaderNodeUVFunc *uvFunc = Object::cast_to<VisualShaderNodeUVFunc>(p_node);
|
||||
|
||||
if (uvFunc) {
|
||||
uvFunc->set_function((VisualShaderNodeUVFunc::Function)p_op_idx);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// IS
|
||||
{
|
||||
VisualShaderNodeIs *is = Object::cast_to<VisualShaderNodeIs>(p_node);
|
||||
|
@ -4244,6 +4254,8 @@ VisualShaderEditor::VisualShaderEditor() {
|
|||
|
||||
// TEXTURES
|
||||
|
||||
add_options.push_back(AddOption("UVFunc", "Textures", "Common", "VisualShaderNodeUVFunc", TTR("Function to be applied on texture coordinates."), -1, VisualShaderNode::PORT_TYPE_VECTOR));
|
||||
|
||||
cubemap_node_option_idx = add_options.size();
|
||||
add_options.push_back(AddOption("CubeMap", "Textures", "Functions", "VisualShaderNodeCubemap", TTR("Perform the cubic texture lookup."), -1, -1));
|
||||
curve_node_option_idx = add_options.size();
|
||||
|
@ -4254,6 +4266,8 @@ VisualShaderEditor::VisualShaderEditor() {
|
|||
add_options.push_back(AddOption("Texture2DArray", "Textures", "Functions", "VisualShaderNodeTexture2DArray", TTR("Perform the 2D-array texture lookup."), -1, -1, -1, -1, -1));
|
||||
texture3d_node_option_idx = add_options.size();
|
||||
add_options.push_back(AddOption("Texture3D", "Textures", "Functions", "VisualShaderNodeTexture3D", TTR("Perform the 3D texture lookup."), -1, -1));
|
||||
add_options.push_back(AddOption("UVPanning", "Textures", "Functions", "VisualShaderNodeUVFunc", TTR("Apply panning function on texture coordinates."), VisualShaderNodeUVFunc::FUNC_PANNING, VisualShaderNode::PORT_TYPE_VECTOR));
|
||||
add_options.push_back(AddOption("UVScaling", "Textures", "Functions", "VisualShaderNodeUVFunc", TTR("Apply scaling function on texture coordinates."), VisualShaderNodeUVFunc::FUNC_SCALING, VisualShaderNode::PORT_TYPE_VECTOR));
|
||||
|
||||
add_options.push_back(AddOption("CubeMapUniform", "Textures", "Variables", "VisualShaderNodeCubemapUniform", TTR("Cubic texture uniform lookup."), -1, -1));
|
||||
add_options.push_back(AddOption("TextureUniform", "Textures", "Variables", "VisualShaderNodeTextureUniform", TTR("2D texture uniform lookup."), -1, -1));
|
||||
|
|
|
@ -560,6 +560,7 @@ void register_scene_types() {
|
|||
ClassDB::register_class<VisualShaderNodeVectorFunc>();
|
||||
ClassDB::register_class<VisualShaderNodeColorFunc>();
|
||||
ClassDB::register_class<VisualShaderNodeTransformFunc>();
|
||||
ClassDB::register_class<VisualShaderNodeUVFunc>();
|
||||
ClassDB::register_class<VisualShaderNodeDotProduct>();
|
||||
ClassDB::register_class<VisualShaderNodeVectorLen>();
|
||||
ClassDB::register_class<VisualShaderNodeDeterminant>();
|
||||
|
|
|
@ -60,6 +60,20 @@ Variant VisualShaderNode::get_input_port_default_value(int p_port) const {
|
|||
return Variant();
|
||||
}
|
||||
|
||||
void VisualShaderNode::remove_input_port_default_value(int p_port) {
|
||||
if (default_input_values.has(p_port)) {
|
||||
default_input_values.erase(p_port);
|
||||
emit_changed();
|
||||
}
|
||||
}
|
||||
|
||||
void VisualShaderNode::clear_default_input_values() {
|
||||
if (!default_input_values.is_empty()) {
|
||||
default_input_values.clear();
|
||||
emit_changed();
|
||||
}
|
||||
}
|
||||
|
||||
bool VisualShaderNode::is_port_separator(int p_index) const {
|
||||
return false;
|
||||
}
|
||||
|
@ -220,6 +234,9 @@ void VisualShaderNode::_bind_methods() {
|
|||
ClassDB::bind_method(D_METHOD("set_input_port_default_value", "port", "value"), &VisualShaderNode::set_input_port_default_value);
|
||||
ClassDB::bind_method(D_METHOD("get_input_port_default_value", "port"), &VisualShaderNode::get_input_port_default_value);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("remove_input_port_default_value", "port"), &VisualShaderNode::remove_input_port_default_value);
|
||||
ClassDB::bind_method(D_METHOD("clear_default_input_values"), &VisualShaderNode::clear_default_input_values);
|
||||
|
||||
ClassDB::bind_method(D_METHOD("set_default_input_values", "values"), &VisualShaderNode::set_default_input_values);
|
||||
ClassDB::bind_method(D_METHOD("get_default_input_values"), &VisualShaderNode::get_default_input_values);
|
||||
|
||||
|
@ -373,6 +390,18 @@ void VisualShaderNodeCustom::set_default_input_values(const Array &p_values) {
|
|||
}
|
||||
}
|
||||
|
||||
void VisualShaderNodeCustom::remove_input_port_default_value(int p_port) {
|
||||
if (!is_initialized) {
|
||||
VisualShaderNode::remove_input_port_default_value(p_port);
|
||||
}
|
||||
}
|
||||
|
||||
void VisualShaderNodeCustom::clear_default_input_values() {
|
||||
if (!is_initialized) {
|
||||
VisualShaderNode::clear_default_input_values();
|
||||
}
|
||||
}
|
||||
|
||||
void VisualShaderNodeCustom::_set_input_port_default_value(int p_port, const Variant &p_value) {
|
||||
VisualShaderNode::set_input_port_default_value(p_port, p_value);
|
||||
}
|
||||
|
|
|
@ -230,6 +230,8 @@ public:
|
|||
Variant get_input_port_default_value(int p_port) const; // if NIL (default if node does not set anything) is returned, it means no default value is wanted if disconnected, thus no input var must be supplied (empty string will be supplied)
|
||||
Array get_default_input_values() const;
|
||||
virtual void set_default_input_values(const Array &p_values);
|
||||
virtual void remove_input_port_default_value(int p_port);
|
||||
virtual void clear_default_input_values();
|
||||
|
||||
virtual int get_output_port_count() const = 0;
|
||||
virtual PortType get_output_port_type(int p_port) const = 0;
|
||||
|
@ -305,6 +307,8 @@ protected:
|
|||
|
||||
virtual void set_input_port_default_value(int p_port, const Variant &p_value) override;
|
||||
virtual void set_default_input_values(const Array &p_values) override;
|
||||
virtual void remove_input_port_default_value(int p_port) override;
|
||||
virtual void clear_default_input_values() override;
|
||||
|
||||
protected:
|
||||
void _set_input_port_default_value(int p_port, const Variant &p_value);
|
||||
|
|
|
@ -2499,6 +2499,143 @@ VisualShaderNodeTransformFunc::VisualShaderNodeTransformFunc() {
|
|||
set_input_port_default_value(0, Transform3D());
|
||||
}
|
||||
|
||||
////////////// UV Func
|
||||
|
||||
String VisualShaderNodeUVFunc::get_caption() const {
|
||||
return "UVFunc";
|
||||
}
|
||||
|
||||
int VisualShaderNodeUVFunc::get_input_port_count() const {
|
||||
return 3;
|
||||
}
|
||||
|
||||
VisualShaderNodeUVFunc::PortType VisualShaderNodeUVFunc::get_input_port_type(int p_port) const {
|
||||
switch (p_port) {
|
||||
case 0:
|
||||
[[fallthrough]]; // uv
|
||||
case 1:
|
||||
return PORT_TYPE_VECTOR; // scale
|
||||
case 2:
|
||||
return PORT_TYPE_VECTOR; // offset & pivot
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return PORT_TYPE_SCALAR;
|
||||
}
|
||||
|
||||
String VisualShaderNodeUVFunc::get_input_port_name(int p_port) const {
|
||||
switch (p_port) {
|
||||
case 0:
|
||||
return "uv";
|
||||
case 1:
|
||||
return "scale";
|
||||
case 2:
|
||||
switch (func) {
|
||||
case FUNC_PANNING:
|
||||
return "offset";
|
||||
case FUNC_SCALING:
|
||||
return "pivot";
|
||||
case FUNC_MAX:
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
String VisualShaderNodeUVFunc::get_input_port_default_hint(int p_port) const {
|
||||
if (p_port == 0) {
|
||||
return "UV";
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
int VisualShaderNodeUVFunc::get_output_port_count() const {
|
||||
return 1;
|
||||
}
|
||||
|
||||
VisualShaderNodeUVFunc::PortType VisualShaderNodeUVFunc::get_output_port_type(int p_port) const {
|
||||
return PORT_TYPE_VECTOR;
|
||||
}
|
||||
|
||||
String VisualShaderNodeUVFunc::get_output_port_name(int p_port) const {
|
||||
return "uv";
|
||||
}
|
||||
|
||||
bool VisualShaderNodeUVFunc::is_show_prop_names() const {
|
||||
return true;
|
||||
}
|
||||
|
||||
String VisualShaderNodeUVFunc::generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview) const {
|
||||
String code;
|
||||
|
||||
String uv;
|
||||
if (p_input_vars[0].is_empty()) {
|
||||
uv = "vec3(UV.xy, 0.0)";
|
||||
} else {
|
||||
uv = vformat("%s", p_input_vars[0]);
|
||||
}
|
||||
String scale = vformat("%s", p_input_vars[1]);
|
||||
String offset_pivot = vformat("%s", p_input_vars[2]);
|
||||
|
||||
switch (func) {
|
||||
case FUNC_PANNING: {
|
||||
code += vformat("\t%s = fma(%s, %s, %s);\n", p_output_vars[0], offset_pivot, scale, uv);
|
||||
} break;
|
||||
case FUNC_SCALING: {
|
||||
code += vformat("\t%s = fma((%s - %s), %s, %s);\n", p_output_vars[0], uv, offset_pivot, scale, offset_pivot);
|
||||
} break;
|
||||
case FUNC_MAX:
|
||||
break;
|
||||
}
|
||||
return code;
|
||||
}
|
||||
|
||||
void VisualShaderNodeUVFunc::set_function(VisualShaderNodeUVFunc::Function p_func) {
|
||||
ERR_FAIL_INDEX(int(p_func), FUNC_MAX);
|
||||
if (func == p_func) {
|
||||
return;
|
||||
}
|
||||
func = p_func;
|
||||
|
||||
if (p_func == FUNC_PANNING) {
|
||||
set_input_port_default_value(2, Vector3()); // offset
|
||||
} else { // FUNC_SCALING
|
||||
set_input_port_default_value(2, Vector3(0.5, 0.5, 0.0)); // pivot
|
||||
}
|
||||
emit_changed();
|
||||
}
|
||||
|
||||
VisualShaderNodeUVFunc::Function VisualShaderNodeUVFunc::get_function() const {
|
||||
return func;
|
||||
}
|
||||
|
||||
Vector<StringName> VisualShaderNodeUVFunc::get_editable_properties() const {
|
||||
Vector<StringName> props;
|
||||
props.push_back("function");
|
||||
return props;
|
||||
}
|
||||
|
||||
void VisualShaderNodeUVFunc::_bind_methods() {
|
||||
ClassDB::bind_method(D_METHOD("set_function", "func"), &VisualShaderNodeUVFunc::set_function);
|
||||
ClassDB::bind_method(D_METHOD("get_function"), &VisualShaderNodeUVFunc::get_function);
|
||||
|
||||
ADD_PROPERTY(PropertyInfo(Variant::INT, "function", PROPERTY_HINT_ENUM, "Panning,Scaling"), "set_function", "get_function");
|
||||
|
||||
BIND_ENUM_CONSTANT(FUNC_PANNING);
|
||||
BIND_ENUM_CONSTANT(FUNC_SCALING);
|
||||
BIND_ENUM_CONSTANT(FUNC_MAX);
|
||||
}
|
||||
|
||||
VisualShaderNodeUVFunc::VisualShaderNodeUVFunc() {
|
||||
set_input_port_default_value(1, Vector3(1.0, 1.0, 0.0)); // scale
|
||||
set_input_port_default_value(2, Vector3()); // offset
|
||||
}
|
||||
|
||||
////////////// Dot Product
|
||||
|
||||
String VisualShaderNodeDotProduct::get_caption() const {
|
||||
|
|
|
@ -1018,6 +1018,51 @@ public:
|
|||
|
||||
VARIANT_ENUM_CAST(VisualShaderNodeTransformFunc::Function)
|
||||
|
||||
///////////////////////////////////////
|
||||
/// UV FUNC
|
||||
///////////////////////////////////////
|
||||
|
||||
class VisualShaderNodeUVFunc : public VisualShaderNode {
|
||||
GDCLASS(VisualShaderNodeUVFunc, VisualShaderNode);
|
||||
|
||||
public:
|
||||
enum Function {
|
||||
FUNC_PANNING,
|
||||
FUNC_SCALING,
|
||||
FUNC_MAX,
|
||||
};
|
||||
|
||||
protected:
|
||||
Function func = FUNC_PANNING;
|
||||
|
||||
static void _bind_methods();
|
||||
|
||||
public:
|
||||
virtual String get_caption() const override;
|
||||
|
||||
virtual int get_input_port_count() const override;
|
||||
virtual PortType get_input_port_type(int p_port) const override;
|
||||
virtual String get_input_port_name(int p_port) const override;
|
||||
virtual String get_input_port_default_hint(int p_port) const override;
|
||||
|
||||
virtual int get_output_port_count() const override;
|
||||
virtual PortType get_output_port_type(int p_port) const override;
|
||||
virtual String get_output_port_name(int p_port) const override;
|
||||
|
||||
virtual bool is_show_prop_names() const override;
|
||||
|
||||
virtual String generate_code(Shader::Mode p_mode, VisualShader::Type p_type, int p_id, const String *p_input_vars, const String *p_output_vars, bool p_for_preview = false) const override;
|
||||
|
||||
void set_function(Function p_op);
|
||||
Function get_function() const;
|
||||
|
||||
virtual Vector<StringName> get_editable_properties() const override;
|
||||
|
||||
VisualShaderNodeUVFunc();
|
||||
};
|
||||
|
||||
VARIANT_ENUM_CAST(VisualShaderNodeUVFunc::Function)
|
||||
|
||||
///////////////////////////////////////
|
||||
/// DOT
|
||||
///////////////////////////////////////
|
||||
|
|
Loading…
Reference in a new issue