KiCad PCB EDA Suite
Loading...
Searching...
No Matches
drc_tool.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright The 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 <tool/tool_manager.h>
26#include <tools/pcb_actions.h>
27#include <tools/pcb_tool_base.h>
30#include <tools/drc_tool.h>
31#include <kiface_base.h>
32#include <dialog_drc.h>
33#include <board_commit.h>
35#include <progress_reporter.h>
36#include <drc/drc_engine.h>
37#include <drc/drc_item.h>
39#include <macros.h>
40
42 PCB_TOOL_BASE( "pcbnew.DRCTool" ),
43 m_editFrame( nullptr ),
44 m_pcb( nullptr ),
45 m_drcDialog( nullptr ),
46 m_drcRunning( false )
47{
48}
49
50
54
55
57{
59
60 if( m_pcb != m_editFrame->GetBoard() )
61 {
62 if( m_drcDialog )
64
65 m_pcb = m_editFrame->GetBoard();
66 m_drcEngine = m_pcb->GetDesignSettings().m_DRCEngine;
67 }
68}
69
70
71void DRC_TOOL::ShowDRCDialog( wxWindow* aParent )
72{
73 bool show_dlg_modal = true;
74
75 // the dialog needs a parent frame. if it is not specified, this is the PCB editor frame
76 // specified in DRC_TOOL class.
77 if( !aParent )
78 {
79 // if any parent is specified, the dialog is modal.
80 // if this is the default PCB editor frame, it is not modal
81 show_dlg_modal = false;
82 aParent = m_editFrame;
83 }
84
85 Activate();
87
88 if( !m_drcDialog )
89 {
90 m_drcDialog = new DIALOG_DRC( m_editFrame, aParent );
91 updatePointers( false );
92
93 if( show_dlg_modal )
94 m_drcDialog->ShowModal();
95 else
96 m_drcDialog->Show( true );
97 }
98 else // The dialog is just not visible (because the user has double clicked on an error item)
99 {
100 updatePointers( false );
101 m_drcDialog->Show( true );
102 }
103}
104
105
107{
108 ShowDRCDialog( nullptr );
109 return 0;
110}
111
112
114{
115 if( m_drcDialog )
116 return m_drcDialog->IsShownOnScreen();
117
118 return false;
119}
120
121
123{
124 if( m_drcDialog )
125 {
126 m_drcDialog->Destroy();
127 m_drcDialog = nullptr;
128 }
129}
130
131
132void DRC_TOOL::RunTests( PROGRESS_REPORTER* aProgressReporter, bool aRefillZones,
133 bool aReportAllTrackErrors, bool aTestFootprints )
134{
135 // One at a time, please.
136 // Note that the main GUI entry points to get here are blocked, so this is really an
137 // insurance policy and as such we make no attempts to queue up the DRC run or anything.
138 if( m_drcRunning )
139 return;
140
141 ZONE_FILLER_TOOL* zoneFiller = m_toolMgr->GetTool<ZONE_FILLER_TOOL>();
142 BOARD_COMMIT commit( m_editFrame );
144 bool netlistFetched = false;
145 wxWindowDisabler disabler( /* disable everything except: */ m_drcDialog );
146
147 m_drcRunning = true;
148
149 if( aRefillZones )
150 {
151 aProgressReporter->AdvancePhase( _( "Refilling all zones..." ) );
152
153 zoneFiller->FillAllZones( m_drcDialog, aProgressReporter );
154 }
155
156 m_drcEngine->SetDrawingSheet( m_editFrame->GetCanvas()->GetDrawingSheet() );
157
158 if( aTestFootprints && !Kiface().IsSingle() )
159 {
160 if( m_editFrame->FetchNetlistFromSchematic( netlist, _( "Schematic parity tests require a "
161 "fully annotated schematic." ) ) )
162 {
163 netlistFetched = true;
164 }
165
166 if( m_drcDialog )
167 m_drcDialog->Raise();
168
169 m_drcEngine->SetSchematicNetlist( &netlist );
170 }
171
172 m_drcEngine->SetProgressReporter( aProgressReporter );
173
174 m_drcEngine->SetViolationHandler(
175 [&]( const std::shared_ptr<DRC_ITEM>& aItem, VECTOR2I aPos, int aLayer,
176 const std::vector<PCB_SHAPE>& aShapes )
177 {
178 PCB_MARKER* marker = new PCB_MARKER( aItem, aPos, aLayer );
179 marker->SetShapes( aShapes );
180 commit.Add( marker );
181 } );
182
183 m_drcEngine->RunTests( m_editFrame->GetUserUnits(), aReportAllTrackErrors, aTestFootprints,
184 &commit );
185
186 m_drcEngine->SetProgressReporter( nullptr );
187 m_drcEngine->ClearViolationHandler();
188
189 if( m_drcDialog )
190 {
191 m_drcDialog->SetDrcRun();
192
193 if( aTestFootprints && netlistFetched )
194 m_drcDialog->SetFootprintTestsRun();
195 }
196
197 commit.Push( _( "DRC" ), SKIP_UNDO | SKIP_SET_DIRTY );
198
199 m_drcRunning = false;
200
201 m_editFrame->ShowSolderMask();
202
203 // update the m_drcDialog listboxes
204 updatePointers( aProgressReporter->IsCancelled() );
205}
206
207
208void DRC_TOOL::updatePointers( bool aDRCWasCancelled )
209{
210 // update my pointers, m_editFrame is the only unchangeable one
211 m_pcb = m_editFrame->GetBoard();
212
213 m_editFrame->ResolveDRCExclusions( aDRCWasCancelled );
214
215 if( m_drcDialog )
216 m_drcDialog->UpdateData();
217}
218
219
221{
222 if( m_drcDialog )
223 {
224 m_drcDialog->Show( true );
225 m_drcDialog->Raise();
226 m_drcDialog->PrevMarker();
227 }
228 else
229 {
230 ShowDRCDialog( nullptr );
231 }
232
233 return 0;
234}
235
236
238{
239 if( m_drcDialog )
240 {
241 m_drcDialog->Show( true );
242 m_drcDialog->Raise();
243 m_drcDialog->NextMarker();
244 }
245 else
246 {
247 ShowDRCDialog( nullptr );
248 }
249
250 return 0;
251}
252
253
255{
256 if( m_drcDialog && m_drcDialog->IsShownOnScreen() )
257 {
258 PCB_SELECTION_TOOL* selectionTool = m_toolMgr->GetTool<PCB_SELECTION_TOOL>();
259 PCB_SELECTION& selection = selectionTool->GetSelection();
260
261 if( selection.GetSize() == 1 && selection.Front()->Type() == PCB_MARKER_T )
262 m_drcDialog->SelectMarker( static_cast<PCB_MARKER*>( selection.Front() ) );
263 }
264
265 return 0;
266}
267
268
269void DRC_TOOL::CrossProbe( const PCB_MARKER* aMarker )
270{
271 if( !IsDRCDialogShown() )
272 ShowDRCDialog( nullptr );
273
274 m_drcDialog->SelectMarker( aMarker );
275}
276
277
279{
280 if( m_drcDialog )
281 m_drcDialog->ExcludeMarker();
282
283 return 0;
284}
285
286
KIFACE_BASE & Kiface()
Global KIFACE_BASE "get" accessor.
static TOOL_ACTION excludeMarker
Definition actions.h:128
static TOOL_ACTION nextMarker
Definition actions.h:127
static TOOL_ACTION prevMarker
Definition actions.h:126
static TOOL_ACTION selectionClear
Clear the current selection.
Definition actions.h:223
void Reset(RESET_REASON aReason) override
Bring the tool to a known, initial state.
Definition drc_tool.cpp:56
void updatePointers(bool aDRCWasCancelled)
Update needed pointers from the one pointer which is known not to change.
Definition drc_tool.cpp:208
void ShowDRCDialog(wxWindow *aParent)
Opens the DRC dialog.
Definition drc_tool.cpp:71
int NextMarker(const TOOL_EVENT &aEvent)
Definition drc_tool.cpp:237
void DestroyDRCDialog()
Close and free the DRC dialog.
Definition drc_tool.cpp:122
DIALOG_DRC * m_drcDialog
Definition drc_tool.h:114
PCB_EDIT_FRAME * m_editFrame
Definition drc_tool.h:112
bool IsDRCDialogShown()
Check to see if the DRC_TOOL dialog is currently shown.
Definition drc_tool.cpp:113
int CrossProbe(const TOOL_EVENT &aEvent)
Definition drc_tool.cpp:254
int ExcludeMarker(const TOOL_EVENT &aEvent)
Definition drc_tool.cpp:278
void setTransitions() override
< Set up handlers for various events.
Definition drc_tool.cpp:287
BOARD * m_pcb
Definition drc_tool.h:113
int PrevMarker(const TOOL_EVENT &aEvent)
Definition drc_tool.cpp:220
bool m_drcRunning
Definition drc_tool.h:115
void RunTests(PROGRESS_REPORTER *aProgressReporter, bool aRefillZones, bool aReportAllTrackErrors, bool aTestFootprints)
Run the DRC tests.
Definition drc_tool.cpp:132
std::shared_ptr< DRC_ENGINE > m_drcEngine
Definition drc_tool.h:116
static const TOOL_EVENT SelectedEvent
Definition actions.h:346
static const TOOL_EVENT PointSelectedEvent
Definition actions.h:345
Store information read from a netlist along with the flags used to update the NETLIST in the BOARD.
static TOOL_ACTION runDRC
void SetShapes(const std::vector< PCB_SHAPE > &aShapes)
Definition pcb_marker.h:154
The selection tool: currently supports:
PCB_SELECTION & GetSelection()
PCB_TOOL_BASE(TOOL_ID aId, const std::string &aName)
Constructor.
const PCB_SELECTION & selection() const
A progress reporter interface for use in multi-threaded environments.
virtual bool IsCancelled() const =0
virtual void AdvancePhase()=0
Use the next available virtual zone of the dialog progress bar.
T * getEditFrame() const
Return the application window object, casted to requested user type.
Definition tool_base.h:186
TOOL_MANAGER * m_toolMgr
Definition tool_base.h:220
RESET_REASON
Determine the reason of reset for a tool.
Definition tool_base.h:78
Generic, UI-independent tool event.
Definition tool_event.h:171
void Go(int(T::*aStateFunc)(const TOOL_EVENT &), const TOOL_EVENT_LIST &aConditions=TOOL_EVENT(TC_ANY, TA_ANY))
Define which state (aStateFunc) to go when a certain event arrives (aConditions).
void Activate()
Run the tool.
Handle actions specific to filling copper zones.
void FillAllZones(wxWindow *aCaller, PROGRESS_REPORTER *aReporter=nullptr, bool aHeadless=false)
#define _(s)
This file contains miscellaneous commonly used macros and functions.
#define SKIP_SET_DIRTY
Definition sch_commit.h:42
#define SKIP_UNDO
Definition sch_commit.h:40
@ PCB_MARKER_T
class PCB_MARKER, a marker used to show something
Definition typeinfo.h:99
VECTOR2< int32_t > VECTOR2I
Definition vector2d.h:695