"""Beide Wege zum Blattwerk muessen dasselbe ergeben. Es gibt zwei Knoepfe, die Blattwerk erzeugen: * "_Leaf anlegen" beim Erzeugen des Baums (TREEGEN_OT_create) * "Blattwerk streuen" auf einer Auswahl (TREEGEN_OT_leaves) Nur der zweite rechnete die Wachstums-Staffel. Von der Spielseite am Modifier nachgemessen: der S1-Setzling aus dem Create-Pfad trug Size 0.85, Max Radius 0.04, Min Height 0.25 - exakt die Altbaum-Werte. Das ist dieselbe Fehlerklasse, die vorher schon die Stufen-Deckung und build_group erwischt hat: ZWEI QUELLEN fuer dieselbe Frage. Ein Test, der nur einen der beiden Wege prueft, findet so etwas nie - deshalb prueft dieser hier die DIFFERENZ zwischen ihnen und nicht die absoluten Werte. Aufruf: blender --background --factory-startup --python tests/test_zwei_pfade.py """ import os import sys import importlib.util import bpy ROOT = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) spec = importlib.util.spec_from_file_location( "tg", os.path.join(ROOT, "stylized_tree_generator.py")) tg = importlib.util.module_from_spec(spec) sys.modules["tg"] = tg spec.loader.exec_module(tg) tg.register() fails = [] for o in list(bpy.data.objects): bpy.data.objects.remove(o, do_unlink=True) me = bpy.data.meshes.new("Leaf_Card") me.from_pydata([(-0.5, 0, 0), (0, 0, 0.7), (0.5, 0, 0), (0, 0, -0.1)], [], [(0, 1, 2), (0, 2, 3)]) me.update() card = bpy.data.objects.new("Leaf_Card", me) bpy.context.scene.collection.objects.link(card) s = bpy.context.scene.tree_gen_settings s.leaf_card = card s.apply_modifier = True s.preset = "birke" s.variant = 1 s.use_growth = True s.stages = 4 # Die Werte, die die Staffel anfasst. "Density" steht bewusst NICHT dabei: sie # wird nach dem Streuen per Bisektion eingeregelt und darf sich zwischen zwei # Laeufen minimal unterscheiden. GESTAFFELT = ("Size", "Max Radius", "Min Height") def werte(leaf_obj): md = leaf_obj.modifiers.get("GN_Leaves") ids = tg.leaf_socket_ids(md.node_group) return {k: round(float(md[ids[k]]), 6) for k in GESTAFFELT if k in ids} def bauen(mit_haken): for o in list(bpy.context.scene.objects): if o is not card: bpy.data.objects.remove(o, do_unlink=True) s.art_name = "P" if mit_haken else "Q" s.make_leaf = mit_haken bpy.ops.object.treegen_create() staemme = sorted((o for o in bpy.context.scene.objects if o.type == 'MESH' and o is not card and not o.name.endswith(("_Leaf", "_Frucht"))), key=lambda o: o.name) if not mit_haken: for o in bpy.context.scene.objects: o.select_set(o in staemme) bpy.context.view_layer.objects.active = staemme[0] bpy.ops.object.treegen_leaves() out = [] for st in staemme: bl = bpy.data.objects.get(st.name + "_Leaf") out.append((st.name, float(st.get("growth_t", 1.0)), werte(bl) if bl else None)) return out erzeugt = bauen(True) # Haekchen "_Leaf anlegen" operator = bauen(False) # Knopf "Blattwerk streuen" print("%-5s %7s | %-34s | %-34s" % ("Stufe", "growth", "beim Erzeugen", "per Operator")) for (n1, gt, w1), (n2, _gt, w2) in zip(erzeugt, operator): def zeig(w): if w is None: return "keine Blattebene" return " ".join("%s %.3f" % (k[:3], w[k]) for k in GESTAFFELT if k in w) gleich = "" if w1 == w2 else " <-- WEICHT AB" print("%-5s %7.2f | %-34s | %-34s%s" % (n1.split("_")[-1], gt, zeig(w1), zeig(w2), gleich)) if w1 is None or w2 is None: fails.append("%s: eine der beiden Ebenen fehlt" % n1) continue for k in GESTAFFELT: if k not in w1 or k not in w2: continue if abs(w1[k] - w2[k]) > 1e-6: fails.append("%s: '%s' ist beim Erzeugen %.4f, per Operator %.4f - " "die Wachstums-Staffel greift nur auf einem Weg" % (n1, k, w1[k], w2[k])) # Und die Staffel muss ueberhaupt greifen: waeren beide Wege gleich FALSCH, # waere der Vergleich oben zufrieden. Also zusaetzlich, dass sich S1 von S4 # unterscheidet. if len(erzeugt) >= 2 and erzeugt[0][2] and erzeugt[-1][2]: s1, s4 = erzeugt[0][2], erzeugt[-1][2] if s1.get("Size") is not None and abs(s1["Size"] - s4["Size"]) < 1e-6: fails.append("S1 und S4 tragen dieselbe Card-Groesse (%.3f) - die " "Staffel greift auf KEINEM der beiden Wege" % s1["Size"]) print("") if fails: print("ERGEBNIS: %d FEHLER" % len(fails)) for f in fails: print(" - " + f) sys.exit(1) print("ERGEBNIS: ALLE CHECKS OK")