Gaussian blur node.

This commit is contained in:
Relintai 2021-10-24 00:44:02 +02:00
parent 61c6ea476e
commit a5e81bc69c
2 changed files with 244 additions and 232 deletions

View File

@ -563,242 +563,34 @@ const Commons = preload("res://addons/mat_maker_gd/nodes/common/commons.gd")
#emboss.mmg
#Creates highlights and shadows from an input heightmap
#{
# "connections": [
# {
# "from": "gen_inputs",
# "from_port": 0,
# "to": "buffer",
# "to_port": 0
# },
# {
# "from": "buffer",
# "from_port": 0,
# "to": "598",
# "to_port": 0
# },
# {
# "from": "598",
# "from_port": 0,
# "to": "gen_outputs",
# "to_port": 0
# }
# ],
# "nodes": [
# {
# "name": "buffer",
# "node_position": {
# "x": -65.493774,
# "y": -609.5
# },
# "parameters": {
# "lod": 0,
# "size": 9
# },
# "seed_value": 10109,
# "type": "buffer"
# },
# {
# "name": "598",
# "node_position": {
# "x": -77.579605,
# "y": -529.738281
# },
# "parameters": {
# "amount": 5,
# "angle": 0,
# "size": 9,
# "width": 1
# },
# "shader_model": {
# "code": "",
# "global": "",
# "includes": [
# ""
# ],
# "inputs": [
# {
# "default": "0.0",
# "function": true,
# "label": "",
# "name": "in",
# "type": "f"
# }
# ],
# "instance": "float $(name)_fct(vec2 uv) {\n\tfloat pixels = max(1.0, $width);\n\tfloat e = 1.0/$size;\n\tfloat rv = 0.0;\n\tfor (float dx = -pixels; dx <= pixels; dx += 1.0) {\n\t\tfor (float dy = -pixels; dy <= pixels; dy += 1.0) {\n\t\t\tif (abs(dx) > 0.5 || abs(dy) > 0.5) {\n\t\t\t\trv += $in(uv+e*vec2(dx, dy))*cos(atan(dy, dx)-$angle*3.14159265359/180.0)/length(vec2(dx, dy));\n\t\t\t}\n\t\t}\n\t}\n\treturn $amount*rv/pixels+0.5;\n}",
# "name": "Emboss",
# "outputs": [
# {
# "f": "$(name)_fct($uv)",
# "type": "f"
# }
# ],
# "parameters": [
# {
# "default": 9,
# "first": 6,
# "label": "Size",
# "last": 12,
# "name": "size",
# "type": "size"
# },
# {
# "control": "None",
# "default": 0,
# "label": "Angle",
# "max": 180,
# "min": -180,
# "name": "angle",
# "step": 0.1,
# "type": "float"
# },
# {
# "control": "None",
# "default": 1,
# "label": "Amount",
# "max": 10,
# "min": 0,
# "name": "amount",
# "step": 0.1,
# "type": "float"
# },
# {
# "control": "None",
# "default": 1,
# "label": "Width",
# "max": 5,
# "min": 1,
# "name": "width",
# "step": 1,
# "type": "float"
# }
# ]
# },
# "type": "shader"
# },
# {
# "name": "gen_inputs",
# "node_position": {
# "x": -461.57959,
# "y": -574.119141
# },
# "parameters": {
#float $(name)_fct(vec2 uv) {
# float pixels = max(1.0, $width);
# float e = 1.0/$size;
# float rv = 0.0;
#
# },
# "ports": [
# {
# "group_size": 0,
# "longdesc": "The input height map",
# "name": "port0",
# "shortdesc": "Input",
# "type": "f"
# }
# ],
# "type": "ios"
# },
# {
# "name": "gen_outputs",
# "node_position": {
# "x": 187.506226,
# "y": -557.119141
# },
# "parameters": {
#
# },
# "ports": [
# {
# "group_size": 0,
# "longdesc": "The generated image",
# "name": "port0",
# "shortdesc": "Output",
# "type": "f"
# }
# ],
# "type": "ios"
# },
# {
# "name": "gen_parameters",
# "node_position": {
# "x": -111.036682,
# "y": -777.5
# },
# "parameters": {
# "param0": 9,
# "param1": 0,
# "param2": 5,
# "param3": 1
# },
# "type": "remote",
# "widgets": [
# {
# "label": "Size",
# "linked_widgets": [
# {
# "node": "buffer",
# "widget": "size"
# },
# {
# "node": "598",
# "widget": "size"
# }
# ],
# "longdesc": "The resolution of the input image",
# "name": "param0",
# "shortdesc": "Size",
# "type": "linked_control"
# },
# {
# "label": "Angle",
# "linked_widgets": [
# {
# "node": "598",
# "widget": "angle"
# }
# ],
# "longdesc": "The angle of the simulated light",
# "name": "param1",
# "shortdesc": "Angle",
# "type": "linked_control"
# },
# {
# "label": "Amount",
# "linked_widgets": [
# {
# "node": "598",
# "widget": "amount"
# }
# ],
# "longdesc": "The strength of the emboss effect",
# "name": "param2",
# "shortdesc": "Strength",
# "type": "linked_control"
# },
# {
# "label": "Width",
# "linked_widgets": [
# {
# "node": "598",
# "widget": "width"
# }
# ],
# "longdesc": "The width (in pixels) of the area sampled for each pixel",
# "name": "param3",
# "shortdesc": "Width",
# "type": "linked_control"
# }
# ]
# for (float dx = -pixels; dx <= pixels; dx += 1.0) {
# for (float dy = -pixels; dy <= pixels; dy += 1.0) {
# if (abs(dx) > 0.5 || abs(dy) > 0.5) {
# rv += $in(uv+e*vec2(dx, dy))*cos(atan(dy, dx)-$angle*3.14159265359/180.0)/length(vec2(dx, dy));
# }
# }
# ],
# "parameters": {
# "param0": 9,
# "param1": 0,
# "param2": 5,
# "param3": 1
# },
# "shortdesc": "Emboss",
# "type": "graph"
# }
#
# return $amount*rv/pixels+0.5;
#}
#Outputs:
#Output - (float)
#$(name)_fct($uv)
#Inputs:
#input, float, default 0
#size, int (image size)
#angle, float, min: -180, max: 180, default: 0, step: 0.1
#amount, float, min: 0, max: 10, default: 1, step: 0.1
#width, float, min: 1, max: 5, default: 1, step: 1
#----------------------
#invert.mmg
#A filter that inverts the R, G, and B channels of its input while keeping the A channel unchanged

