1 /*
2  * This program source code file is part of KiCad, a free EDA CAD application.
3  *
4  * Copyright (C) 1992-2020 KiCad Developers, see AUTHORS.txt for contributors.
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, you may find one here:
18  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
19  * or you may search the http://www.gnu.org website for the version 2 license,
20  * or you may write to the Free Software Foundation, Inc.,
21  * 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA
22  */
23 
24 #include <pcb_edit_frame.h>
25 #include <pcbnew_settings.h>
26 #include <dialog_update_pcb.h>
27 #include <ratsnest/ratsnest_data.h>
28 #include <wx_html_report_panel.h>
29 #include <netlist_reader/pcb_netlist.h>
30 #include <netlist_reader/board_netlist_updater.h>
31 #include <tool/tool_manager.h>
32 #include <tools/pcb_actions.h>
33 #include <kiface_base.h>
34 #include <kiplatform/ui.h>
35 
36 
DIALOG_UPDATE_PCB(PCB_EDIT_FRAME * aParent,NETLIST * aNetlist)37 DIALOG_UPDATE_PCB::DIALOG_UPDATE_PCB( PCB_EDIT_FRAME* aParent, NETLIST* aNetlist ) :
38     DIALOG_UPDATE_PCB_BASE( aParent ),
39     m_frame( aParent ),
40     m_netlist( aNetlist ),
41     m_initialized( false )
42 {
43     auto cfg = m_frame->GetPcbNewSettings();
44 
45     m_cbRelinkFootprints->SetValue( cfg->m_NetlistDialog.associate_by_ref_sch );
46     m_cbUpdateFootprints->SetValue( cfg->m_NetlistDialog.update_footprints );
47     m_cbDeleteExtraFootprints->SetValue( cfg->m_NetlistDialog.delete_extra_footprints );
48 
49     m_messagePanel->SetLabel( _("Changes To Be Applied") );
50     m_messagePanel->SetFileName( Prj().GetProjectPath() + wxT( "report.txt" ) );
51     m_messagePanel->SetLazyUpdate( true );
52     m_netlist->SortByReference();
53 
54     m_messagePanel->SetVisibleSeverities( cfg->m_NetlistDialog.report_filter );
55 
56     m_messagePanel->GetSizer()->SetSizeHints( this );
57     m_messagePanel->Layout();
58 
59     // We use a sdbSizer to get platform-dependent ordering of the action buttons, but
60     // that requires us to correct the button labels here.
61     m_sdbSizer1OK->SetLabel( _( "Update PCB" ) );
62     m_sdbSizer1Cancel->SetLabel( _( "Close" ) );
63     m_sdbSizer1->Layout();
64 
65     m_sdbSizer1OK->SetDefault();
66     finishDialogSettings();
67 
68     m_initialized = true;
69     PerformUpdate( true );
70 }
71 
72 
~DIALOG_UPDATE_PCB()73 DIALOG_UPDATE_PCB::~DIALOG_UPDATE_PCB()
74 {
75     auto cfg = m_frame->GetPcbNewSettings();
76 
77     cfg->m_NetlistDialog.associate_by_ref_sch    = m_cbRelinkFootprints->GetValue();
78     cfg->m_NetlistDialog.update_footprints       = m_cbUpdateFootprints->GetValue();
79     cfg->m_NetlistDialog.delete_extra_footprints = m_cbDeleteExtraFootprints->GetValue();
80     cfg->m_NetlistDialog.report_filter           = m_messagePanel->GetVisibleSeverities();
81 
82     if( m_runDragCommand )
83     {
84         KIGFX::VIEW_CONTROLS* controls = m_frame->GetCanvas()->GetViewControls();
85         controls->SetCursorPosition( controls->GetMousePosition() );
86         m_frame->GetToolManager()->RunAction( PCB_ACTIONS::move, true );
87     }
88 }
89 
90 
PerformUpdate(bool aDryRun)91 void DIALOG_UPDATE_PCB::PerformUpdate( bool aDryRun )
92 {
93     m_messagePanel->Clear();
94 
95     REPORTER& reporter = m_messagePanel->Reporter();
96 
97     m_runDragCommand = false;
98 
99     m_netlist->SetFindByTimeStamp( !m_cbRelinkFootprints->GetValue() );
100     m_netlist->SetReplaceFootprints( m_cbUpdateFootprints->GetValue() );
101 
102     if( !aDryRun )
103     {
104         m_frame->GetToolManager()->DeactivateTool();
105         m_frame->GetToolManager()->RunAction( PCB_ACTIONS::selectionClear, true );
106     }
107 
108     BOARD_NETLIST_UPDATER updater( m_frame, m_frame->GetBoard() );
109     updater.SetReporter ( &reporter );
110     updater.SetIsDryRun( aDryRun );
111     updater.SetLookupByTimestamp( !m_cbRelinkFootprints->GetValue() );
112     updater.SetDeleteUnusedFootprints( m_cbDeleteExtraFootprints->GetValue());
113     updater.SetReplaceFootprints( m_cbUpdateFootprints->GetValue() );
114     updater.UpdateNetlist( *m_netlist );
115 
116     m_messagePanel->Flush( true );
117 
118     if( aDryRun )
119         return;
120 
121     m_frame->OnNetlistChanged( updater, &m_runDragCommand );
122 }
123 
124 
OnOptionChanged(wxCommandEvent & event)125 void DIALOG_UPDATE_PCB::OnOptionChanged( wxCommandEvent& event )
126 {
127     if( m_initialized )
128     {
129         PerformUpdate( true );
130         m_sdbSizer1OK->Enable( true );
131         m_sdbSizer1OK->SetDefault();
132     }
133 }
134 
135 
OnUpdateClick(wxCommandEvent & event)136 void DIALOG_UPDATE_PCB::OnUpdateClick( wxCommandEvent& event )
137 {
138     m_messagePanel->SetLabel( _( "Changes Applied to PCB" ) );
139     PerformUpdate( false );
140 
141     m_sdbSizer1Cancel->SetDefault();
142     // Widgets has a tendency to keep both buttons highlighted without the following:
143     m_sdbSizer1OK->Enable( false );
144 }
145