Merge pull request #34 from Calinou/add-return-type-hints

Add return type hints to all scripts
This commit is contained in:
Rodz Labs 2019-10-21 20:56:30 +02:00 committed by GitHub
commit 448287d2c9
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
57 changed files with 534 additions and 564 deletions

View File

@ -11,42 +11,42 @@ signal parameter_changed
class InputPort:
var generator : MMGenBase = null
var input_index : int = 0
func _init(g : MMGenBase, i : int):
func _init(g : MMGenBase, i : int) -> void:
generator = g
input_index = i
func to_str():
func to_str() -> String:
return generator.name+".in("+str(input_index)+")"
class OutputPort:
var generator : MMGenBase = null
var output_index : int = 0
func _init(g : MMGenBase, o : int):
func _init(g : MMGenBase, o : int) -> void:
generator = g
output_index = o
func to_str():
func to_str() -> String:
return generator.name+".out("+str(output_index)+")"
var position : Vector2 = Vector2(0, 0)
var model = null
var parameters = {}
func _ready():
func _ready() -> void:
init_parameters()
func can_be_deleted() -> bool:
return true
func toggle_editable():
return false
func is_editable():
func toggle_editable() -> bool:
return false
func init_parameters():
func is_editable() -> bool:
return false
func init_parameters() -> void:
for p in get_parameter_defs():
if !parameters.has(p.name):
if p.has("default"):
@ -56,16 +56,16 @@ func init_parameters():
else:
print("No default value for parameter "+p.name)
func set_position(p):
func set_position(p) -> void:
position = p
func get_type():
func get_type() -> String:
return "generic"
func get_type_name():
func get_type_name() -> String:
return "Unnamed"
func get_parameter_defs():
func get_parameter_defs() -> Array:
return []
func set_parameter(n : String, v):
@ -83,16 +83,16 @@ func source_changed(__):
for i in range(get_output_defs().size()):
notify_output_change(i)
func get_input_defs():
func get_input_defs() -> Array:
return []
func get_output_defs():
func get_output_defs() -> Array:
return []
func get_source(input_index : int):
func get_source(input_index : int) -> OutputPort:
return get_parent().get_port_source(name, input_index)
func get_targets(output_index : int):
func get_targets(output_index : int) -> Array:
return get_parent().get_port_targets(name, output_index)
# get the list of outputs that depend on the input whose index is passed as parameter
@ -107,15 +107,15 @@ func get_input_shader(input_index : int):
if source != null:
return source.get_shader()
func get_shader(output_index : int, context):
return get_shader_code("UV", output_index, context);
func get_shader(output_index : int, context) -> Dictionary:
return get_shader_code("UV", output_index, context)
func render(output_index : int, renderer : MMGenRenderer, size : int):
var context : MMGenContext = MMGenContext.new(renderer)
var source = get_shader_code("UV", output_index, context)
while source is GDScriptFunctionState:
source = yield(source, "completed")
if source == null:
if source.empty():
source = { defs="", code="", textures={}, rgba="vec4(0.0)" }
var shader : String = renderer.generate_shader(source)
var result = renderer.render_shader(shader, source.textures, size)
@ -123,11 +123,11 @@ func render(output_index : int, renderer : MMGenRenderer, size : int):
result = yield(result, "completed")
return result
func get_shader_code(uv : String, output_index : int, context : MMGenContext):
func get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var rv = _get_shader_code(uv, output_index, context)
while rv is GDScriptFunctionState:
rv = yield(rv, "completed")
if rv != null:
if !rv.empty():
if !rv.has("f"):
if rv.has("rgb"):
rv.f = "(dot("+rv.rgb+", vec3(1.0))/3.0)"
@ -144,10 +144,10 @@ func get_shader_code(uv : String, output_index : int, context : MMGenContext):
rv.rgba = "vec4("+rv.rgb+", 1.0)"
return rv
func _get_shader_code(__, __, __):
return null
func _get_shader_code(__, __, __) -> Dictionary:
return {}
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
print("cannot save "+name)
return data

View File

@ -4,35 +4,35 @@ class_name MMGenBuffer
"""
Texture generator buffers, that render their input in a specific resolution and provide the result as output.
This is useful when using generators that sample their inputs several times (such as convolutions)
This is useful when using generators that sample their inputs several times (such as convolutions)
"""
var updated : bool = false
func _ready():
func _ready() -> void:
if !parameters.has("size"):
parameters.size = 4
func get_type():
func get_type() -> String:
return "buffer"
func get_type_name():
func get_type_name() -> String:
return "Buffer"
func get_parameter_defs():
func get_parameter_defs() -> Array:
return [ { name="size", type="size", first=4, last=12, default=4 } ]
func get_input_defs():
func get_input_defs() -> Array:
return [ { name="in", type="rgba" } ]
func get_output_defs():
func get_output_defs() -> Array:
return [ { type="rgba" } ]
func source_changed(input_port_index : int):
updated = false
.source_changed(input_port_index)
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var source = get_source(0)
if source != null and !updated:
var result = source.generator.render(source.output_index, context.renderer, pow(2, 4+parameters.size))
@ -47,6 +47,6 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
rv = yield(rv, "completed")
return rv
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.type = "buffer"
return data

View File

@ -9,26 +9,26 @@ Comments to put in the graph
var text : String = "Double-click to write a comment"
var size : Vector2 = Vector2(0, 0)
func _ready():
func _ready() -> void:
if !parameters.has("size"):
parameters.size = 4
func get_type():
func get_type() -> String:
return "comment"
func get_type_name():
func get_type_name() -> String:
return "Comment"
func get_parameter_defs():
func get_parameter_defs() -> Array:
return []
func get_input_defs():
return []
func get_output_defs():
func get_input_defs() -> Array:
return []
func _serialize(data):
func get_output_defs() -> Array:
return []
func _serialize(data: Dictionary) -> Dictionary:
data.type = "comment"
data.text = text
data.size = { x=size.x, y=size.y }

View File

@ -5,13 +5,13 @@ class_name MMGenContext
var renderer : MMGenRenderer
var variants : Dictionary = {}
func _init(r : MMGenRenderer):
func _init(r : MMGenRenderer) -> void:
renderer = r
func has_variant(generator):
func has_variant(generator) -> bool:
return variants.has(generator)
func get_variant(generator, variant):
func get_variant(generator, variant) -> int:
var rv = -1
if variants.has(generator):
rv = variants[generator].find(variant)

View File

@ -4,31 +4,31 @@ class_name MMGenConvolution
var convolution_params : Dictionary = {}
func get_type():
func get_type() -> String:
return "convolution"
func get_type_name():
if convolution_params.has("name"):
func get_type_name() -> String:
if convolution_params.has("name"):
return convolution_params.name
return .get_type_name()
func get_parameter_defs():
func get_parameter_defs() -> Array:
var rv : Array = [ { name="size", type="size", first=4, last=11, default=4 } ]
if convolution_params.has("parameters"):
for p in convolution_params.parameters:
rv.push_back(p)
return rv
func get_input_defs():
func get_input_defs() -> Array:
return [ { name="in", type=convolution_params.input_type } ]
func get_output_defs():
func get_output_defs() -> Array:
return [ { type=convolution_params.output_type } ]
func set_convolution_params(data: Dictionary):
func set_convolution_params(data: Dictionary) -> void:
convolution_params = data
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var genname = "o"+str(get_instance_id())
var epsilon = 1.0/pow(2, 4+parameters.size)
var types = { "rgba": { type="vec4", init="vec4(0.0)" }, "rgb": { type="vec3", init="vec3(0.0)" }, "f": { type="float", init="0.0" } }
@ -167,6 +167,6 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
rv[convolution_params.output_type] = "%s_%d" % [ genname, variant_index ]
return rv
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.convolution_params = convolution_params
return data

View File

@ -8,24 +8,24 @@ var connections = []
var editable = false
func get_type():
func get_type() -> String:
return "graph"
func get_type_name():
func get_type_name() -> String:
return label
func toggle_editable():
func toggle_editable() -> bool:
editable = !editable
if editable:
model = null
return true
func is_editable():
func is_editable() -> bool:
return editable
func get_parameter_defs():
func get_parameter_defs() -> Array:
if has_node("gen_parameters"):
return get_node("gen_parameters").get_parameter_defs()
return []
@ -34,12 +34,12 @@ func set_parameter(p, v):
if has_node("gen_parameters"):
return get_node("gen_parameters").set_parameter(p, v)
func get_input_defs():
func get_input_defs() -> Array:
if has_node("gen_inputs"):
return get_node("gen_inputs").get_output_defs()
return []
func get_output_defs():
func get_output_defs() -> Array:
if has_node("gen_outputs"):
return get_node("gen_outputs").get_input_defs()
return []
@ -72,7 +72,7 @@ func get_port_targets(gen_name: String, output_index: int) -> Array:
rv.push_back(InputPort.new(tgt_gen, c.to_port))
return rv
func add_generator(generator : MMGenBase):
func add_generator(generator : MMGenBase) -> void:
var name = generator.name
var index = 1
while has_node(name):
@ -81,22 +81,22 @@ func add_generator(generator : MMGenBase):
generator.name = name
add_child(generator)
func remove_generator(generator : MMGenBase):
func remove_generator(generator : MMGenBase) -> void:
var new_connections = []
for c in connections:
if c.from != generator.name and c.to != generator.name:
new_connections.append(c)
connections = new_connections
generator.queue_free()
func replace_generator(old : MMGenBase, new : MMGenBase):
func replace_generator(old : MMGenBase, new : MMGenBase) -> void:
new.name = old.name
new.position = old.position
remove_child(old)
old.free()
add_child(new)
func connect_children(from, from_port : int, to, to_port : int):
func connect_children(from, from_port : int, to, to_port : int) -> bool:
# check the new connection does not create a loop
var spreadlist = [ InputPort.new(to, to_port) ]
while !spreadlist.empty():
@ -120,7 +120,7 @@ func connect_children(from, from_port : int, to, to_port : int):
connections.append({from=from.name, from_port=from_port, to=to.name, to_port=to_port})
return true
func disconnect_children(from, from_port : int, to, to_port : int):
func disconnect_children(from, from_port : int, to, to_port : int) -> bool:
while true:
var remove = -1
for i in connections.size():
@ -132,7 +132,7 @@ func disconnect_children(from, from_port : int, to, to_port : int):
connections.remove(remove)
return true
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var outputs = get_node("gen_outputs")
if outputs != null:
var rv = outputs._get_shader_code(uv, output_index, context)
@ -141,7 +141,7 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
return rv
return { globals=[], defs="", code="", textures={} }
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.label = label
data.nodes = []
for c in get_children():
@ -149,10 +149,10 @@ func _serialize(data):
data.connections = connections
return data
func edit(node):
func edit(node) -> void:
node.get_parent().call_deferred("update_view", self)
func create_subgraph(gens):
func create_subgraph(gens) -> void:
# Remove material, gen_inputs and gen_outputs nodes
var generators = []
var center = Vector2(0, 0)

View File