View File

@ -0,0 +1,220 @@
tool
extends MMNode
var Filter = preload("res://addons/mat_maker_gd/nodes/common/filter.gd")
export(Resource) var image : Resource
export(Resource) var input : Resource
export(Resource) var sigma : Resource
export(int, "Both,X,Y") var direction : int = 0
var size : int = 0
func _init_properties():
if !image:
image = MMNodeUniversalProperty.new()
image.default_type = MMNodeUniversalProperty.MMNodeUniversalPropertyDefaultType.DEFAULT_TYPE_IMAGE
image.output_slot_type = MMNodeUniversalProperty.SlotTypes.SLOT_TYPE_IMAGE
if !input:
input = MMNodeUniversalProperty.new()
input.default_type = MMNodeUniversalProperty.MMNodeUniversalPropertyDefaultType.DEFAULT_TYPE_COLOR
input.set_default_value(1)
input.input_slot_type = MMNodeUniversalProperty.SlotTypes.SLOT_TYPE_UNIVERSAL
input.slot_name = ">>> Input1 "
if !sigma:
sigma = MMNodeUniversalProperty.new()
sigma.default_type = MMNodeUniversalProperty.MMNodeUniversalPropertyDefaultType.DEFAULT_TYPE_FLOAT
sigma.set_default_value(50)
sigma.input_slot_type = MMNodeUniversalProperty.SlotTypes.SLOT_TYPE_UNIVERSAL
sigma.slot_name = "Sigma"
register_input_property(input)
register_output_property(image)
register_input_property(sigma)
func _register_methods(mm_graph_node) -> void:
mm_graph_node.add_slot_texture_universal(image)
mm_graph_node.add_slot_label_universal(input)
mm_graph_node.add_slot_int_universal(sigma)
mm_graph_node.add_slot_enum("get_direction", "set_direction", "Direction", [ "Both", "X", "Y" ])
func _render(material) -> void:
size = max(material.image_size.x, material.image_size.y)
var img : Image = render_image(material)
image.set_value(img)
func render_image(material) -> Image:
var img : Image = Image.new()
img.create(material.image_size.x, material.image_size.y, false, Image.FORMAT_RGBA8)
img.lock()
var w : float = img.get_width()
var h : float = img.get_width()
var pseed : float = randf() + randi()
if direction == 0:
for x in range(img.get_width()):
for y in range(img.get_height()):
var v : Vector2 = Vector2(x / w, y / h)
var col : Color = get_value_x(v, pseed)
img.set_pixel(x, y, col)
img.unlock()
image.set_value(img)
var image2 : Image = Image.new()
image2.create(material.image_size.x, material.image_size.y, false, Image.FORMAT_RGBA8)
image2.lock()
for x in range(img.get_width()):
for y in range(img.get_height()):
var v : Vector2 = Vector2(x / w, y / h)
var col : Color = get_value_y_img(v, pseed)
image2.set_pixel(x, y, col)
image2.unlock()
return image2
if direction == 1:
for x in range(img.get_width()):
for y in range(img.get_height()):
var v : Vector2 = Vector2(x / w, y / h)
var col : Color = get_value_x(v, pseed)
img.set_pixel(x, y, col)
if direction == 2:
for x in range(img.get_width()):
for y in range(img.get_height()):
var v : Vector2 = Vector2(x / w, y / h)
var col : Color = get_value_y(v, pseed)
img.set_pixel(x, y, col)
img.unlock()
return img
func get_value_x(uv : Vector2, pseed : int) -> Color:
var sig_def : float = sigma.get_default_value(uv)
var sig : float = sigma.get_value(uv)
return gaussian_blur_x(uv, size, sig_def, sig)
func get_value_y(uv : Vector2, pseed : int) -> Color:
var sig_def : float = sigma.get_default_value(uv)
var sig : float = sigma.get_value(uv)
return gaussian_blur_y(uv, size, sig_def, sig)
func get_value_y_img(uv : Vector2, pseed : int) -> Color:
var sig_def : float = sigma.get_default_value(uv)
var sig : float = sigma.get_value(uv)
return gaussian_blur_y_img(uv, size, sig_def, sig)
func get_direction() -> int:
return direction
func set_direction(val : int) -> void:
direction = val
set_dirty(true)
#----------------------
#gaussian_blur_x.mmg
#vec4 $(name)_fct(vec2 uv) {
# float e = 1.0 / $size;
# vec4 rv = vec4(0.0);
# float sum = 0.0;
# float sigma = max(0.000001, $sigma * $amount(uv));
#
# for (float i = -50.0; i <= 50.0; i += 1.0) {
# float coef = exp(-0.5 * (pow(i / sigma, 2.0))) / (6.28318530718 * sigma * sigma);
# rv += $in(uv+vec2(i*e, 0.0))*coef;
# sum += coef;
# }
#
# return rv/sum;
#}
func gaussian_blur_x(uv : Vector2, psize : float, psigma : float, pamount : float) -> Color:
var e : float = 1.0 / psize
var rv : Color = Color()
var sum : float = 0.0
var sigma : float = max(0.000001, psigma * pamount)#pamount(uv))
var i : float = -50
while i <= 50: #for (float i = -50.0; i <= 50.0; i += 1.0) {
var coef : float = exp(-0.5 * (pow(i / sigma, 2.0))) / (6.28318530718 * sigma * sigma)
rv += input.get_value(uv + Vector2(i*e, 0.0)) * coef
sum += coef
i += 1
return rv / sum;
#----------------------
#gaussian_blur_y.mmg
#vec4 $(name)_fct(vec2 uv) {
# float e = 1.0/$size;
# vec4 rv = vec4(0.0);
# float sum = 0.0;
# float sigma = max(0.000001, $sigma*$amount(uv));
# for (float i = -50.0; i <= 50.0; i += 1.0) {
# float coef = exp(-0.5 * (pow(i / sigma, 2.0))) / (6.28318530718*sigma*sigma);
# rv += $in(uv+vec2(0.0, i*e))*coef;
# sum += coef;
# }
#
# return rv/sum;
#}
func gaussian_blur_y(uv : Vector2, psize : float, psigma : float, pamount : float) -> Color:
var e : float = 1.0 / psize
var rv : Color = Color()
var sum : float = 0.0
var sigma : float = max(0.000001, psigma * pamount)#pamount(uv))
var i : float = -50
while i <= 50: #for (float i = -50.0; i <= 50.0; i += 1.0) {
var coef : float = exp(-0.5 * (pow(i / sigma, 2.0))) / (6.28318530718 * sigma * sigma)
rv += input.get_value(uv + Vector2(0.0, i * e)) * coef
sum += coef
i += 1
return rv / sum;
func gaussian_blur_y_img(uv : Vector2, psize : float, psigma : float, pamount : float) -> Color:
var e : float = 1.0 / psize
var rv : Color = Color()
var sum : float = 0.0
var sigma : float = max(0.000001, psigma * pamount)#pamount(uv))
var i : float = -50
while i <= 50: #for (float i = -50.0; i <= 50.0; i += 1.0) {
var coef : float = exp(-0.5 * (pow(i / sigma, 2.0))) / (6.28318530718 * sigma * sigma)
rv += image.get_value(uv + Vector2(0.0, i * e)) * coef
sum += coef
i += 1
return rv / sum;