Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorColin Marmont <Kdaf>2022-02-28 14:23:56 +0300
committerSybren A. Stüvel <sybren@blender.org>2022-02-28 14:28:19 +0300
commit1558b270e9fcbc2e23fa248b0e7e770dddae155c (patch)
tree1377db616df34efcb147664788808d85338ba19d /source/blender/editors/animation
parent6f23401e984ee5bad621109ff78eeb6850044fee (diff)
Animation: Sensible frame range for motion paths
Motion paths can now be initialised to more sensible frame ranges, rather than simply 1-250: - Scene Frame Range - Selected Keyframes - All Keyframes The Motion Paths operators are now also added to the Object context menu and the Dopesheet context menu. The scene range operator was removed, because the operators now automatically find the range when baking the motion paths. The clear operator now appears separated in "Selected Only" and "All", because it was not clear for the user what the button was doing. Reviewed By: sybren, looch Maniphest Tasks: T93047 Differential Revision: https://developer.blender.org/D13687
Diffstat (limited to 'source/blender/editors/animation')
-rw-r--r--source/blender/editors/animation/anim_motion_paths.c49
-rw-r--r--source/blender/editors/animation/keyframes_keylist.cc48
2 files changed, 90 insertions, 7 deletions
diff --git a/source/blender/editors/animation/anim_motion_paths.c b/source/blender/editors/animation/anim_motion_paths.c
index 539227933cf..2c99cd1cc1f 100644
--- a/source/blender/editors/animation/anim_motion_paths.c
+++ b/source/blender/editors/animation/anim_motion_paths.c
@@ -340,6 +340,55 @@ static void motionpath_free_free_tree_data(ListBase *targets)
}
}
+void animviz_motionpath_compute_range(Object *ob, Scene *scene)
+{
+ struct AnimKeylist *keylist = ED_keylist_create();
+ bAnimVizSettings *avs;
+ if (ob->mode == OB_MODE_POSE) {
+ avs = &ob->pose->avs;
+ bArmature *arm = ob->data;
+
+ if (!ELEM(NULL, ob->adt, ob->adt->action, arm->adt)) {
+ /* Loop through all the fcurves and get only the keylists for the bone location fcurves */
+ LISTBASE_FOREACH (FCurve *, fcu, &ob->adt->action->curves) {
+ if (strstr(fcu->rna_path, "pose.bones[") && strstr(fcu->rna_path, "location")) {
+ fcurve_to_keylist(arm->adt, fcu, keylist, 0);
+ }
+ }
+ }
+ }
+ else {
+ avs = &ob->avs;
+
+ if (!ELEM(NULL, ob->adt, ob->adt->action)) {
+ /* Loop through all the fcurves and get only the keylists for the location fcurves */
+ LISTBASE_FOREACH (FCurve *, fcu, &ob->adt->action->curves) {
+ if (strcmp(fcu->rna_path, "location") == 0) {
+ fcurve_to_keylist(ob->adt, fcu, keylist, 0);
+ }
+ }
+ }
+ }
+
+ if (ED_keylist_is_empty(keylist) || (avs->path_range == MOTIONPATH_RANGE_SCENE)) {
+ /* Apply scene frame range if no keys where found or if scene range is selected */
+ avs->path_sf = PSFRA;
+ avs->path_ef = PEFRA;
+ }
+ else {
+ /* Compute keys range */
+ Range2f frame_range;
+ const bool only_selected = avs->path_range == MOTIONPATH_RANGE_KEYS_SELECTED;
+ /* Get range for all keys if selected_only is false or if no keys are selected */
+ if (!(only_selected && ED_keylist_selected_keys_frame_range(keylist, &frame_range))) {
+ ED_keylist_all_keys_frame_range(keylist, &frame_range);
+ }
+ avs->path_sf = frame_range.min;
+ avs->path_ef = frame_range.max;
+ }
+ ED_keylist_free(keylist);
+}
+
void animviz_calc_motionpaths(Depsgraph *depsgraph,
Main *bmain,
Scene *scene,
diff --git a/source/blender/editors/animation/keyframes_keylist.cc b/source/blender/editors/animation/keyframes_keylist.cc
index 3f9592fb4ae..0b795fea278 100644
--- a/source/blender/editors/animation/keyframes_keylist.cc
+++ b/source/blender/editors/animation/keyframes_keylist.cc
@@ -304,7 +304,21 @@ const struct ListBase *ED_keylist_listbase(const AnimKeylist *keylist)
return &keylist->key_columns;
}
-bool ED_keylist_frame_range(const struct AnimKeylist *keylist, Range2f *r_frame_range)
+static void keylist_first_last(const struct AnimKeylist *keylist,
+ const struct ActKeyColumn **first_column,
+ const struct ActKeyColumn **last_column)
+{
+ if (keylist->is_runtime_initialized) {
+ *first_column = &keylist->runtime.key_columns[0];
+ *last_column = &keylist->runtime.key_columns[keylist->column_len - 1];
+ }
+ else {
+ *first_column = static_cast<const ActKeyColumn *>(keylist->key_columns.first);
+ *last_column = static_cast<const ActKeyColumn *>(keylist->key_columns.last);
+ }
+}
+
+bool ED_keylist_all_keys_frame_range(const struct AnimKeylist *keylist, Range2f *r_frame_range)
{
BLI_assert(r_frame_range);
@@ -314,13 +328,33 @@ bool ED_keylist_frame_range(const struct AnimKeylist *keylist, Range2f *r_frame_
const ActKeyColumn *first_column;
const ActKeyColumn *last_column;
- if (keylist->is_runtime_initialized) {
- first_column = &keylist->runtime.key_columns[0];
- last_column = &keylist->runtime.key_columns[keylist->column_len - 1];
+ keylist_first_last(keylist, &first_column, &last_column);
+ r_frame_range->min = first_column->cfra;
+ r_frame_range->max = last_column->cfra;
+
+ return true;
+}
+
+bool ED_keylist_selected_keys_frame_range(const struct AnimKeylist *keylist,
+ Range2f *r_frame_range)
+{
+ BLI_assert(r_frame_range);
+
+ if (ED_keylist_is_empty(keylist)) {
+ return false;
}
- else {
- first_column = static_cast<const ActKeyColumn *>(keylist->key_columns.first);
- last_column = static_cast<const ActKeyColumn *>(keylist->key_columns.last);
+
+ const ActKeyColumn *first_column;
+ const ActKeyColumn *last_column;
+ keylist_first_last(keylist, &first_column, &last_column);
+ while (first_column && !(first_column->sel & SELECT)) {
+ first_column = first_column->next;
+ }
+ while (last_column && !(last_column->sel & SELECT)) {
+ last_column = last_column->prev;
+ }
+ if (!first_column || !last_column || first_column == last_column) {
+ return false;
}
r_frame_range->min = first_column->cfra;
r_frame_range->max = last_column->cfra;