@ -6,16 +6,16 @@ class_name MMGenImage
Texture generator from image
"""
func get_type():
func get_type() -> String:
return "image"
func get_type_name():
func get_type_name() -> String:
return "Image"
func get_parameter_defs():
func get_parameter_defs() -> Array:
return [ { name="image", type="path" } ]
func set_parameter(n : String, v):
func set_parameter(n : String, v) -> void:
.set_parameter(n, v)
if n == "image":
texture.load(v)

View File

@ -8,34 +8,34 @@ IOs just forward their inputs to their outputs and are used to specify graph int
var ports : Array = []
func get_type():
func get_type() -> String:
return "ios"
func get_type_name():
func get_type_name() -> String:
match name:
"gen_inputs": return "Inputs"
"gen_outputs": return "Outputs"
_: return "IOs"
func get_io_defs():
func get_io_defs() -> Array:
var rv : Array = []
for p in ports:
rv.push_back({ name=p.name, type="rgba" })
return rv
func get_input_defs():
func get_input_defs() -> Array:
return [] if name == "gen_inputs" else get_io_defs()
func get_output_defs():
func get_output_defs() -> Array:
return [] if name == "gen_outputs" else get_io_defs()
func source_changed(input_index : int):
func source_changed(input_index : int) -> void:
if name == "gen_outputs":
get_parent().notify_output_change(input_index)
else:
notify_output_change(input_index)
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var source = get_source(output_index)
if source != null:
var rv = source.generator._get_shader_code(uv, source.output_index, context)
@ -44,7 +44,7 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
return rv
return { defs="", code="", textures={} }
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.type = "ios"
data.ports = ports
return data

View File

@ -24,7 +24,7 @@ const TEXTURE_SIZE_MAX = 12 # 4096x4096
# The default texture size as a power-of-two exponent
const TEXTURE_SIZE_DEFAULT = 10 # 1024x1024
func _ready():
func _ready() -> void:
texture_list = TEXTURE_LIST
for t in texture_list:
generated_textures[t.texture] = null
@ -33,13 +33,13 @@ func _ready():
func can_be_deleted() -> bool:
return false
func get_type():
func get_type() -> String:
return "material"
func get_type_name():
func get_type_name() -> String:
return "Material"
func get_parameter_defs():
func get_parameter_defs() -> Array:
return [
{ name="albedo_color", label="Albedo", type="color", default={ r=1.0, g=1.0, b=1.0, a=1.0} },
{ name="metallic", label="Metallic", type="float", min=0.0, max=1.0, step=0.05, default=1.0 },
@ -51,7 +51,7 @@ func get_parameter_defs():
{ name="size", label="Size", type="size", first=TEXTURE_SIZE_MIN, last=TEXTURE_SIZE_MAX, default=TEXTURE_SIZE_DEFAULT }
]
func get_input_defs():
func get_input_defs() -> Array:
return [
{ name="albedo_texture", label="", type="rgb" },
{ name="metallic_texture", label="", type="f" },
@ -62,7 +62,7 @@ func get_input_defs():
{ name="depth_texture", label="", type="f" }
]
func get_image_size():
func get_image_size() -> int:
var rv : int
if parameters.has("size"):
rv = int(pow(2, parameters.size+TEXTURE_SIZE_MIN))
@ -70,21 +70,21 @@ func get_image_size():
rv = int(pow(2, TEXTURE_SIZE_DEFAULT))
return rv
func update_preview():
func update_preview() -> void:
var graph_edit = self
while graph_edit is MMGenBase:
graph_edit = graph_edit.get_parent()
if graph_edit.has_method("send_changed_signal"):
graph_edit.send_changed_signal()
func set_parameter(p, v):
func set_parameter(p, v) -> void:
.set_parameter(p, v)
update_preview()
func source_changed(input_index : int):
func source_changed(input_index : int) -> void:
update_preview()
func render_textures(renderer : MMGenRenderer):
func render_textures(renderer : MMGenRenderer) -> void:
for t in texture_list:
var texture = null
if t.has("port"):
@ -135,21 +135,21 @@ func render_textures(renderer : MMGenRenderer):
generated_textures[t.texture] = texture
func update_materials(material_list):
func update_materials(material_list) -> void:
for m in material_list:
update_spatial_material(m)
func get_generated_texture(slot, file_prefix = null):
func get_generated_texture(slot, file_prefix = null) -> ImageTexture:
if file_prefix != null:
var file_name = "%s_%s.png" % [ file_prefix, slot ]
if File.new().file_exists(file_name):
return load(file_name)
return load(file_name) as ImageTexture
else:
return null
else:
return generated_textures[slot]
func update_spatial_material(m, file_prefix = null):
func update_spatial_material(m, file_prefix = null) -> void:
var texture
# Make the material double-sided for better visiblity in the preview
@ -161,7 +161,7 @@ func update_spatial_material(m, file_prefix = null):
m.roughness = parameters.roughness
# Metallic
texture = get_generated_texture("orm", file_prefix)
m.metallic_texture = texture
m.metallic_texture = texture
m.metallic_texture_channel = SpatialMaterial.TEXTURE_CHANNEL_BLUE
# Roughness
m.roughness_texture = texture
@ -199,7 +199,7 @@ func update_spatial_material(m, file_prefix = null):
else:
m.depth_enabled = false
func export_textures(prefix, editor_interface = null):
func export_textures(prefix, editor_interface = null) -> SpatialMaterial:
for t in texture_list:
var texture = generated_textures[t.texture]
if texture != null:
@ -215,5 +215,7 @@ func export_textures(prefix, editor_interface = null):
resource_filesystem.scan()
return new_material
func _serialize(data):
return null
func _serialize(data: Dictionary) -> Dictionary:
return data

View File

@ -8,7 +8,7 @@ Remote can be used to control parameters from several generators in the same gra
var widgets = null
func set_widgets(w):
func set_widgets(w) -> void:
widgets = w
var i = 0
for w in widgets:
@ -17,13 +17,13 @@ func set_widgets(w):
parameters[param_name] = 0
i += 1
func get_type():
func get_type() -> String:
return "remote"
func get_type_name():
func get_type_name() -> String:
return "Parameters" if name == "gen_parameters" else "Remote"
func get_parameter_defs():
func get_parameter_defs() -> Array:
var rv = []
var i = 0
for w in widgets:
@ -55,7 +55,7 @@ func get_parameter_defs():
print(w.type)
return rv
func set_parameter(p, v):
func set_parameter(p, v) -> void:
var parent = get_parent()
var param_index = p.trim_prefix("param").to_int()
var widget = widgets[param_index]
@ -79,28 +79,28 @@ func set_parameter(p, v):
if name == "gen_parameters":
get_parent().parameters[p] = v
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.type = "remote"
data.widgets = widgets
return data
func create_linked_control(label):
func create_linked_control(label) -> int:
var index = widgets.size()
widgets.push_back({ label=label, type="linked_control", linked_widgets=[] })
return index
func create_config_control(label):
func create_config_control(label) -> int:
var index = widgets.size()
widgets.push_back({ label=label, type="config_control", linked_widgets=[], configurations={} })
return index
func set_label(index, new_label):
func set_label(index, new_label) -> void:
widgets[index].label = new_label
func can_link_parameter(index, generator, param):
func can_link_parameter(index, generator, param) -> bool:
return true
func link_parameter(index, generator, param):
func link_parameter(index, generator, param) -> void:
if !can_link_parameter(index, generator, param):
return
var widget = widgets[index]
@ -113,13 +113,13 @@ func link_parameter(index, generator, param):
parameters["param"+str(index)] = 0
emit_signal("parameter_changed", "", null)
func remove_parameter(index):
func remove_parameter(index) -> void:
for i in range(index, widgets.size()-2):
parameters["param"+str(i)] = parameters["param"+str(i+1)]
widgets.remove(index)
emit_signal("parameter_changed", "", null)
func add_configuration(index, config_name):
func add_configuration(index, config_name) -> void:
var widget = widgets[index]
if widget.type == "config_control":
widget.configurations[config_name] = []
@ -128,7 +128,7 @@ func add_configuration(index, config_name):
parameters["param"+str(index)] =configurations.find(config_name)
update_configuration(index, config_name)
func update_configuration(index, config_name):
func update_configuration(index, config_name) -> void:
var widget = widgets[index]
if widget.type == "config_control":
var c = []
@ -141,7 +141,7 @@ func update_configuration(index, config_name):
widget.configurations[config_name] = c
emit_signal("parameter_changed", "", null)
func remove_configuration(index, config_name):
func remove_configuration(index, config_name) -> void:
var widget = widgets[index]
if widget.type == "config_control":
widget.configurations.erase(config_name)

View File

@ -7,30 +7,30 @@ var uses_seed = false
var editable = false
func toggle_editable():
func toggle_editable() -> bool:
editable = !editable
if editable:
model = null
return true
func is_editable():
func is_editable() -> bool:
return editable
func get_type():
func get_type() -> String:
return "shader"
func get_type_name():
if shader_model.has("name"):
func get_type_name() -> String:
if shader_model.has("name"):
return shader_model.name
return .get_type_name()
func get_parameter_defs():
func get_parameter_defs() -> Array:
if shader_model == null or !shader_model.has("parameters"):
return []
else:
return shader_model.parameters
func get_input_defs():
func get_input_defs() -> Array:
if shader_model == null or !shader_model.has("inputs"):
return []
else:
@ -55,12 +55,12 @@ func set_shader_model(data: Dictionary):
else:
shader_model.outputs[i].type = "f"
func set_position(p):
func set_position(p) -> void:
.set_position(p)
if uses_seed:
source_changed(0)
func get_seed():
func get_seed() -> int:
var s = ((int(position.x) * 0x1f1f1f1f) ^ int(position.y)) % 65536
return s
@ -81,7 +81,7 @@ func find_keyword_call(string, keyword):
parenthesis_level -= 1
return ""
func replace_input(string, context, input, type, src, default):
func replace_input(string, context, input, type, src, default) -> Dictionary:
var required_globals = []
var required_defs = ""
var required_code = ""
@ -117,10 +117,10 @@ func replace_input(string, context, input, type, src, default):
string = string.replace("$%s(%s)" % [ input, uv ], src_code.string)
return { string=string, globals=required_globals, defs=required_defs, code=required_code, textures=required_textures, new_pass_required=new_pass_required }
func is_word_letter(l):
func is_word_letter(l) -> bool:
return "azertyuiopqsdfghjklmwxcvbnAZERTYUIOPQSDFGHJKLMWXCVBN1234567890_".find(l) != -1
func replace_variable(string, variable, value):
func replace_variable(string, variable, value) -> String:
string = string.replace("$(%s)" % variable, value)
var keyword_size = variable.length()+1
var new_string = ""
@ -138,7 +138,7 @@ func replace_variable(string, variable, value):
string = string.right(keyword_size)
return new_string
func subst(string, context, uv = ""):
func subst(string, context, uv = "") -> Dictionary:
var genname = "o"+str(get_instance_id())
var required_globals = []
var required_defs = ""
@ -205,7 +205,7 @@ func subst(string, context, uv = ""):
cont = changed and new_pass_required
return { string=string, globals=required_globals, defs=required_defs, code=required_code, textures=required_textures }
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
uses_seed = false
var genname = "o"+str(get_instance_id())
var output_info = [ { field="rgba", type="vec4" }, { field="rgb", type="vec3" }, { field="f", type="float" } ]
@ -271,11 +271,11 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
rv.globals.push_back(shader_model.global)
return rv
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
data.shader_model = shader_model
return data
func edit(node):
func edit(node) -> void:
if shader_model != null:
var edit_window = load("res://addons/material_maker/widgets/node_editor/node_editor.tscn").instance()
node.get_parent().add_child(edit_window)

View File

@ -8,20 +8,20 @@ Texture generator switch
var editable = false
func get_type():
func get_type() -> String:
return "switch"
func get_type_name():
func get_type_name() -> String:
return "Switch"
func toggle_editable():
func toggle_editable() -> bool:
editable = !editable
return true
func is_editable():
func is_editable() -> bool:
return editable
func get_parameter_defs():
func get_parameter_defs() -> Array:
var choices = parameters.choices if parameters.has("choices") else 2
return [
{ name="outputs", label="Outputs", type="float", min=1, max=5, step=1, default=2 },
@ -29,7 +29,7 @@ func get_parameter_defs():
{ name="source", label="Source", type="float", min=0, max=choices-1, step=1, default=0 },
]
func get_input_defs():
func get_input_defs() -> Array:
var rv : Array = []
for c in range(parameters.choices):
for o in range(parameters.outputs):
@ -37,27 +37,25 @@ func get_input_defs():
rv.push_back({ name=n, label=n, type="rgba" })
return rv
func get_output_defs():
func get_output_defs() -> Array:
var rv : Array = []
for o in range(parameters.outputs):
var n = PoolByteArray([65+o]).get_string_from_ascii()
rv.push_back({ name=n, type="rgba" })
return rv
func set_parameter(p, v):
func set_parameter(p, v) -> void:
.set_parameter(p, v)
emit_signal("parameter_changed", "__update_all__", null)
# get the list of outputs that depend on the input whose index is passed as parameter
func follow_input(input_index : int) -> Array:
return [ OutputPort.new(self, input_index % int(parameters.outputs)) ]
func source_changed(input_index : int):
func source_changed(input_index : int) -> void:
notify_output_change(input_index % int(parameters.outputs))
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var source = get_source(output_index+parameters.source*parameters.outputs)
if source != null:
var rv = source.generator._get_shader_code(uv, source.output_index, context)
@ -66,5 +64,5 @@ func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
return rv
return { globals=[], defs="", code="", textures={} }
func _serialize(data):
func _serialize(data: Dictionary) -> Dictionary:
return data

View File

@ -8,10 +8,10 @@ Base class for texture generators that provide a texture as output
var texture : ImageTexture = ImageTexture.new()
func get_output_defs():
func get_output_defs() -> Array:
return [ { rgba="" } ]
func _get_shader_code(uv : String, output_index : int, context : MMGenContext):
func _get_shader_code(uv : String, output_index : int, context : MMGenContext) -> Dictionary:
var genname = "o"+str(get_instance_id())
var rv = { globals=[], defs="", code="" }
var texture_name = genname+"_tex"

View File

@ -17,7 +17,7 @@ static func load_gen(filename: String) -> MMGenBase:
return create_gen(data)
return null
static func add_to_gen_graph(gen_graph, generators, connections):
static func add_to_gen_graph(gen_graph, generators, connections) -> Dictionary:
var rv = { generators=[], connections=[] }
var gennames = {}
for n in generators:

View File

@ -8,10 +8,10 @@ var debug_file_index : int = 0
var rendering : bool = false
signal done
func _ready():
func _ready() -> void:
$ColorRect.material = $ColorRect.material.duplicate(true)
static func generate_shader(src_code):
static func generate_shader(src_code) -> String:
var code
code = "shader_type canvas_item;\n"
code += "render_mode blend_disabled;\n"
@ -34,7 +34,7 @@ static func generate_shader(src_code):
code += shader_code
return code
static func generate_combined_shader(red_code, green_code, blue_code):
static func generate_combined_shader(red_code, green_code, blue_code) -> String:
var code
code = "shader_type canvas_item;\n"
code += "render_mode blend_disabled;\n"
@ -64,12 +64,12 @@ static func generate_combined_shader(red_code, green_code, blue_code):
code += shader_code
return code
func setup_material(shader_material, textures, shader_code):
func setup_material(shader_material, textures, shader_code) -> void:
for k in textures.keys():
shader_material.set_shader_param(k+"_tex", textures[k])
shader_material.shader.code = shader_code
func render_shader(shader, textures, render_size):
func render_shader(shader, textures, render_size) -> Object:
if debug_path != null and debug_path != "":
var file_name = debug_path+str(debug_file_index)+".shader"
var f = File.new()
@ -95,19 +95,19 @@ func render_shader(shader, textures, render_size):
yield(get_tree(), "idle_frame")
return self
func copy_to_texture(t : ImageTexture):
func copy_to_texture(t : ImageTexture) -> void:
var image : Image = get_texture().get_data()
if image != null:
image.lock()
t.create_from_image(get_texture().get_data())
image.unlock()
func save_to_file(fn : String):
func save_to_file(fn : String) -> void:
var image : Image = get_texture().get_data()
image.lock()
image.save_png(fn)
image.unlock()
func release():
func release() -> void:
rendering = false
emit_signal("done")

View File

@ -19,11 +19,11 @@ onready var subgraph_ui : HBoxContainer = $GraphUI/SubGraphUI
signal save_path_changed
signal graph_changed
func _ready():
func _ready() -> void:
OS.low_processor_usage_mode = true
center_view()
func _gui_input(event):
func _gui_input(event) -> void:
if event is InputEventKey and event.pressed:
var scancode_with_modifiers = event.get_scancode_with_modifiers()
if scancode_with_modifiers == KEY_DELETE || scancode_with_modifiers == KEY_BACKSPACE:
@ -36,10 +36,10 @@ func get_source(node, port):
if c.to == node and c.to_port == port:
return { node=c.from, slot=c.from_port }
func offset_from_global_position(global_position):
func offset_from_global_position(global_position) -> Vector2:
return (scroll_offset + global_position - rect_global_position) / zoom
func add_node(node):
func add_node(node) -> void:
add_child(node)
node.connect("close_request", self, "remove_node", [ node ])
@ -51,12 +51,12 @@ func connect_node(from, from_slot, to, to_slot):
.connect_node(from, from_slot, to, to_slot)
send_changed_signal()
func disconnect_node(from, from_slot, to, to_slot):
func disconnect_node(from, from_slot, to, to_slot) -> void:
if generator.disconnect_children(get_node(from).generator, from_slot, get_node(to).generator, to_slot):
.disconnect_node(from, from_slot, to, to_slot)
send_changed_signal();
func remove_node(node):
func remove_node(node) -> void:
generator.remove_generator(node.generator)
var node_name = node.name
for c in get_connection_list():
@ -67,7 +67,7 @@ func remove_node(node):
# Global operations on graph
func update_tab_title():
func update_tab_title() -> void:
if !get_parent().has_method("set_tab_title"):
print("no set_tab_title method")
return
@ -79,18 +79,18 @@ func update_tab_title():
if get_parent().has_method("set_tab_title"):
get_parent().set_tab_title(get_index(), title)
func set_need_save(ns):
func set_need_save(ns) -> void:
if ns != need_save:
need_save = ns
update_tab_title()
func set_save_path(path):
func set_save_path(path) -> void:
if path != save_path:
save_path = path
update_tab_title()
emit_signal("save_path_changed", self, path)
func clear_view():
func clear_view() -> void:
clear_connections()
for c in get_children():
if c is GraphNode:
@ -99,7 +99,7 @@ func clear_view():
# Center view
func center_view():
func center_view() -> void:
var center = Vector2(0, 0)
var node_count = 0
for c in get_children():
@ -110,7 +110,7 @@ func center_view():
center /= node_count
scroll_offset = center - 0.5*rect_size
func update_view(g):
func update_view(g) -> void:
clear_view()
generator = g
update_graph(generator.get_children(), generator.connections)
@ -118,7 +118,7 @@ func update_view(g):
subgraph_ui.get_node("Label").text = generator.label
center_view()
func clear_material():
func clear_material() -> void:
if top_generator != null:
remove_child(top_generator)
top_generator.free()
@ -126,7 +126,7 @@ func clear_material():
generator = null
send_changed_signal()
func update_graph(generators, connections):
func update_graph(generators, connections) -> Array:
var rv = []
for g in generators:
var node = node_factory.create_node(g.get_type())
@ -140,7 +140,7 @@ func update_graph(generators, connections):
.connect_node("node_"+c.from, c.from_port, "node_"+c.to, c.to_port)
return rv
func new_material():
func new_material() -> void:
clear_material()
var loader = MMGenLoader.new()
top_generator = loader.create_gen({nodes=[{name="Material", type="material"}], connections=[]})
@ -171,10 +171,10 @@ func create_nodes(data, position : Vector2 = Vector2(0, 0)):
return update_graph(new_stuff.generators, new_stuff.connections)
return []
func create_gen_from_type(gen_name):
func create_gen_from_type(gen_name) -> void:
create_nodes({ type=gen_name, parameters={} }, scroll_offset+0.5*rect_size)
func load_file(filename):
func load_file(filename) -> void:
clear_material()
top_generator = MMGenLoader.load_gen(filename)
if top_generator != null:
@ -184,7 +184,7 @@ func load_file(filename):
set_need_save(false)
center_view()
func save_file(filename):
func save_file(filename) -> void:
var data = top_generator.serialize()
var file = File.new()
if file.open(filename, File.WRITE) == OK:
@ -193,7 +193,7 @@ func save_file(filename):
set_save_path(filename)
set_need_save(false)
func export_textures():
func export_textures() -> void:
if save_path != null:
var prefix = save_path.left(save_path.rfind("."))
for c in get_children():
@ -202,27 +202,27 @@ func export_textures():
# Cut / copy / paste
func get_selected_nodes():
func get_selected_nodes() -> Array:
var selected_nodes = []
for n in get_children():
if n is GraphNode and n.selected:
selected_nodes.append(n)
return selected_nodes
func remove_selection():
func remove_selection() -> void:
for c in get_children():
if c is GraphNode and c.selected and c.name != "Material":
remove_node(c)
# Maybe move this to gen_graph...
func serialize_selection():
func serialize_selection() -> Dictionary:
var data = { nodes = [], connections = [] }
var nodes = []
for c in get_children():
if c is GraphNode and c.selected and c.name != "Material":
nodes.append(c)
if nodes.empty():
return null
return {}
var center = Vector2(0, 0)
for n in nodes:
center += n.offset+0.5*n.rect_size
@ -242,20 +242,20 @@ func serialize_selection():
data.connections.append(connection)
return data
func can_copy():
func can_copy() -> bool:
for c in get_children():
if c is GraphNode and c.selected and c.name != "Material":
return true
return false
func cut():
func cut() -> void:
copy()
remove_selection()
func copy():
func copy() -> void:
OS.clipboard = to_json(serialize_selection())
func paste(pos = Vector2(0, 0)):
func paste(pos = Vector2(0, 0)) -> void:
for c in get_children():
if c is GraphNode:
c.selected = false
@ -265,42 +265,41 @@ func paste(pos = Vector2(0, 0)):
# Delay after graph update
func send_changed_signal():
func send_changed_signal() -> void:
set_need_save(true)
timer.start(0.1)
func do_send_changed_signal():
func do_send_changed_signal() -> void:
emit_signal("graph_changed")
# Drag and drop
func can_drop_data(position, data):
func can_drop_data(position, data) -> bool:
return typeof(data) == TYPE_DICTIONARY and (data.has('type') or (data.has('nodes') and data.has('connections')))
func drop_data(position, data):
func drop_data(position, data) -> void:
# The following mitigates the SpinBox problem (captures mouse while dragging)
if Input.get_mouse_mode() == Input.MOUSE_MODE_CAPTURED:
Input.set_mouse_mode(Input.MOUSE_MODE_VISIBLE)
create_nodes(data, offset_from_global_position(get_global_transform().xform(position)))
return true
func on_ButtonUp_pressed():
func on_ButtonUp_pressed() -> void:
if generator != top_generator && generator.get_parent() is MMGenGraph:
call_deferred("update_view", generator.get_parent())
func _on_Label_text_changed(new_text):
func _on_Label_text_changed(new_text) -> void:
generator.label = new_text
# Create subgraph
func create_subgraph():
func create_subgraph() -> void:
var generators = []
for n in get_selected_nodes():
generators.push_back(n.generator)
generator.create_subgraph(generators)
update_view(generator)
func _on_ButtonShowTree_pressed():
func _on_ButtonShowTree_pressed() -> void:
var graph_tree : Popup = preload("res://addons/material_maker/widgets/graph_tree/graph_tree.tscn").instance()
graph_tree.init("Top", top_generator)
add_child(graph_tree)

View File

@ -9,40 +9,40 @@ const PRESET_OPTIONS = [
[{ name="skip", default_value=false }]
]
func _init(p):
func _init(p) -> void:
plugin = p
func get_import_options(preset : int):
func get_import_options(preset : int) -> Array:
return PRESET_OPTIONS[preset]
func get_import_order():
func get_import_order() -> int:
return 1
func get_importer_name():
func get_importer_name() -> String:
return "material_maker.import"
func get_option_visibility(option: String, options: Dictionary):
func get_option_visibility(option: String, options: Dictionary) -> bool:
return true
func get_preset_count():
func get_preset_count() -> int:
return 2
func get_preset_name(preset: int) -> String:
return PRESET_NAMES[preset]
func get_priority():
func get_priority() -> float:
return 0.1
func get_recognized_extensions():
func get_recognized_extensions() -> Array:
return [ "ptex" ]
func get_resource_type():
func get_resource_type() -> String:
return "Material"
func get_save_extension():
func get_save_extension() -> String:
return "tres"
func get_visible_name():
func get_visible_name() -> String:
return "Material Maker Importer"
func import(source_file: String, save_path: String, options: Dictionary, platform_variants: Array, gen_files: Array) -> int:

View File

@ -6,7 +6,7 @@ var libraries = []
onready var tree : Tree = $Tree
onready var filter_line_edit : LineEdit = $HBoxContainer/Filter
func _ready():
func _ready() -> void:
tree.set_column_expand(0, true)
tree.set_column_expand(1, false)
tree.set_column_min_width(1, 32)
@ -21,7 +21,7 @@ func _unhandled_input(event : InputEvent) -> void:
filter_line_edit.grab_focus()
filter_line_edit.select_all()
func get_selected_item_name():
func get_selected_item_name() -> String:
var tree_item : TreeItem = tree.get_selected()
var rv = ""
while tree_item != null and tree_item != tree.get_root():
@ -32,7 +32,7 @@ func get_selected_item_name():
tree_item = tree_item.get_parent()
return rv
func add_library(file_name : String, filter : String = ""):
func add_library(file_name : String, filter : String = "") -> bool:
var root = tree.get_root()
var file = File.new()
if file.open(file_name, File.READ) != OK:
@ -46,7 +46,7 @@ func add_library(file_name : String, filter : String = ""):
return true
return false
func update_tree(filter : String = ""):
func update_tree(filter : String = "") -> void:
filter = filter.to_lower()
tree.clear()
var root = tree.create_item()
@ -55,12 +55,12 @@ func update_tree(filter : String = ""):
if filter == "" or m.tree_item.to_lower().find(filter) != -1:
add_item(m, m.tree_item, get_preview_texture(m), null, filter != "")
func get_preview_texture(data : Dictionary):
func get_preview_texture(data : Dictionary) -> ImageTexture:
if data.has("icon") and data.has("library"):
var image_path = data.library.left(data.library.rfind("."))+"/"+data.icon+".png"
var t : ImageTexture
if image_path.left(6) == "res://":
return load(image_path)
return load(image_path) as ImageTexture
else:
t = ImageTexture.new()
var image : Image = Image.new()
@ -69,7 +69,7 @@ func get_preview_texture(data : Dictionary):
return t
return null
func add_item(item, item_name, item_icon = null, item_parent = null, force_expand = false):
func add_item(item, item_name, item_icon = null, item_parent = null, force_expand = false) -> TreeItem:
if item_parent == null:
item.tree_item = item_name
item_parent = tree.get_root()
@ -110,7 +110,7 @@ func add_item(item, item_name, item_icon = null, item_parent = null, force_expan
new_parent.set_text(0, prefix)
return add_item(item, suffix, item_icon, new_parent, force_expand)
func serialize_library(array, library_name = null, item = null):
func serialize_library(array, library_name = null, item = null) -> void:
if item == null:
item = tree.get_root()
item = item.get_children()
@ -121,7 +121,7 @@ func serialize_library(array, library_name = null, item = null):
serialize_library(array, library_name, item)
item = item.get_next()
func save_library(library_name, item = null):
func save_library(library_name, item = null) -> void:
var array = []
serialize_library(array, library_name)
var file = File.new()
@ -129,5 +129,5 @@ func save_library(library_name, item = null):
file.store_string(to_json({lib=array}))
file.close()
func _on_Filter_text_changed(filter):
func _on_Filter_text_changed(filter) -> void:
update_tree(filter)

View File

@ -21,5 +21,5 @@ func get_drag_data(position):
preview = Label.new()
preview.text = data.tree_item
set_drag_preview(preview)
return data
return data
return null

View File

@ -44,10 +44,10 @@ signal quit
var is_mac = false
func _ready():
func _ready() -> void:
if OS.get_name() == "OSX":
is_mac = true
# In HTML5 export, copy all examples to the filesystem
if OS.get_name() == "HTML5":
print("Copying samples")
@ -63,6 +63,7 @@ func _ready():
print(f)
dir.copy("res://addons/material_maker/examples/"+f, "/examples/"+f)
print("Done")
# Upscale everything if the display requires it (crude hiDPI support).
# This prevents UI elements from being too small on hiDPI displays.
if OS.get_screen_dpi() >= 192 and OS.get_screen_size().x >= 2048:
@ -87,7 +88,7 @@ func get_current_graph_edit() -> MMGraphEdit:
return graph_edit
return null
func create_menu(menu, menu_name):
func create_menu(menu, menu_name) -> PopupMenu:
menu.clear()
menu.connect("id_pressed", self, "_on_PopupMenu_id_pressed")
for i in MENU.size():
@ -121,7 +122,7 @@ func create_menu(menu, menu_name):
menu.add_separator()
return menu
func create_menu_load_recent(menu):
func create_menu_load_recent(menu) -> void:
menu.clear()
if recent_files.empty():
@ -133,16 +134,16 @@ func create_menu_load_recent(menu):
if !menu.is_connected("id_pressed", self, "_on_LoadRecent_id_pressed"):
menu.connect("id_pressed", self, "_on_LoadRecent_id_pressed")
func _on_LoadRecent_id_pressed(id):
func _on_LoadRecent_id_pressed(id) -> void:
do_load_material(recent_files[id])
func load_recents():
func load_recents() -> void:
var f = File.new()
if f.open("user://recent_files.bin", File.READ) == OK:
recent_files = parse_json(f.get_as_text())
f.close()
func add_recent(path):
func add_recent(path) -> void:
while true:
var index = recent_files.find(path)
if index >= 0:
@ -155,7 +156,7 @@ func add_recent(path):
f.store_string(to_json(recent_files))
f.close()
func create_menu_create(menu):
func create_menu_create(menu) -> void:
var gens = MMGenLoader.get_generator_list()
menu.clear()
for i in gens.size():
@ -163,13 +164,13 @@ func create_menu_create(menu):
if !menu.is_connected("id_pressed", self, "_on_Create_id_pressed"):
menu.connect("id_pressed", self, "_on_Create_id_pressed")
func _on_Create_id_pressed(id):
func _on_Create_id_pressed(id) -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
var gens = MMGenLoader.get_generator_list()
graph_edit.create_gen_from_type(gens[id])
func menu_about_to_show(name, menu):
func menu_about_to_show(name, menu) -> void:
for i in MENU.size():
if MENU[i].menu != name:
continue
@ -181,21 +182,21 @@ func menu_about_to_show(name, menu):
var is_disabled = call(command_name)
menu.set_item_disabled(menu.get_item_index(i), is_disabled)
func new_pane():
func new_pane() -> GraphEdit:
var graph_edit = preload("res://addons/material_maker/graph_edit.tscn").instance()
graph_edit.node_factory = $NodeFactory
graph_edit.renderer = $Renderer
graph_edit.editor_interface = editor_interface
projects.add_child(graph_edit)
projects.current_tab = graph_edit.get_index()
return graph_edit
return graph_edit
func new_material():
func new_material() -> void:
var graph_edit = new_pane()
graph_edit.new_material()
graph_edit.update_tab_title()
func load_material():
func load_material() -> void:
var dialog = FileDialog.new()
add_child(dialog)
dialog.rect_min_size = Vector2(500, 500)
@ -205,11 +206,11 @@ func load_material():
dialog.connect("files_selected", self, "do_load_materials")
dialog.popup_centered()
func do_load_materials(filenames):
func do_load_materials(filenames) -> void:
for f in filenames:
do_load_material(f)
func do_load_material(filename):
func do_load_material(filename) -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
var node_count = 2 # So test below succeeds if graph_edit is null...
if graph_edit != null:
@ -224,7 +225,7 @@ func do_load_material(filename):
graph_edit.load_file(filename)
add_recent(filename)
func save_material():
func save_material() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
if graph_edit.save_path != null:
@ -232,7 +233,7 @@ func save_material():
else:
save_material_as()
func save_material_as():
func save_material_as() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
var dialog = FileDialog.new()
@ -244,81 +245,79 @@ func save_material_as():
dialog.connect("file_selected", graph_edit, "save_file")
dialog.popup_centered()
func close_material():
func close_material() -> void:
projects.close_tab()
func export_material():
func export_material() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null :
graph_edit.export_textures()
func export_material_is_disabled():
func export_material_is_disabled() -> bool:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit == null or graph_edit.save_path == null:
return true
return false
return graph_edit == null or graph_edit.save_path == null
func quit():
func quit() -> void:
if Engine.editor_hint:
emit_signal("quit")
else:
get_tree().quit()
func edit_cut():
func edit_cut() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
graph_edit.cut()
func edit_cut_is_disabled():
func edit_cut_is_disabled() -> bool:
var graph_edit : MMGraphEdit = get_current_graph_edit()
return graph_edit == null or !graph_edit.can_copy()
func edit_copy():
func edit_copy() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
graph_edit.copy()
func edit_copy_is_disabled():
func edit_copy_is_disabled() -> bool:
return edit_cut_is_disabled()
func edit_paste():
func edit_paste() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
graph_edit.paste()
func edit_paste_is_disabled():
func edit_paste_is_disabled() -> bool:
var data = parse_json(OS.clipboard)
return data == null
func view_center():
func view_center() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
graph_edit.center_view()
func view_reset_zoom():
func view_reset_zoom() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
graph_edit.zoom = 1
func get_selected_nodes():
func get_selected_nodes() -> Array:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
return graph_edit.get_selected_nodes()
else:
return []
func create_subgraph():
func create_subgraph() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
graph_edit.create_subgraph()
func make_selected_nodes_editable():
func make_selected_nodes_editable() -> void:
var selected_nodes = get_selected_nodes()
if !selected_nodes.empty():
for n in selected_nodes:
if n.generator.toggle_editable():
n.update_node()
func add_to_user_library():
func add_to_user_library() -> void:
var selected_nodes = get_selected_nodes()
if !selected_nodes.empty():
var dialog = preload("res://addons/material_maker/widgets/line_dialog.tscn").instance()
@ -328,7 +327,7 @@ func add_to_user_library():
dialog.connect("ok", self, "do_add_to_user_library", [ selected_nodes ])
dialog.popup_centered()
func do_add_to_user_library(name, nodes):
func do_add_to_user_library(name, nodes) -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
var data
if nodes.size() == 1:
@ -348,11 +347,11 @@ func do_add_to_user_library(name, nodes):
result.release()
library.add_item(data, name, library.get_preview_texture(data))
func save_user_library():
func save_user_library() -> void:
print("Saving user library")
library.save_library("user://library/user.json")
func show_doc():
func show_doc() -> void:
var base_dir = OS.get_executable_path().replace("\\", "/").get_base_dir()
# In release builds, documentation is expected to be located in
@ -374,15 +373,15 @@ func show_doc():
# Open online documentation
OS.shell_open("https://rodzill4.github.io/godot-procedural-textures/doc/")
func bug_report():
func bug_report() -> void:
OS.shell_open("https://github.com/RodZill4/godot-procedural-textures/issues")
func about():
func about() -> void:
var about_box = preload("res://addons/material_maker/widgets/about/about.tscn").instance()
add_child(about_box)
about_box.popup_centered()
func _on_PopupMenu_id_pressed(id):
func _on_PopupMenu_id_pressed(id) -> void:
var node_type = null
if MENU[id].has("command"):
var command = MENU[id].command
@ -391,11 +390,11 @@ func _on_PopupMenu_id_pressed(id):
# Preview
func update_preview():
func update_preview() -> void:
update_preview_2d()
update_preview_3d()
func update_preview_2d(node = null):
func update_preview_2d(node = null) -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null:
var preview = $VBoxContainer/HBoxContainer/VBoxContainer/Preview
@ -413,7 +412,7 @@ func update_preview_2d(node = null):
result.release()
preview.set_2d(tex)
func update_preview_3d():
func update_preview_3d() -> void:
var graph_edit : MMGraphEdit = get_current_graph_edit()
if graph_edit != null and graph_edit.top_generator != null and graph_edit.top_generator.has_node("Material"):
var gen_material = graph_edit.top_generator.get_node("Material")
@ -422,7 +421,7 @@ func update_preview_3d():
status = yield(status, "completed")
gen_material.update_materials($VBoxContainer/HBoxContainer/VBoxContainer/Preview.get_materials())
func _on_Projects_tab_changed(tab):
func _on_Projects_tab_changed(tab) -> void:
var new_tab = projects.get_current_tab_control()
if new_tab != current_tab:
if new_tab != null:
@ -434,7 +433,7 @@ func _on_Projects_tab_changed(tab):
current_tab = new_tab
update_preview()
func _on_Preview_show_background_preview(v):
func _on_Preview_show_background_preview(v) -> void:
var pv = $VBoxContainer/HBoxContainer/VBoxContainer/Preview/MaterialPreview
var bgpv = $VBoxContainer/HBoxContainer/ProjectsPane/BackgroundPreview/Viewport
bgpv.world = pv.find_world()

View File

@ -5,17 +5,17 @@ extends GraphNode
class OutPort:
var node = null
var port = null
func get_shader_code(uv):
func get_shader_code(uv) -> String:
return node.get_shader_code(uv, port)
func generate_shader():
func generate_shader() -> String:
return node.generate_shader(port)
func get_globals():
func get_globals() -> String:
return node.get_globals()
func get_textures():
func get_textures() -> Dictionary:
return node.get_textures()
var generated = false
@ -113,7 +113,7 @@ func get_source(index = 0):
return out_port
return null
func get_source_f(source):
func get_source_f(source) -> String:
var rv
if source.has("f"):
rv = source.f
@ -123,7 +123,7 @@ func get_source_f(source):
rv = "***error***"
return rv
func get_source_rgb(source):
func get_source_rgb(source) -> String:
var rv
if source.has("rgb") or source.has("rgba"):
rv = source.rgb
@ -133,7 +133,7 @@ func get_source_rgb(source):
rv = "***error***"
return rv
func get_source_rgba(source):
func get_source_rgba(source) -> String:
var rv
if source.has("rgba"):
rv = source.rgba
@ -145,14 +145,14 @@ func get_source_rgba(source):
rv = "***error***"
return rv
func reset():
func reset() -> void:
generated = false
generated_variants = []
func _get_shader_code(uv, slot = 0):
pass
func _get_shader_code(uv, slot = 0) -> Dictionary:
return {}
func get_shader_code(uv, slot = 0):
func get_shader_code(uv, slot = 0) -> String:
var rv
if slot == 0:
rv = _get_shader_code(uv)
@ -174,12 +174,12 @@ func get_shader_code(uv, slot = 0):
rv.rgba = "vec4("+rv.rgb+", 1.0)"
return rv
func get_shader_code_with_globals(uv, slot = 0):
func get_shader_code_with_globals(uv, slot = 0) -> String:
var code = get_shader_code(uv, slot)
code.globals = get_globals()
return code
func get_globals():
func get_globals() -> Array:
var list = []
for i in range(get_connection_input_count()):
var source = get_source(i)
@ -189,8 +189,8 @@ func get_globals():
if list.find(g) == -1:
list.append(g)
return list
func get_textures():
func get_textures() -> Dictionary:
var list = {}
for i in range(get_connection_input_count()):
var source = get_source(i)
@ -204,7 +204,7 @@ func serialize_element(e):
if typeof(e) == TYPE_COLOR:
return { type= "Color", r=e.r, g=e.g, b=e.b, a=e.a }
return e
func deserialize_element(e):
if typeof(e) == TYPE_DICTIONARY:
if e.has("type") and e.type == "Color":
@ -215,7 +215,7 @@ func deserialize_element(e):
return gradient
return e
func generate_shader(slot = 0):
func generate_shader(slot = 0) -> String:
# Reset all nodes
for c in get_parent().get_children():
if c is GraphNode:
@ -247,19 +247,19 @@ func deserialize(data):
# Render targets again for multipass filters
func rerender_targets():
func rerender_targets() -> void:
for c in get_parent().get_connection_list():
if c.from == name:
var node = get_parent().get_node(c.to)
if node != null and node is GraphNode:
node._rerender()
func _rerender():
func _rerender() -> void:
rerender_targets()
# Generic code for convolution nodes
func get_convolution_shader(convolution):
func get_convolution_shader(convolution) -> String:
var shader_code
shader_code = "shader_type canvas_item;\n"
shader_code += "uniform sampler2D input_tex;\n"
@ -288,9 +288,9 @@ func get_convolution_shader(convolution):
shader_code += "color += vec3(%.9f, %.9f, %.9f);\n" % [ convolution.translate.x, convolution.translate.y, convolution.translate.z ]
shader_code += "COLOR = vec4(color, 1.0);\n"
shader_code += "}\n"
return shader_code;
return shader_code
func get_shader_code_convolution(src, convolution, uv):
func get_shader_code_convolution(src, convolution, uv) -> String:
var rv = { defs="", code="" }
var variant_index = generated_variants.find(uv)
var need_defs = false

View File

@ -3,10 +3,7 @@ extends Node
var includes
func _ready():
pass
func create_node(type):
func create_node(type) -> Node:
var node = null
var file_name = "res://addons/material_maker/nodes/"+type+".tscn"
if ResourceLoader.exists(file_name):

View File

@ -12,7 +12,7 @@ const DIRECTIONS = [
{ name="Y", mask=DIRECTION_V }
]
func _ready():
func _ready() -> void:
# init size widget
$HBoxContainer1/size.clear()
for i in range(7):
@ -26,7 +26,7 @@ func _ready():
initialize_properties([ $HBoxContainer1/size, $HBoxContainer2/direction, $HBoxContainer3/sigma ])
saved_texture = ImageTexture.new()
func get_gaussian_blur_shader(horizontal):
func get_gaussian_blur_shader(horizontal) -> String:
var convolution = { x=0, y=0, kernel=[], epsilon=1.0/pow(2, 5+parameters.size) }
var kernel_size = 50
if horizontal:
@ -43,27 +43,27 @@ func get_gaussian_blur_shader(horizontal):
convolution.kernel[x+kernel_size] /= sum
return get_convolution_shader(convolution)
func _rerender():
func _rerender() -> void:
if DIRECTIONS[parameters.direction].mask & DIRECTION_H != 0:
get_parent().renderer.precalculate_shader(input_shader, get_source().get_textures(), int(pow(2, 5+parameters.size)), saved_texture, self, "pass_1", [])
else:
get_parent().renderer.precalculate_shader(input_shader, get_source().get_textures(), int(pow(2, 5+parameters.size)), saved_texture, self, "pass_2", [])
func pass_1():
func pass_1() -> void:
if DIRECTIONS[parameters.direction].mask & DIRECTION_V != 0:
get_parent().renderer.precalculate_shader(get_gaussian_blur_shader(true), { input=saved_texture }, int(pow(2, 5+parameters.size)), saved_texture, self, "pass_2", [])
else:
get_parent().renderer.precalculate_shader(get_gaussian_blur_shader(true), { input=saved_texture }, int(pow(2, 5+parameters.size)), saved_texture, self, "rerender_targets", [])
func pass_2():
func pass_2() -> void:
get_parent().renderer.precalculate_shader(get_gaussian_blur_shader(false), { input=saved_texture }, int(pow(2, 5+parameters.size)), saved_texture, self, "rerender_targets", [])
func get_textures():
func get_textures() -> Dictionary:
var list = {}
list[name] = saved_texture
return list
func _get_shader_code(uv, slot = 0):
func _get_shader_code(uv, slot = 0) -> Dictionary:
var rv = { defs="", code="" }
var src = get_source()
if src == null:

View File

@ -6,16 +6,16 @@ var generator = null setget set_generator
onready var label = $VBox/Label
onready var editor = $VBox/TextEdit
func set_generator(g):
func set_generator(g) -> void:
generator = g
label.text = generator.text
rect_size = generator.size
func _on_resize_request(new_size):
func _on_resize_request(new_size) -> void:
rect_size = new_size
generator.size = new_size
func _on_Label_gui_input(ev):
func _on_Label_gui_input(ev) -> void:
if ev is InputEventMouseButton and ev.doubleclick and ev.button_index == BUTTON_LEFT:
editor.rect_min_size = label.rect_size + Vector2(0, rect_size.y - get_minimum_size().y)
editor.text = label.text
@ -24,7 +24,7 @@ func _on_Label_gui_input(ev):
editor.select_all()
editor.grab_focus()
func _on_TextEdit_focus_exited():
func _on_TextEdit_focus_exited() -> void:
label.text = editor.text
generator.text = editor.text
label.visible = true

View File

@ -1,7 +1,7 @@
tool
extends HBoxContainer
func connect_buttons(object, edit_fct, load_fct, save_fct):
func connect_buttons(object, edit_fct, load_fct, save_fct) -> void:
$Edit.connect("pressed", object, edit_fct)
$Load.connect("pressed", object, load_fct)
$Save.connect("pressed", object, save_fct)
$Save.connect("pressed", object, save_fct)

View File

@ -21,7 +21,7 @@ const CONVOLUTION = {
const INDICES = [ 0, 1, 2, 5, 8, 7, 6, 3 ]
const COEFS = [ 1, 2, 1, 0, -1, -2, -1, 0 ]
func _ready():
func _ready() -> void:
$HBoxContainer1/size.clear()
for i in range(7):
$HBoxContainer1/size.add_item(str(int(pow(2, 5+i))), i)
@ -30,22 +30,22 @@ func _ready():
final_texture = ImageTexture.new()
initialize_properties([ $HBoxContainer1/size, $HBoxContainer2/direction ])
func _rerender():
func _rerender() -> void:
get_parent().renderer.precalculate_shader(input_shader, get_source().get_textures(), int(pow(2, 5+parameters.size)), input_texture, self, "pass_1", [])
func pass_1():
func pass_1() -> void:
var convolution = CONVOLUTION
convolution.epsilon=1.0/pow(2, 5+parameters.size)
for i in range(8):
convolution.kernel[INDICES[i]] = COEFS[(i+8-int(parameters.direction))%8]
get_parent().renderer.precalculate_shader(get_convolution_shader(convolution), {input=input_texture}, int(pow(2, 5+parameters.size)), final_texture, self, "rerender_targets", [])
func get_textures():
func get_textures() -> Dictionary:
var list = {}
list[name] = final_texture
return list
func _get_shader_code(uv, slot = 0):
func _get_shader_code(uv, slot = 0) -> Dictionary:
var rv = { defs="", code="" }
var src = get_source()
if src == null:

View File

@ -3,29 +3,29 @@ extends "res://addons/material_maker/node_base.gd"
var suffix = "suffix"
func _ready():
func _ready() -> void:
initialize_properties([ $resolution ])
func _get_shader_code(uv, slot = 0):
func _get_shader_code(uv, slot = 0) -> Dictionary:
var rv = { defs="", code="", f="0.0" }
var src = get_source()
if src != null:
rv = src.get_shader_code(uv)
return rv
func export_textures(prefix, size = null):
func export_textures(prefix, size = null) -> void:
var suffix = $Suffix.text
if suffix != "":
if size == null:
size = int(pow(2, 8+parameters.resolution))
get_parent().renderer.export_texture(get_source(), "%s_%s.png" % [ prefix, suffix ], size)
func serialize():
func serialize() -> Dictionary:
var data = .serialize()
data.suffix = $Suffix.text
return data
func deserialize(data):
func deserialize(data) -> void:
if data.has("suffix"):
$Suffix.text = data.suffix
.deserialize(data)

View File

@ -14,18 +14,18 @@ var preview_position : int
var preview_size : int
var preview_timer : Timer = null
func set_generator(g):
func set_generator(g) -> void:
generator = g
generator.connect("parameter_changed", self, "on_parameter_changed")
call_deferred("update_node")
func on_close_request():
func on_close_request() -> void:
generator.get_parent().remove_generator(generator)
func on_offset_changed():
func on_offset_changed() -> void:
generator.set_position(offset)
func on_parameter_changed(p, v):
func on_parameter_changed(p, v) -> void:
if ignore_parameter_change == p:
return
if p == "__update_all__":
@ -52,7 +52,7 @@ func on_parameter_changed(p, v):
print("unsupported widget "+str(o))
update_shaders()
func initialize_properties():
func initialize_properties() -> void:
var parameter_names = []
for p in generator.get_parameter_defs():
parameter_names.push_back(p.name)
@ -79,35 +79,35 @@ func initialize_properties():
else:
print("unsupported widget "+str(o))
func update_shaders():
func update_shaders() -> void:
get_parent().send_changed_signal()
update_preview()
func _on_text_changed(new_text, variable):
func _on_text_changed(new_text, variable) -> void:
ignore_parameter_change = variable
generator.set_parameter(variable, float(new_text))
ignore_parameter_change = ""
update_shaders()
func _on_value_changed(new_value, variable):
func _on_value_changed(new_value, variable) -> void:
ignore_parameter_change = variable
generator.set_parameter(variable, new_value)
ignore_parameter_change = ""
update_shaders()
func _on_color_changed(new_color, variable):
func _on_color_changed(new_color, variable) -> void:
ignore_parameter_change = variable
generator.set_parameter(variable, new_color)
ignore_parameter_change = ""
update_shaders()
func _on_gradient_changed(new_gradient, variable):
func _on_gradient_changed(new_gradient, variable) -> void:
ignore_parameter_change = variable
generator.set_parameter(variable, MMType.serialize_value(new_gradient))
ignore_parameter_change = ""
update_shaders()
func create_parameter_control(p : Dictionary):
func create_parameter_control(p : Dictionary) -> Control:
var control = null
if p.type == "float":
if p.has("widget") and p.widget == "spinbox":
@ -142,14 +142,14 @@ func create_parameter_control(p : Dictionary):
control = preload("res://addons/material_maker/widgets/gradient_editor.tscn").instance()
return control
func save_preview_widget():
func save_preview_widget() -> void:
if preview != null:
remove_child(preview)
if preview_timer != null:
preview_timer.stop()
remove_child(preview_timer)
func restore_preview_widget():
func restore_preview_widget() -> void:
if preview == null:
preview = TextureRect.new()
preview.visible = false
@ -165,7 +165,7 @@ func restore_preview_widget():
preview_timer.connect("timeout", self, "do_update_preview")
add_child(preview_timer)
func update_node():
func update_node() -> void:
# Clean node
var custom_node_buttons = null
save_preview_widget()
@ -203,7 +203,7 @@ func update_node():
var control : Control = Control.new()
control.rect_min_size.y = 16
hsizer.add_child(control)
add_child(hsizer)
var input_names_width : int = 0
for c in get_children():
@ -305,16 +305,16 @@ func update_node():
# Preview
restore_preview_widget()
func edit_generator():
func edit_generator() -> void:
if generator.has_method("edit"):
generator.edit(self)
func update_generator(shader_model):
func update_generator(shader_model) -> void:
generator.set_shader_model(shader_model)
update_node()
update_shaders()
func load_generator():
func load_generator() -> void:
var dialog = FileDialog.new()
add_child(dialog)
dialog.rect_min_size = Vector2(500, 500)
@ -324,7 +324,7 @@ func load_generator():
dialog.connect("file_selected", self, "do_load_generator")
dialog.popup_centered()
func do_load_generator(file_name : String):
func do_load_generator(file_name : String) -> void:
var new_generator = null
if file_name.ends_with(".mmn"):
var file = File.new()
@ -343,7 +343,7 @@ func do_load_generator(file_name : String):
generator = new_generator
call_deferred("update_node")
func save_generator():
func save_generator() -> void:
var dialog = FileDialog.new()
add_child(dialog)
dialog.rect_min_size = Vector2(500, 500)
@ -353,7 +353,7 @@ func save_generator():
dialog.connect("file_selected", self, "do_save_generator")
dialog.popup_centered()
func do_save_generator(file_name : String):
func do_save_generator(file_name : String) -> void:
var file = File.new()
if file.open(file_name, File.WRITE) == OK:
var data = generator.serialize()
@ -362,13 +362,13 @@ func do_save_generator(file_name : String):
file.store_string(to_json(data))
file.close()
func update_preview_buttons(index : int):
func update_preview_buttons(index : int) -> void:
for i in range(output_count):
if i != index:
var line = get_child(i)
line.get_child(line.get_child_count()-1).pressed = false
func on_preview_button(pressed : bool, index : int):
func on_preview_button(pressed : bool, index : int) -> void:
if pressed:
preview_index = index
var width
@ -385,14 +385,14 @@ func on_preview_button(pressed : bool, index : int):
remove_child(preview)
rect_size = Vector2(0, 0)
func update_preview(size : int = 0):
func update_preview(size : int = 0) -> void:
if preview_index == -1:
return
if size != 0:
preview_size = size
preview_timer.start(0.2)
func do_update_preview():
func do_update_preview() -> void:
var renderer = get_parent().renderer
var result = generator.render(preview_index, renderer, preview_size)
while result is GDScriptFunctionState:

View File

@ -3,22 +3,22 @@ extends GraphNode
var generator = null
func _ready():
func _ready() -> void:
set_slot(0, false, 0, Color(0.5, 0.5, 1), true, 0, Color(0.5, 0.5, 1))
func set_texture(path):
func set_texture(path) -> void:
if path == null:
return
if generator != null:
generator.set_parameter("image", path)
$TextureButton.texture_normal = generator.texture
func get_textures():
func get_textures() -> Dictionary:
var list = {}
list[name] = $TextureButton.texture_normal
return list
func _on_TextureButton_pressed():
func _on_TextureButton_pressed() -> void:
var dialog = FileDialog.new()
add_child(dialog)
dialog.rect_min_size = Vector2(500, 500)

View File

@ -6,7 +6,7 @@ var links = {}
onready var grid = $Controls
func add_control(text, control):
func add_control(text, control) -> void:
var index = grid.get_child_count() / 4
var label = preload("res://addons/material_maker/widgets/linked_widgets/editable_label.tscn").instance()
label.set_text(text)
@ -24,7 +24,7 @@ func add_control(text, control):
grid.add_child(button)
button.connect("pressed", generator, "remove_parameter", [ index ])
func update_node():
func update_node() -> void:
var i : int = 0
for c in grid.get_children():
c.queue_free()
@ -52,7 +52,7 @@ func update_node():
rect_size = Vector2(0, 0)
initialize_properties()
func _on_value_changed(new_value, variable):
func _on_value_changed(new_value, variable) -> void:
var param_index = variable.trim_prefix("param").to_int()
var widget = generator.widgets[param_index]
if widget.type == "config_control":
@ -83,41 +83,41 @@ func _on_value_changed(new_value, variable):
else:
._on_value_changed(new_value, variable)
func do_add_configuration(config_name, param_index):
func do_add_configuration(config_name, param_index) -> void:
generator.add_configuration(param_index, config_name)
func on_label_changed(new_name, index):
func on_label_changed(new_name, index) -> void:
generator.set_label(index, new_name)
func _on_AddLink_pressed():
func _on_AddLink_pressed() -> void:
var widget = Control.new()
add_control("Unnamed", widget)
var link = MMNodeLink.new(get_parent())
link.pick(widget, generator, generator.create_linked_control("Unnamed"), true)
func _on_AddConfig_pressed():
func _on_AddConfig_pressed() -> void:
var widget = Control.new()
add_control("Unnamed", widget)
var link = MMNodeLink.new(get_parent())
link.pick(widget, generator, generator.create_config_control("Unnamed"), true)
func _on_Link_pressed(index):
func _on_Link_pressed(index) -> void:
var link = MMNodeLink.new(get_parent())
link.pick(grid.get_child(index*4+1), generator, index)
func _on_Remote_resize_request(new_minsize):
func _on_Remote_resize_request(new_minsize) -> void:
rect_size = new_minsize
func _on_HBoxContainer_minimum_size_changed():
func _on_HBoxContainer_minimum_size_changed() -> void:
print("_on_HBoxContainer_minimum_size_changed "+str($HBoxContainer.rect_min_size))
func on_parameter_changed(p, v):
func on_parameter_changed(p, v) -> void:
if p == "":
update_node()
else:
.on_parameter_changed(p, v)
func on_enter_widget(widget):
func on_enter_widget(widget) -> void:
var param_index = widget.name.trim_prefix("param").to_int()
var w = generator.widgets[param_index]
var new_links = []
@ -134,7 +134,7 @@ func on_enter_widget(widget):
# store new links
links[widget] = new_links
func on_exit_widget(widget):
func on_exit_widget(widget) -> void:
if links.has(widget):
for l in links[widget]:
l.queue_free()

View File

@ -3,16 +3,16 @@ extends MMGraphNodeGeneric
var fixed_lines : int = 0
func _ready():
func _ready() -> void:
update_node()
func update_preview_buttons(index : int):
func update_preview_buttons(index : int) -> void:
for i in range(generator.parameters.outputs):
if i != index:
var line = get_child(i)
line.get_child(2).pressed = false
func update_node():
func update_node() -> void:
print("update_node")
if generator == null or !generator.parameters.has("outputs") or !generator.parameters.has("choices"):
return

View File

@ -6,25 +6,25 @@ var material_maker = null
var importer = null
var renderer = null
func _enter_tree():
func _enter_tree() -> void:
add_tool_menu_item("Material Maker", self, "open_material_maker")
add_tool_menu_item("Register Material Maker Import", self, "register_material_maker_import")
renderer = preload("res://addons/material_maker/engine/renderer.tscn").instance()
add_child(renderer)
func register_material_maker_import(__):
func register_material_maker_import(__) -> void:
importer = preload("res://addons/material_maker/import_plugin/ptex_import.gd").new(self)
add_import_plugin(importer)
remove_tool_menu_item("Register Material Maker Import")
add_tool_menu_item("Unregister Material Maker Import", self, "unregister_material_maker_import")
func unregister_material_maker_import(__):
func unregister_material_maker_import(__) -> void:
remove_import_plugin(importer)
importer = null
remove_tool_menu_item("Unregister Material Maker Import")
add_tool_menu_item("Register Material Maker Import", self, "register_material_maker_import")
func _exit_tree():
func _exit_tree() -> void:
remove_tool_menu_item("Material Maker")
if material_maker != null:
material_maker.hide()
@ -34,15 +34,14 @@ func _exit_tree():
remove_import_plugin(importer)
importer = null
func _get_state():
var s = { mm_button=mm_button, material_maker=material_maker }
return s
func _get_state() -> Dictionary:
return { mm_button=mm_button, material_maker=material_maker }
func _set_state(s):
func _set_state(s) -> void:
mm_button = s.mm_button
material_maker = s.material_maker
func open_material_maker(__):
func open_material_maker(__) -> void:
if material_maker == null:
material_maker = preload("res://addons/material_maker/window_dialog.tscn").instance()
var panel = material_maker.get_node("MainWindow")
@ -51,7 +50,7 @@ func open_material_maker(__):
add_child(material_maker)
material_maker.popup_centered()
func close_material_maker():
func close_material_maker() -> void:
if material_maker != null:
material_maker.hide()
material_maker.queue_free()

View File

@ -22,7 +22,7 @@ onready var camera = $MaterialPreview/Preview3d/CameraPivot/Camera
signal need_update
signal show_background_preview
func _ready():
func _ready() -> void:
$Config/Model.clear()
for o in objects.get_children():
var m = o.get_surface_material(0)
@ -38,26 +38,26 @@ func _ready():
_on_Preview_resized()
$MaterialPreview/Preview3d/CameraPivot/Camera/RemoteTransform.set_remote_node("../../../../../../../ProjectsPane/BackgroundPreview/Viewport/Camera")
func _on_Environment_item_selected(id):
func _on_Environment_item_selected(id) -> void:
current_environment.visible = false
current_environment = environments.get_child(id)
$MaterialPreview/Preview3d/CameraPivot/Camera.set_environment(current_environment.environment)
get_node("../../ProjectsPane/BackgroundPreview/Viewport/Camera").set_environment(current_environment.environment)
current_environment.visible = true
func _on_Model_item_selected(id):
func _on_Model_item_selected(id) -> void:
current_object.visible = false
current_object = objects.get_child(id)
current_object.visible = true
emit_signal("need_update")
func get_materials():
func get_materials() -> Array:
return [ current_object.get_surface_material(0) ]
func set_2d(tex: Texture):
func set_2d(tex: Texture) -> void:
$Preview2D.material.set_shader_param("tex", tex)
func _on_Preview_resized():
func _on_Preview_resized() -> void:
if preview_maximized:
var size = min(rect_size.x, rect_size.y)
$Preview2D.rect_position = 0.5*Vector2(rect_size.x-size, rect_size.y-size)
@ -66,15 +66,15 @@ func _on_Preview_resized():
$Preview2D.rect_position = Vector2(0, rect_size.y-64)
$Preview2D.rect_size = Vector2(64, 64)
func _on_Preview2D_gui_input(ev : InputEvent):
func _on_Preview2D_gui_input(ev : InputEvent) -> void:
if ev is InputEventMouseButton and ev.button_index == 1 and ev.pressed:
preview_maximized = !preview_maximized
_on_Preview_resized()
func _on_Background_toggled(button_pressed):
func _on_Background_toggled(button_pressed) -> void:
emit_signal("show_background_preview", button_pressed)
func on_gui_input(event):
func on_gui_input(event) -> void:
if event is InputEventMouseButton:
$MaterialPreview/Preview3d/ObjectRotate.stop(false)
$Config/Rotate.pressed = false
@ -107,7 +107,7 @@ func on_gui_input(event):
elif event.button_mask & BUTTON_MASK_RIGHT:
camera_stand.rotate(camera_basis.z.normalized(), -motion.x)
func _on_Rotate_toggled(button_pressed):
func _on_Rotate_toggled(button_pressed) -> void:
if button_pressed:
$MaterialPreview/Preview3d/ObjectRotate.play("rotate")
else:

View File

@ -1,5 +1,5 @@
tool
extends Area
func _on_Light_input_event(camera, event, click_position, click_normal, shape_idx):
func _on_Light_input_event(camera, event, click_position, click_normal, shape_idx) -> void:
print(event)

View File

@ -2,39 +2,39 @@ extends Object
class_name MMGradient
class CustomSorter:
static func compare(a, b):
static func compare(a, b) -> bool:
return a.v < b.v
var points = [ { v=0.0, c=Color(0.0, 0.0, 0.0, 0.0) }, { v=1.0, c=Color(1.0, 1.0, 1.0, 1.0) } ]
var sorted = true
func to_string():
func to_string() -> String:
var rv = PoolStringArray()
for p in points:
rv.append("("+str(p.v)+","+str(p.c)+")")
return rv.join(",")
func duplicate():
func duplicate() -> Object:
var copy = get_script().new()
copy.clear()
for p in points:
copy.add_point(p.v, p.c)
return copy
func clear():
func clear() -> void:
points.clear()
sorted = true
func add_point(v, c):
func add_point(v, c) -> void:
points.append({ v=v, c=c })
sorted = false
func sort():
func sort() -> void:
if !sorted:
points.sort_custom(CustomSorter, "compare")
sorted = true
func get_color(x):
func get_color(x) -> Color:
sort()
if points.size() > 0:
if x < points[0].v:
@ -52,10 +52,10 @@ func get_color(x):
return Color(0.0, 0.0, 0.0, 1.0)
# get_color_in_shader
func gcis(color):
func gcis(color) -> String:
return "vec4(%.9f,%.9f,%.9f,%.9f)" % [color.r, color.g, color.b, color.a]
func get_shader(name):
func get_shader(name) -> String:
sort()
var shader
shader = "vec4 "+name+"(float x) {\n"
@ -78,7 +78,7 @@ func get_shader(name):
shader += "}\n"
return shader
func serialize():
func serialize() -> Dictionary:
sort()
var rv = []
for p in points:
@ -86,7 +86,7 @@ func serialize():
rv = { type="Gradient", points=rv }
return rv
func deserialize(v):
func deserialize(v) -> void:
clear()
if typeof(v) == TYPE_ARRAY:
for i in v:

View File

@ -3,7 +3,7 @@ class_name MMType
const Gradient = preload("res://addons/material_maker/types/gradient.gd")
static func serialize_value(value):
static func serialize_value(value) -> Dictionary:
if typeof(value) == TYPE_COLOR:
return { type="Color", r=value.r, g=value.g, b=value.b, a=value.a }
elif typeof(value) == TYPE_OBJECT and value.has_method("serialize"):

View File

@ -2,12 +2,11 @@ tool
extends WindowDialog
func _ready():
func _ready() -> void:
if Engine.editor_hint:
$VBoxContainer/VBoxContainer1/ApplicationName.text = "Material Maker"
else:
$VBoxContainer/VBoxContainer1/ApplicationName.text = ProjectSettings.get_setting("application/config/name")+" v"+ProjectSettings.get_setting("application/config/release")
pass
func open_url(url):
func open_url(url) -> void:
OS.shell_open(url)

View File

@ -4,14 +4,14 @@ class_name MMGradientEditor
class GradientCursor:
extends ColorRect
const WIDTH = 10
func _ready():
func _ready() -> void:
rect_position = Vector2(0, 15)
rect_size = Vector2(WIDTH, 15)
func _gui_input(ev):
func _gui_input(ev) -> void:
if ev is InputEventMouseButton:
if ev.button_index == BUTTON_LEFT && ev.doubleclick:
get_parent().select_color(self, ev.global_position)
@ -24,20 +24,18 @@ class GradientCursor:
rect_position.x += ev.relative.x
rect_position.x = min(max(0, rect_position.x), get_parent().rect_size.x-rect_size.x)
get_parent().update_value()
func get_position():
func get_position() -> Vector2:
return rect_position.x / (get_parent().rect_size.x - WIDTH)
func set_color(c):
func set_color(c) -> void:
color = c
get_parent().update_value()
static func sort(a, b):
if a.get_position() < b.get_position():
return true
return false
func _draw():
static func sort(a, b) -> bool:
return a.get_position() < b.get_position()
func _draw() -> void:
var c = color
c.a = 1.0
draw_rect(Rect2(0, 0, rect_size.x, rect_size.y), c, false)
@ -47,11 +45,11 @@ export var embedded : bool = true
signal updated(value)
func _ready():
func _ready() -> void:
$Gradient.material = $Gradient.material.duplicate(true)
set_value(MMGradient.new())
func set_value(v):
func set_value(v) -> void:
value = v
for c in get_children():
if c is GradientCursor:
@ -61,20 +59,20 @@ func set_value(v):
add_cursor(p.v*(rect_size.x-GradientCursor.WIDTH), p.c)
update_shader()
func update_value():
func update_value() -> void:
value.clear()
for p in get_children():
if p != $Gradient && p != $Background:
value.add_point(p.rect_position.x/(rect_size.x-GradientCursor.WIDTH), p.color)
update_shader()
func add_cursor(x, color):
func add_cursor(x, color) -> void:
var cursor = GradientCursor.new()
add_child(cursor)
cursor.rect_position.x = x
cursor.color = color
func _gui_input(ev):
func _gui_input(ev) -> void:
if ev is InputEventMouseButton && ev.button_index == 1 && ev.doubleclick:
if ev.position.y > 15:
var p = max(0, min(ev.position.x, rect_size.x-GradientCursor.WIDTH))
@ -93,29 +91,29 @@ func _gui_input(ev):
var active_cursor
func select_color(cursor, position):
func select_color(cursor, position) -> void:
active_cursor = cursor
$Gradient/Popup/ColorPicker.color = cursor.color
$Gradient/Popup/ColorPicker.connect("color_changed", cursor, "set_color")
$Gradient/Popup.rect_position = position
$Gradient/Popup.popup()
func _on_Popup_popup_hide():
func _on_Popup_popup_hide() -> void:
$Gradient/Popup/ColorPicker.disconnect("color_changed", active_cursor, "set_color")
# Calculating a color from the gradient and generating the shader
func get_sorted_cursors():
func get_sorted_cursors() -> Array:
var array = get_children()
array.erase($Gradient)
array.erase($Background)
array.sort_custom(GradientCursor, "sort")
return array
func get_gradient_color(x):
func get_gradient_color(x) -> Color:
return value.get_color(x / (rect_size.x - GradientCursor.WIDTH))
func update_shader():
func update_shader() -> void:
var shader
shader = "shader_type canvas_item;\n"
shader += value.get_shader("gradient")

View File

@ -2,14 +2,14 @@ extends Popup
signal updated(value)
func init(value):
func init(value) -> void:
$Panel/Control.set_value(value)
func _on_Control_updated(value):
func _on_Control_updated(value) -> void:
emit_signal("updated", value)
func _on_GradientPopup_popup_hide():
func _on_GradientPopup_popup_hide() -> void:
queue_free()

View File

@ -3,14 +3,14 @@ extends Popup
signal item_double_clicked(generator)
func init(graph_name : String, generator : MMGenGraph):
func init(graph_name : String, generator : MMGenGraph) -> void:
$Tree.clear()
var root : TreeItem = $Tree.create_item(null)
root.set_text(0, graph_name)
root.set_metadata(0, generator)
fill_item(root, generator)
func fill_item(parent : TreeItem, generator : MMGenGraph):
func fill_item(parent : TreeItem, generator : MMGenGraph) -> void:
for c in generator.get_children():
if c is MMGenGraph:
var item : TreeItem = $Tree.create_item(parent)
@ -18,6 +18,6 @@ func fill_item(parent : TreeItem, generator : MMGenGraph):
item.set_metadata(0, c)
fill_item(item, c)
func _on_Tree_item_double_clicked():
func _on_Tree_item_double_clicked() -> void:
emit_signal("item_double_clicked", $Tree.get_selected().get_metadata(0))
queue_free()

View File

@ -1,12 +1,12 @@
tool
extends HSlider
func _ready():
func _ready() -> void:
update_label(value)
func set_value(v):
func set_value(v) -> void:
.set_value(v)
update_label(v)
func update_label(v):
$Label.text = str(v)
func update_label(v) -> void:
$Label.text = str(v)

View File

@ -3,18 +3,18 @@ extends WindowDialog
signal ok
func set_value(v):
func set_value(v) -> void:
$VBoxContainer/LineEdit.text = v
func set_texts(title, label):
func set_texts(title, label) -> void:
window_title = title
$VBoxContainer/Label.text = label
$VBoxContainer/LineEdit.grab_focus()
$VBoxContainer/LineEdit.grab_click_focus()
func _on_OK_pressed():
func _on_OK_pressed() -> void:
_on_LineEdit_text_entered($VBoxContainer/LineEdit.text)
func _on_LineEdit_text_entered(new_text):
func _on_LineEdit_text_entered(new_text) -> void:
emit_signal("ok", new_text)
queue_free()

View File

@ -5,16 +5,13 @@ var text setget set_text, get_text
signal label_changed(new_label)
func _ready():
pass
func get_text():
func get_text() -> String:
return $Label.text
func set_text(t):
func set_text(t) -> void:
$Label.text = t
func _on_gui_input(ev):
func _on_gui_input(ev) -> void:
if ev is InputEventMouseButton and ev.pressed and ev.button_index == BUTTON_LEFT:
$Label.visible = false
$Editor.text = $Label.text
@ -22,10 +19,10 @@ func _on_gui_input(ev):
$Editor.select()
$Editor.grab_focus()
func _on_Editor_text_entered(__):
func _on_Editor_text_entered(__) -> void:
_on_Editor_focus_exited()
func _on_Editor_focus_exited():
func _on_Editor_focus_exited() -> void:
$Label.text = $Editor.text
$Label.visible = true
$Editor.visible = false

View File

@ -10,14 +10,14 @@ var generator = null
var param_index = 0
var creating = false
func _init(parent):
func _init(parent) -> void:
size_flags_horizontal = SIZE_EXPAND_FILL
size_flags_vertical = SIZE_EXPAND_FILL
rect_size = parent.rect_size
rect_clip_content = true
parent.add_child(self)
func pick(s, g, i, c = false):
func pick(s, g, i, c = false) -> void:
source = s
end = get_global_transform().xform_inv(source.get_global_transform().xform(0.5*source.rect_size))
generator = g
@ -25,14 +25,14 @@ func pick(s, g, i, c = false):
creating = c
set_process_input(true)
func show_link(s, t):
func show_link(s, t) -> void:
set_process_input(false)
mouse_filter = Control.MOUSE_FILTER_IGNORE
source = s
target = t
update()
func closest(rect, point):
func closest(rect, point) -> Vector2:
return Vector2(max(rect.position.x, min(rect.end.x, point.x)), max(rect.position.y, min(rect.end.y, point.y)))
func find_control(gp):
@ -45,7 +45,7 @@ func find_control(gp):
return { node=c, widget=widget }
return null
func _draw():
func _draw() -> void:
#draw_rect(Rect2(rect_position, rect_size), Color(1.0, 0.0, 0.0, 0.2))
#draw_rect(Rect2(rect_position, rect_size), Color(1.0, 1.0, 0.0), false)
var start = get_global_transform().xform_inv(source.get_global_transform().xform(0.5*source.rect_size))
@ -61,7 +61,7 @@ func _draw():
start = closest(rect, end)
draw_line(start, end, color, 1, true)
func _input(event):
func _input(event: InputEvent) -> void:
if event is InputEventKey:
if event.scancode == KEY_ESCAPE:
set_process_input(false)

View File

@ -3,10 +3,10 @@ extends WindowDialog
signal ok
func set_value(n, v):
func set_value(n, v) -> void:
$VBoxContainer/GridContainer/name.text = n
$VBoxContainer/GridContainer/value.text = v
func _on_OK_pressed():
func _on_OK_pressed() -> void:
emit_signal("ok", $VBoxContainer/GridContainer/name.text, $VBoxContainer/GridContainer/value.text)
queue_free()

View File

@ -1,10 +1,7 @@
tool
extends HBoxContainer
func _ready():
pass
func set_model_data(data):
func set_model_data(data) -> void:
$Name.text = data.name
$Label.text = data.label
if data.type == "rgb":
@ -15,7 +12,7 @@ func set_model_data(data):
$Type.selected = 0
$Default.text = data.default
func get_model_data():
func get_model_data() -> Dictionary:
var data = { name=$Name.text, label=$Label.text, default=$Default.text }
if $Type.selected == 1:
data.type = "rgb"
@ -25,5 +22,5 @@ func get_model_data():
data.type = "f"
return data
func _on_Delete_pressed():
func _on_Delete_pressed() -> void:
queue_free()

View File

@ -13,18 +13,18 @@ const OutputEditor = preload("res://addons/material_maker/widgets/node_editor/ou
signal node_changed
func _ready():
func _ready() -> void:
main_code_editor.add_color_region("//", "", Color(0, 0.5, 0), true)
instance_functions_editor.add_color_region("//", "", Color(0, 0.5, 0), true)
global_functions_editor.add_color_region("//", "", Color(0, 0.5, 0), true)
func add_item(parent, scene):
func add_item(parent, scene) -> Node:
var object = scene.instance()
parent.add_child(object)
parent.move_child(object, parent.get_child_count()-2)
return object
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("name"):
$Sizer/Tabs/General/Name/Name.text = data.name
if data.has("parameters"):
@ -43,7 +43,7 @@ func set_model_data(data):
if data.has("code"):
main_code_editor.text = data.code
func get_model_data():
func get_model_data() -> Dictionary:
var data = {
name=$Sizer/Tabs/General/Name/Name.text,
global=global_functions_editor.text,
@ -64,21 +64,21 @@ func get_model_data():
data.outputs.append(o.get_model_data())
return data
func _on_AddParameter_pressed():
func _on_AddParameter_pressed() -> void:
add_item($Sizer/Tabs/General/Parameters/Sizer, ParameterEditor)
func _on_AddInput_pressed():
func _on_AddInput_pressed() -> void:
add_item($Sizer/Tabs/General/Inputs/Sizer, InputEditor)
func _on_AddOutput_pressed():
func _on_AddOutput_pressed() -> void:
add_item($Sizer/Tabs/Outputs/Outputs/Sizer, OutputEditor)
func _on_Apply_pressed():
func _on_Apply_pressed() -> void:
emit_signal("node_changed", get_model_data())
func _on_OK_pressed():
func _on_OK_pressed() -> void:
emit_signal("node_changed", get_model_data())
queue_free()
func _on_Cancel_pressed():
func _on_Cancel_pressed() -> void:
queue_free()

View File

@ -1,10 +1,7 @@
tool
extends HBoxContainer
func _ready():
pass
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("rgb"):
$Type.selected = 1
$Value.text = data.rgb
@ -15,7 +12,7 @@ func set_model_data(data):
$Type.selected = 0
$Value.text = data.f
func get_model_data():
func get_model_data() -> Dictionary:
if $Type.selected == 1:
return { rgb=$Value.text }
elif $Type.selected == 2:
@ -23,5 +20,5 @@ func get_model_data():
else:
return { f=$Value.text }
func _on_Delete_pressed():
func _on_Delete_pressed() -> void:
queue_free()

View File

@ -1,13 +1,13 @@
tool
extends HBoxContainer
func _ready():
func _ready() -> void:
$Type.clear()
for t in $Types.get_children():
$Type.add_item(t.name)
_on_Type_item_selected($Type.selected)
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("name"):
$Name.text = data.name
if data.has("label"):
@ -20,17 +20,17 @@ func set_model_data(data):
$Type.selected = selected
_on_Type_item_selected(selected)
func get_model_data():
func get_model_data() -> Dictionary:
var data = $Types.get_node($Type.get_item_text($Type.selected)).get_model_data()
data.name=$Name.text
data.label=$Label.text
data.type=$Type.get_item_text($Type.selected)
return data
func _on_Delete_pressed():
func _on_Delete_pressed() -> void:
queue_free()
func _on_Type_item_selected(ID):
func _on_Type_item_selected(ID) -> void:
for t in $Types.get_children():
t.visible = false
var t = $Types.get_child(ID)

View File

@ -1,14 +1,11 @@
tool
extends HBoxContainer
func _ready():
pass
func get_model_data() -> Dictionary:
return {
default = $Default.pressed,
}
func get_model_data():
var data = {}
data.default = $Default.pressed
return data
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("default"):
$Default.pressed = data.default
$Default.pressed = data.default

View File

@ -1,15 +1,13 @@
tool
extends HBoxContainer
func _ready():
pass
func get_model_data() -> Dictionary:
var default_color = $Default.color
func get_model_data():
var data = {}
var default = $Default.color
data.default = { r=default.r, g=default.g, b=default.b, a=default.a}
return data
return {
default = { r=default_color.r, g=default_color.g, b=default_color.b, a=default_color.a },
}
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("default"):
$Default.color = Color(data.default.r, data.default.g, data.default.b, data.default.a)

View File

@ -10,16 +10,16 @@ const ENUM_REMOVE = -3
const ENUM_UP = -4
const ENUM_DOWN = -5
func _ready():
func _ready() -> void:
update_enum_list()
func get_model_data():
var data = {}
data.values = enum_values
data.default = enum_current
return data
func get_model_data() -> Dictionary:
return {
values = enum_values,
default = enum_current,
}
func set_model_data(data):
func set_model_data(data) -> void:
enum_values = data.values.duplicate()
if data.has("default"):
enum_current = data.default
@ -27,7 +27,7 @@ func set_model_data(data):
enum_current = 0
update_enum_list()
func update_enum_list():
func update_enum_list() -> void:
var options = $EnumValues
options.clear()
if !enum_values.empty():
@ -46,7 +46,7 @@ func update_enum_list():
options.selected = enum_current
options.add_item("Add value", ENUM_ADD)
func _on_EnumValues_item_selected(id):
func _on_EnumValues_item_selected(id) -> void:
id = $EnumValues.get_item_id(id)
if id >= 0 and id < enum_values.size():
enum_current = id
@ -77,7 +77,7 @@ func _on_EnumValues_item_selected(id):
enum_current += 1
update_enum_list()
func update_enum_value(n, v, i):
func update_enum_value(n, v, i) -> void:
if i == -1:
enum_values.append({ name=n, value=v })
enum_current = enum_values.size()-1

View File

@ -1,20 +1,20 @@
tool
extends HBoxContainer
func _ready():
pass
func get_model_data() -> Dictionary:
var data = {
min = $Min.value,
max = $Max.value,
step = $Step.value,
default = $Default.value,
}
func get_model_data():
var data = {}
data.min = $Min.value
data.max = $Max.value
data.step = $Step.value
data.default = $Default.value
if $SpinBox.pressed:
data.widget = "spinbox"
return data
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("min"):
$Min.value = data.min
if data.has("max"):

View File

@ -3,15 +3,12 @@ extends HBoxContainer
onready var default = $Default
func _ready():
pass
func get_model_data() -> Dictionary:
return {
default = default.value.serialize(),
}
func get_model_data():
var data = {}
data.default = default.value.serialize()
return data
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("default"):
var v = MMGradient.new()
v.deserialize(data.default)

View File

@ -5,17 +5,17 @@ var size_first = 0
var size_last = 12
var size_default = 10
func _ready():
func _ready() -> void:
update_size_configuration()
func get_model_data():
var data = {}
data.first = size_first
data.last = size_last
data.default = size_default
return data
func get_model_data() -> Dictionary:
return {
first = size_first,
last = size_last,
default = size_default,
}
func set_model_data(data):
func set_model_data(data) -> void:
if data.has("first"):
size_first = data.first
if data.has("last"):
@ -24,25 +24,25 @@ func set_model_data(data):
size_last = data.default
update_size_configuration()
func update_size_option_button(button, first, last, current):
func update_size_option_button(button, first, last, current) -> void:
button.clear()
for i in range(first, last+1):
var s = pow(2, i)
button.add_item("%dx%d" % [ s, s ])
button.selected = current - first
func update_size_configuration():
func update_size_configuration() -> void:
update_size_option_button($First, 0, size_last, size_first)
update_size_option_button($Last, size_first, 12, size_last)
update_size_option_button($Default, size_first, size_last, size_default)
func _on_First_item_selected(ID):
func _on_First_item_selected(ID) -> void:
size_first = ID
update_size_configuration()
func _on_Last_item_selected(ID):
func _on_Last_item_selected(ID) -> void:
size_last = size_first + ID
update_size_configuration()
func _on_Default_item_selected(ID):
func _on_Default_item_selected(ID) -> void:
size_default = size_first + ID

View File

@ -6,16 +6,13 @@ var current_tab = -1 setget set_current_tab
signal tab_changed
signal no_more_tabs
func _ready():
pass
func add_child(control, legible_unique_name = false):
func add_child(control, legible_unique_name = false) -> void:
.add_child(control, legible_unique_name)
if !(control is Tabs):
$Tabs.add_tab(control.name)
move_child(control, $Tabs.get_tab_count()-1)
func close_tab(tab = null):
func close_tab(tab = null) -> void:
if tab == null:
tab = $Tabs.get_current_tab()
get_child(tab).queue_free()
@ -29,12 +26,12 @@ func close_tab(tab = null):
else:
set_current_tab(0)
func move_active_tab_to(idx_to):
func move_active_tab_to(idx_to) -> void:
$Tabs.move_tab(current_tab, idx_to)
move_child(get_child(current_tab), idx_to)
set_current_tab(idx_to)
func set_current_tab(t):
func set_current_tab(t) -> void:
if t == current_tab or t < 0 or t >= $Tabs.get_tab_count():
return
var node
@ -49,15 +46,14 @@ func set_current_tab(t):
$Tabs.current_tab = current_tab
emit_signal("tab_changed", current_tab)
func set_tab_title(index, title):
func set_tab_title(index, title) -> void:
$Tabs.set_tab_title(index, title)
func get_current_tab_control():
func get_current_tab_control() -> Node:
return get_child(current_tab)
func _on_Tabs_tab_changed(tab):
func _on_Tabs_tab_changed(tab) -> void:
set_current_tab(tab)
func _on_Projects_resized():
func _on_Projects_resized() -> void:
$Tabs.rect_size.x = rect_size.x

View File

@ -3,15 +3,15 @@ extends WindowDialog
signal ok
func _ready():
func _ready() -> void:
popup()
func set_title(title):
func set_title(title) -> void:
window_title = title
func set_text(text):
func set_text(text) -> void:
$VBoxContainer/TextEdit.text = text
func _on_OK_pressed():
func _on_OK_pressed() -> void:
emit_signal("ok", $VBoxContainer/TextEdit.text)
queue_free()