DIALOG_DRC_CONTROL: fix a crash on wxWidgets 3.1.3, Windows,

Happens when right clicking on an item in displayed lists.
The crash was due to a bug in wxWidgets, and the fix is only a workaround

Also remove duplicate code.
This commit is contained in:
jean-pierre charras 2019-12-02 10:15:04 +01:00
parent 2a3d4ffe88
commit 5cd7f3fdee
5 changed files with 43 additions and 74 deletions

View File

@ -75,27 +75,6 @@ DIALOG_DRC_CONTROL::DIALOG_DRC_CONTROL( DRC* aTester, PCB_EDIT_FRAME* aEditorFra
InitValues(); InitValues();
// Connect events
m_ClearanceListBox->Connect( ID_CLEARANCE_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickClearance ),
NULL, this );
m_ClearanceListBox->Connect( ID_CLEARANCE_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpClearance ),
NULL, this );
m_UnconnectedListBox->Connect( ID_UNCONNECTED_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickUnconnected ),
NULL, this );
m_UnconnectedListBox->Connect( ID_UNCONNECTED_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpUnconnected ),
NULL, this );
m_FootprintsListBox->Connect( ID_FOOTPRINTS_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickFootprints ),
NULL, this );
m_FootprintsListBox->Connect( ID_FOOTPRINTS_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpFootprints ),
NULL, this );
// Now all widgets have the size fixed, call FinishDialogSettings
FinishDialogSettings(); FinishDialogSettings();
} }
@ -105,26 +84,6 @@ DIALOG_DRC_CONTROL::~DIALOG_DRC_CONTROL()
m_config->Write( DrcRefillZonesKey, m_cbRefillZones->GetValue() ); m_config->Write( DrcRefillZonesKey, m_cbRefillZones->GetValue() );
m_config->Write( DrcTrackToZoneTestKey, m_cbReportTracksToZonesErrors->GetValue() ); m_config->Write( DrcTrackToZoneTestKey, m_cbReportTracksToZonesErrors->GetValue() );
m_config->Write( DrcTestFootprintsKey, m_cbTestFootprints->GetValue() ); m_config->Write( DrcTestFootprintsKey, m_cbTestFootprints->GetValue() );
// Disconnect events
m_ClearanceListBox->Disconnect( ID_CLEARANCE_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickClearance ),
NULL, this );
m_ClearanceListBox->Disconnect( ID_CLEARANCE_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpClearance ),
NULL, this );
m_UnconnectedListBox->Disconnect( ID_UNCONNECTED_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickUnconnected ),
NULL, this );
m_UnconnectedListBox->Disconnect( ID_UNCONNECTED_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpUnconnected ),
NULL, this );
m_FootprintsListBox->Disconnect( ID_FOOTPRINTS_LIST, wxEVT_LEFT_DCLICK,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnLeftDClickFootprints ),
NULL, this );
m_FootprintsListBox->Disconnect( ID_FOOTPRINTS_LIST, wxEVT_RIGHT_UP,
wxMouseEventHandler( DIALOG_DRC_CONTROL::OnRightUpFootprints ),
NULL, this );
} }
@ -337,14 +296,7 @@ void DIALOG_DRC_CONTROL::OnLeftDClickClearance( wxMouseEvent& event )
void DIALOG_DRC_CONTROL::OnRightUpFootprints( wxMouseEvent& event ) void DIALOG_DRC_CONTROL::OnRightUpFootprints( wxMouseEvent& event )
{ {
// popup menu to go to either of the items listed in the DRC_ITEM. int selection = rightUpClicSelection( m_FootprintsListBox, event );
// Check if user right-clicked on a different item
int selection = m_FootprintsListBox->HitTest( event.GetPosition() );
if( selection == wxNOT_FOUND )
selection = m_FootprintsListBox->GetSelection();
else
m_FootprintsListBox->SetSelection( selection );
if( selection != wxNOT_FOUND ) if( selection != wxNOT_FOUND )
doSelectionMenu( m_FootprintsListBox->GetItem( selection ) ); doSelectionMenu( m_FootprintsListBox->GetItem( selection ) );
@ -384,16 +336,33 @@ bool DIALOG_DRC_CONTROL::focusOnItem( const DRC_ITEM* aItem )
} }
int DIALOG_DRC_CONTROL::rightUpClicSelection( DRCLISTBOX* aListBox, wxMouseEvent& event )
{
#if wxCHECK_VERSION( 3, 1, 3 )
// wxWidgets 3.1.3 has a bug in HitTest(): one cannot have the item selection
// on a right click: the returned value is always 10 so do not try to select
// an item on the right click. Just use the current selection (if any)
int selection = aListBox->GetSelection();
#else
// Check if user right-clicked on a different item, and select the right clicked item
int selection = aListBox->HitTest( event.GetPosition() );
if( selection >= (int)aListBox->GetItemCount() ) // Should not happen.
selection = wxNOT_FOUND;
#endif
if( selection == wxNOT_FOUND )
selection = aListBox->GetSelection();
else if( aListBox->GetSelection() != selection )
aListBox->SetSelection( selection );
return selection;
}
void DIALOG_DRC_CONTROL::OnRightUpUnconnected( wxMouseEvent& event ) void DIALOG_DRC_CONTROL::OnRightUpUnconnected( wxMouseEvent& event )
{ {
// popup menu to go to either of the items listed in the DRC_ITEM. // popup menu to go to either of the items listed in the DRC_ITEM.
// Check if user right-clicked on a different item int selection = rightUpClicSelection( m_UnconnectedListBox, event );
int selection = m_UnconnectedListBox->HitTest( event.GetPosition() );
if( selection == wxNOT_FOUND )
selection = m_UnconnectedListBox->GetSelection();
else
m_UnconnectedListBox->SetSelection( selection );
if( selection != wxNOT_FOUND ) if( selection != wxNOT_FOUND )
doSelectionMenu( m_UnconnectedListBox->GetItem( selection ) ); doSelectionMenu( m_UnconnectedListBox->GetItem( selection ) );
@ -403,13 +372,7 @@ void DIALOG_DRC_CONTROL::OnRightUpUnconnected( wxMouseEvent& event )
void DIALOG_DRC_CONTROL::OnRightUpClearance( wxMouseEvent& event ) void DIALOG_DRC_CONTROL::OnRightUpClearance( wxMouseEvent& event )
{ {
// popup menu to go to either of the items listed in the DRC_ITEM. // popup menu to go to either of the items listed in the DRC_ITEM.
// Check if user right-clicked on a different item int selection = rightUpClicSelection( m_ClearanceListBox, event );
int selection = m_ClearanceListBox->HitTest( event.GetPosition() );
if( selection == wxNOT_FOUND )
selection = m_ClearanceListBox->GetSelection();
else
m_ClearanceListBox->SetSelection( selection );
if( selection != wxNOT_FOUND ) if( selection != wxNOT_FOUND )
doSelectionMenu( m_ClearanceListBox->GetItem( selection ) ); doSelectionMenu( m_ClearanceListBox->GetItem( selection ) );

View File

@ -3,7 +3,7 @@
* *
* Copyright (C) 2011 Jean-Pierre Charras, jean-pierre.charras@ujf-grenoble.fr * Copyright (C) 2011 Jean-Pierre Charras, jean-pierre.charras@ujf-grenoble.fr
* Copyright (C) 2009 Dick Hollenbeck, dick@softplc.com * Copyright (C) 2009 Dick Hollenbeck, dick@softplc.com
* Copyright (C) 2004-2012 KiCad Developers, see AUTHORS.txt for contributors. * Copyright (C) 2004-2019 KiCad Developers, see AUTHORS.txt for contributors.
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License * modify it under the terms of the GNU General Public License
@ -92,6 +92,10 @@ private:
void SetDRCParameters( ); void SetDRCParameters( );
/// @return the selection on a right click on a DRCLISTBOX
/// return wxNOT_FOUND if no selection
int rightUpClicSelection( DRCLISTBOX* aListBox, wxMouseEvent& event );
/// wxEVT_COMMAND_CHECKBOX_CLICKED event handler for ID_CHECKBOX_RPT_FILE /// wxEVT_COMMAND_CHECKBOX_CLICKED event handler for ID_CHECKBOX_RPT_FILE
void OnReportCheckBoxClicked( wxCommandEvent& event ) override; void OnReportCheckBoxClicked( wxCommandEvent& event ) override;

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version Oct 26 2018) // C++ code generated with wxFormBuilder (version Jul 10 2019)
// http://www.wxformbuilder.org/ // http://www.wxformbuilder.org/
// //
// PLEASE DO *NOT* EDIT THIS FILE! // PLEASE DO *NOT* EDIT THIS FILE!
@ -150,7 +150,7 @@ DIALOG_DRC_CONTROL_BASE::DIALOG_DRC_CONTROL_BASE( wxWindow* parent, wxWindowID i
m_ClearanceListBox = new DRCLISTBOX( m_panelViolations, ID_CLEARANCE_LIST, wxDefaultPosition, wxDefaultSize, 0, NULL, 0 ); m_ClearanceListBox = new DRCLISTBOX( m_panelViolations, ID_CLEARANCE_LIST, wxDefaultPosition, wxDefaultSize, 0, NULL, 0 );
m_ClearanceListBox->SetFont( wxFont( wxNORMAL_FONT->GetPointSize(), wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL, false, wxEmptyString ) ); m_ClearanceListBox->SetFont( wxFont( wxNORMAL_FONT->GetPointSize(), wxFONTFAMILY_DEFAULT, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL, false, wxEmptyString ) );
m_ClearanceListBox->SetToolTip( _("Left-click to center on problem marker. Right-click to highlight items.") ); m_ClearanceListBox->SetToolTip( _("Left-click to center on problem marker. \nRight-click to highlight items.") );
bSizerViolationsBox->Add( m_ClearanceListBox, 1, wxEXPAND|wxALL, 5 ); bSizerViolationsBox->Add( m_ClearanceListBox, 1, wxEXPAND|wxALL, 5 );
@ -158,13 +158,13 @@ DIALOG_DRC_CONTROL_BASE::DIALOG_DRC_CONTROL_BASE( wxWindow* parent, wxWindowID i
m_panelViolations->SetSizer( bSizerViolationsBox ); m_panelViolations->SetSizer( bSizerViolationsBox );
m_panelViolations->Layout(); m_panelViolations->Layout();
bSizerViolationsBox->Fit( m_panelViolations ); bSizerViolationsBox->Fit( m_panelViolations );
m_Notebook->AddPage( m_panelViolations, _("Violations / Markers (%d)"), true ); m_Notebook->AddPage( m_panelViolations, _("Violations / Markers (%d)"), false );
m_panelUnconnectedItems = new wxPanel( m_Notebook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL ); m_panelUnconnectedItems = new wxPanel( m_Notebook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* bSizerUnconnectedBox; wxBoxSizer* bSizerUnconnectedBox;
bSizerUnconnectedBox = new wxBoxSizer( wxVERTICAL ); bSizerUnconnectedBox = new wxBoxSizer( wxVERTICAL );
m_UnconnectedListBox = new DRCLISTBOX( m_panelUnconnectedItems, ID_UNCONNECTED_LIST, wxDefaultPosition, wxDefaultSize, 0, NULL, 0 ); m_UnconnectedListBox = new DRCLISTBOX( m_panelUnconnectedItems, ID_UNCONNECTED_LIST, wxDefaultPosition, wxDefaultSize, 0, NULL, 0 );
m_UnconnectedListBox->SetToolTip( _("Left-click to center on unconnected pair. Right-click to highlight unconnected items.") ); m_UnconnectedListBox->SetToolTip( _("Left-click to center on unconnected pair. \nRight-click to highlight unconnected items.") );
bSizerUnconnectedBox->Add( m_UnconnectedListBox, 1, wxALL|wxEXPAND, 5 ); bSizerUnconnectedBox->Add( m_UnconnectedListBox, 1, wxALL|wxEXPAND, 5 );
@ -172,7 +172,7 @@ DIALOG_DRC_CONTROL_BASE::DIALOG_DRC_CONTROL_BASE( wxWindow* parent, wxWindowID i
m_panelUnconnectedItems->SetSizer( bSizerUnconnectedBox ); m_panelUnconnectedItems->SetSizer( bSizerUnconnectedBox );
m_panelUnconnectedItems->Layout(); m_panelUnconnectedItems->Layout();
bSizerUnconnectedBox->Fit( m_panelUnconnectedItems ); bSizerUnconnectedBox->Fit( m_panelUnconnectedItems );
m_Notebook->AddPage( m_panelUnconnectedItems, _("Unconnected Items (%d)"), false ); m_Notebook->AddPage( m_panelUnconnectedItems, _("Unconnected Items (%d)"), true );
m_panelFootprintWarnings = new wxPanel( m_Notebook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL ); m_panelFootprintWarnings = new wxPanel( m_Notebook, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* bSizerFootprintsBox; wxBoxSizer* bSizerFootprintsBox;
bSizerFootprintsBox = new wxBoxSizer( wxVERTICAL ); bSizerFootprintsBox = new wxBoxSizer( wxVERTICAL );

View File

@ -14,6 +14,7 @@
<property name="file">dialog_drc_base</property> <property name="file">dialog_drc_base</property>
<property name="first_id">1000</property> <property name="first_id">1000</property>
<property name="help_provider">none</property> <property name="help_provider">none</property>
<property name="image_path_wrapper_function_name"></property>
<property name="indent_with_spaces"></property> <property name="indent_with_spaces"></property>
<property name="internationalize">1</property> <property name="internationalize">1</property>
<property name="name">dialog_drc_base</property> <property name="name">dialog_drc_base</property>
@ -25,6 +26,7 @@
<property name="skip_php_events">1</property> <property name="skip_php_events">1</property>
<property name="skip_python_events">1</property> <property name="skip_python_events">1</property>
<property name="ui_table">UI</property> <property name="ui_table">UI</property>
<property name="use_array_enum">0</property>
<property name="use_enum">0</property> <property name="use_enum">0</property>
<property name="use_microsoft_bom">0</property> <property name="use_microsoft_bom">0</property>
<object class="Dialog" expanded="1"> <object class="Dialog" expanded="1">
@ -1285,7 +1287,7 @@
<object class="notebookpage" expanded="1"> <object class="notebookpage" expanded="1">
<property name="bitmap"></property> <property name="bitmap"></property>
<property name="label">Violations / Markers (%d)</property> <property name="label">Violations / Markers (%d)</property>
<property name="select">1</property> <property name="select">0</property>
<object class="wxPanel" expanded="1"> <object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property> <property name="BottomDockable">1</property>
<property name="LeftDockable">1</property> <property name="LeftDockable">1</property>
@ -1395,7 +1397,7 @@
<property name="style"></property> <property name="style"></property>
<property name="subclass">DRCLISTBOX; dialog_drclistbox.h</property> <property name="subclass">DRCLISTBOX; dialog_drclistbox.h</property>
<property name="toolbar_pane">0</property> <property name="toolbar_pane">0</property>
<property name="tooltip">Left-click to center on problem marker. Right-click to highlight items.</property> <property name="tooltip">Left-click to center on problem marker. &#x0A;Right-click to highlight items.</property>
<property name="validator_data_type"></property> <property name="validator_data_type"></property>
<property name="validator_style">wxFILTER_NONE</property> <property name="validator_style">wxFILTER_NONE</property>
<property name="validator_type">wxDefaultValidator</property> <property name="validator_type">wxDefaultValidator</property>
@ -1415,7 +1417,7 @@
<object class="notebookpage" expanded="1"> <object class="notebookpage" expanded="1">
<property name="bitmap"></property> <property name="bitmap"></property>
<property name="label">Unconnected Items (%d)</property> <property name="label">Unconnected Items (%d)</property>
<property name="select">0</property> <property name="select">1</property>
<object class="wxPanel" expanded="1"> <object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property> <property name="BottomDockable">1</property>
<property name="LeftDockable">1</property> <property name="LeftDockable">1</property>
@ -1525,7 +1527,7 @@
<property name="style"></property> <property name="style"></property>
<property name="subclass">DRCLISTBOX; </property> <property name="subclass">DRCLISTBOX; </property>
<property name="toolbar_pane">0</property> <property name="toolbar_pane">0</property>
<property name="tooltip">Left-click to center on unconnected pair. Right-click to highlight unconnected items.</property> <property name="tooltip">Left-click to center on unconnected pair. &#x0A;Right-click to highlight unconnected items.</property>
<property name="validator_data_type"></property> <property name="validator_data_type"></property>
<property name="validator_style">wxFILTER_NONE</property> <property name="validator_style">wxFILTER_NONE</property>
<property name="validator_type">wxDefaultValidator</property> <property name="validator_type">wxDefaultValidator</property>

View File

@ -1,5 +1,5 @@
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version Oct 26 2018) // C++ code generated with wxFormBuilder (version Jul 10 2019)
// http://www.wxformbuilder.org/ // http://www.wxformbuilder.org/
// //
// PLEASE DO *NOT* EDIT THIS FILE! // PLEASE DO *NOT* EDIT THIS FILE!