feat: Add restore cutout depth extension with edge depth correction
- Introduced a new extension for restoring cutout depth with edge correction. - Implemented edge depth extension algorithm in `edge_depth.py` to enhance depth accuracy near cutout edges. - Updated `generate_moge_artifacts` to include an option for extending depth edges during depth generation. - Modified cutout job processing to enable edge depth extension based on depth request. - Added comprehensive tests for edge depth functionality, ensuring correct behavior under various scenarios. - Updated existing node loading functions to remove asset revision dependencies, simplifying the loading process. - Created new design and proposal documentation outlining the goals and decisions for the extension.
This commit is contained in:
78
tools/nodes/common/cutout_center.py
Normal file
78
tools/nodes/common/cutout_center.py
Normal file
@@ -0,0 +1,78 @@
|
||||
"""Build a shared center on the original Cutout mesh."""
|
||||
|
||||
|
||||
from .nodes import evaluate_field, group_input, sample_field
|
||||
|
||||
|
||||
def vector(group, operation, first, second=None):
|
||||
node = group.nodes.new("ShaderNodeVectorMath")
|
||||
node.operation = operation
|
||||
for value, socket in ((first, node.inputs[0]), (second, node.inputs[3 if operation == "SCALE" else 1])):
|
||||
if value is None:
|
||||
continue
|
||||
if hasattr(value, "node"):
|
||||
group.links.new(value, socket)
|
||||
else:
|
||||
socket.default_value = value
|
||||
return node.outputs[0]
|
||||
|
||||
|
||||
def axes(group, value):
|
||||
node = group.nodes.new("ShaderNodeSeparateXYZ")
|
||||
group.links.new(value, node.inputs[0])
|
||||
return node.outputs
|
||||
|
||||
|
||||
def combine(group, x, y, z=0):
|
||||
node = group.nodes.new("ShaderNodeCombineXYZ")
|
||||
for value, socket in zip((x, y, z), node.inputs):
|
||||
if hasattr(value, "node"):
|
||||
group.links.new(value, socket)
|
||||
else:
|
||||
socket.default_value = value
|
||||
return node.outputs[0]
|
||||
|
||||
|
||||
def set_position(group, geometry, position):
|
||||
node = group.nodes.new("GeometryNodeSetPosition")
|
||||
group.links.new(geometry, node.inputs["Geometry"])
|
||||
group.links.new(position, node.inputs["Position"])
|
||||
return node.outputs[0]
|
||||
|
||||
|
||||
def sample_surface(group, geometry, value, data_type, domain_position, query):
|
||||
"""Keep point indices on points before the face interpolation adapts domains."""
|
||||
field = evaluate_field(group, sample_field(group, geometry, value, data_type), data_type, "POINT")
|
||||
flat = set_position(group, geometry, domain_position)
|
||||
sample = group.nodes.new("GeometryNodeSampleNearestSurface")
|
||||
sample.data_type = data_type
|
||||
group.links.new(flat, sample.inputs["Mesh"])
|
||||
group.links.new(field, sample.inputs["Value"])
|
||||
group.links.new(query, sample.inputs["Sample Position"])
|
||||
return sample.outputs[0]
|
||||
|
||||
|
||||
def build_center_surface(group, unsplit):
|
||||
"""Smooth the unsplit displaced surface without moving its XY coordinates."""
|
||||
nodes, links = group.nodes, group.links
|
||||
controls = group_input(nodes, {"Center Smooth"})
|
||||
position = nodes.new("GeometryNodeInputPosition").outputs[0]
|
||||
components = axes(group, position)
|
||||
uv = nodes.new("GeometryNodeInputNamedAttribute")
|
||||
uv.data_type = "FLOAT_VECTOR"
|
||||
uv.inputs["Name"].default_value = "UVMap"
|
||||
coordinates = uv.outputs["Attribute"]
|
||||
blur = nodes.new("GeometryNodeBlurAttribute")
|
||||
blur.data_type = "FLOAT"
|
||||
links.new(components["Z"], blur.inputs["Value"])
|
||||
links.new(controls.outputs["Center Smooth"], blur.inputs["Iterations"])
|
||||
support = set_position(group, unsplit, combine(group, components["X"], components["Y"], blur.outputs[0]))
|
||||
height = sample_surface(group, support, components["Z"], "FLOAT", coordinates, coordinates)
|
||||
normal = nodes.new("GeometryNodeInputNormal").outputs[0]
|
||||
normal_blur = nodes.new("GeometryNodeBlurAttribute")
|
||||
normal_blur.data_type = "FLOAT_VECTOR"
|
||||
links.new(evaluate_field(group, normal, "FLOAT_VECTOR", "POINT"), normal_blur.inputs["Value"])
|
||||
links.new(controls.outputs["Center Smooth"], normal_blur.inputs["Iterations"])
|
||||
normal = normal_blur.outputs[0]
|
||||
normal = vector(group, "NORMALIZE", sample_surface(group, support, normal, "FLOAT_VECTOR", coordinates, coordinates))
|
||||
return {"geometry": support, "preview": support, "height": height, "normal": normal}
|
||||
Reference in New Issue
Block a user