Better locality-of-reference for footprint chooser filters.

This commit is contained in:
Jeff Young 2024-03-23 12:38:35 +00:00
parent 490dbfdf83
commit 7218d501d4
7 changed files with 146 additions and 96 deletions

View File

@ -59,6 +59,7 @@ LIB_TREE::LIB_TREE( wxWindow* aParent, const wxString& aRecentSearchesKey, LIB_T
m_details_ctrl( nullptr ),
m_inTimerEvent( false ),
m_recentSearchesKey( aRecentSearchesKey ),
m_filtersSizer( nullptr ),
m_skipNextRightClick( false ),
m_previewWindow( nullptr ),
m_previewDisabled( false )
@ -132,7 +133,7 @@ LIB_TREE::LIB_TREE( wxWindow* aParent, const wxString& aRecentSearchesKey, LIB_T
m_sort_ctrl->Bind( wxEVT_CHAR_HOOK, &LIB_TREE::onTreeCharHook, this );
search_sizer->Add( m_sort_ctrl, 0, wxEXPAND | wxRIGHT, 5 );
search_sizer->Add( m_sort_ctrl, 0, wxEXPAND, 5 );
sizer->Add( search_sizer, 0, wxEXPAND | wxBOTTOM, 5 );
@ -164,6 +165,12 @@ LIB_TREE::LIB_TREE( wxWindow* aParent, const wxString& aRecentSearchesKey, LIB_T
Bind( wxEVT_TIMER, &LIB_TREE::onDebounceTimer, this, m_debounceTimer->GetId() );
}
if( aFlags & FILTERS )
{
m_filtersSizer = new wxBoxSizer( wxVERTICAL );
sizer->Add( m_filtersSizer, 0, wxEXPAND | wxLEFT, 4 );
}
// Tree control
int dvFlags = ( aFlags & MULTISELECT ) ? wxDV_MULTIPLE : wxDV_SINGLE;
m_tree_ctrl = new WX_DATAVIEWCTRL( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, dvFlags );
@ -175,7 +182,7 @@ LIB_TREE::LIB_TREE( wxWindow* aParent, const wxString& aRecentSearchesKey, LIB_T
m_tree_ctrl->SetRowHeight( rowHeight );
#endif
sizer->Add( m_tree_ctrl, 5, wxRIGHT | wxBOTTOM | wxEXPAND, 5 );
sizer->Add( m_tree_ctrl, 5, wxEXPAND, 5 );
// Description panel
if( aFlags & DETAILS )

View File

@ -53,7 +53,8 @@ public:
{
NONE = 0x00,
SEARCH = 0x01,
DETAILS = 0x02,
FILTERS = 0x02,
DETAILS = 0x04,
ALL_WIDGETS = 0x0F,
MULTISELECT = 0x10
};
@ -151,6 +152,8 @@ public:
wxWindow* GetFocusTarget();
wxSizer* GetFiltersSizer() { return m_filtersSizer; }
/**
* Focus the search widget if it exists
*/
@ -242,6 +245,8 @@ protected:
wxString m_recentSearchesKey;
wxBoxSizer* m_filtersSizer;
bool m_skipNextRightClick;
wxPoint m_hoverPos;

View File

@ -79,24 +79,28 @@ DIALOG_FOOTPRINT_CHOOSER::DIALOG_FOOTPRINT_CHOOSER( PCB_BASE_FRAME* aParent,
wxBoxSizer* bSizerBottom;
bSizerBottom = new wxBoxSizer( wxHORIZONTAL );
// Add a spacer on the left
bSizerBottom->Add( 20, 0, 0, 0, 5 );
m_grButton3DView = new BITMAP_BUTTON( this, wxID_ANY,
wxNullBitmap, wxDefaultPosition, wxDefaultSize/*, wxBU_AUTODRAW|wxBORDER_NONE*/ );
bSizerBottom->Add( 0, 0, 1, 0, 5 ); // Add spacer to right-align buttons
BITMAP_BUTTON* separator = new BITMAP_BUTTON( this, wxID_ANY, wxNullBitmap );
separator->SetIsSeparator();
bSizerBottom->Add( separator, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_grButton3DView = new BITMAP_BUTTON( this, wxID_ANY, wxNullBitmap );
m_grButton3DView->SetIsRadioButton();
m_grButton3DView->SetBitmap( KiBitmapBundle( BITMAPS::shape_3d ) );
m_grButton3DView->Check( !m_showFpMode );
bSizerBottom->Add( m_grButton3DView, 0, wxALIGN_CENTER_VERTICAL, 5 );
bSizerBottom->Add( m_grButton3DView, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_grButtonFpView = new BITMAP_BUTTON( this, wxID_ANY,
wxNullBitmap, wxDefaultPosition, wxDefaultSize/*, wxBU_AUTODRAW|wxBORDER_NONE*/ );
m_grButtonFpView = new BITMAP_BUTTON( this, wxID_ANY, wxNullBitmap );
m_grButtonFpView->SetIsRadioButton();
m_grButtonFpView->SetBitmap( KiBitmapBundle( BITMAPS::module ) );
m_grButtonFpView->Check( m_showFpMode );
bSizerBottom->Add( m_grButtonFpView, 0, wxALIGN_CENTER_VERTICAL, 5 );
bSizerBottom->Add( m_grButtonFpView, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
bSizerBottom->Add( 0, 0, 1, wxEXPAND, 5 );
separator = new BITMAP_BUTTON( this, wxID_ANY, wxNullBitmap );
separator->SetIsSeparator();
bSizerBottom->Add( separator, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
if( aPreselect.IsValid() )
m_chooserPanel->SetPreselect( aPreselect );
@ -111,6 +115,7 @@ DIALOG_FOOTPRINT_CHOOSER::DIALOG_FOOTPRINT_CHOOSER( PCB_BASE_FRAME* aParent,
sdbSizer->AddButton( cancelButton );
sdbSizer->Realize();
bSizerBottom->Add( 20, 0, 0, 0, 5 ); // Add spacer
bSizerBottom->Add( sdbSizer, 0, wxEXPAND | wxALL, 5 );
m_SizerTop->Add( bSizerBottom, 0, wxEXPAND, 5 );

View File

@ -93,19 +93,6 @@ FOOTPRINT_CHOOSER_FRAME::FOOTPRINT_CHOOSER_FRAME( KIWAY* aKiway, wxWindow* aPare
wxPanel* bottomPanel = new wxPanel( this );
wxBoxSizer* bottomSizer = new wxBoxSizer( wxVERTICAL );
m_filterByFPFilters = new wxCheckBox( bottomPanel, wxID_ANY, _( "Apply footprint filters" ) );
m_filterByPinCount = new wxCheckBox( bottomPanel, wxID_ANY, _( "Filter by pin count" ) );
m_filterByFPFilters->Show( false );
m_filterByPinCount->Show( false );
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
{
m_filterByFPFilters->SetValue( cfg->m_FootprintChooser.use_fp_filters );
m_filterByPinCount->SetValue( cfg->m_FootprintChooser.filter_on_pin_count );
}
wxBoxSizer* frameSizer = new wxBoxSizer( wxVERTICAL );
m_chooserPanel = new PANEL_FOOTPRINT_CHOOSER( this, this, s_FootprintHistoryList,
@ -136,38 +123,33 @@ FOOTPRINT_CHOOSER_FRAME::FOOTPRINT_CHOOSER_FRAME( KIWAY* aKiway, wxWindow* aPare
build3DCanvas(); // must be called after creating m_chooserPanel
m_preview3DCanvas->Show( !m_showFpMode );
// The m_filterByFPFilters can have a long string, if the symbol has a FP filter
// with many items, so give it its own sizer
wxBoxSizer* fpFilterSizerByFP = new wxBoxSizer( wxVERTICAL );
fpFilterSizerByFP->Add( m_filterByFPFilters, 0, wxLEFT | wxTOP | wxEXPAND, 5 );
bottomSizer->Add( fpFilterSizerByFP, 0, wxLEFT | wxTOP, 5 );
// buttonsSizer contains the m_filterByPinCount and BITMAP buttons
// buttonsSizer contains the BITMAP buttons
wxBoxSizer* buttonsSizer = new wxBoxSizer( wxHORIZONTAL );
buttonsSizer->Add( m_filterByPinCount, 0, wxALL | wxALIGN_CENTER_VERTICAL, 5 );
// Add a spacer between the wxCheckBox and bitmap buttons
buttonsSizer->Add( 0, 0, 1, wxEXPAND, 5 );
buttonsSizer->Add( 0, 0, 1, 0, 5 ); // Add spacer to right-align buttons
m_grButton3DView = new BITMAP_BUTTON( bottomPanel, wxID_ANY,
wxNullBitmap, wxDefaultPosition,
wxDefaultSize/*, wxBU_AUTODRAW|wxBORDER_NONE*/ );
BITMAP_BUTTON* separator = new BITMAP_BUTTON( bottomPanel, wxID_ANY, wxNullBitmap );
separator->SetIsSeparator();
buttonsSizer->Add( separator, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_grButton3DView = new BITMAP_BUTTON( bottomPanel, wxID_ANY, wxNullBitmap );
m_grButton3DView->SetIsRadioButton();
m_grButton3DView->SetBitmap( KiBitmapBundle( BITMAPS::shape_3d ) );
m_grButton3DView->Check( !m_showFpMode );
buttonsSizer->Add( m_grButton3DView, 0, wxALL | wxALIGN_CENTER_VERTICAL, 5 );
buttonsSizer->Add( m_grButton3DView, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_grButtonFpView = new BITMAP_BUTTON( bottomPanel, wxID_ANY,
wxNullBitmap, wxDefaultPosition,
wxDefaultSize/*, wxBU_AUTODRAW|wxBORDER_NONE*/ );
m_grButtonFpView = new BITMAP_BUTTON( bottomPanel, wxID_ANY, wxNullBitmap );
m_grButtonFpView->SetIsRadioButton();
m_grButtonFpView->SetBitmap( KiBitmapBundle( BITMAPS::module ) );
m_grButtonFpView->Check( m_showFpMode );
buttonsSizer->Add( m_grButtonFpView, 0, wxALL | wxALIGN_CENTER_VERTICAL, 5 );
buttonsSizer->Add( m_grButtonFpView, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_show3DViewer = new wxCheckBox( bottomPanel, wxID_ANY, _( "3D Viewer Shown in Separate Window" ) );
buttonsSizer->Add( 30, 0, 0, 0, 5 ); // Add spacer
buttonsSizer->Add( m_show3DViewer, 0, wxALL | wxALIGN_CENTER_VERTICAL, 5 );
separator = new BITMAP_BUTTON( bottomPanel, wxID_ANY, wxNullBitmap );
separator->SetIsSeparator();
buttonsSizer->Add( separator, 0, wxRIGHT | wxALIGN_CENTER_VERTICAL, 1 );
m_show3DViewer = new wxCheckBox( bottomPanel, wxID_ANY, _( "Show 3D viewer in own window" ) );
buttonsSizer->Add( m_show3DViewer, 0, wxALL | wxALIGN_CENTER_VERTICAL, 3 );
wxStdDialogButtonSizer* sdbSizer = new wxStdDialogButtonSizer();
wxButton* okButton = new wxButton( bottomPanel, wxID_OK );
@ -177,11 +159,9 @@ FOOTPRINT_CHOOSER_FRAME::FOOTPRINT_CHOOSER_FRAME( KIWAY* aKiway, wxWindow* aPare
sdbSizer->AddButton( cancelButton );
sdbSizer->Realize();
// Add a spacer between the bitmap buttons and thesdbSizer
buttonsSizer->Add( 0, 0, 1, wxEXPAND, 5 );
buttonsSizer->Add( sdbSizer, 1, wxALL, 5 );
bottomSizer->Add( buttonsSizer, 0, wxEXPAND | wxLEFT, 5 );
buttonsSizer->Add( 20, 0, 0, 0, 5 ); // Add spacer
buttonsSizer->Add( sdbSizer, 0, wxALL | wxALIGN_CENTER_VERTICAL, 5 );
bottomSizer->Add( buttonsSizer, 0, wxEXPAND, 5 );
bottomPanel->SetSizer( bottomSizer );
frameSizer->Add( bottomPanel, 0, wxEXPAND );
@ -194,33 +174,21 @@ FOOTPRINT_CHOOSER_FRAME::FOOTPRINT_CHOOSER_FRAME( KIWAY* aKiway, wxWindow* aPare
Layout();
m_chooserPanel->FinishSetup();
m_filterByPinCount->Bind( wxEVT_CHECKBOX,
[&]( wxCommandEvent& evt )
{
m_chooserPanel->Regenerate();
} );
m_filterByFPFilters->Bind( wxEVT_CHECKBOX,
[&]( wxCommandEvent& evt )
{
m_chooserPanel->Regenerate();
} );
// Connect Events
m_grButton3DView->Connect( wxEVT_COMMAND_BUTTON_CLICKED ,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::on3DviewReq ),
NULL, this );
nullptr, this );
m_grButtonFpView->Connect( wxEVT_COMMAND_BUTTON_CLICKED ,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpViewReq ),
NULL, this );
nullptr, this );
m_show3DViewer->Connect( wxEVT_COMMAND_CHECKBOX_CLICKED ,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onExternalViewer3DEnable ),
NULL, this );
nullptr, this );
Connect( FP_SELECTION_EVENT, // custom event fired by a PANEL_FOOTPRINT_CHOOSER
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpChanged ), NULL, this );
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpChanged ), nullptr, this );
// Needed on Linux to fix the position of widgets in bottomPanel
PostSizeEvent();
@ -232,21 +200,24 @@ FOOTPRINT_CHOOSER_FRAME::~FOOTPRINT_CHOOSER_FRAME()
// Disconnect Events
m_grButton3DView->Disconnect( wxEVT_COMMAND_BUTTON_CLICKED,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::on3DviewReq ),
NULL, this );
nullptr, this );
m_grButtonFpView->Disconnect( wxEVT_COMMAND_BUTTON_CLICKED,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpViewReq ),
NULL, this );
nullptr, this );
m_show3DViewer->Disconnect( wxEVT_COMMAND_CHECKBOX_CLICKED ,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onExternalViewer3DEnable ),
NULL, this );
nullptr, this );
Disconnect( FP_SELECTION_EVENT,
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpChanged ), NULL, this );
wxCommandEventHandler( FOOTPRINT_CHOOSER_FRAME::onFpChanged ), nullptr, this );
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
{
if( m_filterByFPFilters )
cfg->m_FootprintChooser.use_fp_filters = m_filterByFPFilters->GetValue();
if( m_filterByPinCount )
cfg->m_FootprintChooser.filter_on_pin_count = m_filterByPinCount->GetValue();
}
}
@ -306,6 +277,30 @@ void FOOTPRINT_CHOOSER_FRAME::Update3DView( bool aMarkDirty,
}
bool FOOTPRINT_CHOOSER_FRAME::filterByPinCount()
{
if( m_filterByPinCount )
return m_filterByPinCount->GetValue();
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
return cfg->m_FootprintChooser.filter_on_pin_count;
return false;
}
bool FOOTPRINT_CHOOSER_FRAME::filterByFPFilters()
{
if( m_filterByFPFilters )
return m_filterByFPFilters->GetValue();
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
return cfg->m_FootprintChooser.use_fp_filters;
return false;
}
bool FOOTPRINT_CHOOSER_FRAME::filterFootprint( LIB_TREE_NODE& aNode )
{
if( aNode.m_Type == LIB_TREE_NODE::TYPE::LIBRARY )
@ -313,7 +308,7 @@ bool FOOTPRINT_CHOOSER_FRAME::filterFootprint( LIB_TREE_NODE& aNode )
// Normally lib nodes get scored by the max of their children's scores. However, if a
// lib node *has* no children then the scorer will call the filter on the lib node itself,
// and we just want to return true if we're not filtering at all.
return !m_filterByPinCount->GetValue() && !m_filterByFPFilters->GetValue();
return !filterByPinCount() && !filterByFPFilters();
}
auto patternMatch =
@ -339,13 +334,13 @@ bool FOOTPRINT_CHOOSER_FRAME::filterFootprint( LIB_TREE_NODE& aNode )
return false;
};
if( m_pinCount > 0 && m_filterByPinCount->GetValue() )
if( m_pinCount > 0 && filterByPinCount() )
{
if( aNode.m_PinCount != m_pinCount )
return false;
}
if( !m_fpFilters.empty() && m_filterByFPFilters->GetValue() )
if( !m_fpFilters.empty() && filterByFPFilters() )
{
if( !patternMatch( aNode.m_LibId, m_fpFilters ) )
return false;
@ -386,6 +381,9 @@ COLOR_SETTINGS* FOOTPRINT_CHOOSER_FRAME::GetColorSettings( bool aForceRefresh )
}
static wxRect s_dialogRect( 0, 0, 0, 0 );
void FOOTPRINT_CHOOSER_FRAME::KiwayMailIn( KIWAY_EXPRESS& mail )
{
const std::string& payload = mail.GetPayload();
@ -394,6 +392,10 @@ void FOOTPRINT_CHOOSER_FRAME::KiwayMailIn( KIWAY_EXPRESS& mail )
{
case MAIL_SYMBOL_NETLIST:
{
wxSizer* filtersSizer = m_chooserPanel->GetFiltersSizer();
wxWindow* filtersWindow = filtersSizer->GetContainingWindow();
wxString msg;
m_pinCount = 0;
m_fpFilters.clear();
@ -414,9 +416,17 @@ void FOOTPRINT_CHOOSER_FRAME::KiwayMailIn( KIWAY_EXPRESS& mail )
if( m_pinCount > 0 )
{
m_filterByPinCount->SetLabel( m_filterByPinCount->GetLabel()
+ wxString::Format( wxS( " (%d)" ), m_pinCount ) );
m_filterByPinCount->Show( true );
msg.Printf( _( "Filter by pin count (%d)" ), m_pinCount );
m_filterByPinCount = new wxCheckBox( filtersWindow, wxID_ANY, msg );
m_filterByPinCount->Bind( wxEVT_CHECKBOX,
[&]( wxCommandEvent& evt )
{
m_chooserPanel->Regenerate();
} );
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
m_filterByPinCount->SetValue( cfg->m_FootprintChooser.filter_on_pin_count );
}
}
@ -428,12 +438,33 @@ void FOOTPRINT_CHOOSER_FRAME::KiwayMailIn( KIWAY_EXPRESS& mail )
m_fpFilters.back()->SetPattern( filter.Lower() );
}
m_filterByFPFilters->SetLabel( m_filterByFPFilters->GetLabel()
+ wxString::Format( wxS( " (%s)" ), strings[1] ) );
m_filterByFPFilters->Show( true );
msg.Printf( _( "Apply footprint filters (%s)" ), strings[1] );
m_filterByFPFilters = new wxCheckBox( filtersWindow, wxID_ANY, msg );
m_filterByFPFilters->Bind( wxEVT_CHECKBOX,
[&]( wxCommandEvent& evt )
{
m_chooserPanel->Regenerate();
} );
if( PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( Kiface().KifaceSettings() ) )
m_filterByFPFilters->SetValue( cfg->m_FootprintChooser.use_fp_filters );
}
if( m_filterByFPFilters )
m_chooserPanel->GetFiltersSizer()->Add( m_filterByFPFilters, 0, wxEXPAND|wxBOTTOM, 4 );
if( m_filterByPinCount )
m_chooserPanel->GetFiltersSizer()->Add( m_filterByPinCount, 0, wxEXPAND|wxBOTTOM, 4 );
m_chooserPanel->GetViewerPanel()->SetPinFunctions( pinNames );
// Save the wxFormBuilder size of the dialog...
if( s_dialogRect.GetSize().x == 0 || s_dialogRect.GetSize().y == 0 )
s_dialogRect = wxRect( wxWindow::GetPosition(), wxWindow::GetSize() );
// ... and then give it a kick to get it to layout the new items
GetSizer()->SetSizeHints( this );
break;
}
@ -459,9 +490,6 @@ bool FOOTPRINT_CHOOSER_FRAME::ShowModal( wxString* aFootprint, wxWindow* aParent
}
static wxRect s_dialogRect( 0, 0, 0, 0 );
void FOOTPRINT_CHOOSER_FRAME::SetPosition( const wxPoint& aNewPosition )
{
PCB_BASE_FRAME::SetPosition( aNewPosition );

View File

@ -72,6 +72,8 @@ protected:
FOOTPRINT_CHOOSER_FRAME( KIWAY* aKiway, wxWindow* aParent );
private:
bool filterByPinCount();
bool filterByFPFilters();
bool filterFootprint( LIB_TREE_NODE& aNode );
void Show3DViewerFrame();

View File

@ -122,7 +122,7 @@ PANEL_FOOTPRINT_CHOOSER::PANEL_FOOTPRINT_CHOOSER( PCB_BASE_FRAME* aFrame, wxTopL
detailsPanel->SetSizer( detailsSizer );
m_details = new HTML_WINDOW( detailsPanel, wxID_ANY, wxDefaultPosition, wxDefaultSize );
detailsSizer->Add( m_details, 1, wxEXPAND | wxALL, 5 );
detailsSizer->Add( m_details, 1, wxEXPAND, 5 );
detailsPanel->Layout();
detailsSizer->Fit( detailsPanel );
@ -130,7 +130,7 @@ PANEL_FOOTPRINT_CHOOSER::PANEL_FOOTPRINT_CHOOSER( PCB_BASE_FRAME* aFrame, wxTopL
m_vsplitter->SetMinimumPaneSize( 20 );
m_vsplitter->SplitHorizontally( m_hsplitter, detailsPanel );
sizer->Add( m_vsplitter, 1, wxEXPAND | wxALL, 5 );
sizer->Add( m_vsplitter, 1, wxEXPAND, 5 );
m_tree = new LIB_TREE( m_hsplitter, wxT( "footprints" ), fpTable, m_adapter,
LIB_TREE::FLAGS::ALL_WIDGETS, m_details );
@ -143,7 +143,7 @@ PANEL_FOOTPRINT_CHOOSER::PANEL_FOOTPRINT_CHOOSER( PCB_BASE_FRAME* aFrame, wxTopL
m_preview_ctrl = new FOOTPRINT_PREVIEW_WIDGET( m_RightPanel, m_frame->Kiway() );
m_preview_ctrl->SetUserUnits( m_frame->GetUserUnits() );
m_RightPanelSizer->Add( m_preview_ctrl, 1, wxEXPAND | wxALL, 5 );
m_RightPanelSizer->Add( m_preview_ctrl, 1, wxEXPAND, 5 );
m_RightPanel->SetSizer( m_RightPanelSizer );
m_RightPanel->Layout();

View File

@ -73,15 +73,12 @@ public:
wxWindow* GetFocusTarget() const { return m_tree->GetFocusTarget(); }
wxSizer* GetFiltersSizer() const { return m_tree->GetFiltersSizer(); }
void Regenerate() { m_tree->Regenerate( true ); }
FOOTPRINT_PREVIEW_WIDGET* GetViewerPanel() const { return m_preview_ctrl; }
wxPanel* m_RightPanel;
wxBoxSizer* m_RightPanelSizer;
const FOOTPRINT* m_CurrFootprint;
protected:
static constexpr int DblClickDelay = 100; // milliseconds
@ -99,6 +96,12 @@ protected:
*/
void onFootprintChosen( wxCommandEvent& aEvent );
public:
wxPanel* m_RightPanel;
wxBoxSizer* m_RightPanelSizer;
const FOOTPRINT* m_CurrFootprint;
protected:
wxTimer* m_dbl_click_timer;
wxTimer* m_open_libs_timer;