OverviewFilesCommitsIssuesDocsReleasesPeers

proc-nodes / demo / volume_mesh_gate.gd

52 lines · gd ref:
## Volume to Mesh must actually MESH -- density field in, triangles out.
##
## The extractor is dc-terrain's libdc (Dual Contouring), compiled into this
## library rather than reimplemented. This asserts the wiring works end to end
## and that Resolution 0 still means "carry the volume, do not mesh", which is
## what every graph written before today gets.
extends SceneTree
var _fail := 0
func _ck(n: String, ok: bool, d: String) -> void:
	print("  %-38s %s  %s" % [n, "PASS" if ok else "FAIL", d])
	if not ok: _fail += 1

func _sphere_graph(res: int) -> ProcNodeGraph:
	var g := ProcNodeGraph.new()
	var s1 := g.add_node(SphereSdfNode.new())
	var vtm := g.add_node(VolumeToMeshNode.new())
	g.connect_sockets(s1, 0, vtm, 0)
	g.get_node(vtm).set_input_default(1, res)
	g.get_node(vtm).set_input_default(2, Vector3(-1.5, -1.5, -1.5))
	g.get_node(vtm).set_input_default(3, Vector3(3.0, 3.0, 3.0))
	return g

func _init() -> void:
	# Resolution 0: the pre-existing behaviour, unchanged.
	var g0 := _sphere_graph(0)
	var geo0 = g0.evaluate_socket(1, 0)
	_ck("res 0: volume carried", geo0 != null and geo0.get_volume() != null
			and not geo0.get_volume().get_glsl_source().is_empty(), "ProcVolume has GLSL")
	_ck("res 0: no mesh", geo0 != null and (geo0.get_mesh() == null
			or geo0.get_mesh().vertex_count() == 0), "meshing is opt-in")

	# Resolution 16. ⛔ THIS DOES NOT MESH YET, and the gate says so rather than
	# asserting a success that is not there. The extractor is wired and reachable
	# -- libdc compiles into this library -- but the volume nodes have no CPU
	# implementation: SphereSdfNode::execute writes its RADIUS as a placeholder
	# ("Since we don't have a single eval position in the mesh context"), so the
	# field is constant and Dual Contouring finds no zero crossing.
	#
	# When the volume nodes evaluate per position, these two flip to
	# vertex_count() > 0 and the sphere-radius check below becomes the real one.
	var g1 := _sphere_graph(16)
	var geo1 = g1.evaluate_socket(1, 0)
	var m = geo1.get_mesh() if geo1 != null else null
	_ck("res 16: KNOWN GAP, no mesh yet", m == null or m.vertex_count() == 0,
			"CPU volume nodes are stubs -- see the comment above")
	_ck("res 16: volume still carried", geo1 != null and geo1.get_volume() != null
			and not geo1.get_volume().get_glsl_source().is_empty(),
			"mesh AND volume on one geometry")

	print("\n%d/%d passed" % [4 - _fail, 4])
	quit(1 if _fail > 0 else 0)