Files
animation/tools/tailor/md_tee_v1.py
T

84 lines
3.5 KiB
Python
Raw Normal View History

# Lena tank/tee -- WORKING recipe (verified on Lena's avatar 2026-07-30,
# result: tools/tailor/lena_tee_v1.zprj + lena_tee_v1_garment.fbx).
# Run inside a bridge session:
# python tools/md_bridge.py --file tools/tailor/md_tee_v1.py --timeout 500
#
# Prereq: Lena avatar imported at true scale. If GetAvatarCount() == 0:
# op = ApiTypes.ImportExportOption(); op.scale = 10.0
# op.bAddArrangementPoints = True; op.bAutoTranslate = True
# import_api.ImportFBX(r"...\tools\tailor\avatar\Lena_QuatSkin_Avatar.fbx", op)
# (ImportAvatar() is for .avt files only -- returns False on FBX.)
#
# HARD-WON FACTS (do not rediscover):
# - 2D pattern space: units are mm, +y is UP in the 3D mapping. Straps/neck
# at HIGH y, hem at y=0. (Panels built y-down drape upside-down and tangle
# at the neck -- looked like seam bugs, wasn't.)
# - MD internal 3D unit is mm (gravity default -9800). Blender-exported FBX
# avatars land 10x small -- import with op.scale = 10.
# - CreatePatternWithPoints takes (x, y, type) triples; type 0 = corner.
# Returned id is the pattern index; line i = edge point[i] -> point[i+1].
# - Seams: AddSeamlinePairGroup(patA, lineA, patB, lineB, False, False),
# SAME line index both panels for front/back pairs (cross-pairing sews the
# garment over the face). Whole-edge sewing only -> build the neck gap and
# armholes into the outline as extra points.
# - Placement: SetArrangement(pattern, arrangementIndex) assigns, then
# utility_api.ResetClothArrangement() APPLIES it (ReDrape3DArrangement only
# materializes not-yet-draped cloth). Arrangement indices REGENERATE when
# the avatar changes -- always look up by name.
# - utility_api.Simulate(nFrames) is synchronous; ~1 min per 300 frames.
import os
import tempfile
REPO = r"C:\Users\Jeremy\tinqs\animation"
report = {}
n = pattern_api.GetPatternCount()
for i in range(n - 1, -1, -1):
pattern_api.DeletePatternPiece(i)
# Measurements: chest 1083 mm + ease -> 590 panel; shoulder line 440 wide
# (tips at x 75/515); neck gap 260 (x 165..425); front scoop 140 deep, back
# straight; armhole 165 tall (y 455 down to 290); hem->strap 480.
TOP = 480.0
def panel(scoop, dx, straight_back):
if straight_back:
neck = [(215.0, 455.0), (295.0, 455.0), (375.0, 455.0)]
ny = 455.0
else:
neck = [(215.0, TOP - scoop * 0.75), (295.0, TOP - scoop),
(375.0, TOP - scoop * 0.75)]
ny = TOP
pts = ([(75.0, 455.0), (165.0, ny)] + neck +
[(425.0, ny), (515.0, 455.0),
(590.0, 290.0), (590.0, 0.0), (0.0, 0.0), (0.0, 290.0)])
return pattern_api.CreatePatternWithPoints([(x + dx, y, 0) for (x, y) in pts])
front = panel(140.0, 0.0, False)
back = panel(0.0, 800.0, True)
report["ids"] = [front, back]
# Lines: 0 shoulder_L | 1-4 neckline (open) | 5 shoulder_R | 6 armhole_R
# 7 side_R | 8 hem | 9 side_L | 10 armhole_L
for line in (0, 5, 7, 9):
pattern_api.AddSeamlinePairGroup(front, line, back, line, False, False)
arr = {a["ArrangementName"]: int(a["ArrangementIndex"])
for a in pattern_api.GetArrangementList()}
pattern_api.SetArrangement(front, arr["Body_Front_Center_1"])
pattern_api.SetArrangement(back, arr["Body_Back_Center_1"])
pattern_api.SetArrangementPosition(front, 50, 55, 50)
pattern_api.SetArrangementPosition(back, 0, 55, 50)
utility_api.ResetClothArrangement()
report["sim"] = utility_api.Simulate(300)
utility_api.Refresh3DWindow()
snap = os.path.join(tempfile.gettempdir(), "tinqs_md_tee_final.png")
export_api.ExportSnapshot3D(snap)
report["snap"] = snap
result = report