diff --git a/pcbnew/tools/edit_tool.cpp b/pcbnew/tools/edit_tool.cpp index c0e30627dc..727f20b9b3 100644 --- a/pcbnew/tools/edit_tool.cpp +++ b/pcbnew/tools/edit_tool.cpp @@ -229,6 +229,8 @@ int EDIT_TOOL::Properties( TOOL_EVENT& aEvent ) // Check if user wants to edit pad or module properties if( item->Type() == PCB_MODULE_T ) { + item->ClearFlags(); // Necessary for having an undo entry + for( D_PAD* pad = static_cast( item )->Pads(); pad; pad = pad->Next() ) { if( pad->ViewBBox().Contains( getViewControls()->GetCursorPosition() ) ) @@ -240,20 +242,34 @@ int EDIT_TOOL::Properties( TOOL_EVENT& aEvent ) } } - editFrame->SaveCopyInUndoList( item, UR_CHANGED ); - editFrame->OnModify(); + std::vector& undoList = editFrame->GetScreen()->m_UndoList.m_CommandsList; + + // It is necessary to determine if anything has changed + PICKED_ITEMS_LIST* lastChange = undoList.empty() ? NULL : undoList.back(); + + // Display properties dialog editFrame->OnEditItemRequest( NULL, item ); - item->ViewUpdate( KIGFX::VIEW_ITEM::GEOMETRY ); + PICKED_ITEMS_LIST* currentChange = undoList.empty() ? NULL : undoList.back(); - updateRatsnest( true ); - getModel( PCB_T )->GetRatsnest()->Recalculate(); - - if( unselect ) + if( lastChange != currentChange ) // Something has changed + { + // Some of properties dialogs alter pointers, so we should deselect them m_toolMgr->RunAction( COMMON_ACTIONS::selectionClear ); + + processChanges( currentChange ); + + // Seems unnecessary, as the items are removed/added to the board + // updateRatsnest( true ); + // getModel( PCB_T )->GetRatsnest()->Recalculate(); + + m_toolMgr->RunAction( COMMON_ACTIONS::pointEditorUpdate ); + } } - m_toolMgr->RunAction( COMMON_ACTIONS::pointEditorUpdate ); + if( unselect ) + m_toolMgr->RunAction( COMMON_ACTIONS::selectionClear ); + setTransitions(); return 0; @@ -509,3 +525,40 @@ bool EDIT_TOOL::makeSelection( const SELECTION_TOOL::SELECTION& aSelection ) return !aSelection.Empty(); } + + +void EDIT_TOOL::processChanges( const PICKED_ITEMS_LIST* aList ) +{ + for( unsigned int i = 0; i < aList->GetCount(); ++i ) + { + UNDO_REDO_T operation = aList->GetPickedItemStatus( i ); + EDA_ITEM* updItem = aList->GetPickedItem( i ); + + switch( operation ) + { + case UR_CHANGED: + updItem->ViewUpdate( KIGFX::VIEW_ITEM::GEOMETRY ); + break; + + case UR_DELETED: + if( updItem->Type() == PCB_MODULE_T ) + static_cast( updItem )->RunOnChildren( boost::bind( &KIGFX::VIEW::Remove, + getView(), _1 ) ); + + getView()->Remove( updItem ); + break; + + case UR_NEW: + if( updItem->Type() == PCB_MODULE_T ) + static_cast( updItem )->RunOnChildren( boost::bind( &KIGFX::VIEW::Add, + getView(), _1 ) ); + + getView()->Add( updItem ); + break; + + default: + assert( false ); // Not handled + break; + } + } +} diff --git a/pcbnew/tools/edit_tool.h b/pcbnew/tools/edit_tool.h index b23f076e96..207e446493 100644 --- a/pcbnew/tools/edit_tool.h +++ b/pcbnew/tools/edit_tool.h @@ -133,6 +133,9 @@ private: ///> If there are no items currently selected, it tries to choose the item that is under ///> the cursor or displays a disambiguation menu if there are multpile items. bool makeSelection( const SELECTION_TOOL::SELECTION& aSelection ); + + ///> Updates view with the changes in the list. + void processChanges( const PICKED_ITEMS_LIST* aList ); }; #endif diff --git a/pcbnew/xchgmod.cpp b/pcbnew/xchgmod.cpp index 7fafc6a914..1343ed9fb2 100644 --- a/pcbnew/xchgmod.cpp +++ b/pcbnew/xchgmod.cpp @@ -428,10 +428,8 @@ void PCB_EDIT_FRAME::Exchange_Module( MODULE* aOldModule, /* place module without ratsnest refresh: this will be made later * when all modules are on board */ - wxPoint oldpos = GetCrossHairPosition(); - SetCrossHairPosition( aOldModule->GetPosition(), false ); PlaceModule( aNewModule, NULL, true ); - SetCrossHairPosition( oldpos, false ); + aNewModule->SetPosition( aOldModule->GetPosition() ); // Flip footprint if needed if( aOldModule->GetLayer() != aNewModule->GetLayer() ) @@ -457,9 +455,8 @@ void PCB_EDIT_FRAME::Exchange_Module( MODULE* aOldModule, for( D_PAD* pad = aNewModule->Pads(); pad != NULL; pad = pad->Next() ) { pad->SetNetCode( NETINFO_LIST::UNCONNECTED ); - D_PAD* old_pad = aOldModule->Pads(); - for( ; old_pad != NULL; old_pad = old_pad->Next() ) + for( D_PAD* old_pad = aOldModule->Pads(); old_pad != NULL; old_pad = old_pad->Next() ) { if( pad->PadNameEqual( old_pad ) ) pad->SetNetCode( old_pad->GetNetCode() );