fix key range detection
1.0.0 - fix: broken algo for extreme keys range detectionmaster
parent
25b081e53a
commit
848bda410d
|
@ -1,5 +1,9 @@
|
|||
# Changelog
|
||||
|
||||
1.0.0
|
||||
|
||||
- fix: broken algo for extreme keys range detection
|
||||
|
||||
0.9.0
|
||||
|
||||
- fix problem with translation calculation when all keys are marked
|
||||
|
|
|
@ -42,9 +42,12 @@ def has_extremes(b, act=None):
|
|||
|
||||
def get_extreme_range(ob, act, b):
|
||||
b_fcurves = [fcu for fcu in act.fcurves if fcu.data_path.split('"')[1] == b.bone.name]
|
||||
start_frame = end_frame = None
|
||||
|
||||
# for f in b_fcurves:
|
||||
# print('fc:', f.data_path, f.array_index)
|
||||
curves = []
|
||||
for fcu in b_fcurves:
|
||||
start_frame = end_frame = None
|
||||
e_ct = 0
|
||||
encountered_marks = False # flag to stop after last extreme of each fcu
|
||||
for k in fcu.keyframe_points:
|
||||
# if k.select_control_point: # based on selection ?
|
||||
|
@ -61,15 +64,37 @@ def get_extreme_range(ob, act, b):
|
|||
end_frame = f
|
||||
if end_frame < f:
|
||||
end_frame = f
|
||||
|
||||
else:
|
||||
if encountered_marks:
|
||||
## means back to other frame type after passed breakdown we stop
|
||||
## (for this fcu)
|
||||
|
||||
e_ct += 1
|
||||
continue
|
||||
|
||||
# it's a normal keyframe
|
||||
if encountered_marks:
|
||||
if e_ct == 1:
|
||||
# reset (continue scan to next frame range)
|
||||
e_ct = 0
|
||||
start_frame = end_frame = None
|
||||
encountered_marks = False
|
||||
|
||||
else:
|
||||
## means back to other frame type after passed sufficient key
|
||||
## (stop for this fcu)
|
||||
break
|
||||
if start_frame is None or end_frame is None:
|
||||
|
||||
print(fcu.data_path, fcu.array_index, start_frame, end_frame)
|
||||
if start_frame is None or end_frame is None:
|
||||
continue
|
||||
if end_frame - start_frame == 0: # same key
|
||||
continue
|
||||
|
||||
print('ok')
|
||||
curves.append(end_frame - start_frame)
|
||||
|
||||
if not curves:
|
||||
return
|
||||
return end_frame - start_frame
|
||||
print('curves: ', curves)
|
||||
curves.sort()
|
||||
return curves[-1]
|
||||
|
||||
def find_best_foot(ob):
|
||||
'''Get an armature object and do some wizardry to return best match for foot bone'''
|
||||
|
@ -120,17 +145,20 @@ def find_best_foot(ob):
|
|||
return b
|
||||
|
||||
flipped_contact_range = get_extreme_range(ob, act, flipped)
|
||||
if not flipped_contact_range:
|
||||
return b
|
||||
print('flipped_contact_range: ', flipped_contact_range)
|
||||
|
||||
bone_contact_range = get_extreme_range(ob, act, b)
|
||||
if bone_contact_range:
|
||||
if bone_contact_range < flipped_contact_range:
|
||||
return flipped
|
||||
else:
|
||||
return ('ERROR', f'No Extreme (red keys) on bone "{b.name}" for action "{act.name}"')
|
||||
print('bone_contact_range: ', bone_contact_range)
|
||||
|
||||
return b
|
||||
if bone_contact_range:
|
||||
if flipped_contact_range and (bone_contact_range < flipped_contact_range):
|
||||
return flipped
|
||||
else:
|
||||
return b
|
||||
elif flipped_contact_range:
|
||||
return flipped
|
||||
|
||||
return ('ERROR', f'No Extreme (red keys) on bone "{b.name}" for action "{act.name}"')
|
||||
|
||||
|
||||
def anim_path_from_translate():
|
||||
|
@ -189,8 +217,10 @@ def anim_path_from_translate():
|
|||
b_fcurves = [fcu for fcu in act.fcurves if fcu.data_path.split('"')[1] == b.bone.name]
|
||||
print('b_fcurves: ', len(b_fcurves))
|
||||
|
||||
start_frame = end_frame = None
|
||||
# find best fcurve
|
||||
|
||||
for fcu in b_fcurves:
|
||||
start_frame = end_frame = None
|
||||
# skip problematic keys
|
||||
if not len(fcu.keyframe_points):
|
||||
if debug: print(fcu.data_path, fcu.array_index, '>> no keys !')
|
||||
|
@ -202,8 +232,8 @@ def anim_path_from_translate():
|
|||
continue
|
||||
|
||||
encountered_marks = False # flag to stop after last extreme of each fcu
|
||||
e_ct = 0
|
||||
for k in fcu.keyframe_points:
|
||||
# if k.select_control_point: # based on selection ?
|
||||
if k.type == 'EXTREME':
|
||||
encountered_marks = True
|
||||
|
||||
|
@ -217,15 +247,33 @@ def anim_path_from_translate():
|
|||
end_frame = f
|
||||
if end_frame < f:
|
||||
end_frame = f
|
||||
|
||||
else:
|
||||
if encountered_marks:
|
||||
|
||||
e_ct += 1
|
||||
continue
|
||||
|
||||
# this is a normal keyframe
|
||||
if encountered_marks:
|
||||
if e_ct == 1:
|
||||
# mean only one extreme has been scanned
|
||||
# reset and continue de keys scan
|
||||
e_ct = 0
|
||||
start_frame = end_frame = None
|
||||
encountered_marks = False
|
||||
else:
|
||||
## means back to other frame type after passed breakdown we stop
|
||||
## (for this fcu)
|
||||
break
|
||||
|
||||
if start_frame is None or end_frame is None:
|
||||
continue
|
||||
if start_frame == end_frame:
|
||||
continue
|
||||
|
||||
# we have a range and were probably happy with this one.
|
||||
break
|
||||
|
||||
if start_frame is None or end_frame is None:
|
||||
return ('ERROR', f'No / All / not enough keyframe marked Extreme {ob.name} > {b.name}')
|
||||
return ('ERROR', f'No / All or not enough keyframe marked Extreme {ob.name} > {b.name}')
|
||||
if start_frame == end_frame:
|
||||
return ('ERROR', f'Only one key detected as extreme (at frame {start_frame}) !\nNeed at least two chained marked keys')
|
||||
|
||||
|
|
|
@ -4,7 +4,7 @@ bl_info = {
|
|||
"name": "Unfold Anim Cycle",
|
||||
"description": "Anim tools to develop walk/run cycles along a curve",
|
||||
"author": "Samuel Bernou",
|
||||
"version": (0, 9, 1),
|
||||
"version": (1, 0, 0),
|
||||
"blender": (3, 0, 0),
|
||||
"location": "View3D",
|
||||
"warning": "",
|
||||
|
|
Loading…
Reference in New Issue