151 lines
5.6 KiB
Python
151 lines
5.6 KiB
Python
from assets.garment_programs.circle_skirt import *
|
|
from assets.garment_programs.skirt_paneled import *
|
|
from copy import deepcopy
|
|
|
|
|
|
class SkirtLevels(BaseBottoms):
|
|
"""Skirt constiting of multuple stitched skirts"""
|
|
|
|
def __init__(self, body, design, rise=None) -> None:
|
|
super().__init__(body, design, rise=rise)
|
|
|
|
ldesign = design['levels-skirt']
|
|
lbody = deepcopy(body) # We will modify the values, so need a copy
|
|
n_levels = ldesign['num_levels']['v']
|
|
ruffle = ldesign['level_ruffle']['v']
|
|
|
|
# Adjust length to the common denominators
|
|
self.eval_length(ldesign, body)
|
|
|
|
# Definitions
|
|
self.rise = ldesign['rise']['v'] if rise is None else rise
|
|
base_skirt_class = globals()[ldesign['base']['v']]
|
|
self.subs.append(base_skirt_class(
|
|
body,
|
|
design,
|
|
length=self.base_len,
|
|
rise=self.rise,
|
|
slit=False))
|
|
|
|
if (hasattr(base := self.subs[0], 'design')
|
|
and 'low_angle' in base.design):
|
|
self.angle = base.design['low_angle']['v']
|
|
else:
|
|
self.angle = 0
|
|
|
|
# Place the levels
|
|
level_skirt_class = globals()[ldesign['level']['v']]
|
|
for i in range(n_levels):
|
|
# Adjust the mesurement to trick skirts into producing correct width
|
|
# TODOLOW More elegant overwrite
|
|
lbody['waist'] = ruffle * self.subs[-1].interfaces['bottom'].edges.length()
|
|
lbody['waist_back_width'] = ruffle * self.subs[-1].interfaces['bottom_b'].edges.length()
|
|
self.subs.append(level_skirt_class(
|
|
lbody,
|
|
design,
|
|
tag=str(i),
|
|
length=self.level_len,
|
|
slit=False,
|
|
top_ruffles=False))
|
|
|
|
# Placement
|
|
# Rotation if base is assymetric
|
|
self.subs[-1].rotate_by(R.from_euler(
|
|
'XYZ', [0, 0, -self.angle], degrees=True))
|
|
|
|
self.subs[-1].place_by_interface(
|
|
self.subs[-1].interfaces['top'],
|
|
self.subs[-2].interfaces['bottom'],
|
|
gap=5
|
|
)
|
|
# Stitch
|
|
self.stitching_rules.append((
|
|
self.subs[-2].interfaces['bottom'],
|
|
self.subs[-1].interfaces['top']
|
|
))
|
|
|
|
self.interfaces = {
|
|
'top': self.subs[0].interfaces['top']
|
|
}
|
|
|
|
def eval_length(self, ldesign, body):
|
|
|
|
# With convertion to absolute values
|
|
total_length = ldesign['length']['v'] * body['_leg_length']
|
|
self.base_len = total_length * ldesign['base_length_frac']['v']
|
|
self.level_len = (total_length - self.base_len) / ldesign['num_levels']['v']
|
|
|
|
# Add hip_line (== zero length)
|
|
self.base_len = body['hips_line'] * ldesign['rise']['v'] + self.base_len
|
|
|
|
|
|
class SkirtLayers(BaseBottoms):
|
|
"""Skirt consisting of multiple layered skirts stitched at the waistline"""
|
|
|
|
def __init__(self, body, design, rise=None):
|
|
super().__init__(body, design, rise=rise)
|
|
|
|
ldesign = design['layers-skirt']
|
|
lbody = deepcopy(body) # We will modify the values, so need a copy
|
|
n_layers = ldesign['num_layers']['v']
|
|
ruffle = ldesign['layer_ruffle']['v']
|
|
|
|
# Definitions
|
|
self.rise = ldesign['rise']['v'] if rise is None else rise
|
|
base_skirt_class = globals()[ldesign['base']['v']]
|
|
|
|
total_length = ldesign['length']['v'] * body['_leg_length']
|
|
layer_lengths = self.eval_layer_lengths(ldesign, total_length, n_layers)
|
|
# Place the levels
|
|
self.layers = []
|
|
for i in range(n_layers):
|
|
# Adjust the measurements to produce correct width with ruffle
|
|
waist_multiplier = 1 + ruffle * i
|
|
lbody['waist'] = self.body['waist'] * waist_multiplier
|
|
lbody['waist_back_width'] = self.body['waist_back_width'] * waist_multiplier
|
|
layer_length = layer_lengths[i]
|
|
skirt_layer = base_skirt_class(
|
|
lbody,
|
|
design,
|
|
tag=str(i),
|
|
length=layer_length,
|
|
rise=self.rise,
|
|
slit=False,
|
|
top_ruffles=False)
|
|
|
|
# Place the layer at the waistline
|
|
skirt_layer.translate_by([0, self.body['_waist_level'], 0])
|
|
|
|
self.layers.append(skirt_layer)
|
|
|
|
# Interfaces
|
|
self.interfaces = {
|
|
'top': self.layers[0].interfaces['top'],
|
|
'bottom': self.layers[-1].interfaces['bottom']
|
|
}
|
|
|
|
# Stitching rules: stitch each outer layer's top interface
|
|
# to the 'top' interface of the component (waistline)
|
|
|
|
for layer in self.layers[1:]:
|
|
self.stitching_rules.append(
|
|
(self.interfaces['top'], layer.interfaces['top'])
|
|
)
|
|
|
|
|
|
# Add layers to subcomponents
|
|
self.subs.extend(self.layers)
|
|
for id,layer in enumerate(self.layers):
|
|
layer.front.translate_by([0,0, 5*id])
|
|
layer.back.translate_by([0, 0, -5*id])
|
|
|
|
def eval_layer_lengths(self, ldesign, total_length, n_layers):
|
|
"""Calculate lengths for each layer"""
|
|
if 'layer_lengths' in ldesign:
|
|
# If specific lengths are provided for each layer
|
|
layer_lengths = [ldesign['layer_lengths'][i]['v'] * total_length for i in range(n_layers)]
|
|
else:
|
|
# Distribute the total length among layers, possibly making outer layers longer
|
|
base_length = total_length / n_layers
|
|
layer_lengths = [base_length * (1 + 0.1 * i) for i in range(n_layers)]
|
|
return layer_lengths |