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:
authorJoshua Leung <aligorith@gmail.com>2008-05-14 13:00:22 +0400
committerJoshua Leung <aligorith@gmail.com>2008-05-14 13:00:22 +0400
commit9fdb4965a32fdc5fbfe6ad169630672e70d85470 (patch)
tree8c25094eb69f70bcb2b05fbf19fcb4be74f4d7e1 /source/blender/src/transform_conversions.c
parentf98085bd7ec3aba6775df4ab25c2c5475e37cae3 (diff)
NLA and IPO now have the "AfterTrans Keyframe" option that prevents the creation of duplicate keyframes after transform.
Diffstat (limited to 'source/blender/src/transform_conversions.c')
-rw-r--r--source/blender/src/transform_conversions.c115
1 files changed, 112 insertions, 3 deletions
diff --git a/source/blender/src/transform_conversions.c b/source/blender/src/transform_conversions.c
index 6636c435b8c..e42eedee1f7 100644
--- a/source/blender/src/transform_conversions.c
+++ b/source/blender/src/transform_conversions.c
@@ -144,6 +144,8 @@ extern ListBase editelems;
/* local function prototype - for Object/Bone Constraints */
static short constraints_list_needinv(TransInfo *t, ListBase *list);
+/* local function prototype - for finding number of keyframes that are selected for editing */
+static int count_ipo_keys(Ipo *ipo, char side, float cfra);
/* ************************** Functions *************************** */
@@ -2490,6 +2492,93 @@ static void posttrans_action_clean (bAction *act)
BLI_freelistN(&act_data);
}
+/* Called by special_aftertrans_update to make sure selected keyframes replace
+ * any other keyframes which may reside on that frame (that is not selected).
+ * remake_all_ipos should have already been called
+ */
+static void posttrans_nla_clean (TransInfo *t)
+{
+ Base *base;
+ Object *ob;
+ bActionStrip *strip;
+ bActionChannel *achan;
+ bConstraintChannel *conchan;
+ float cfra;
+ char side;
+ int i;
+
+ /* which side of the current frame should be allowed */
+ if (t->mode == TFM_TIME_EXTEND) {
+ /* only side on which mouse is gets transformed */
+ float xmouse, ymouse;
+
+ areamouseco_to_ipoco(G.v2d, t->imval, &xmouse, &ymouse);
+ side = (xmouse > CFRA) ? 'R' : 'L';
+ }
+ else {
+ /* normal transform - both sides of current frame are considered */
+ side = 'B';
+ }
+
+ /* only affect keyframes */
+ for (base=G.scene->base.first; base; base=base->next) {
+ ob= base->object;
+
+ /* Check object ipos */
+ i= count_ipo_keys(ob->ipo, side, CFRA);
+ if (i) posttrans_ipo_clean(ob->ipo);
+
+ /* Check object constraint ipos */
+ for (conchan=ob->constraintChannels.first; conchan; conchan=conchan->next) {
+ i= count_ipo_keys(conchan->ipo, side, CFRA);
+ if (i) posttrans_ipo_clean(ob->ipo);
+ }
+
+ /* skip actions and nlastrips if object is collapsed */
+ if (ob->nlaflag & OB_NLA_COLLAPSED)
+ continue;
+
+ /* Check action ipos */
+ if (ob->action) {
+ /* exclude if strip is selected too */
+ for (strip=ob->nlastrips.first; strip; strip=strip->next) {
+ if (strip->flag & ACTSTRIP_SELECT) {
+ if (strip->act == ob->action)
+ break;
+ }
+ }
+ if (strip==NULL) {
+ cfra = get_action_frame(ob, CFRA);
+
+ for (achan=ob->action->chanbase.first; achan; achan=achan->next) {
+ if (EDITABLE_ACHAN(achan)) {
+ i= count_ipo_keys(achan->ipo, side, cfra);
+ if (i) {
+ actstrip_map_ipo_keys(ob, achan->ipo, 0, 1);
+ posttrans_ipo_clean(achan->ipo);
+ actstrip_map_ipo_keys(ob, achan->ipo, 1, 1);
+ }
+
+ /* Check action constraint ipos */
+ if (EXPANDED_ACHAN(achan) && FILTER_CON_ACHAN(achan)) {
+ for (conchan=achan->constraintChannels.first; conchan; conchan=conchan->next) {
+ if (EDITABLE_CONCHAN(conchan)) {
+ i = count_ipo_keys(conchan->ipo, side, cfra);
+ if (i) {
+ actstrip_map_ipo_keys(ob, conchan->ipo, 0, 1);
+ posttrans_ipo_clean(conchan->ipo);
+ actstrip_map_ipo_keys(ob, conchan->ipo, 1, 1);
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+ }
+}
+
/* ----------------------------- */
/* This function tests if a point is on the "mouse" side of the cursor/frame-marking */
@@ -3487,8 +3576,6 @@ void special_aftertrans_update(TransInfo *t)
if (key->ipo) {
IpoCurve *icu;
-
-
if ( (G.saction->flag & SACTION_NOTRANSKEYCULL)==0 &&
(cancelled == 0) )
{
@@ -3507,17 +3594,39 @@ void special_aftertrans_update(TransInfo *t)
G.saction->flag &= ~SACTION_MOVING;
}
else if (t->spacetype == SPACE_NLA) {
+ recalc_all_ipos(); // bad
synchronize_action_strips();
/* cleanup */
for (base=G.scene->base.first; base; base=base->next)
base->flag &= ~(BA_HAS_RECALC_OB|BA_HAS_RECALC_DATA);
- recalc_all_ipos(); // bad
+ /* after transform, remove duplicate keyframes on a frame that resulted from transform */
+ if ( (G.snla->flag & SNLA_NOTRANSKEYCULL)==0 &&
+ (cancelled == 0) )
+ {
+ posttrans_nla_clean(t);
+ }
}
else if (t->spacetype == SPACE_IPO) {
// FIXME! is there any code from the old transform_ipo that needs to be added back?
+ /* after transform, remove duplicate keyframes on a frame that resulted from transform */
+ if (G.sipo->ipo)
+ {
+ if ( (G.sipo->flag & SIPO_NOTRANSKEYCULL)==0 &&
+ (cancelled == 0) )
+ {
+ if (NLA_IPO_SCALED) {
+ actstrip_map_ipo_keys(OBACT, G.sipo->ipo, 0, 1);
+ posttrans_ipo_clean(G.sipo->ipo);
+ actstrip_map_ipo_keys(OBACT, G.sipo->ipo, 1, 1);
+ }
+ else
+ posttrans_ipo_clean(G.sipo->ipo);
+ }
+ }
+
/* resetting slow-parents isn't really necessary when editing sequence ipo's */
if (G.sipo->blocktype==ID_SEQ)
resetslowpar= 0;