From d5577b994c70363d5761f1592eddba2ebe9d62dc Mon Sep 17 00:00:00 2001 From: Thomas Goyne Date: Wed, 22 Feb 2012 22:00:54 +0000 Subject: [PATCH] Move lead in/out logic to the timing controllers This makes adding lead in/out work correctly when autocommit is disabled, and improves the behavior of adding lead-in when in karaoke mode. Originally committed to SVN as r6502. --- aegisub/src/ass_karaoke.cpp | 19 ++++++++++++++++++ aegisub/src/ass_karaoke.h | 2 ++ aegisub/src/audio_timing.h | 6 ++++++ aegisub/src/audio_timing_dialogue.cpp | 14 +++++++++++++ aegisub/src/audio_timing_karaoke.cpp | 29 +++++++++++++++++++++++++++ aegisub/src/command/time.cpp | 12 ++++------- 6 files changed, 74 insertions(+), 8 deletions(-) diff --git a/aegisub/src/ass_karaoke.cpp b/aegisub/src/ass_karaoke.cpp index 8a31a1d0b..55b1a8f5c 100644 --- a/aegisub/src/ass_karaoke.cpp +++ b/aegisub/src/ass_karaoke.cpp @@ -264,6 +264,25 @@ void AssKaraoke::SetStartTime(size_t syl_idx, int time) { prev.duration += delta; } +void AssKaraoke::SetLineTimes(int start_time, int end_time) { + assert(end_time >= start_time); + + size_t idx = 0; + do { + int delta = start_time - syls[idx].start_time; + syls[idx].start_time = start_time; + syls[idx].duration = std::max(0, syls[idx].duration - delta); + } while (++idx < syls.size() && syls[idx].start_time < start_time); + + idx = syls.size() - 1; + while (syls[idx].start_time > end_time) { + syls[idx].start_time = end_time; + syls[idx].duration = 0; + --idx; + } + syls[idx].duration = end_time - syls[idx].start_time; +} + void AssKaraoke::SplitLines(std::set const& lines, agi::Context *c) { if (lines.empty()) return; diff --git a/aegisub/src/ass_karaoke.h b/aegisub/src/ass_karaoke.h index 93288c3eb..a59b860de 100644 --- a/aegisub/src/ass_karaoke.h +++ b/aegisub/src/ass_karaoke.h @@ -77,6 +77,8 @@ public: void RemoveSplit(size_t syl_idx); /// Set the start time of a syllable in ms void SetStartTime(size_t syl_idx, int time); + /// Adjust the line's start and end times without shifting the syllables + void SetLineTimes(int start_time, int end_time); typedef std::vector::const_iterator iterator; diff --git a/aegisub/src/audio_timing.h b/aegisub/src/audio_timing.h index 13964784b..683480dac 100644 --- a/aegisub/src/audio_timing.h +++ b/aegisub/src/audio_timing.h @@ -103,6 +103,12 @@ public: /// Revert all changes to the last committed state. virtual void Revert() = 0; + /// Add lead-in time to the current timing unit + virtual void AddLeadIn() = 0; + + /// Add lead-out time to the current timing unit + virtual void AddLeadOut() = 0; + /// @brief Determine if a position is close to a draggable marker /// @param ms The time in milliseconds to test /// @param sensitivity Distance in milliseconds to consider markers as nearby diff --git a/aegisub/src/audio_timing_dialogue.cpp b/aegisub/src/audio_timing_dialogue.cpp index 5c5cbc990..aab5ca057 100644 --- a/aegisub/src/audio_timing_dialogue.cpp +++ b/aegisub/src/audio_timing_dialogue.cpp @@ -372,6 +372,8 @@ public: void Prev(); void Commit(); void Revert(); + void AddLeadIn(); + void AddLeadOut(); bool IsNearbyMarker(int ms, int sensitivity) const; std::vector OnLeftClick(int ms, bool ctrl_down, int sensitivity, int snap_range); std::vector OnRightClick(int ms, bool, int sensitivity, int snap_range); @@ -545,6 +547,18 @@ void AudioTimingControllerDialogue::Revert() RegenerateInactiveLines(); } +void AudioTimingControllerDialogue::AddLeadIn() +{ + DialogueTimingMarker *m = active_line.GetLeftMarker(); + SetMarkers(std::vector(1, m), *m - OPT_GET("Audio/Lead/IN")->GetInt()); +} + +void AudioTimingControllerDialogue::AddLeadOut() +{ + DialogueTimingMarker *m = active_line.GetRightMarker(); + SetMarkers(std::vector(1, m), *m + OPT_GET("Audio/Lead/OUT")->GetInt()); +} + bool AudioTimingControllerDialogue::IsNearbyMarker(int ms, int sensitivity) const { assert(sensitivity >= 0); diff --git a/aegisub/src/audio_timing_karaoke.cpp b/aegisub/src/audio_timing_karaoke.cpp index bc72eb67a..37f32f51d 100644 --- a/aegisub/src/audio_timing_karaoke.cpp +++ b/aegisub/src/audio_timing_karaoke.cpp @@ -115,6 +115,7 @@ class AudioTimingControllerKaraoke : public AudioTimingController { void OnAutoNextChange(agi::OptionValue const& opt); void DoCommit(); + void ApplyLead(bool announce_primary); public: // AudioTimingController implementation @@ -128,6 +129,8 @@ public: void Prev(); void Commit(); void Revert(); + void AddLeadIn(); + void AddLeadOut(); bool IsNearbyMarker(int ms, int sensitivity) const; std::vector OnLeftClick(int ms, bool, int sensitivity, int); std::vector OnRightClick(int, bool, int, int) { return std::vector(); } @@ -279,6 +282,32 @@ void AudioTimingControllerKaraoke::Revert() { AnnounceMarkerMoved(); } +void AudioTimingControllerKaraoke::AddLeadIn() { + start_marker.Move(start_marker - OPT_GET("Audio/Lead/IN")->GetInt()); + labels.front().range = TimeRange(start_marker, labels.front().range.end()); + ApplyLead(cur_syl == 0); +} + +void AudioTimingControllerKaraoke::AddLeadOut() { + end_marker.Move(end_marker + OPT_GET("Audio/Lead/OUT")->GetInt()); + labels.back().range = TimeRange(labels.back().range.begin(), end_marker); + ApplyLead(cur_syl == markers.size()); +} + +void AudioTimingControllerKaraoke::ApplyLead(bool announce_primary) { + kara->SetLineTimes(start_marker, end_marker); + + AnnounceUpdatedStyleRanges(); + AnnounceMarkerMoved(); + if (announce_primary) + AnnounceUpdatedPrimaryRange(); + + if (auto_commit) + DoCommit(); + else + commit_id = -1; +} + bool AudioTimingControllerKaraoke::IsNearbyMarker(int ms, int sensitivity) const { TimeRange range(ms - sensitivity, ms + sensitivity); diff --git a/aegisub/src/command/time.cpp b/aegisub/src/command/time.cpp index d85717e81..631905b91 100644 --- a/aegisub/src/command/time.cpp +++ b/aegisub/src/command/time.cpp @@ -250,10 +250,8 @@ struct time_add_lead_in : public Command { STR_DISP("Add lead in") STR_HELP("Add lead in") void operator()(agi::Context *c) { - if (AssDialogue *line = c->selectionController->GetActiveLine()) { - line->Start = line->Start - OPT_GET("Audio/Lead/IN")->GetInt(); - c->ass->Commit(_("add lead in"), AssFile::COMMIT_DIAG_TIME); - } + if (c->audioController->GetTimingController()) + c->audioController->GetTimingController()->AddLeadIn(); } }; @@ -263,10 +261,8 @@ struct time_add_lead_out : public Command { STR_DISP("Add lead out") STR_HELP("Add lead out") void operator()(agi::Context *c) { - if (AssDialogue *line = c->selectionController->GetActiveLine()) { - line->End = line->End + OPT_GET("Audio/Lead/OUT")->GetInt(); - c->ass->Commit(_("add lead out"), AssFile::COMMIT_DIAG_TIME); - } + if (c->audioController->GetTimingController()) + c->audioController->GetTimingController()->AddLeadOut(); } };