From 951065390e3df45fbffef7de9bb7da82f2bd482e Mon Sep 17 00:00:00 2001 From: JamesJ <13408010-JamesJCode@users.noreply.gitlab.com> Date: Wed, 27 Mar 2024 10:26:05 +0000 Subject: [PATCH] Add composite update callback to BOARD_LISTENER Required for net inspector otherwise composite operations (such as undo / redo, and length tuning) can result in multiple add / remove events firing which results in inconsistent length state. Fixes https://gitlab.com/kicad/code/kicad/-/issues/17527 (for 9.0) --- pcbnew/board.cpp | 9 +++++++++ pcbnew/board.h | 13 +++++++++++++ pcbnew/board_commit.cpp | 20 ++++---------------- pcbnew/dialogs/dialog_generators.cpp | 9 +++++++++ pcbnew/dialogs/dialog_generators.h | 3 +++ pcbnew/undo_redo.cpp | 10 ++-------- pcbnew/widgets/appearance_controls.cpp | 13 +++++++++++++ pcbnew/widgets/appearance_controls.h | 3 +++ pcbnew/widgets/pcb_net_inspector_panel.cpp | 13 +++++++++++++ pcbnew/widgets/pcb_net_inspector_panel.h | 3 +++ pcbnew/widgets/pcb_search_pane.cpp | 10 ++++++++++ pcbnew/widgets/pcb_search_pane.h | 3 +++ 12 files changed, 85 insertions(+), 24 deletions(-) diff --git a/pcbnew/board.cpp b/pcbnew/board.cpp index 19ae065bb2..d5888e2bf1 100644 --- a/pcbnew/board.cpp +++ b/pcbnew/board.cpp @@ -2516,6 +2516,15 @@ void BOARD::OnItemsChanged( std::vector& aItems ) } +void BOARD::OnItemsCompositeUpdate( std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aChangedItems ) +{ + InvokeListeners( &BOARD_LISTENER::OnBoardCompositeUpdate, *this, aAddedItems, aRemovedItems, + aChangedItems ); +} + + void BOARD::OnRatsnestChanged() { InvokeListeners( &BOARD_LISTENER::OnBoardRatsnestChanged, *this ); diff --git a/pcbnew/board.h b/pcbnew/board.h index 9db9812c17..8b388e5493 100644 --- a/pcbnew/board.h +++ b/pcbnew/board.h @@ -252,6 +252,11 @@ public: virtual void OnBoardItemsChanged( BOARD& aBoard, std::vector& aBoardItem ) { } virtual void OnBoardHighlightNetChanged( BOARD& aBoard ) { } virtual void OnBoardRatsnestChanged( BOARD& aBoard ) { } + virtual void OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) + { + } }; /** @@ -1193,6 +1198,14 @@ public: */ void OnItemsChanged( std::vector& aItems ); + /** + * Notify the board and its listeners that items on the board have + * been modified in a composite operations + */ + void OnItemsCompositeUpdate( std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aChangedItems ); + /** * Notify the board and its listeners that the ratsnest has been recomputed. */ diff --git a/pcbnew/board_commit.cpp b/pcbnew/board_commit.cpp index c7769bbe54..f0111d595c 100644 --- a/pcbnew/board_commit.cpp +++ b/pcbnew/board_commit.cpp @@ -483,14 +483,8 @@ void BOARD_COMMIT::Push( const wxString& aMessage, int aCommitFlags ) } ); } - if( bulkAddedItems.size() > 0 ) - board->FinalizeBulkAdd( bulkAddedItems ); - - if( bulkRemovedItems.size() > 0 ) - board->FinalizeBulkRemove( bulkRemovedItems ); - - if( itemsChanged.size() > 0 ) - board->OnItemsChanged( itemsChanged ); + if( bulkAddedItems.size() > 0 || bulkRemovedItems.size() > 0 || itemsChanged.size() > 0 ) + board->OnItemsCompositeUpdate( bulkAddedItems, bulkRemovedItems, itemsChanged ); if( m_isBoardEditor ) { @@ -717,14 +711,8 @@ void BOARD_COMMIT::Revert() boardItem->ClearEditFlags(); } - if( bulkAddedItems.size() > 0 ) - board->FinalizeBulkAdd( bulkAddedItems ); - - if( bulkRemovedItems.size() > 0 ) - board->FinalizeBulkRemove( bulkRemovedItems ); - - if( itemsChanged.size() > 0 ) - board->OnItemsChanged( itemsChanged ); + if( bulkAddedItems.size() > 0 || bulkRemovedItems.size() > 0 || itemsChanged.size() > 0 ) + board->OnItemsCompositeUpdate( bulkAddedItems, bulkRemovedItems, itemsChanged ); if( m_isBoardEditor ) { diff --git a/pcbnew/dialogs/dialog_generators.cpp b/pcbnew/dialogs/dialog_generators.cpp index f341bd2df2..cb5e32ab01 100644 --- a/pcbnew/dialogs/dialog_generators.cpp +++ b/pcbnew/dialogs/dialog_generators.cpp @@ -342,6 +342,15 @@ void DIALOG_GENERATORS::OnBoardItemsChanged( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) +{ + RebuildModels(); +} + + DIALOG_GENERATORS::DIALOG_GENERATORS( PCB_EDIT_FRAME* aEditorFrame, wxWindow* aParent ) : DIALOG_GENERATORS_BASE( aParent ) { diff --git a/pcbnew/dialogs/dialog_generators.h b/pcbnew/dialogs/dialog_generators.h index 3b33431159..1ac29b10e5 100644 --- a/pcbnew/dialogs/dialog_generators.h +++ b/pcbnew/dialogs/dialog_generators.h @@ -71,6 +71,9 @@ private: virtual void OnBoardItemChanged( BOARD& aBoard, BOARD_ITEM* aBoardItem ) override; virtual void OnBoardItemsChanged( BOARD& aBoard, std::vector& aBoardItems ) override; + virtual void OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) override; std::map>> m_columnNameTypes; std::map m_dataModels; diff --git a/pcbnew/undo_redo.cpp b/pcbnew/undo_redo.cpp index 65e0b765ad..e76d24a7d7 100644 --- a/pcbnew/undo_redo.cpp +++ b/pcbnew/undo_redo.cpp @@ -601,14 +601,8 @@ void PCB_BASE_EDIT_FRAME::PutDataInPreviousState( PICKED_ITEMS_LIST* aList ) } } - if( added_items.size() > 0 ) - GetBoard()->FinalizeBulkAdd( added_items ); - - if( deleted_items.size() > 0 ) - GetBoard()->FinalizeBulkRemove( deleted_items ); - - if( changed_items.size() > 0 ) - GetBoard()->OnItemsChanged( changed_items ); + if( added_items.size() > 0 || deleted_items.size() > 0 || changed_items.size() > 0 ) + GetBoard()->OnItemsCompositeUpdate( added_items, deleted_items, changed_items ); } diff --git a/pcbnew/widgets/appearance_controls.cpp b/pcbnew/widgets/appearance_controls.cpp index ad78aed313..83d2d4f7f4 100644 --- a/pcbnew/widgets/appearance_controls.cpp +++ b/pcbnew/widgets/appearance_controls.cpp @@ -1157,6 +1157,19 @@ void APPEARANCE_CONTROLS::OnBoardItemsChanged( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) +{ + if( doesBoardItemNeedRebuild( aAddedItems ) || doesBoardItemNeedRebuild( aRemovedItems ) + || doesBoardItemNeedRebuild( aDeletedItems ) ) + { + handleBoardItemsChanged(); + } +} + + void APPEARANCE_CONTROLS::handleBoardItemsChanged() { Freeze(); diff --git a/pcbnew/widgets/appearance_controls.h b/pcbnew/widgets/appearance_controls.h index a5d8892f8b..82be140532 100644 --- a/pcbnew/widgets/appearance_controls.h +++ b/pcbnew/widgets/appearance_controls.h @@ -210,6 +210,9 @@ public: void OnBoardItemsRemoved( BOARD& aBoard, std::vector& aItems ) override; void OnBoardItemChanged( BOARD& aBoard, BOARD_ITEM* aItem ) override; void OnBoardItemsChanged( BOARD& aBoard, std::vector& aItems ) override; + void OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) override; ///< Update the colors on all the widgets from the new chosen color theme. void OnColorThemeChanged(); diff --git a/pcbnew/widgets/pcb_net_inspector_panel.cpp b/pcbnew/widgets/pcb_net_inspector_panel.cpp index 76fc09cf28..7baecbb755 100644 --- a/pcbnew/widgets/pcb_net_inspector_panel.cpp +++ b/pcbnew/widgets/pcb_net_inspector_panel.cpp @@ -1097,6 +1097,19 @@ void PCB_NET_INSPECTOR_PANEL::OnBoardItemsChanged( BOARD& aBo } +void PCB_NET_INSPECTOR_PANEL::OnBoardCompositeUpdate( BOARD& aBoard, + std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) +{ + if( !IsShownOnScreen() ) + return; + + buildNetsList(); + m_netsList->Refresh(); +} + + void PCB_NET_INSPECTOR_PANEL::OnBoardHighlightNetChanged( BOARD& aBoard ) { if( m_highlighting_nets || !IsShownOnScreen() ) diff --git a/pcbnew/widgets/pcb_net_inspector_panel.h b/pcbnew/widgets/pcb_net_inspector_panel.h index 0c0cfe2e34..86bd409dcb 100644 --- a/pcbnew/widgets/pcb_net_inspector_panel.h +++ b/pcbnew/widgets/pcb_net_inspector_panel.h @@ -82,6 +82,9 @@ public: virtual void OnBoardItemsChanged( BOARD& aBoard, std::vector& aBoardItems ) override; virtual void OnBoardHighlightNetChanged( BOARD& aBoard ) override; + virtual void OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) override; /** * Prepare the panel when shown in the editor diff --git a/pcbnew/widgets/pcb_search_pane.cpp b/pcbnew/widgets/pcb_search_pane.cpp index affa40e7a4..eee0f5f9bc 100644 --- a/pcbnew/widgets/pcb_search_pane.cpp +++ b/pcbnew/widgets/pcb_search_pane.cpp @@ -153,3 +153,13 @@ void PCB_SEARCH_PANE::OnBoardRatsnestChanged( BOARD& aBoard ) RefreshSearch(); } + +void PCB_SEARCH_PANE::OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) +{ + if( !IsShownOnScreen() ) + return; + + RefreshSearch(); +} \ No newline at end of file diff --git a/pcbnew/widgets/pcb_search_pane.h b/pcbnew/widgets/pcb_search_pane.h index 152e4bfd8d..c4da625833 100644 --- a/pcbnew/widgets/pcb_search_pane.h +++ b/pcbnew/widgets/pcb_search_pane.h @@ -42,6 +42,9 @@ public: std::vector& aBoardItems ) override; virtual void OnBoardHighlightNetChanged( BOARD& aBoard ) override; virtual void OnBoardRatsnestChanged( BOARD& aBoard ) override; + virtual void OnBoardCompositeUpdate( BOARD& aBoard, std::vector& aAddedItems, + std::vector& aRemovedItems, + std::vector& aDeletedItems ) override; private: void onUnitsChanged( wxCommandEvent& event );