Inform user of bad DRC rules when filling zones.

ADDED: facility for hypertext links in infobar.

Also made use of this for via constraint errors when routing.

Fixes https://gitlab.com/kicad/code/kicad/issues/5800
This commit is contained in:
Jeff Young 2020-10-16 12:20:37 +01:00
parent 834c7bbe05
commit eea7957e16
11 changed files with 89 additions and 25 deletions

View File

@ -26,6 +26,7 @@
#include <wx/infobar.h>
#include <wx/sizer.h>
#include <wx/timer.h>
#include <wx/hyperlink.h>
wxDEFINE_EVENT( KIEVT_SHOW_INFOBAR, wxCommandEvent );
@ -199,6 +200,19 @@ void WX_INFOBAR::AddButton( wxButton* aButton )
}
void WX_INFOBAR::AddButton( wxHyperlinkCtrl* aHypertextButton )
{
wxSizer* sizer = GetSizer();
wxASSERT( aHypertextButton );
sizer->Add( aHypertextButton, wxSizerFlags().Centre().Border( wxRIGHT ) );
if( IsShown() )
sizer->Layout();
}
void WX_INFOBAR::AddCloseButton( const wxString& aTooltip )
{
wxBitmapButton* button = wxBitmapButton::NewCloseButton( this, ID_CLOSE_INFOBAR );

View File

@ -25,7 +25,9 @@
#include <wx/infobar.h>
#include <wx/wx.h>
class wxAuiManager;
class wxHyperlinkCtrl;
enum
@ -105,6 +107,14 @@ public:
*/
void AddButton( wxButton* aButton );
/**
* Add an already created hypertext link to the infobar.
* New buttons are added in the right-most position.
*
* @param aHypertextButton is the button to add
*/
void AddButton( wxHyperlinkCtrl* aHypertextButton );
/**
* Add a button with the provided ID and text.
* The new button is created on the right-most positon.

View File

@ -210,8 +210,7 @@ void DIALOG_DRC::OnRunDRCClick( wxCommandEvent& aEvent )
// issues (on at least OSX) if we don't.
drcTool->DestroyDRCDialog();
m_brdEditor->ShowBoardSetupDialog( _( "Rules" ), pe.What(), ID_RULES_EDITOR,
pe.lineNumber, pe.byteIndex );
m_brdEditor->ShowBoardSetupDialog( _( "Rules" ) );
return;
}

View File

@ -386,6 +386,9 @@ bool PANEL_SETUP_RULES::TransferDataToWindow()
ConvertSmartQuotesAndDashes( &str );
m_textEditor->AddText( str << '\n' );
}
wxCommandEvent dummy;
OnCompile( dummy );
}
}

View File

@ -406,7 +406,7 @@ void DRC_ENGINE::loadRules( const wxFileName& aPath )
}
bool DRC_ENGINE::CompileRules()
void DRC_ENGINE::compileRules()
{
ReportAux( wxString::Format( "Compiling Rules (%d rules, %d conditions): ",
(int) m_rules.size(),
@ -477,8 +477,6 @@ bool DRC_ENGINE::CompileRules()
}
}
}
return true;
}
@ -497,14 +495,17 @@ void DRC_ENGINE::InitEngine( const wxFileName& aRulePath )
m_ruleConditions.clear();
m_rules.clear();
m_rulesValid = false;
loadImplicitRules();
loadRules( aRulePath );
CompileRules();
compileRules();
for( int ii = DRCE_FIRST; ii < DRCE_LAST; ++ii )
m_errorLimits[ ii ] = INT_MAX;
m_rulesValid = true;
}

View File

@ -164,7 +164,7 @@ public:
bool GetReportAllTrackErrors() const { return m_reportAllTrackErrors; }
bool GetTestFootprints() const { return m_testFootprints; }
bool CompileRules();
bool RulesValid() { return m_rulesValid; }
void ReportViolation( const std::shared_ptr<DRC_ITEM>& aItem, wxPoint aPos );
bool ReportProgress( double aProgress );
@ -193,7 +193,7 @@ private:
*/
void loadRules( const wxFileName& aPath );
void freeCompiledRules();
void compileRules();
struct CONSTRAINT_WITH_CONDITIONS
{
@ -215,6 +215,7 @@ protected:
std::vector<DRC_RULE_CONDITION*> m_ruleConditions;
std::vector<DRC_RULE*> m_rules;
bool m_rulesValid;
std::vector<DRC_TEST_PROVIDER*> m_testProviders;
EDA_UNITS m_userUnits;

View File

@ -876,8 +876,7 @@ void PCB_EDIT_FRAME::ActivateGalCanvas()
}
void PCB_EDIT_FRAME::ShowBoardSetupDialog( const wxString& aInitialPage, const wxString& aErrorMsg,
int aErrorCtrlId, int aErrorLine, int aErrorCol )
void PCB_EDIT_FRAME::ShowBoardSetupDialog( const wxString& aInitialPage )
{
// Make sure everything's up-to-date
GetBoard()->BuildListOfNets();
@ -887,9 +886,6 @@ void PCB_EDIT_FRAME::ShowBoardSetupDialog( const wxString& aInitialPage, const w
if( !aInitialPage.IsEmpty() )
dlg.SetInitialPage( aInitialPage, wxEmptyString );
if( !aErrorMsg.IsEmpty() )
dlg.SetError( aErrorMsg, aInitialPage, aErrorCtrlId, aErrorLine, aErrorCol );
if( dlg.ShowQuasiModal() == wxID_OK )
{
Prj().GetProjectFile().NetSettings().ResolveNetClassAssignments( true );

View File

@ -475,9 +475,7 @@ public:
/**
* Function ShowBoardSetupDialog
*/
void ShowBoardSetupDialog( const wxString& aInitialPage = wxEmptyString,
const wxString& aErrorMsg = wxEmptyString, int aErrorCtrlId = -1,
int aErrorLine = -1, int aErrorCol = -1 );
void ShowBoardSetupDialog( const wxString& aInitialPage = wxEmptyString );
/* toolbars update UI functions: */

View File

@ -19,7 +19,7 @@
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <wx/numdlg.h>
#include <wx/hyperlink.h>
#include <functional>
using namespace std::placeholders;
#include <class_board.h>
@ -32,6 +32,7 @@ using namespace std::placeholders;
#include <dialogs/dialog_pns_settings.h>
#include <dialogs/dialog_pns_diff_pair_dimensions.h>
#include <dialogs/dialog_track_via_size.h>
#include <widgets/infobar.h>
#include <confirm.h>
#include <bitmaps.h>
#include <tool/action_menu.h>
@ -717,15 +718,39 @@ int ROUTER_TOOL::onViaCommand( const TOOL_EVENT& aEvent )
// Cannot place microvias or blind vias if not allowed (obvious)
if( ( viaType == VIATYPE::BLIND_BURIED ) && ( !bds.m_BlindBuriedViaAllowed ) )
{
frame()->ShowInfoBarError( _( "Blind/buried vias have to be enabled in "
"Board Setup > Design Rules > Constraints." ) );
WX_INFOBAR* infobar = frame()->GetInfoBar();
wxHyperlinkCtrl* button = new wxHyperlinkCtrl( infobar, wxID_ANY,
_("Show board setup"), wxEmptyString );
button->Bind( wxEVT_COMMAND_HYPERLINK, std::function<void( wxHyperlinkEvent& aEvent )>(
[&]( wxHyperlinkEvent& aEvent )
{
getEditFrame<PCB_EDIT_FRAME>()->ShowBoardSetupDialog( _( "Constraints" ) );
} ) );
infobar->ShowMessageFor( _( "Blind/buried vias have to be enabled in "
"Board Setup > Design Rules > Constraints." ),
10000, wxICON_ERROR );
infobar->AddButton( button );
return false;
}
if( ( viaType == VIATYPE::MICROVIA ) && ( !bds.m_MicroViasAllowed ) )
{
frame()->ShowInfoBarError( _( "Microvias have to be enabled in "
"Board Setup > Design Rules > Constraints." ) );
WX_INFOBAR* infobar = frame()->GetInfoBar();
wxHyperlinkCtrl* button = new wxHyperlinkCtrl( infobar, wxID_ANY,
_("Show board setup"), wxEmptyString );
button->Bind( wxEVT_COMMAND_HYPERLINK, std::function<void( wxHyperlinkEvent& aEvent )>(
[&]( wxHyperlinkEvent& aEvent )
{
getEditFrame<PCB_EDIT_FRAME>()->ShowBoardSetupDialog( _( "Constraints" ) );
} ) );
infobar->ShowMessageFor( _( "Microvias have to be enabled in "
"Board Setup > Design Rules > Constraints." ),
10000, wxICON_ERROR );
infobar->AddButton( button );
return false;
}

View File

@ -197,8 +197,7 @@ void PCB_INSPECTION_TOOL::reportClearance( DRC_CONSTRAINT_TYPE_T aClearanceType,
}
catch( PARSE_ERROR& pe )
{
m_frame->ShowBoardSetupDialog( _( "Rules" ), pe.What(), ID_RULES_EDITOR,
pe.lineNumber, pe.byteIndex );
m_frame->ShowBoardSetupDialog( _( "Rules" ) );
return;
}
@ -390,8 +389,7 @@ int PCB_INSPECTION_TOOL::InspectConstraints( const TOOL_EVENT& aEvent )
}
catch( PARSE_ERROR& pe )
{
m_frame->ShowBoardSetupDialog( _( "Rules" ), pe.What(), ID_RULES_EDITOR,
pe.lineNumber, pe.byteIndex );
m_frame->ShowBoardSetupDialog( _( "Rules" ) );
return 1;
}

View File

@ -28,7 +28,9 @@
#include <connectivity/connectivity_data.h>
#include <board_commit.h>
#include <widgets/progress_reporter.h>
#include <widgets/infobar.h>
#include <wx/event.h>
#include <wx/hyperlink.h>
#include <tool/tool_manager.h>
#include "pcb_actions.h"
#include "zone_filler_tool.h"
@ -102,6 +104,23 @@ void ZONE_FILLER_TOOL::FillAllZones( wxWindow* aCaller, PROGRESS_REPORTER* aRepo
ZONE_FILLER filler( board(), &commit );
if( !board()->GetDesignSettings().m_DRCEngine->RulesValid() )
{
WX_INFOBAR* infobar = frame()->GetInfoBar();
wxHyperlinkCtrl* button = new wxHyperlinkCtrl( infobar, wxID_ANY, _("Show DRC rules"),
wxEmptyString );
button->Bind( wxEVT_COMMAND_HYPERLINK, std::function<void( wxHyperlinkEvent& aEvent )>(
[&]( wxHyperlinkEvent& aEvent )
{
getEditFrame<PCB_EDIT_FRAME>()->ShowBoardSetupDialog( _( "Rules" ) );
} ) );
infobar->ShowMessageFor( _( "Zone fills may be inaccurate. DRC rules contain errors." ),
10000, wxICON_WARNING );
infobar->AddButton( button );
}
if( aReporter )
filler.SetProgressReporter( aReporter );
else