Skip to content

Commit 0b0e028

Browse files
Merge branch 'solver_issue222' into develop_v0.3.x
2 parents 7c5b51c + e435461 commit 0b0e028

20 files changed

Lines changed: 398 additions & 85 deletions

python/mmSolver/_api/collection.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,13 @@ def _get_auxiliary_attr(col, attr, key, default_value):
143143
keyable=False,
144144
hidden=True,
145145
attributeType='bool')
146+
elif isinstance(default_value, (int, long)):
147+
maya.cmds.addAttr(
148+
attr_node,
149+
longName=aux_name,
150+
keyable=False,
151+
hidden=True,
152+
attributeType='long')
146153
else:
147154
maya.cmds.addAttr(
148155
attr_node,
@@ -189,6 +196,13 @@ def _set_auxiliary_attr(col, attr, key, value):
189196
keyable=False,
190197
hidden=True,
191198
attributeType='bool')
199+
elif isinstance(value, (int, long)):
200+
maya.cmds.addAttr(
201+
attr_node,
202+
longName=aux_name,
203+
keyable=False,
204+
hidden=True,
205+
attributeType='long')
192206
else:
193207
maya.cmds.addAttr(
194208
attr_node,

python/mmSolver/_api/constant.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -224,6 +224,7 @@
224224
EVENT_NAME_NODE_NAME_CHANGED = 'node_name_changed'
225225
EVENT_NAME_NODE_DELETED = 'node_deleted'
226226
EVENT_NAME_MEMBERSHIP_CHANGED = 'node_membership_changed'
227+
EVENT_NAME_MAYA_SCENE_CLOSING = 'maya_scene_closing'
227228
EVENT_NAME_LIST = [
228229
EVENT_NAME_MARKER_CREATED,
229230
EVENT_NAME_BUNDLE_CREATED,
@@ -235,6 +236,7 @@
235236
EVENT_NAME_NODE_NAME_CHANGED,
236237
EVENT_NAME_NODE_DELETED,
237238
EVENT_NAME_MEMBERSHIP_CHANGED,
239+
EVENT_NAME_MAYA_SCENE_CLOSING,
238240
]
239241

240242

python/mmSolver/_api/solverbasic.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -303,6 +303,7 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
303303
lineup_iter_num = self.get_lineup_iteration_num()
304304
use_euler_filter = self._use_euler_filter
305305
eval_object_relationships = self.get_eval_object_relationships()
306+
remove_unused_objects = eval_object_relationships
306307
eval_complex_graphs = self.get_eval_complex_graphs()
307308
precomputed_data = self.get_precomputed_data()
308309

@@ -334,6 +335,8 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
334335
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
335336
sol.set_use_smoothness(False)
336337
sol.set_use_stiffness(False)
338+
sol.set_remove_unused_markers(remove_unused_objects)
339+
sol.set_remove_unused_attributes(remove_unused_objects)
337340
sol.set_precomputed_data(precomputed_data)
338341
for action, vaction in sol.compile(col, mkr_list, attr_list,
339342
withtest=withtest):
@@ -357,6 +360,8 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
357360
sol.set_use_smoothness(not is_first_frame)
358361
sol.set_use_stiffness(not is_first_frame)
359362
sol.set_time_eval_mode(time_eval_mode)
363+
sol.set_remove_unused_markers(remove_unused_objects)
364+
sol.set_remove_unused_attributes(remove_unused_objects)
360365
sol.set_precomputed_data(precomputed_data)
361366

362367
generator = api_compile.compile_solver_with_cache(

python/mmSolver/_api/solverstandard.py

Lines changed: 46 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,7 @@
4646
'lens_distortion',
4747
]
4848

49+
4950
def _gen_two_frame_fwd(int_list):
5051
"""
5152
Given a list of integers, create list of Frame pairs, moving
@@ -170,6 +171,7 @@ def _compile_multi_root_frames(col,
170171
attr_list,
171172
batch_frame_list,
172173
root_iter_num,
174+
remove_unused_objects,
173175
precomputed_data,
174176
withtest,
175177
verbose):
@@ -192,6 +194,11 @@ def _compile_multi_root_frames(col,
192194
Number of iterations to use, when solving root frames.
193195
:type root_iter_num: int
194196
197+
:param remove_unused_objects:
198+
Should objects that are detected as 'unused' be removed from
199+
the solver?
200+
:type remove_unused_objects: bool
201+
195202
:param withtest:
196203
Compile the test/validation Action, as well as the solve Action?
197204
:type withtest: bool
@@ -233,6 +240,8 @@ def _compile_multi_root_frames(col,
233240
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
234241
sol.set_use_smoothness(False)
235242
sol.set_use_stiffness(False)
243+
sol.set_remove_unused_markers(remove_unused_objects)
244+
sol.set_remove_unused_attributes(remove_unused_objects)
236245
sol.set_precomputed_data(precomputed_data)
237246

238247
cache = api_compile.create_compile_solver_cache()
@@ -317,6 +326,7 @@ def _compile_multi_inbetween_frames(col,
317326
global_solve,
318327
eval_complex_graphs,
319328
anim_iter_num,
329+
remove_unused_objects,
320330
precomputed_data,
321331
withtest,
322332
verbose):
@@ -350,6 +360,11 @@ def _compile_multi_inbetween_frames(col,
350360
Number of iterations for solving animated attributes.
351361
:type anim_iter_num: int
352362
363+
:param remove_unused_objects:
364+
Should objects that are detected as 'unused' be removed from
365+
the solver?
366+
:type remove_unused_objects: bool
367+
353368
:param withtest:
354369
Should validation tests be generated?
355370
:type withtest: bool
@@ -373,6 +388,8 @@ def _compile_multi_inbetween_frames(col,
373388
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
374389
sol.set_use_smoothness(False)
375390
sol.set_use_stiffness(False)
391+
sol.set_remove_unused_markers(remove_unused_objects)
392+
sol.set_remove_unused_attributes(remove_unused_objects)
376393
sol.set_precomputed_data(precomputed_data)
377394

378395
cache = api_compile.create_compile_solver_cache()
@@ -397,6 +414,8 @@ def _compile_multi_inbetween_frames(col,
397414
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
398415
sol.set_use_smoothness(not is_first_frame)
399416
sol.set_use_stiffness(not is_first_frame)
417+
sol.set_remove_unused_markers(remove_unused_objects)
418+
sol.set_remove_unused_attributes(remove_unused_objects)
400419
sol.set_time_eval_mode(time_eval_mode)
401420
sol.set_precomputed_data(precomputed_data)
402421

@@ -422,6 +441,7 @@ def _compile_multi_frame(col,
422441
root_frame_strategy,
423442
triangulate_bundles,
424443
use_euler_filter,
444+
remove_unused_objects,
425445
precomputed_data,
426446
withtest,
427447
verbose):
@@ -492,6 +512,11 @@ def _compile_multi_frame(col,
492512
will remove "Euler Flipping".
493513
:type use_euler_filter: bool
494514
515+
:param remove_unused_objects:
516+
Should objects that are detected as 'unused' be removed from
517+
the solver?
518+
:type remove_unused_objects: bool
519+
495520
:param withtest:
496521
Should validation tests be generated?
497522
:type withtest: bool
@@ -559,6 +584,8 @@ def _compile_multi_frame(col,
559584
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
560585
sol.set_use_smoothness(False)
561586
sol.set_use_stiffness(False)
587+
sol.set_remove_unused_markers(remove_unused_objects)
588+
sol.set_remove_unused_attributes(remove_unused_objects)
562589
sol.set_precomputed_data(precomputed_data)
563590

564591
cache = api_compile.create_compile_solver_cache()
@@ -596,6 +623,8 @@ def _compile_multi_frame(col,
596623
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
597624
sol.set_use_smoothness(False)
598625
sol.set_use_stiffness(False)
626+
sol.set_remove_unused_markers(remove_unused_objects)
627+
sol.set_remove_unused_attributes(remove_unused_objects)
599628
sol.set_precomputed_data(precomputed_data)
600629

601630
cache = api_compile.create_compile_solver_cache()
@@ -641,6 +670,7 @@ def _compile_multi_frame(col,
641670
batch_frame_list,
642671
root_iter_num,
643672
precomputed_data,
673+
remove_unused_objects,
644674
withtest,
645675
verbose
646676
)
@@ -680,6 +710,7 @@ def _compile_multi_frame(col,
680710
global_solve,
681711
eval_complex_graphs,
682712
anim_iter_num,
713+
remove_unused_objects,
683714
precomputed_data,
684715
withtest,
685716
verbose,
@@ -697,6 +728,7 @@ def _compile_single_frame(col,
697728
lineup_iter_num,
698729
auto_attr_blocks,
699730
precomputed_data,
731+
remove_unused_objects,
700732
withtest,
701733
verbose):
702734
"""
@@ -727,6 +759,11 @@ def _compile_single_frame(col,
727759
pass
728760
:type lineup_iter_num: int
729761
762+
:param remove_unused_objects:
763+
Should objects that are detected as 'unused' be removed from
764+
the solver?
765+
:type remove_unused_objects: bool
766+
730767
:param withtest:
731768
Should validation tests be generated?
732769
:type withtest: bool
@@ -754,6 +791,8 @@ def _compile_single_frame(col,
754791
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
755792
sol.set_use_smoothness(False)
756793
sol.set_use_stiffness(False)
794+
sol.set_remove_unused_markers(remove_unused_objects)
795+
sol.set_remove_unused_attributes(remove_unused_objects)
757796
sol.set_precomputed_data(precomputed_data)
758797

759798
cache = api_compile.create_compile_solver_cache()
@@ -771,6 +810,8 @@ def _compile_single_frame(col,
771810
sol.set_auto_diff_type(const.AUTO_DIFF_TYPE_FORWARD)
772811
sol.set_use_smoothness(False)
773812
sol.set_use_stiffness(False)
813+
sol.set_remove_unused_markers(remove_unused_objects)
814+
sol.set_remove_unused_attributes(remove_unused_objects)
774815
sol.set_precomputed_data(precomputed_data)
775816

776817
cache = api_compile.create_compile_solver_cache()
@@ -1278,6 +1319,7 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
12781319
only_root_frames = self.get_only_root_frames()
12791320
global_solve = self.get_global_solve()
12801321
eval_object_relationships = self.get_eval_object_relationships()
1322+
remove_unused_objects = eval_object_relationships
12811323
eval_complex_graphs = self.get_eval_complex_graphs()
12821324
block_iter_num = self.get_block_iteration_num()
12831325
root_iter_num = self.get_root_iteration_num()
@@ -1294,8 +1336,9 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
12941336
verbose = True
12951337
precomputed_data = self.get_precomputed_data()
12961338

1339+
LOG.warn('eval_object_relationships=%r', eval_object_relationships)
1340+
12971341
# Pre-calculate the 'affects' relationship.
1298-
# LOG.warn('eval_object_relationships: %r', eval_object_relationships)
12991342
if eval_object_relationships is True:
13001343
generator = solverutils.compile_solver_affects(
13011344
col,
@@ -1322,6 +1365,7 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
13221365
block_iter_num,
13231366
lineup_iter_num,
13241367
auto_attr_blocks,
1368+
remove_unused_objects,
13251369
precomputed_data,
13261370
withtest,
13271371
verbose,
@@ -1345,6 +1389,7 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
13451389
root_frame_strategy,
13461390
triangulate_bundles,
13471391
use_euler_filter,
1392+
remove_unused_objects,
13481393
precomputed_data,
13491394
withtest,
13501395
verbose,

python/mmSolver/_api/solverstep.py

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -287,6 +287,22 @@ def set_use_stiffness(self, value):
287287

288288
############################################################################
289289

290+
def get_remove_unused_markers(self):
291+
return self._data.get('remove_unused_markers')
292+
293+
def set_remove_unused_markers(self, value):
294+
assert isinstance(value, (bool, int))
295+
self._data['remove_unused_markers'] = bool(value)
296+
297+
def get_remove_unused_attributes(self):
298+
return self._data.get('remove_unused_attributes')
299+
300+
def set_remove_unused_attributes(self, value):
301+
assert isinstance(value, (bool, int))
302+
self._data['remove_unused_attributes'] = bool(value)
303+
304+
############################################################################
305+
290306
def get_attributes_use_animated(self):
291307
return self._attributes_use.get('animated')
292308

@@ -546,6 +562,9 @@ def compile(self, col, mkr_list, attr_list, withtest=False):
546562
kwargs['robustLossScale'] = 1.0
547563
kwargs['timeEvalMode'] = self.get_time_eval_mode()
548564

565+
kwargs['removeUnusedMarkers'] = self.get_remove_unused_markers()
566+
kwargs['removeUnusedAttributes'] = self.get_remove_unused_attributes()
567+
549568
# TODO: Add 'robustLossType' flag.
550569
# TODO: Add 'robustLossScale' flag.
551570
# TODO: Add 'autoParamScaling' flag.

python/mmSolver/_api/solverutils.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,12 @@
3434
def compile_solver_affects(col, mkr_list, attr_list,
3535
precomputed_data,
3636
withtest):
37+
# Reset the used hints to 'unknown' before setting 'used' or
38+
# 'unused' flags.
39+
generator = compile_reset_used_hints(col, mkr_list, attr_list)
40+
for action, vaction in generator:
41+
yield action, vaction
42+
3743
sol = solveraffects.SolverAffects()
3844
sol.set_precomputed_data(precomputed_data)
3945

python/mmSolver/api.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -185,6 +185,7 @@
185185
EVENT_NAME_NODE_NAME_CHANGED,
186186
EVENT_NAME_NODE_DELETED,
187187
EVENT_NAME_MEMBERSHIP_CHANGED,
188+
EVENT_NAME_MAYA_SCENE_CLOSING,
188189
EVENT_NAME_LIST,
189190

190191
ATTRIBUTE_USED_HINT_DEFAULT_VALUE,
@@ -303,6 +304,7 @@
303304
'EVENT_NAME_NODE_NAME_CHANGED',
304305
'EVENT_NAME_NODE_DELETED',
305306
'EVENT_NAME_MEMBERSHIP_CHANGED',
307+
'EVENT_NAME_MAYA_SCENE_CLOSING',
306308
'EVENT_NAME_LIST',
307309
'ATTRIBUTE_USED_HINT_DEFAULT_VALUE',
308310
'ATTRIBUTE_USED_HINT_USED_VALUE',

python/mmSolver/tools/registerevents/lib.py

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,3 +84,17 @@ def run_update_output_attributes_in_solver_ui(**kwargs):
8484
e = time.time()
8585
LOG.debug("run_update_output_attributes_in_solver_ui: time=%s", e - s)
8686
return
87+
88+
89+
def run_close_all_windows(**kwargs):
90+
"""
91+
Find and close all tool UIs sub-classed from BaseMayaWindow.
92+
"""
93+
LOG.debug("run_close_all_windows: %r", kwargs)
94+
s = time.time()
95+
import mmSolver.ui.base_maya_window
96+
cls = mmSolver.ui.base_maya_window.BaseMayaWindow
97+
cls.close_all_instances()
98+
e = time.time()
99+
LOG.debug("run_close_all_windows: time=%s", e - s)
100+
return

python/mmSolver/tools/registerevents/tool.py

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,19 @@ def _register_changed_attribute_update_solver_ui():
7979
return
8080

8181

82+
def _register_closing_maya_scene():
83+
"""When the current Maya scene is closing, close all windows, because
84+
the windows might have pointers/references to objects in the scene
85+
file and we cannot allow the pointers to dangle.
86+
"""
87+
import mmSolver.api as mmapi
88+
event_utils.add_function_to_event(
89+
mmapi.EVENT_NAME_MAYA_SCENE_CLOSING,
90+
lib.run_close_all_windows,
91+
deferred=False)
92+
return
93+
94+
8295
def register_events():
8396
"""
8497
Initialises the registry of events for mmSolver.
@@ -90,4 +103,16 @@ def register_events():
90103
_register_created_marker_connect_to_collection()
91104
_register_changed_collection_update_solver_ui()
92105
_register_changed_attribute_update_solver_ui()
106+
_register_closing_maya_scene()
107+
108+
# Maya callback when Maya scene is "flushing" from memory ( AKA
109+
# the scene is closing).
110+
def flushing_scene_func():
111+
LOG.debug('MM Solver Flushing Scene...')
112+
event_name = mmapi.EVENT_NAME_MAYA_SCENE_CLOSING
113+
event_utils.trigger_event(event_name)
114+
115+
import maya.cmds
116+
maya.cmds.scriptJob(
117+
conditionTrue=('flushingScene', flushing_scene_func))
93118
return

0 commit comments

Comments
 (0)