Convert parent-less module items to board items on paste.
Fixes https://gitlab.com/kicad/code/kicad/issues/4938
This commit is contained in:
parent
8a010bc23e
commit
be957e0105
|
@ -76,7 +76,7 @@ ZONE_CONTAINER::ZONE_CONTAINER( const ZONE_CONTAINER& aZone )
|
||||||
m_Poly( nullptr ),
|
m_Poly( nullptr ),
|
||||||
m_CornerSelection( nullptr )
|
m_CornerSelection( nullptr )
|
||||||
{
|
{
|
||||||
initDataFromSrcInCopyCtor( aZone );
|
InitDataFromSrcInCopyCtor( aZone );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -84,7 +84,7 @@ ZONE_CONTAINER& ZONE_CONTAINER::operator=( const ZONE_CONTAINER& aOther )
|
||||||
{
|
{
|
||||||
BOARD_CONNECTED_ITEM::operator=( aOther );
|
BOARD_CONNECTED_ITEM::operator=( aOther );
|
||||||
|
|
||||||
initDataFromSrcInCopyCtor( aOther );
|
InitDataFromSrcInCopyCtor( aOther );
|
||||||
|
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
@ -97,10 +97,10 @@ ZONE_CONTAINER::~ZONE_CONTAINER()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void ZONE_CONTAINER::initDataFromSrcInCopyCtor( const ZONE_CONTAINER& aZone )
|
void ZONE_CONTAINER::InitDataFromSrcInCopyCtor( const ZONE_CONTAINER& aZone )
|
||||||
{
|
{
|
||||||
// members are expected non initialize in this.
|
// members are expected non initialize in this.
|
||||||
// initDataFromSrcInCopyCtor() is expected to be called
|
// InitDataFromSrcInCopyCtor() is expected to be called
|
||||||
// only from a copy constructor.
|
// only from a copy constructor.
|
||||||
|
|
||||||
// Copy only useful EDA_ITEM flags:
|
// Copy only useful EDA_ITEM flags:
|
||||||
|
@ -1310,7 +1310,7 @@ MODULE_ZONE_CONTAINER::MODULE_ZONE_CONTAINER( BOARD_ITEM_CONTAINER* aParent ) :
|
||||||
MODULE_ZONE_CONTAINER::MODULE_ZONE_CONTAINER( const MODULE_ZONE_CONTAINER& aZone )
|
MODULE_ZONE_CONTAINER::MODULE_ZONE_CONTAINER( const MODULE_ZONE_CONTAINER& aZone )
|
||||||
: ZONE_CONTAINER( aZone.GetParent(), true )
|
: ZONE_CONTAINER( aZone.GetParent(), true )
|
||||||
{
|
{
|
||||||
initDataFromSrcInCopyCtor( aZone );
|
InitDataFromSrcInCopyCtor( aZone );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -82,6 +82,11 @@ public:
|
||||||
return aItem && aItem->Type() == PCB_ZONE_AREA_T;
|
return aItem && aItem->Type() == PCB_ZONE_AREA_T;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Copy aZone data to me
|
||||||
|
*/
|
||||||
|
void InitDataFromSrcInCopyCtor( const ZONE_CONTAINER& aZone );
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return a wxPoint, position of the first point of the outline
|
* @return a wxPoint, position of the first point of the outline
|
||||||
*/
|
*/
|
||||||
|
@ -818,12 +823,6 @@ public:
|
||||||
virtual void SwapData( BOARD_ITEM* aImage ) override;
|
virtual void SwapData( BOARD_ITEM* aImage ) override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
/** Copy aZone data to me
|
|
||||||
* members are expected non initialize in this.
|
|
||||||
* copyDataFromSrc() is expected to be called *only* from a copy constructor.
|
|
||||||
*/
|
|
||||||
void initDataFromSrcInCopyCtor( const ZONE_CONTAINER& aZone );
|
|
||||||
|
|
||||||
SHAPE_POLY_SET* m_Poly; ///< Outline of the zone.
|
SHAPE_POLY_SET* m_Poly; ///< Outline of the zone.
|
||||||
int m_cornerSmoothingType;
|
int m_cornerSmoothingType;
|
||||||
unsigned int m_cornerRadius;
|
unsigned int m_cornerRadius;
|
||||||
|
|
|
@ -27,6 +27,9 @@
|
||||||
#include <build_version.h>
|
#include <build_version.h>
|
||||||
#include <class_board.h>
|
#include <class_board.h>
|
||||||
#include <class_track.h>
|
#include <class_track.h>
|
||||||
|
#include <class_drawsegment.h>
|
||||||
|
#include <class_pcb_text.h>
|
||||||
|
#include <class_text_mod.h>
|
||||||
#include <common.h>
|
#include <common.h>
|
||||||
#include <netinfo.h>
|
#include <netinfo.h>
|
||||||
#include <pcb_parser.h>
|
#include <pcb_parser.h>
|
||||||
|
@ -61,7 +64,7 @@ void CLIPBOARD_IO::SetBoard( BOARD* aBoard )
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected, bool isModEdit )
|
||||||
{
|
{
|
||||||
VECTOR2I refPoint( 0, 0 );
|
VECTOR2I refPoint( 0, 0 );
|
||||||
|
|
||||||
|
@ -75,26 +78,6 @@ void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
||||||
// Prepare net mapping that assures that net codes saved in a file are consecutive integers
|
// Prepare net mapping that assures that net codes saved in a file are consecutive integers
|
||||||
m_mapping->SetBoard( m_board );
|
m_mapping->SetBoard( m_board );
|
||||||
|
|
||||||
// Differentiate how it is formatted depending on what selection contains
|
|
||||||
bool onlyModuleParts = true;
|
|
||||||
for( const auto i : aSelected )
|
|
||||||
{
|
|
||||||
// check if it not one of the module primitives
|
|
||||||
if( ( i->Type() != PCB_MODULE_EDGE_T ) &&
|
|
||||||
( i->Type() != PCB_MODULE_TEXT_T ) &&
|
|
||||||
( i->Type() != PCB_MODULE_ZONE_AREA_T ) &&
|
|
||||||
( i->Type() != PCB_PAD_T ) )
|
|
||||||
{
|
|
||||||
onlyModuleParts = false;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// if there is only parts of a module selected, format it as a new module else
|
|
||||||
// format it as an entire board
|
|
||||||
MODULE partialModule( m_board );
|
|
||||||
|
|
||||||
// only a module selected.
|
|
||||||
if( aSelected.Size() == 1 && aSelected.Front()->Type() == PCB_MODULE_T )
|
if( aSelected.Size() == 1 && aSelected.Front()->Type() == PCB_MODULE_T )
|
||||||
{
|
{
|
||||||
// make the module safe to transfer to other pcbs
|
// make the module safe to transfer to other pcbs
|
||||||
|
@ -113,10 +96,11 @@ void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
||||||
|
|
||||||
Format( static_cast<BOARD_ITEM*>( &newModule ) );
|
Format( static_cast<BOARD_ITEM*>( &newModule ) );
|
||||||
}
|
}
|
||||||
// partial module selected.
|
else if( isModEdit )
|
||||||
else if( onlyModuleParts )
|
|
||||||
{
|
{
|
||||||
for( const auto item : aSelected )
|
MODULE partialModule( m_board );
|
||||||
|
|
||||||
|
for( const EDA_ITEM* item : aSelected )
|
||||||
{
|
{
|
||||||
BOARD_ITEM* clone = static_cast<BOARD_ITEM*>( item->Clone() );
|
BOARD_ITEM* clone = static_cast<BOARD_ITEM*>( item->Clone() );
|
||||||
|
|
||||||
|
@ -142,9 +126,7 @@ void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
||||||
partialModule.MoveAnchorPosition( moveVector );
|
partialModule.MoveAnchorPosition( moveVector );
|
||||||
|
|
||||||
Format( &partialModule, 0 );
|
Format( &partialModule, 0 );
|
||||||
|
|
||||||
}
|
}
|
||||||
// lots of stuff selected
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// we will fake being a .kicad_pcb to get the full parser kicking
|
// we will fake being a .kicad_pcb to get the full parser kicking
|
||||||
|
@ -152,8 +134,8 @@ void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
||||||
LOCALE_IO io;
|
LOCALE_IO io;
|
||||||
|
|
||||||
m_formatter.Print( 0, "(kicad_pcb (version %d) (host pcbnew %s)\n",
|
m_formatter.Print( 0, "(kicad_pcb (version %d) (host pcbnew %s)\n",
|
||||||
SEXPR_BOARD_FILE_VERSION, m_formatter.Quotew( GetBuildVersion() ).c_str() );
|
SEXPR_BOARD_FILE_VERSION,
|
||||||
|
m_formatter.Quotew( GetBuildVersion() ).c_str() );
|
||||||
|
|
||||||
m_formatter.Print( 0, "\n" );
|
m_formatter.Print( 0, "\n" );
|
||||||
|
|
||||||
|
@ -162,28 +144,72 @@ void CLIPBOARD_IO::SaveSelection( const PCBNEW_SELECTION& aSelected )
|
||||||
|
|
||||||
m_formatter.Print( 0, "\n" );
|
m_formatter.Print( 0, "\n" );
|
||||||
|
|
||||||
|
for( EDA_ITEM* i : aSelected )
|
||||||
for( const auto i : aSelected )
|
|
||||||
{
|
{
|
||||||
// Dont format stuff that cannot exist standalone!
|
BOARD_ITEM* item = static_cast<BOARD_ITEM*>( i );
|
||||||
if( ( i->Type() != PCB_MODULE_EDGE_T ) &&
|
BOARD_ITEM* copy = nullptr;
|
||||||
( i->Type() != PCB_MODULE_TEXT_T ) &&
|
|
||||||
( i->Type() != PCB_MODULE_ZONE_AREA_T ) &&
|
if( item->Type() == PCB_MODULE_EDGE_T )
|
||||||
( i->Type() != PCB_PAD_T ) )
|
|
||||||
{
|
{
|
||||||
auto item = static_cast<BOARD_ITEM*>( i );
|
// Convert to PCB_LINE_T
|
||||||
std::unique_ptr<BOARD_ITEM> clone( static_cast<BOARD_ITEM*> ( item->Clone() ) );
|
copy = (BOARD_ITEM*) reinterpret_cast<DRAWSEGMENT*>( item )->Clone();
|
||||||
|
copy->SetLayer( item->GetLayer() );
|
||||||
|
}
|
||||||
|
else if( item->Type() == PCB_MODULE_TEXT_T )
|
||||||
|
{
|
||||||
|
// Convert to PCB_TEXT_T
|
||||||
|
MODULE* mod = static_cast<MODULE*>( item->GetParent() );
|
||||||
|
TEXTE_MODULE* mod_text = static_cast<TEXTE_MODULE*>( item );
|
||||||
|
TEXTE_PCB* pcb_text = new TEXTE_PCB( m_board );
|
||||||
|
|
||||||
|
if( mod_text->GetText() == "${VALUE}" )
|
||||||
|
pcb_text->SetText( mod->GetValue() );
|
||||||
|
else if( mod_text->GetText() == "${REFERENCE}" )
|
||||||
|
pcb_text->SetText( mod->GetReference() );
|
||||||
|
else
|
||||||
|
pcb_text->CopyText( *mod_text );
|
||||||
|
|
||||||
|
pcb_text->SetEffects( *mod_text );
|
||||||
|
pcb_text->SetLayer( mod_text->GetLayer() );
|
||||||
|
copy = pcb_text;
|
||||||
|
}
|
||||||
|
else if( item->Type() == PCB_PAD_T )
|
||||||
|
{
|
||||||
|
// Create a parent to own the copied pad
|
||||||
|
MODULE* mod = new MODULE( m_board );
|
||||||
|
D_PAD* pad = (D_PAD*) item->Clone();
|
||||||
|
|
||||||
|
mod->SetPosition( pad->GetPosition() );
|
||||||
|
pad->SetPos0( wxPoint() );
|
||||||
|
mod->Add( pad );
|
||||||
|
copy = mod;
|
||||||
|
}
|
||||||
|
else if( item->Type() == PCB_MODULE_ZONE_AREA_T )
|
||||||
|
{
|
||||||
|
// Convert to PCB_ZONE_AREA_T
|
||||||
|
ZONE_CONTAINER* zone = new ZONE_CONTAINER( m_board );
|
||||||
|
zone->InitDataFromSrcInCopyCtor( *static_cast<ZONE_CONTAINER*>( item ) );
|
||||||
|
copy = zone;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
copy = static_cast<BOARD_ITEM*>( item->Clone() );
|
||||||
|
|
||||||
// locked means "locked in place"; copied items therefore can't be locked
|
// locked means "locked in place"; copied items therefore can't be locked
|
||||||
if( MODULE* module = dyn_cast<MODULE*>( clone.get() ) )
|
if( MODULE* module = dyn_cast<MODULE*>( copy ) )
|
||||||
module->SetLocked( false );
|
module->SetLocked( false );
|
||||||
else if( TRACK* track = dyn_cast<TRACK*>( clone.get() ) )
|
else if( TRACK* track = dyn_cast<TRACK*>( copy ) )
|
||||||
track->SetLocked( false );
|
track->SetLocked( false );
|
||||||
|
}
|
||||||
|
|
||||||
|
if( copy )
|
||||||
|
{
|
||||||
// locate the reference point at (0, 0) in the copied items
|
// locate the reference point at (0, 0) in the copied items
|
||||||
clone->Move( (wxPoint) -refPoint );
|
copy->Move( (wxPoint) -refPoint );
|
||||||
|
|
||||||
Format( clone.get(), 1 );
|
Format( copy, 1 );
|
||||||
|
|
||||||
|
delete copy;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_formatter.Print( 0, "\n)" );
|
m_formatter.Print( 0, "\n)" );
|
||||||
|
|
|
@ -58,7 +58,7 @@ public:
|
||||||
/* Writes all the settings of the BOARD* set by setBoard() and then adds all
|
/* Writes all the settings of the BOARD* set by setBoard() and then adds all
|
||||||
* the BOARD_ITEM* found in selection formatted by PCB_IO to clipboard as a text
|
* the BOARD_ITEM* found in selection formatted by PCB_IO to clipboard as a text
|
||||||
*/
|
*/
|
||||||
void SaveSelection( const PCBNEW_SELECTION& selected );
|
void SaveSelection( const PCBNEW_SELECTION& selected, bool isModEdit );
|
||||||
|
|
||||||
BOARD_ITEM* Parse();
|
BOARD_ITEM* Parse();
|
||||||
|
|
||||||
|
|
|
@ -1466,7 +1466,7 @@ int EDIT_TOOL::copyToClipboard( const TOOL_EVENT& aEvent )
|
||||||
selection.SetReferencePoint( refPoint );
|
selection.SetReferencePoint( refPoint );
|
||||||
|
|
||||||
io.SetBoard( board() );
|
io.SetBoard( board() );
|
||||||
io.SaveSelection( selection );
|
io.SaveSelection( selection, m_editModules );
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -830,12 +830,12 @@ int PCBNEW_CONTROL::placeBoardItems( std::vector<BOARD_ITEM*>& aItems, bool aIsN
|
||||||
{
|
{
|
||||||
m_toolMgr->RunAction( PCB_ACTIONS::selectionClear, true );
|
m_toolMgr->RunAction( PCB_ACTIONS::selectionClear, true );
|
||||||
|
|
||||||
auto selectionTool = m_toolMgr->GetTool<SELECTION_TOOL>();
|
SELECTION_TOOL* selectionTool = m_toolMgr->GetTool<SELECTION_TOOL>();
|
||||||
auto editTool = m_toolMgr->GetTool<EDIT_TOOL>();
|
EDIT_TOOL* editTool = m_toolMgr->GetTool<EDIT_TOOL>();
|
||||||
|
|
||||||
PCBNEW_SELECTION& selection = selectionTool->GetSelection();
|
PCBNEW_SELECTION& selection = selectionTool->GetSelection();
|
||||||
|
|
||||||
for( auto item : aItems )
|
for( BOARD_ITEM* item : aItems )
|
||||||
{
|
{
|
||||||
item->SetSelected();
|
item->SetSelected();
|
||||||
selection.Add( item );
|
selection.Add( item );
|
||||||
|
|
Loading…
Reference in New Issue