mirror of
https://github.com/cookiengineer/audacity
synced 2025-09-24 16:01:16 +02:00
Bug 1290 - "Split New" clips cannot be dragged back into the track they came from.
Earlier fix was broken and allowed clips to overlap. Updated code: - Checks that the modified slide amount is legal, against ALL clips, not just against later clips in the array. - Computes tolerance correctly. - Typically uses tolerance just once. - Moves selection with clip - Only restarts sliding with a 'clean slate' IF there was room on the original track. Previously the code could reject a move to a new track, and then mistakenly allow just the horizontal part of the move on the original track(s), even with a clip blocking the way.
This commit is contained in:
parent
33d9a130c8
commit
1b4999d0d3
@ -2382,16 +2382,18 @@ bool WaveTrack::CanInsertClip(WaveClip* clip, double &slideBy, double &toleranc
|
||||
{
|
||||
// clips overlap.
|
||||
// Try to rescue it.
|
||||
// The rescue logic is not perfect, but
|
||||
// a) will not move the clip by more than once
|
||||
// b) is OK in simple scenarios.
|
||||
// The rescue logic is not perfect, and will typically
|
||||
// move the clip at most once.
|
||||
// We divide by 1000 rather than set to 0, to allow for
|
||||
// a second 'micro move' that is really about rounding error.
|
||||
if( -d1 < tolerance ){
|
||||
// right edge of clip overlaps slightly.
|
||||
// slide clip left a small amount.
|
||||
slideBy +=d1;
|
||||
d2 += d1;
|
||||
tolerance /=1000;
|
||||
}
|
||||
|
||||
if( -d2 < tolerance ){
|
||||
} else if( -d2 < tolerance ){
|
||||
// left edge of clip overlaps slightly.
|
||||
// slide clip right a small amount.
|
||||
slideBy -= d2;
|
||||
tolerance /=1000;
|
||||
}
|
||||
|
@ -711,7 +711,7 @@ UIHandle::Result TimeShiftHandle::Drag
|
||||
// The tolerance is supposed to be the time for one pixel, i.e. one pixel tolerance
|
||||
// at current zoom.
|
||||
double slide = desiredSlideAmount; // remember amount requested.
|
||||
double tolerance = viewInfo.PositionToTime(event.m_x+1) - viewInfo.PositionToTime(event.m_x+1);
|
||||
double tolerance = viewInfo.PositionToTime(event.m_x+1) - viewInfo.PositionToTime(event.m_x);
|
||||
|
||||
// The desiredSlideAmount may change and the tolerance may get used up.
|
||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||
@ -722,24 +722,61 @@ UIHandle::Result TimeShiftHandle::Drag
|
||||
ok = trackClip.dstTrack->CanInsertClip(pSrcClip, desiredSlideAmount, tolerance);
|
||||
}
|
||||
|
||||
if( ok ) {
|
||||
// fits ok, but desiredSlideAmount could have been updated to get the clip to fit.
|
||||
// Check again, in the new position, this time with zero tolerance.
|
||||
tolerance = 0.0;
|
||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||
ok && ii < nn; ++ii) {
|
||||
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
||||
WaveClip *const pSrcClip = trackClip.clip;
|
||||
if (pSrcClip)
|
||||
ok = trackClip.dstTrack->CanInsertClip(pSrcClip, desiredSlideAmount, tolerance);
|
||||
}
|
||||
}
|
||||
|
||||
if (!ok) {
|
||||
// Failure, even with using tolerance.
|
||||
// Failure -- put clips back where they were
|
||||
// Failure -- we'll put clips back where they were
|
||||
// ok will next indicate if a horizontal slide is OK.
|
||||
ok = true; // assume slide is OK.
|
||||
tolerance = 0.0;
|
||||
desiredSlideAmount = slide;
|
||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||
ii < nn; ++ii) {
|
||||
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
||||
WaveClip *const pSrcClip = trackClip.clip;
|
||||
if (pSrcClip){
|
||||
// back to the track it came from...
|
||||
trackClip.dstTrack = static_cast<WaveTrack*>(trackClip.track);
|
||||
ok = ok && trackClip.dstTrack->CanInsertClip(pSrcClip, desiredSlideAmount, tolerance);
|
||||
}
|
||||
}
|
||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||
ii < nn; ++ii) {
|
||||
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
||||
WaveClip *const pSrcClip = trackClip.clip;
|
||||
if (pSrcClip){
|
||||
|
||||
// Attempt to move to a new track did not work.
|
||||
// Put the clip back appropriately shifted!
|
||||
trackClip.holder->Offset(slide);
|
||||
if( ok)
|
||||
trackClip.holder->Offset(slide);
|
||||
// Assume track is wave because it has a clip
|
||||
static_cast<WaveTrack*>(trackClip.track)->
|
||||
AddClip(std::move(trackClip.holder));
|
||||
}
|
||||
}
|
||||
// Make the offset permanent; start from a "clean slate"
|
||||
mMouseClickX = event.m_x;
|
||||
if( ok ) {
|
||||
mMouseClickX = event.m_x;
|
||||
if (mClipMoveState.capturedClipIsSelection) {
|
||||
// Slide the selection, too
|
||||
viewInfo.selectedRegion.move( slide );
|
||||
}
|
||||
mClipMoveState.hSlideAmount = 0;
|
||||
}
|
||||
|
||||
return RefreshAll;
|
||||
}
|
||||
else {
|
||||
@ -778,7 +815,6 @@ UIHandle::Result TimeShiftHandle::Drag
|
||||
viewInfo.selectedRegion.move( mClipMoveState.hSlideAmount );
|
||||
}
|
||||
|
||||
|
||||
if (slidVertically) {
|
||||
// NEW origin
|
||||
mClipMoveState.hSlideAmount = 0;
|
||||
|
Loading…
x
Reference in New Issue
Block a user