mirror of
https://github.com/cookiengineer/audacity
synced 2025-07-23 16:08:07 +02:00
Bug 1290 - "Split New" clips cannot be dragged back into the track they came from.
Fixed by giving some tolerance in how the dragged clip(s) are placed. The tolerance is 1px, so it depends on the zoom. Therefore if zoomed in your positioning is more precise.
This commit is contained in:
parent
4d43d2273b
commit
e984211cce
@ -2372,13 +2372,32 @@ bool WaveTrack::CanOffsetClip(WaveClip* clip, double amount,
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool WaveTrack::CanInsertClip(WaveClip* clip, double slideBy)
|
bool WaveTrack::CanInsertClip(WaveClip* clip, double &slideBy, double &tolerance)
|
||||||
{
|
{
|
||||||
for (const auto &c : mClips)
|
for (const auto &c : mClips)
|
||||||
{
|
{
|
||||||
if (c->GetStartTime() < (clip->GetEndTime()+slideBy) &&
|
double d1 = c->GetStartTime() - (clip->GetEndTime()+slideBy);
|
||||||
c->GetEndTime() > (clip->GetStartTime()+slideBy))
|
double d2 = (clip->GetStartTime()+slideBy) - c->GetEndTime();
|
||||||
return false; // clips overlap
|
if ( (d1<0) && (d2<0) )
|
||||||
|
{
|
||||||
|
// 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.
|
||||||
|
if( -d1 < tolerance ){
|
||||||
|
slideBy +=d1;
|
||||||
|
d2 += d1;
|
||||||
|
tolerance /=1000;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( -d2 < tolerance ){
|
||||||
|
slideBy -= d2;
|
||||||
|
tolerance /=1000;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return false; // clips overlap No tolerance left.
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
@ -491,7 +491,7 @@ class AUDACITY_DLL_API WaveTrack final : public PlayableTrack {
|
|||||||
// Before moving a clip into a track (or inserting a clip), use this
|
// Before moving a clip into a track (or inserting a clip), use this
|
||||||
// function to see if the times are valid (i.e. don't overlap with
|
// function to see if the times are valid (i.e. don't overlap with
|
||||||
// existing clips).
|
// existing clips).
|
||||||
bool CanInsertClip(WaveClip* clip, double slideBy=0.0);
|
bool CanInsertClip(WaveClip* clip, double &slideBy, double &tolerance);
|
||||||
|
|
||||||
// Remove the clip from the track and return a SMART pointer to it.
|
// Remove the clip from the track and return a SMART pointer to it.
|
||||||
// You assume responsibility for its memory!
|
// You assume responsibility for its memory!
|
||||||
|
@ -707,25 +707,39 @@ UIHandle::Result TimeShiftHandle::Drag
|
|||||||
|
|
||||||
// Now check that the move is possible
|
// Now check that the move is possible
|
||||||
bool ok = true;
|
bool ok = true;
|
||||||
|
// The test for tolerance will need review with FishEye!
|
||||||
|
// 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);
|
||||||
|
|
||||||
|
// The desiredSlideAmount may change and the tolerance may get used up.
|
||||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||||
ok && ii < nn; ++ii) {
|
ok && ii < nn; ++ii) {
|
||||||
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
||||||
WaveClip *const pSrcClip = trackClip.clip;
|
WaveClip *const pSrcClip = trackClip.clip;
|
||||||
if (pSrcClip)
|
if (pSrcClip)
|
||||||
ok = trackClip.dstTrack->CanInsertClip(pSrcClip, desiredSlideAmount);
|
ok = trackClip.dstTrack->CanInsertClip(pSrcClip, desiredSlideAmount, tolerance);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!ok) {
|
if (!ok) {
|
||||||
|
// Failure, even with using tolerance.
|
||||||
// Failure -- put clips back where they were
|
// Failure -- put clips back where they were
|
||||||
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
for ( unsigned ii = 0, nn = mClipMoveState.capturedClipArray.size();
|
||||||
ii < nn; ++ii) {
|
ii < nn; ++ii) {
|
||||||
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
TrackClip &trackClip = mClipMoveState.capturedClipArray[ii];
|
||||||
WaveClip *const pSrcClip = trackClip.clip;
|
WaveClip *const pSrcClip = trackClip.clip;
|
||||||
if (pSrcClip)
|
if (pSrcClip){
|
||||||
|
// Attempt to move to a new track did not work.
|
||||||
|
// Put the clip back appropriately shifted!
|
||||||
|
trackClip.holder->Offset(slide);
|
||||||
// Assume track is wave because it has a clip
|
// Assume track is wave because it has a clip
|
||||||
static_cast<WaveTrack*>(trackClip.track)->
|
static_cast<WaveTrack*>(trackClip.track)->
|
||||||
AddClip(std::move(trackClip.holder));
|
AddClip(std::move(trackClip.holder));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
// Make the offset permanent; start from a "clean slate"
|
||||||
|
mMouseClickX = event.m_x;
|
||||||
return RefreshAll;
|
return RefreshAll;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user