diff --git a/app/widget/timelinewidget/timelinewidget.cpp b/app/widget/timelinewidget/timelinewidget.cpp index 9a0751df1..b9c942cf1 100644 --- a/app/widget/timelinewidget/timelinewidget.cpp +++ b/app/widget/timelinewidget/timelinewidget.cpp @@ -183,8 +183,7 @@ void TimelineWidget::Clear() block_items_.clear(); // Emit that we've deselected any selected blocks - emit BlocksDeselected(selected_blocks_); - selected_blocks_.clear(); + SignalDeselectedAllBlocks(); // Set null timebase SetTimebase(0); @@ -380,7 +379,7 @@ void TimelineWidget::SelectAll() } } - SignalSelectedBlocks(newly_selected_blocks); + SignalSelectedBlocks(newly_selected_blocks, false); } void TimelineWidget::DeselectAll() @@ -391,11 +390,8 @@ void TimelineWidget::DeselectAll() // Update all viewports UpdateViewports(); - // Emit signal that any previously selected block is no longer selected - emit BlocksDeselected(selected_blocks_); - - // Empty selected blocks list - selected_blocks_.clear(); + // Clear list and emit signal + SignalDeselectedAllBlocks(); } void TimelineWidget::RippleToIn() @@ -1232,11 +1228,23 @@ const QRect& TimelineWidget::GetRubberBandGeometry() const return rubberband_.geometry(); } -void TimelineWidget::SignalSelectedBlocks(const QList &selected_blocks) +void TimelineWidget::SignalSelectedBlocks(QList input, bool filter) { - selected_blocks_.append(selected_blocks); + if (filter) { + // If filtering, remove all the blocks that are already selected + for (int i=0; i &deselected_blocks) @@ -1248,6 +1256,12 @@ void TimelineWidget::SignalDeselectedBlocks(const QList &deselected_blo emit BlocksDeselected(deselected_blocks); } +void TimelineWidget::SignalDeselectedAllBlocks() +{ + emit BlocksDeselected(selected_blocks_); + selected_blocks_.clear(); +} + QVector TimelineWidget::GetEditToInfo(const rational& playhead_time, Timeline::MovementMode mode) { @@ -1423,10 +1437,8 @@ void TimelineWidget::StartRubberBandSelect(bool enable_selecting, bool select_li rubberband_.show(); // We don't touch any blocks that are already selected. If you want these to be deselected by - // default, call DeselectAll() befoer calling StartRubberBandSelect() - foreach (Block* b, selected_blocks_) { - rubberband_already_selected_.append(block_items_.value(b)); - } + // default, call DeselectAll() before calling StartRubberBandSelect() + rubberband_old_selections_ = selections_; MoveRubberBandSelect(enable_selecting, select_links); } @@ -1441,7 +1453,7 @@ void TimelineWidget::MoveRubberBandSelect(bool enable_selecting, bool select_lin return; } - QList new_selected_list; + QList items_in_rubberband; // Determine all items in the rubberband foreach (TimelineAndTrackView* tview, views_) { @@ -1454,64 +1466,40 @@ void TimelineWidget::MoveRubberBandSelect(bool enable_selecting, bool select_lin // Normalize and get items in rect QList rubberband_items = view->items(mapped_rect.normalized()); - new_selected_list.append(rubberband_items); + items_in_rubberband.append(rubberband_items); } - // Filter out any items that were already selected - if (!rubberband_already_selected_.isEmpty()) { - for (int i=0; i(item); if (block_item) { - RemoveSelection(block_item); - } - } - - // Cache limit because we append to this array in this loop and don't need to process those - int lim = new_selected_list.size(); - for (int i=0;i(new_selected_list.at(i)); - if (block_item->block()->type() == Block::kGap) { - continue; - } - - TrackOutput* t = GetTrackFromReference(block_item->Track()); - if (t && t->IsLocked()) { - continue; - } - - // Since new_selected_list is filtered by rubberband_already_selected_, this should certainly - // be deselected by now - AddSelection(block_item); - - if (select_links) { - // Select the block's links Block* b = block_item->block(); - // Add its links to the list - TimelineViewBlockItem* link_item; - foreach (Block* link, b->linked_clips()) { - if ((link_item = block_items_[link]) != nullptr) { - AddSelection(link_item); + if (b->type() == Block::kGap) { + continue; + } - if (!new_selected_list.contains(link_item) - && !rubberband_already_selected_.contains(link_item)) { - new_selected_list.append(link_item); - } + TrackOutput* t = GetTrackFromReference(block_item->Track()); + if (t && t->IsLocked()) { + continue; + } + + AddSelection(block_item); + rubberband_now_selected_.append(block_item->block()); + + if (select_links) { + foreach (Block* link, b->linked_clips()) { + AddSelection(block_items_.value(link)); + rubberband_now_selected_.append(link); } } } } - - rubberband_now_selected_ = new_selected_list; } void TimelineWidget::EndRubberBandSelect() @@ -1519,14 +1507,10 @@ void TimelineWidget::EndRubberBandSelect() rubberband_.hide(); // Emit any blocks that were newly selected - QList selected_blocks; - foreach (QGraphicsItem* item, rubberband_now_selected_) { - selected_blocks.append(static_cast(item)->block()); - } - emit BlocksSelected(selected_blocks); + SignalSelectedBlocks(rubberband_now_selected_); rubberband_now_selected_.clear(); - rubberband_already_selected_.clear(); + rubberband_old_selections_.clear(); } void TimelineWidget::AddSelection(const TimeRange &time, const TrackReference &track) diff --git a/app/widget/timelinewidget/timelinewidget.h b/app/widget/timelinewidget/timelinewidget.h index 9b2503ff3..bf854ff27 100644 --- a/app/widget/timelinewidget/timelinewidget.h +++ b/app/widget/timelinewidget/timelinewidget.h @@ -169,10 +169,34 @@ public: const QRect &GetRubberBandGeometry() const; - void SignalSelectedBlocks(const QList& selected_blocks); + /** + * @brief Track blocks that have newly been selected (this is preferred over emitting BlocksSelected directly) + * + * TimelineWidget keeps track of which blocks are selected internally. Calling this function will + * add to that list and emit a signal to other widgets that said blocks have been selected. + * + * @param selected_blocks + * + * The list of blocks to add to the internal selection list and signal. + * + * @param filter + * + * TRUE to automatically filter blocks that are already selected from the list. In most cases, + * this is preferable and should only be set to FALSE if the list is guaranteed not to contain + * already selected blocks (and therefore filtering can be skipped to save time). + */ + void SignalSelectedBlocks(QList selected_blocks, bool filter = true); + /** + * @brief Track blocks that have been newly deselected + */ void SignalDeselectedBlocks(const QList& deselected_blocks); + /** + * @brief Convenience function to deselect all blocks and signal them + */ + void SignalDeselectedAllBlocks(); + signals: void BlocksSelected(const QList& selected_blocks); @@ -212,8 +236,8 @@ private: QPoint drag_origin_; QRubberBand rubberband_; - QList rubberband_already_selected_; - QList rubberband_now_selected_; + TimelineWidgetSelections rubberband_old_selections_; + QList rubberband_now_selected_; TimelineWidgetSelections selections_;