Revamp component chooser and add footprint preview

This commit brings several changes:

- Add a footprint preview pane to the eeschema component selector
- Upgrade component list to wxTreeListCtrl
- Factor out wxTreeListCtrl subclass TWO_COLUMN_TREE_LIST which
  patches a column size bug
- Linkify datasheet URL in info pane
This commit is contained in:
Chris Pavlina 2017-02-18 21:39:55 -05:00
parent d99da201fb
commit 2632b1d1a0
20 changed files with 1679 additions and 287 deletions

View File

@ -101,6 +101,8 @@ option( BUILD_GITHUB_PLUGIN "Build the GITHUB_PLUGIN for pcbnew." ON )
option( KICAD_SPICE "Build Kicad with internal Spice simulator." OFF )
option( KICAD_FOOTPRINT_SELECTOR "Build experimental eeschema footprint selector." OFF )
# Global setting: exports are explicit
set( CMAKE_CXX_VISIBILITY_PRESET "hidden" )
set( CMAKE_VISIBILITY_INLINES_HIDDEN ON )
@ -307,6 +309,10 @@ if( KICAD_SPICE )
add_definitions( -DKICAD_SPICE )
endif()
if( KICAD_FOOTPRINT_SELECTOR )
add_definitions( -DKICAD_FOOTPRINT_SELECTOR )
endif()
if( KICAD_USE_SCH_IO_MANAGER )
add_definitions( -DKICAD_USE_SCH_IO_MANAGER )
endif()

View File

@ -162,6 +162,8 @@ set( COMMON_DLG_SRCS
set( COMMON_WIDGET_SRCS
widgets/mathplot.cpp
widgets/widget_hotkey_list.cpp
widgets/two_column_tree_list.cpp
widgets/footprint_preview_panel.cpp
)
set( COMMON_PAGE_LAYOUT_SRCS

View File

@ -0,0 +1,62 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2017 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2017 Chris Pavlina <pavlina.chris@gmail.com>
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <widgets/footprint_preview_panel.h>
#include <wx/stattext.h>
#include <kiway.h>
FOOTPRINT_PREVIEW_PANEL* FOOTPRINT_PREVIEW_PANEL::AddToPanel(
KIWAY& aKiway, wxPanel* aPanel, bool aIndicator )
{
FOOTPRINT_PREVIEW_PANEL* fpp = NULL;
KIFACE* kiface = aKiway.KiFACE( KIWAY::FACE_PCB );
if( !kiface )
return NULL;
try {
fpp = static_cast<FOOTPRINT_PREVIEW_PANEL*>(
kiface->CreateWindow( aPanel, FRAME_PCB_FOOTPRINT_PREVIEW, &aKiway ) );
} catch( ... )
{
return NULL;
}
auto sizer = new wxBoxSizer( wxVERTICAL );
sizer->Add( fpp, 1, wxALL | wxEXPAND, 0 );
if( aIndicator )
{
auto label = new wxStaticText( aPanel, -1, wxEmptyString );
auto sizer2 = new wxBoxSizer( wxVERTICAL );
sizer2->Add( 0, 0, 1 );
sizer2->Add( label, 0, wxALL | wxALIGN_CENTER, 0 );
sizer2->Add( 0, 0, 1 );
sizer->Add( sizer2, 1, wxALL | wxALIGN_CENTER, 0 );
sizer2->ShowItems( false );
fpp->LinkErrorLabel( label );
fpp->SetHideSizer( sizer2 );
}
aPanel->SetSizer( sizer );
return fpp;
}

View File

@ -0,0 +1,110 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2017 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2017 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 3
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
/**
* @file two_column_tree_list.cpp
*/
#include <wx/dataview.h>
#include <widgets/two_column_tree_list.h>
/**
* Extra margin to compensate for vertical scrollbar
*/
static const int HORIZ_MARGIN = 30;
TWO_COLUMN_TREE_LIST::TWO_COLUMN_TREE_LIST( wxWindow* aParent, wxWindowID aID,
const wxPoint & aPos, const wxSize & aSize, long aStyle, const wxString & aName )
: wxTreeListCtrl( aParent, aID, aPos, aSize, aStyle, aName ),
m_rubber_band_column( 0 ),
m_clamped_min_width( 50 )
{
Bind( wxEVT_SIZE, &TWO_COLUMN_TREE_LIST::OnSize, this );
GetDataView()->SetIndent( 10 );
}
void TWO_COLUMN_TREE_LIST::OnSize( wxSizeEvent& aEvent )
{
wxDataViewCtrl* view = GetDataView();
if( !view )
return;
wxRect rect = GetClientRect();
view->SetSize( rect );
#ifdef wxHAS_GENERIC_DATAVIEWCTRL
{
wxWindow* win_view = GetView();
win_view->Refresh();
win_view->Update();
}
#endif
// Find the maximum width of both columns
int clamped_column = ( m_rubber_band_column == 0 ) ? 1 : 0;
int clamped_column_width = 0;
int rubber_max_width = 0;
for( wxTreeListItem item = GetFirstItem(); item.IsOk(); item = GetNextItem( item ) )
{
const wxString& text = GetItemText( item, clamped_column );
int width = WidthFor( text );
if( clamped_column == 0 )
{
width += 4 * view->GetIndent();
}
if( width > clamped_column_width )
clamped_column_width = width;
width = WidthFor( GetItemText( item, m_rubber_band_column ) );
if( width > rubber_max_width )
rubber_max_width = width;
}
if( clamped_column_width < m_clamped_min_width )
clamped_column_width = m_clamped_min_width;
// Rubber column width is only limited if the rubber column is on the LEFT.
// If on the right, let the horiz scrollbar show.
int rubber_width = 0;
if( m_rubber_band_column == 0 )
rubber_width = rect.width - clamped_column_width - HORIZ_MARGIN;
else
rubber_width = rubber_max_width;
if( rubber_width <= 0 )
rubber_width = 1;
wxASSERT( m_rubber_band_column == 0 || m_rubber_band_column == 1 );
SetColumnWidth( m_rubber_band_column, rubber_width );
SetColumnWidth( clamped_column, clamped_column_width );
}

View File

@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2016 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2016 KiCad Developers, see CHANGELOG.TXT for contributors.
* Copyright (C) 2016-2017 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@ -26,7 +26,6 @@
#include <widgets/widget_hotkey_list.h>
#include <wx/dataview.h>
#include <wx/statline.h>
#include <draw_frame.h>
@ -39,12 +38,6 @@
static const int HOTKEY_MIN_WIDTH = 100;
/**
* Extra margin to compensate for vertical scrollbar
*/
static const int HORIZ_MARGIN = 30;
/**
* Menu IDs for the hotkey context menu
*/
@ -327,7 +320,7 @@ void WIDGET_HOTKEY_LIST::EditItem( wxTreeListItem aItem )
// Trigger a resize in case column widths have changed
wxSizeEvent dummy_evt;
OnSize( dummy_evt );
TWO_COLUMN_TREE_LIST::OnSize( dummy_evt );
}
}
@ -424,50 +417,6 @@ void WIDGET_HOTKEY_LIST::OnMenu( wxCommandEvent& aEvent )
}
void WIDGET_HOTKEY_LIST::OnSize( wxSizeEvent& aEvent )
{
// Handle this manually - wxTreeListCtrl screws up the width of the first column
wxDataViewCtrl* view = GetDataView();
if( !view )
return;
wxRect rect = GetClientRect();
view->SetSize( rect );
#ifdef wxHAS_GENERIC_DATAVIEWCTRL
{
wxWindow* win_view = GetView();
win_view->Refresh();
win_view->Update();
}
#endif
// Find the maximum width of the hotkey column
int hk_column_width = 0;
for( wxTreeListItem item = GetFirstItem(); item.IsOk(); item = GetNextItem( item ) )
{
const wxString& text = GetItemText( item, 1 );
int width = WidthFor( text );
if( width > hk_column_width )
hk_column_width = width;
}
if( hk_column_width < HOTKEY_MIN_WIDTH )
hk_column_width = HOTKEY_MIN_WIDTH;
int name_column_width = rect.width - hk_column_width - HORIZ_MARGIN;
if( name_column_width <= 0 )
name_column_width = 1;
SetColumnWidth( 1, hk_column_width );
SetColumnWidth( 0, name_column_width );
}
bool WIDGET_HOTKEY_LIST::CheckKeyConflicts( long aKey, const wxString& aSectionTag,
EDA_HOTKEY** aConfKey, EDA_HOTKEY_CONFIG** aConfSect )
{
@ -558,16 +507,17 @@ bool WIDGET_HOTKEY_LIST::ResolveKeyConflicts( long aKey, const wxString& aSectio
WIDGET_HOTKEY_LIST::WIDGET_HOTKEY_LIST( wxWindow* aParent, const HOTKEY_SECTIONS& aSections )
: wxTreeListCtrl( aParent, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTL_SINGLE ),
: TWO_COLUMN_TREE_LIST( aParent, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTL_SINGLE ),
m_sections( aSections )
{
AppendColumn( _( "Command" ) );
AppendColumn( _( "Hotkey" ) );
SetRubberBandColumn( 0 );
SetClampedMinWidth( HOTKEY_MIN_WIDTH );
Bind( wxEVT_TREELIST_ITEM_ACTIVATED, &WIDGET_HOTKEY_LIST::OnActivated, this );
Bind( wxEVT_TREELIST_ITEM_CONTEXT_MENU, &WIDGET_HOTKEY_LIST::OnContextMenu, this );
Bind( wxEVT_MENU, &WIDGET_HOTKEY_LIST::OnMenu, this );
Bind( wxEVT_SIZE, &WIDGET_HOTKEY_LIST::OnSize, this );
}

View File

@ -28,11 +28,13 @@
#include <wx/string.h>
#include <wx/tokenzr.h>
#include <wx/treectrl.h>
#include <wx/arrstr.h>
#include <wx/dataview.h>
#include <widgets/two_column_tree_list.h>
#include <class_library.h>
#include <macros.h>
#include <profile.h>
#include <eda_pattern_match.h>
@ -77,7 +79,7 @@ struct COMPONENT_TREE_SEARCH_CONTAINER::TREE_NODE
unsigned MatchScore; ///< Result-Score after UpdateSearchTerm()
unsigned PreviousScore; ///< Optimization: used to see if we need any tree update.
wxTreeItemId TreeId; ///< Tree-ID if stored in the tree (if MatchScore > 0).
wxTreeListItem TreeId; ///< Tree-ID if stored in the tree (if MatchScore > 0).
};
@ -134,9 +136,17 @@ void COMPONENT_TREE_SEARCH_CONTAINER::ShowUnits( bool aShowUnits )
}
void COMPONENT_TREE_SEARCH_CONTAINER::SetTree( wxTreeCtrl* aTree )
void COMPONENT_TREE_SEARCH_CONTAINER::SetTree( TWO_COLUMN_TREE_LIST* aTree )
{
m_tree = aTree;
if( m_tree )
{
m_tree->AppendColumn( _( "Part" ), wxCOL_WIDTH_AUTOSIZE, wxALIGN_LEFT, wxCOL_RESIZABLE );
m_tree->AppendColumn( _( "Description" ), 100, wxALIGN_LEFT, wxCOL_RESIZABLE );
m_tree->SetRubberBandColumn( 1 );
}
UpdateSearchTerm( wxEmptyString );
}
@ -184,21 +194,7 @@ void COMPONENT_TREE_SEARCH_CONTAINER::AddAliasList( const wxString& aNodeName,
if( !a->GetDescription().empty() )
{
// Preformatting. Unfortunately, the tree widget doesn't have columns
// and using tabs does not work very well or does not work at all
// (depending on OS versions). So indent with spaces in fixed-font width.
// The 98%-ile of length of strings found in the standard library is 15
// characters. Use this as a reasonable cut-off point for aligned indentation.
// For the few component names longer than that, the description is indented a
// bit more.
// The max found in the default lib would be 20 characters, but that creates too
// much visible whitespace for the less extreme component names.
const int COLUMN_DESCR_POS = 15;
const int indent_len = COLUMN_DESCR_POS - a->GetName().length();
display_info = wxString::Format( wxT( " %*s [ %s ]" ),
indent_len > 0 ? indent_len : 0, wxT( "" ),
GetChars( a->GetDescription() ) );
display_info = a->GetDescription();
}
TREE_NODE* alias_node = new TREE_NODE( TREE_NODE::TYPE_ALIAS, lib_node,
@ -209,7 +205,7 @@ void COMPONENT_TREE_SEARCH_CONTAINER::AddAliasList( const wxString& aNodeName,
{
for( int u = 1; u <= a->GetPart()->GetUnitCount(); ++u )
{
wxString unitName = _("Unit");
wxString unitName = _( "Unit" );
unitName += wxT( " " ) + LIB_PART::SubReference( u, false );
TREE_NODE* unit_node = new TREE_NODE( TREE_NODE::TYPE_UNIT,
alias_node, a,
@ -230,7 +226,7 @@ LIB_ALIAS* COMPONENT_TREE_SEARCH_CONTAINER::GetSelectedAlias( int* aUnit )
if( m_tree == NULL )
return NULL;
const wxTreeItemId& select_id = m_tree->GetSelection();
const wxTreeListItem& select_id = m_tree->GetSelection();
for( TREE_NODE* node : m_nodes )
{
@ -449,7 +445,7 @@ void COMPONENT_TREE_SEARCH_CONTAINER::UpdateSearchTerm( const wxString& aSearch
// items is pretty complex, so we just re-build the whole tree.
m_tree->Freeze();
m_tree->DeleteAllItems();
const wxTreeItemId root_id = m_tree->AddRoot( wxEmptyString );
const wxTreeListItem root_id = m_tree->GetRootItem();
const TREE_NODE* first_match = NULL;
const TREE_NODE* preselected_node = NULL;
bool override_preselect = false;
@ -467,16 +463,9 @@ void COMPONENT_TREE_SEARCH_CONTAINER::UpdateSearchTerm( const wxString& aSearch
if( highest_score_seen > kLowestDefaultScore && node->MatchScore == kLowestDefaultScore )
continue;
wxString node_text;
#if 0
// Node text with scoring information for debugging
node_text.Printf( wxT("%s (s=%u)%s"), GetChars(node->DisplayName),
node->MatchScore, GetChars( node->DisplayInfo ));
#else
node_text = node->DisplayName + node->DisplayInfo;
#endif
node->TreeId = m_tree->AppendItem( node->Parent ? node->Parent->TreeId : root_id,
node_text );
node->DisplayName );
m_tree->SetItemText( node->TreeId, 1, node->DisplayInfo );
// If there is only a single library in this container, we want to have it
// unfolded (example: power library, libedit)
@ -517,15 +506,17 @@ void COMPONENT_TREE_SEARCH_CONTAINER::UpdateSearchTerm( const wxString& aSearch
if( first_match && ( !preselected_node || override_preselect ) )
{
m_tree->SelectItem( first_match->TreeId );
m_tree->EnsureVisible( first_match->TreeId );
m_tree->Select( first_match->TreeId );
//m_tree->EnsureVisible( first_match->TreeId );
}
else if( preselected_node )
{
m_tree->SelectItem( preselected_node->TreeId );
m_tree->EnsureVisible( preselected_node->TreeId );
m_tree->Select( preselected_node->TreeId );
//m_tree->EnsureVisible( preselected_node->TreeId );
}
wxSizeEvent dummy;
m_tree->OnSize( dummy );
m_tree->Thaw();
#ifdef SHOW_CALC_TIME

View File

@ -30,7 +30,7 @@
class LIB_ALIAS;
class PART_LIB;
class PART_LIBS;
class wxTreeCtrl;
class TWO_COLUMN_TREE_LIST;
class wxArrayString;
// class COMPONENT_TREE_SEARCH_CONTAINER
@ -104,7 +104,7 @@ public:
*
* @param aTree that is to be modified on search updates.
*/
void SetTree( wxTreeCtrl* aTree );
void SetTree( TWO_COLUMN_TREE_LIST* aTree );
/** Function UpdateSearchTerm
* Update the search string provided by the user and narrow down the result list.
@ -137,7 +137,7 @@ private:
static bool scoreComparator( const TREE_NODE* a1, const TREE_NODE* a2 );
std::vector<TREE_NODE*> m_nodes;
wxTreeCtrl* m_tree;
TWO_COLUMN_TREE_LIST* m_tree;
int m_libraries_added;
int m_components_added;

View File

@ -21,19 +21,25 @@
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
#include <dialog_choose_component.h>
#include <set>
#include <wx/tokenzr.h>
#include <wx/utils.h>
#include <class_library.h>
#include <component_tree_search_container.h>
#include <sch_base_frame.h>
#include <kicad_string.h>
#include <widgets/footprint_preview_panel.h>
#include <widgets/two_column_tree_list.h>
#include <template_fieldnames.h> // Field ID definitions
// Tree navigation helpers.
static wxTreeItemId GetPrevItem( const wxTreeCtrl& tree, const wxTreeItemId& item );
static wxTreeItemId GetNextItem( const wxTreeCtrl& tree, const wxTreeItemId& item );
static wxTreeListItem GetPrevItem( const wxTreeListCtrl& tree, const wxTreeListItem& item );
static wxTreeListItem GetNextItem( const wxTreeListCtrl& tree, const wxTreeListItem& item );
static wxTreeListItem GetPrevSibling( const wxTreeListCtrl& tree, const wxTreeListItem& item );
DIALOG_CHOOSE_COMPONENT::DIALOG_CHOOSE_COMPONENT( SCH_BASE_FRAME* aParent, const wxString& aTitle,
COMPONENT_TREE_SEARCH_CONTAINER* const aContainer,
@ -46,21 +52,24 @@ DIALOG_CHOOSE_COMPONENT::DIALOG_CHOOSE_COMPONENT( SCH_BASE_FRAME* aParent, const
m_received_doubleclick_in_tree = false;
m_search_container->SetTree( m_libraryComponentTree );
m_componentView->SetLayoutDirection( wxLayout_LeftToRight );
m_footprintPreviewPanel = NULL;
m_libraryComponentTree->ScrollTo( m_libraryComponentTree->GetFocusedItem() );
// Initialize footprint preview through Kiway
m_footprintPreviewPanel = FOOTPRINT_PREVIEW_PANEL::AddToPanel( Kiway(), m_footprintView, true );
// The tree showing libs and component uses a fixed font,
// because we want controle the position of some info when drawing the
// tree. Using tabs does not work very well (does not work on Windows)
wxFont font = wxSystemSettings::GetFont( wxSYS_DEFAULT_GUI_FONT );
m_libraryComponentTree->SetFont( wxFont( font.GetPointSize(),
wxFONTFAMILY_MODERN, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_NORMAL ) );
if( m_footprintPreviewPanel )
{
// This hides the GAL panel and shows the status label
m_footprintPreviewPanel->SetStatusText( wxEmptyString );
}
// We have to call SetSizeHints to fix the minimal size of the dialog
// and its widgets.
// this line also fixes an issue on Linux Ubuntu using Unity (dialog not shown).
GetSizer()->SetSizeHints( this );
#ifndef KICAD_FOOTPRINT_SELECTOR
// Footprint chooser isn't implemented yet or isn't selected, don't show it.
m_stFootprint->Hide();
m_chooseFootprint->Hide();
#endif
Layout();
Centre();
}
@ -105,10 +114,10 @@ void DIALOG_CHOOSE_COMPONENT::OnSearchBoxEnter( wxCommandEvent& aEvent )
}
void DIALOG_CHOOSE_COMPONENT::selectIfValid( const wxTreeItemId& aTreeId )
void DIALOG_CHOOSE_COMPONENT::selectIfValid( const wxTreeListItem& aTreeId )
{
if( aTreeId.IsOk() && aTreeId != m_libraryComponentTree->GetRootItem() )
m_libraryComponentTree->SelectItem( aTreeId );
m_libraryComponentTree->Select( aTreeId );
}
@ -119,7 +128,7 @@ void DIALOG_CHOOSE_COMPONENT::OnInterceptSearchBoxKey( wxKeyEvent& aKeyStroke )
// the text search box (which has the focus by default). That way, we are mostly keyboard
// operable.
// (If the tree has the focus, it can handle that by itself).
const wxTreeItemId sel = m_libraryComponentTree->GetSelection();
const wxTreeListItem sel = m_libraryComponentTree->GetSelection();
switch( aKeyStroke.GetKeyCode() )
{
@ -154,7 +163,7 @@ void DIALOG_CHOOSE_COMPONENT::OnInterceptSearchBoxKey( wxKeyEvent& aKeyStroke )
}
void DIALOG_CHOOSE_COMPONENT::OnTreeSelect( wxTreeEvent& aEvent )
void DIALOG_CHOOSE_COMPONENT::OnTreeSelect( wxTreeListEvent& aEvent )
{
updateSelection();
}
@ -164,7 +173,7 @@ void DIALOG_CHOOSE_COMPONENT::OnTreeSelect( wxTreeEvent& aEvent )
// - search for an item.
// - use the mouse to double-click on an item in the tree.
// -> The dialog should close, and the component should _not_ be immediately placed
void DIALOG_CHOOSE_COMPONENT::OnDoubleClickTreeActivation( wxTreeEvent& aEvent )
void DIALOG_CHOOSE_COMPONENT::OnDoubleClickTreeActivation( wxTreeListEvent& aEvent )
{
if( !updateSelection() )
return;
@ -224,7 +233,14 @@ bool DIALOG_CHOOSE_COMPONENT::updateSelection()
m_componentDetails->SetPage( wxEmptyString );
if( selection == NULL )
{
if( m_footprintPreviewPanel )
{
m_footprintPreviewPanel->SetStatusText( wxEmptyString );
}
return false;
}
m_componentDetails->Freeze();
@ -293,17 +309,74 @@ bool DIALOG_CHOOSE_COMPONENT::updateSelection()
wxString text = field.GetFullText();
m_componentDetails->AppendToPage( "<tr><td><b>" + EscapedHTML( name ) + "</b></td>" );
m_componentDetails->AppendToPage( "<td>" + EscapedHTML( text ) + "</td></tr>" );
m_componentDetails->AppendToPage( "<td>" );
if( field.GetId() == DATASHEET )
{
m_componentDetails->AppendToPage( "<a href=\"" + EscapedHTML( text ) + "\">" );
}
m_componentDetails->AppendToPage( EscapedHTML( text ) );
if( field.GetId() == DATASHEET )
{
m_componentDetails->AppendToPage( "</a>" );
}
m_componentDetails->AppendToPage( "</td></tr>" );
}
m_componentDetails->AppendToPage( "</table>" );
m_componentDetails->Thaw();
updateFootprint();
return true;
}
void DIALOG_CHOOSE_COMPONENT::updateFootprint()
{
if( !m_footprintPreviewPanel )
return;
int dummy_unit = 0;
LIB_ALIAS* selection = m_search_container->GetSelectedAlias( &dummy_unit );
if( !selection )
return;
LIB_FIELDS fields;
selection->GetPart()->GetFields( fields );
for( auto const & field: fields )
{
if( field.GetId() != FOOTPRINT )
continue;
wxString fpname = field.GetFullText();
if( fpname == wxEmptyString )
{
m_footprintPreviewPanel->SetStatusText( _( "No footprint specified" ) );
}
else
{
m_footprintPreviewPanel->ClearStatus();
m_footprintPreviewPanel->CacheFootprint( LIB_ID( fpname ) );
m_footprintPreviewPanel->DisplayFootprint( LIB_ID( fpname ) );
}
break;
}
}
void DIALOG_CHOOSE_COMPONENT::OnDatasheetClick( wxHtmlLinkEvent& aEvent )
{
const wxHtmlLinkInfo & info = aEvent.GetLinkInfo();
::wxLaunchDefaultBrowser( info.GetHref() );
}
void DIALOG_CHOOSE_COMPONENT::OnHandlePreviewRepaint( wxPaintEvent& aRepaintEvent )
{
int unit = 0;
@ -376,9 +449,9 @@ void DIALOG_CHOOSE_COMPONENT::renderPreview( LIB_PART* aComponent, int aUnit )
}
static wxTreeItemId GetPrevItem( const wxTreeCtrl& tree, const wxTreeItemId& item )
static wxTreeListItem GetPrevItem( const wxTreeListCtrl& tree, const wxTreeListItem& item )
{
wxTreeItemId prevItem = tree.GetPrevSibling( item );
wxTreeListItem prevItem = GetPrevSibling( tree, item );
if( !prevItem.IsOk() )
{
@ -386,31 +459,40 @@ static wxTreeItemId GetPrevItem( const wxTreeCtrl& tree, const wxTreeItemId& ite
}
else if( tree.IsExpanded( prevItem ) )
{
prevItem = tree.GetLastChild( prevItem );
// wxTreeListCtrl has no .GetLastChild. Simulate it
prevItem = tree.GetFirstChild( prevItem );
wxTreeListItem next;
do
{
next = tree.GetNextSibling( prevItem );
if( next.IsOk() )
{
prevItem = next;
}
} while( next.IsOk() );
}
return prevItem;
}
static wxTreeItemId GetNextItem( const wxTreeCtrl& tree, const wxTreeItemId& item )
static wxTreeListItem GetNextItem( const wxTreeListCtrl& tree, const wxTreeListItem& item )
{
wxTreeItemId nextItem;
wxTreeListItem nextItem;
if( !item.IsOk() )
return nextItem; // item is not valid: return a not valid wxTreeItemId
return nextItem; // item is not valid: return a not valid wxTreeListItem
if( tree.IsExpanded( item ) )
{
wxTreeItemIdValue dummy;
nextItem = tree.GetFirstChild( item, dummy );
nextItem = tree.GetFirstChild( item );
}
else
{
wxTreeItemId root_cell= tree.GetRootItem();
wxTreeListItem root_cell= tree.GetRootItem();
// Walk up levels until we find one that has a next sibling.
for ( wxTreeItemId walk = item; walk.IsOk(); walk = tree.GetItemParent( walk ) )
for ( wxTreeListItem walk = item; walk.IsOk(); walk = tree.GetItemParent( walk ) )
{
if( walk == root_cell ) // the root cell (not displayed) is reached
break; // Exit (calling GetNextSibling( root_cell ) crashes.
@ -424,3 +506,31 @@ static wxTreeItemId GetNextItem( const wxTreeCtrl& tree, const wxTreeItemId& ite
return nextItem;
}
static wxTreeListItem GetPrevSibling( const wxTreeListCtrl& tree, const wxTreeListItem& item )
{
// Why wxTreeListCtrl has no GetPrevSibling when it does have GetNextSibling
// is beyond me. wxTreeCtrl has this.
wxTreeListItem last_item;
wxTreeListItem parent = tree.GetItemParent( item );
if( !parent.IsOk() )
return last_item; // invalid signifies not found
last_item = tree.GetFirstChild( parent );
while( last_item.IsOk() )
{
wxTreeListItem next_item = tree.GetNextSibling( last_item );
if( next_item == item )
{
return last_item;
}
else
{
last_item = next_item;
}
}
return last_item;
}

View File

@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2014 Henner Zeller <h.zeller@acm.org>
* Copyright (C) 2014 KiCad Developers, see change_log.txt for contributors.
* Copyright (C) 2014-2017 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@ -26,10 +26,11 @@
#include <dialog_choose_component_base.h>
class FOOTPRINT_PREVIEW_PANEL;
class COMPONENT_TREE_SEARCH_CONTAINER;
class LIB_ALIAS;
class LIB_PART;
class wxTreeItemId;
class wxTreeListItem;
class SCH_BASE_FRAME;
class DIALOG_CHOOSE_COMPONENT : public DIALOG_CHOOSE_COMPONENT_BASE
@ -76,18 +77,23 @@ protected:
virtual void OnSearchBoxEnter( wxCommandEvent& aEvent ) override;
virtual void OnInterceptSearchBoxKey( wxKeyEvent& aEvent ) override;
virtual void OnTreeSelect( wxTreeEvent& aEvent ) override;
virtual void OnDoubleClickTreeActivation( wxTreeEvent& aEvent ) override;
virtual void OnTreeSelect( wxTreeListEvent& aEvent ) override;
virtual void OnDoubleClickTreeActivation( wxTreeListEvent& aEvent ) override;
virtual void OnInterceptTreeEnter( wxKeyEvent& aEvent ) override;
virtual void OnTreeMouseUp( wxMouseEvent& aMouseEvent ) override;
virtual void OnStartComponentBrowser( wxMouseEvent& aEvent ) override;
virtual void OnHandlePreviewRepaint( wxPaintEvent& aRepaintEvent ) override;
virtual void OnDatasheetClick( wxHtmlLinkEvent& aEvent ) override;
private:
bool updateSelection();
void selectIfValid( const wxTreeItemId& aTreeId );
void selectIfValid( const wxTreeListItem& aTreeId );
void renderPreview( LIB_PART* aComponent, int aUnit );
void updateFootprint();
FOOTPRINT_PREVIEW_PANEL* m_footprintPreviewPanel;
};
#endif /* DIALOG_CHOOSE_COMPONENT_H */

View File

@ -1,10 +1,12 @@
///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version Jan 5 2017)
// C++ code generated with wxFormBuilder (version Feb 5 2017)
// http://www.wxformbuilder.org/
//
// PLEASE DO "NOT" EDIT THIS FILE!
///////////////////////////////////////////////////////////////////////////
#include "widgets/two_column_tree_list.h"
#include "dialog_choose_component_base.h"
///////////////////////////////////////////////////////////////////////////
@ -29,24 +31,69 @@ DIALOG_CHOOSE_COMPONENT_BASE::DIALOG_CHOOSE_COMPONENT_BASE( wxWindow* parent, wx
bSizerMain->Add( bSearchSizer, 0, wxEXPAND, 5 );
m_libraryComponentTree = new wxTreeCtrl( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTR_DEFAULT_STYLE|wxTR_HIDE_ROOT );
m_libraryComponentTree->SetMinSize( wxSize( 400,200 ) );
m_splitter1 = new wxSplitterWindow( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxSP_3D|wxSP_LIVE_UPDATE );
m_splitter1->SetSashGravity( 0.9 );
m_splitter1->Connect( wxEVT_IDLE, wxIdleEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::m_splitter1OnIdle ), NULL, this );
m_splitter1->SetMinimumPaneSize( 1 );
bSizerMain->Add( m_libraryComponentTree, 1, wxALL|wxEXPAND, 5 );
m_panel3 = new wxPanel( m_splitter1, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* bSizer10;
bSizer10 = new wxBoxSizer( wxVERTICAL );
wxBoxSizer* bSizerView;
bSizerView = new wxBoxSizer( wxHORIZONTAL );
m_libraryComponentTree = new TWO_COLUMN_TREE_LIST( m_panel3, wxID_ANY, wxDefaultPosition, wxSize( 320,240 ), wxTL_DEFAULT_STYLE );
m_componentView = new wxPanel( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER );
m_componentView->SetMinSize( wxSize( 200,200 ) );
bSizer10->Add( m_libraryComponentTree, 1, wxEXPAND | wxALL, 5 );
bSizerView->Add( m_componentView, 1, wxEXPAND | wxALL, 5 );
m_componentDetails = new wxHtmlWindow( this, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxHW_SCROLLBAR_AUTO );
bSizerView->Add( m_componentDetails, 1, wxALL|wxEXPAND, 5 );
m_componentDetails = new wxHtmlWindow( m_panel3, wxID_ANY, wxDefaultPosition, wxSize( 320,240 ), wxHW_SCROLLBAR_AUTO|wxSUNKEN_BORDER );
bSizer10->Add( m_componentDetails, 1, wxALL|wxEXPAND, 5 );
bSizerMain->Add( bSizerView, 1, wxEXPAND, 5 );
m_panel3->SetSizer( bSizer10 );
m_panel3->Layout();
bSizer10->Fit( m_panel3 );
m_panel4 = new wxPanel( m_splitter1, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxTAB_TRAVERSAL );
wxBoxSizer* bSizer11;
bSizer11 = new wxBoxSizer( wxVERTICAL );
wxBoxSizer* bSizer12;
bSizer12 = new wxBoxSizer( wxVERTICAL );
m_componentView = new wxPanel( m_panel4, wxID_ANY, wxDefaultPosition, wxSize( -1,-1 ), wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER|wxTAB_TRAVERSAL );
bSizer12->Add( m_componentView, 1, wxEXPAND | wxALL, 5 );
wxBoxSizer* bSizer13;
bSizer13 = new wxBoxSizer( wxVERTICAL );
wxBoxSizer* bSizer14;
bSizer14 = new wxBoxSizer( wxHORIZONTAL );
m_stFootprint = new wxStaticText( m_panel4, wxID_ANY, _("Footprint:"), wxDefaultPosition, wxDefaultSize, 0 );
m_stFootprint->Wrap( -1 );
bSizer14->Add( m_stFootprint, 0, wxALIGN_CENTER_VERTICAL|wxALL, 5 );
wxArrayString m_chooseFootprintChoices;
m_chooseFootprint = new wxChoice( m_panel4, wxID_ANY, wxDefaultPosition, wxDefaultSize, m_chooseFootprintChoices, 0 );
m_chooseFootprint->SetSelection( 0 );
bSizer14->Add( m_chooseFootprint, 1, wxALL|wxEXPAND, 5 );
bSizer13->Add( bSizer14, 0, wxEXPAND, 5 );
m_footprintView = new wxPanel( m_panel4, wxID_ANY, wxDefaultPosition, wxSize( -1,-1 ), wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER|wxTAB_TRAVERSAL );
bSizer13->Add( m_footprintView, 1, wxEXPAND | wxALL, 5 );
bSizer12->Add( bSizer13, 1, wxEXPAND, 5 );
bSizer11->Add( bSizer12, 1, wxEXPAND, 5 );
m_panel4->SetSizer( bSizer11 );
m_panel4->Layout();
bSizer11->Fit( m_panel4 );
m_splitter1->SplitVertically( m_panel3, m_panel4, -300 );
bSizerMain->Add( m_splitter1, 1, wxEXPAND, 5 );
m_stdButtons = new wxStdDialogButtonSizer();
m_stdButtonsOK = new wxButton( this, wxID_OK );
@ -70,9 +117,10 @@ DIALOG_CHOOSE_COMPONENT_BASE::DIALOG_CHOOSE_COMPONENT_BASE( wxWindow* parent, wx
m_searchBox->Connect( wxEVT_COMMAND_TEXT_ENTER, wxCommandEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnSearchBoxEnter ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_KEY_UP, wxKeyEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnInterceptTreeEnter ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_LEFT_UP, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeMouseUp ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_COMMAND_TREE_ITEM_ACTIVATED, wxTreeEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDoubleClickTreeActivation ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_COMMAND_TREE_SEL_CHANGED, wxTreeEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeSelect ), NULL, this );
m_componentView->Connect( wxEVT_LEFT_UP, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnStartComponentBrowser ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_TREELIST_ITEM_ACTIVATED, wxTreeListEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDoubleClickTreeActivation ), NULL, this );
m_libraryComponentTree->Connect( wxEVT_TREELIST_SELECTION_CHANGED, wxTreeListEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeSelect ), NULL, this );
m_componentDetails->Connect( wxEVT_COMMAND_HTML_LINK_CLICKED, wxHtmlLinkEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDatasheetClick ), NULL, this );
m_componentView->Connect( wxEVT_LEFT_DCLICK, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnStartComponentBrowser ), NULL, this );
m_componentView->Connect( wxEVT_PAINT, wxPaintEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnHandlePreviewRepaint ), NULL, this );
}
@ -85,9 +133,10 @@ DIALOG_CHOOSE_COMPONENT_BASE::~DIALOG_CHOOSE_COMPONENT_BASE()
m_searchBox->Disconnect( wxEVT_COMMAND_TEXT_ENTER, wxCommandEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnSearchBoxEnter ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_KEY_UP, wxKeyEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnInterceptTreeEnter ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_LEFT_UP, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeMouseUp ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_COMMAND_TREE_ITEM_ACTIVATED, wxTreeEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDoubleClickTreeActivation ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_COMMAND_TREE_SEL_CHANGED, wxTreeEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeSelect ), NULL, this );
m_componentView->Disconnect( wxEVT_LEFT_UP, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnStartComponentBrowser ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_TREELIST_ITEM_ACTIVATED, wxTreeListEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDoubleClickTreeActivation ), NULL, this );
m_libraryComponentTree->Disconnect( wxEVT_TREELIST_SELECTION_CHANGED, wxTreeListEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnTreeSelect ), NULL, this );
m_componentDetails->Disconnect( wxEVT_COMMAND_HTML_LINK_CLICKED, wxHtmlLinkEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnDatasheetClick ), NULL, this );
m_componentView->Disconnect( wxEVT_LEFT_DCLICK, wxMouseEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnStartComponentBrowser ), NULL, this );
m_componentView->Disconnect( wxEVT_PAINT, wxPaintEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::OnHandlePreviewRepaint ), NULL, this );
}

View File

@ -44,7 +44,7 @@
<property name="minimum_size">-1,-1</property>
<property name="name">DIALOG_CHOOSE_COMPONENT_BASE</property>
<property name="pos"></property>
<property name="size">503,500</property>
<property name="size">800,650</property>
<property name="style">wxDEFAULT_DIALOG_STYLE|wxRESIZE_BORDER</property>
<property name="subclass">DIALOG_SHIM; dialog_shim.h</property>
<property name="title"></property>
@ -278,11 +278,11 @@
</object>
</object>
</object>
<object class="sizeritem" expanded="0">
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxALL|wxEXPAND</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxTreeCtrl" expanded="0">
<object class="wxSplitterWindow" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
@ -313,11 +313,12 @@
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_pane_size">1</property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size">400,200</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_libraryComponentTree</property>
<property name="name">m_splitter1</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
@ -325,9 +326,13 @@
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="sashgravity">0.9</property>
<property name="sashpos">-300</property>
<property name="sashsize">-1</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style">wxTR_DEFAULT_STYLE|wxTR_HIDE_ROOT</property>
<property name="splitmode">wxSPLIT_VERTICAL</property>
<property name="style">wxSP_3D|wxSP_LIVE_UPDATE</property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
@ -338,12 +343,12 @@
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp">OnInterceptTreeEnter</event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp">OnTreeMouseUp</event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
@ -356,124 +361,13 @@
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnTreeBeginDrag"></event>
<event name="OnTreeBeginLabelEdit"></event>
<event name="OnTreeBeginRDrag"></event>
<event name="OnTreeDeleteItem"></event>
<event name="OnTreeEndDrag"></event>
<event name="OnTreeEndLabelEdit"></event>
<event name="OnTreeGetInfo"></event>
<event name="OnTreeItemActivated">OnDoubleClickTreeActivation</event>
<event name="OnTreeItemCollapsed"></event>
<event name="OnTreeItemCollapsing"></event>
<event name="OnTreeItemExpanded"></event>
<event name="OnTreeItemExpanding"></event>
<event name="OnTreeItemGetTooltip"></event>
<event name="OnTreeItemMenu"></event>
<event name="OnTreeItemMiddleClick"></event>
<event name="OnTreeItemRightClick"></event>
<event name="OnTreeKeyDown"></event>
<event name="OnTreeSelChanged">OnTreeSelect</event>
<event name="OnTreeSelChanging"></event>
<event name="OnTreeSetInfo"></event>
<event name="OnTreeStateImageClick"></event>
<event name="OnSplitterDClick"></event>
<event name="OnSplitterSashPosChanged"></event>
<event name="OnSplitterSashPosChanging"></event>
<event name="OnSplitterUnsplit"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizerView</property>
<property name="orient">wxHORIZONTAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND | wxALL</property>
<property name="proportion">1</property>
<object class="splitteritem" expanded="1">
<object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size">200,200</property>
<property name="moveable">1</property>
<property name="name">m_componentView</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp">OnStartComponentBrowser</event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint">OnHandlePreviewRepaint</event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxALL|wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxHtmlWindow" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
@ -508,7 +402,7 @@
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_componentDetails</property>
<property name="name">m_panel3</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
@ -518,19 +412,15 @@
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style">wxHW_SCROLLBAR_AUTO</property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<property name="window_style">wxTAB_TRAVERSAL</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnHtmlCellClicked"></event>
<event name="OnHtmlCellHover"></event>
<event name="OnHtmlLinkClicked"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
@ -551,6 +441,631 @@
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizer10</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND | wxALL</property>
<property name="proportion">1</property>
<object class="wxTreeListCtrl" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size">-1,-1</property>
<property name="moveable">1</property>
<property name="name">m_libraryComponentTree</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size">320,240</property>
<property name="style">wxTL_DEFAULT_STYLE</property>
<property name="subclass">TWO_COLUMN_TREE_LIST; widgets/two_column_tree_list.h</property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp">OnInterceptTreeEnter</event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp">OnTreeMouseUp</event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnTreelistColumnSorted"></event>
<event name="OnTreelistItemActivated">OnDoubleClickTreeActivation</event>
<event name="OnTreelistItemChecked"></event>
<event name="OnTreelistItemContextMenu"></event>
<event name="OnTreelistItemExpanded"></event>
<event name="OnTreelistItemExpanding"></event>
<event name="OnTreelistSelectionChanged">OnTreeSelect</event>
<event name="OnUpdateUI"></event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxALL|wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxHtmlWindow" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_componentDetails</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size">320,240</property>
<property name="style">wxHW_SCROLLBAR_AUTO</property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxSUNKEN_BORDER</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnHtmlCellClicked"></event>
<event name="OnHtmlCellHover"></event>
<event name="OnHtmlLinkClicked">OnDatasheetClick</event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
</object>
</object>
</object>
<object class="splitteritem" expanded="1">
<object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_panel4</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxTAB_TRAVERSAL</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizer11</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizer12</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND | wxALL</property>
<property name="proportion">1</property>
<object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_componentView</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size">-1,-1</property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER|wxTAB_TRAVERSAL</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick">OnStartComponentBrowser</event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint">OnHandlePreviewRepaint</event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizer13</property>
<property name="orient">wxVERTICAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND</property>
<property name="proportion">0</property>
<object class="wxBoxSizer" expanded="1">
<property name="minimum_size"></property>
<property name="name">bSizer14</property>
<property name="orient">wxHORIZONTAL</property>
<property name="permission">none</property>
<object class="sizeritem" expanded="0">
<property name="border">5</property>
<property name="flag">wxALIGN_CENTER_VERTICAL|wxALL</property>
<property name="proportion">0</property>
<object class="wxStaticText" expanded="0">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="label">Footprint:</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_stFootprint</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<property name="wrap">-1</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
<object class="sizeritem" expanded="0">
<property name="border">5</property>
<property name="flag">wxALL|wxEXPAND</property>
<property name="proportion">1</property>
<object class="wxChoice" expanded="0">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="choices"></property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_chooseFootprint</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="selection">0</property>
<property name="show">1</property>
<property name="size"></property>
<property name="style"></property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="validator_data_type"></property>
<property name="validator_style">wxFILTER_NONE</property>
<property name="validator_type">wxDefaultValidator</property>
<property name="validator_variable"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style"></property>
<event name="OnChar"></event>
<event name="OnChoice"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
</object>
</object>
<object class="sizeritem" expanded="1">
<property name="border">5</property>
<property name="flag">wxEXPAND | wxALL</property>
<property name="proportion">1</property>
<object class="wxPanel" expanded="1">
<property name="BottomDockable">1</property>
<property name="LeftDockable">1</property>
<property name="RightDockable">1</property>
<property name="TopDockable">1</property>
<property name="aui_layer"></property>
<property name="aui_name"></property>
<property name="aui_position"></property>
<property name="aui_row"></property>
<property name="best_size"></property>
<property name="bg"></property>
<property name="caption"></property>
<property name="caption_visible">1</property>
<property name="center_pane">0</property>
<property name="close_button">1</property>
<property name="context_help"></property>
<property name="context_menu">1</property>
<property name="default_pane">0</property>
<property name="dock">Dock</property>
<property name="dock_fixed">0</property>
<property name="docking">Left</property>
<property name="enabled">1</property>
<property name="fg"></property>
<property name="floatable">1</property>
<property name="font"></property>
<property name="gripper">0</property>
<property name="hidden">0</property>
<property name="id">wxID_ANY</property>
<property name="max_size"></property>
<property name="maximize_button">0</property>
<property name="maximum_size"></property>
<property name="min_size"></property>
<property name="minimize_button">0</property>
<property name="minimum_size"></property>
<property name="moveable">1</property>
<property name="name">m_footprintView</property>
<property name="pane_border">1</property>
<property name="pane_position"></property>
<property name="pane_size"></property>
<property name="permission">protected</property>
<property name="pin_button">1</property>
<property name="pos"></property>
<property name="resize">Resizable</property>
<property name="show">1</property>
<property name="size">-1,-1</property>
<property name="subclass"></property>
<property name="toolbar_pane">0</property>
<property name="tooltip"></property>
<property name="window_extra_style"></property>
<property name="window_name"></property>
<property name="window_style">wxFULL_REPAINT_ON_RESIZE|wxSUNKEN_BORDER|wxTAB_TRAVERSAL</property>
<event name="OnChar"></event>
<event name="OnEnterWindow"></event>
<event name="OnEraseBackground"></event>
<event name="OnKeyDown"></event>
<event name="OnKeyUp"></event>
<event name="OnKillFocus"></event>
<event name="OnLeaveWindow"></event>
<event name="OnLeftDClick"></event>
<event name="OnLeftDown"></event>
<event name="OnLeftUp"></event>
<event name="OnMiddleDClick"></event>
<event name="OnMiddleDown"></event>
<event name="OnMiddleUp"></event>
<event name="OnMotion"></event>
<event name="OnMouseEvents"></event>
<event name="OnMouseWheel"></event>
<event name="OnPaint"></event>
<event name="OnRightDClick"></event>
<event name="OnRightDown"></event>
<event name="OnRightUp"></event>
<event name="OnSetFocus"></event>
<event name="OnSize"></event>
<event name="OnUpdateUI"></event>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>
</object>

View File

@ -1,5 +1,5 @@
///////////////////////////////////////////////////////////////////////////
// C++ code generated with wxFormBuilder (version Jan 5 2017)
// C++ code generated with wxFormBuilder (version Feb 5 2017)
// http://www.wxformbuilder.org/
//
// PLEASE DO "NOT" EDIT THIS FILE!
@ -12,6 +12,7 @@
#include <wx/xrc/xmlres.h>
#include <wx/intl.h>
class DIALOG_SHIM;
class TWO_COLUMN_TREE_LIST;
#include "dialog_shim.h"
#include <wx/string.h>
@ -22,9 +23,11 @@ class DIALOG_SHIM;
#include <wx/settings.h>
#include <wx/textctrl.h>
#include <wx/sizer.h>
#include <wx/treectrl.h>
#include <wx/panel.h>
#include <wx/treelist.h>
#include <wx/html/htmlwin.h>
#include <wx/panel.h>
#include <wx/choice.h>
#include <wx/splitter.h>
#include <wx/button.h>
#include <wx/dialog.h>
@ -41,9 +44,15 @@ class DIALOG_CHOOSE_COMPONENT_BASE : public DIALOG_SHIM
protected:
wxStaticText* m_searchLabel;
wxTextCtrl* m_searchBox;
wxTreeCtrl* m_libraryComponentTree;
wxPanel* m_componentView;
wxSplitterWindow* m_splitter1;
wxPanel* m_panel3;
TWO_COLUMN_TREE_LIST* m_libraryComponentTree;
wxHtmlWindow* m_componentDetails;
wxPanel* m_panel4;
wxPanel* m_componentView;
wxStaticText* m_stFootprint;
wxChoice* m_chooseFootprint;
wxPanel* m_footprintView;
wxStdDialogButtonSizer* m_stdButtons;
wxButton* m_stdButtonsOK;
wxButton* m_stdButtonsCancel;
@ -55,16 +64,23 @@ class DIALOG_CHOOSE_COMPONENT_BASE : public DIALOG_SHIM
virtual void OnSearchBoxEnter( wxCommandEvent& event ) { event.Skip(); }
virtual void OnInterceptTreeEnter( wxKeyEvent& event ) { event.Skip(); }
virtual void OnTreeMouseUp( wxMouseEvent& event ) { event.Skip(); }
virtual void OnDoubleClickTreeActivation( wxTreeEvent& event ) { event.Skip(); }
virtual void OnTreeSelect( wxTreeEvent& event ) { event.Skip(); }
virtual void OnDoubleClickTreeActivation( wxTreeListEvent& event ) { event.Skip(); }
virtual void OnTreeSelect( wxTreeListEvent& event ) { event.Skip(); }
virtual void OnDatasheetClick( wxHtmlLinkEvent& event ) { event.Skip(); }
virtual void OnStartComponentBrowser( wxMouseEvent& event ) { event.Skip(); }
virtual void OnHandlePreviewRepaint( wxPaintEvent& event ) { event.Skip(); }
public:
DIALOG_CHOOSE_COMPONENT_BASE( wxWindow* parent, wxWindowID id = wxID_ANY, const wxString& title = wxEmptyString, const wxPoint& pos = wxDefaultPosition, const wxSize& size = wxSize( 503,500 ), long style = wxDEFAULT_DIALOG_STYLE|wxRESIZE_BORDER );
DIALOG_CHOOSE_COMPONENT_BASE( wxWindow* parent, wxWindowID id = wxID_ANY, const wxString& title = wxEmptyString, const wxPoint& pos = wxDefaultPosition, const wxSize& size = wxSize( 800,650 ), long style = wxDEFAULT_DIALOG_STYLE|wxRESIZE_BORDER );
~DIALOG_CHOOSE_COMPONENT_BASE();
void m_splitter1OnIdle( wxIdleEvent& )
{
m_splitter1->SetSashPosition( -300 );
m_splitter1->Disconnect( wxEVT_IDLE, wxIdleEventHandler( DIALOG_CHOOSE_COMPONENT_BASE::m_splitter1OnIdle ), NULL, this );
}
};

View File

@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2014 CERN
* Copyright (C) 1992-2014 KiCad Developers, see CHANGELOG.TXT for contributors.
* Copyright (C) 1992-2017 KiCad Developers, see AUTHORS.txt for contributors.
* @author Maciej Suminski <maciej.suminski@cern.ch>
*
* This program is free software; you can redistribute it and/or
@ -45,6 +45,7 @@ enum FRAME_T
FRAME_PCB_MODULE_VIEWER_MODAL,
FRAME_PCB_FOOTPRINT_WIZARD_MODAL,
FRAME_PCB_DISPLAY3D,
FRAME_PCB_FOOTPRINT_PREVIEW,
FRAME_CVPCB,
FRAME_CVPCB_DISPLAY,

View File

@ -0,0 +1,171 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2016-2017 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2017 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2016 Tomasz Wlostowski <tomasz.wlostowski@cern.ch>
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __FOOTPRINT_PREVIEW_PANEL_H
#define __FOOTPRINT_PREVIEW_PANEL_H
#include <wx/wx.h>
#include <map>
#include <deque>
#include <pcb_draw_panel_gal.h>
#include <gal/gal_display_options.h>
#include <lib_id.h>
#include <kiway_player.h>
#include <boost/optional.hpp>
class MODULE;
class KIWAY;
class IO_MGR;
class BOARD;
class wxStaticText;
enum FOOTPRINT_STATUS {
FPS_NOT_FOUND = 0,
FPS_READY = 1,
FPS_LOADING = 2
};
class FOOTPRINT_PREVIEW_PANEL : public PCB_DRAW_PANEL_GAL, public KIWAY_HOLDER
{
public:
struct CACHE_ENTRY {
LIB_ID fpid;
MODULE *module;
FOOTPRINT_STATUS status;
};
virtual ~FOOTPRINT_PREVIEW_PANEL( );
virtual CACHE_ENTRY CacheFootprint ( const LIB_ID& aFPID );
virtual void DisplayFootprint ( const LIB_ID& aFPID );
/**
* Link to a label for displaying error and status messages. Can be NULL to
* unlink. This does not take ownership of the wx object.
*
* TODO if we ever require wx >= 3.1: use wxActivityIndicator for "Loading"
* status
*/
virtual void LinkErrorLabel( wxStaticText* aLabel );
/**
* Set a sizer to be automatically hidden when the status text is cleared.
* This is useful to have a status message take the place of the footprint display
* instead of displaying next to it.
*/
virtual void SetHideSizer( wxSizer* aSizer );
/**
* Set the contents of the status label, and display it if autohide is enabled.
*/
virtual void SetStatusText( wxString const & aText );
/**
* Clear the contents of the status label, and hide it if autohide is enabled.
*/
virtual void ClearStatus();
#ifdef PCBNEW
static FOOTPRINT_PREVIEW_PANEL* New( KIWAY* aKiway, wxWindow* aParent );
#endif
/**
* Get a preview panel via Kiway and add it to a blank wxPanel. May return
* NULL in the event of a kiway error.
*
* @param aKiway - an active Kiway instance
* @param aPanel - a blank panel to receive the previewer
* @param aIndicator - if true, also add indicator elements to display status and errors.
*/
static FOOTPRINT_PREVIEW_PANEL* AddToPanel( KIWAY& aKiway, wxPanel* aPanel, bool aIndicator );
protected:
class LOADER_THREAD : public wxThread
{
public:
LOADER_THREAD ( FOOTPRINT_PREVIEW_PANEL *aParent );
~LOADER_THREAD ();
/**
* Threadsafe accessor to retrieve an entry from the cache.
*/
boost::optional<CACHE_ENTRY> GetFromCache( LIB_ID const & aFPID );
/**
* Threadsafe accessor to push an entry to the queue to be loaded.
* Also adds a placeholder to the cache and returns it.
*/
CACHE_ENTRY AddToQueue( LIB_ID const & aEntry );
protected:
void* Entry() override;
FOOTPRINT_PREVIEW_PANEL *m_parent;
/**
* Threadsafe accessor to pop from the loader queue. Returns a
* cache entry or an empty option if there is none.
*/
boost::optional<CACHE_ENTRY> PopFromQueue();
/**
* Threadsafe accessor to add an entry to the cache. Puts it into
* both the footprint cache and the loader queue.
*/
void AddToCache( CACHE_ENTRY const & aEntry );
private:
/* DO NOT access directly unless you are an accessor function.
* USE THE ACCESSOR FUNCTIONS.
*/
std::deque<CACHE_ENTRY> m_loaderQueue;
std::map<LIB_ID, CACHE_ENTRY> m_cachedFootprints;
wxMutex m_loaderLock;
};
FOOTPRINT_PREVIEW_PANEL(
KIWAY* aKiway, wxWindow* aParent,
KIGFX::GAL_DISPLAY_OPTIONS& aOpts, GAL_TYPE aGalType );
private:
void OnPaint( wxPaintEvent& event );
void OnLoaderThreadUpdate( wxCommandEvent& aEvent );
void renderFootprint( MODULE *module );
std::unique_ptr<LOADER_THREAD> m_loader;
std::unique_ptr<BOARD> m_dummyBoard;
LIB_ID m_currentFPID;
bool m_footprintDisplayed;
wxStaticText* m_label;
wxSizer* m_hidesizer;
};
#endif

View File

@ -0,0 +1,79 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2017 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2017 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 3
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/
/**
* @file two_column_tree_list.h
*/
#include <wx/treelist.h>
#ifndef __two_column_tree_list__
#define __two_column_tree_list__
/**
* Modified wxTreeListCtrl designed for use with two columns, with better
* column resizing. wxTreeListCtrl accumulates error as columns resize,
* leading to columns with a totally wrong size.
*/
class TWO_COLUMN_TREE_LIST : public wxTreeListCtrl
{
public:
/**
* Create a TWO_COLUMN_TREE_LIST.
*/
TWO_COLUMN_TREE_LIST( wxWindow* aParent, wxWindowID aID,
const wxPoint & aPos = wxDefaultPosition,
const wxSize & aSize = wxDefaultSize,
long aStyle = wxTL_DEFAULT_STYLE,
const wxString & aName = wxTreeListCtrlNameStr );
/**
* Set the column number that will "rubber-band" (expand with available space).
* As this is a TWO column tree list, this must be zero or one.
*/
void SetRubberBandColumn( int aRubberBandColumn )
{
m_rubber_band_column = aRubberBandColumn;
}
/**
* Set the minimum width of the non-rubber-band column.
*/
void SetClampedMinWidth( int aClampedMinWidth )
{
m_clamped_min_width = aClampedMinWidth;
}
/**
* Override buggy wxTreeListCtrl size handler.
*/
void OnSize( wxSizeEvent& aEvent );
protected:
int m_rubber_band_column;
int m_clamped_min_width;
};
#endif // __two_column_tree_list__

View File

@ -2,7 +2,7 @@
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2016 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2016 KiCad Developers, see CHANGELOG.TXT for contributors.
* Copyright (C) 2016-2017 KiCad Developers, see AUTHORS.txt for contributors.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@ -33,6 +33,7 @@
#include <vector>
#include <wx/treelist.h>
#include <widgets/two_column_tree_list.h>
#include <hotkeys_basic.h>
@ -51,7 +52,7 @@ typedef std::vector<EDA_HOTKEY> HOTKEY_LIST;
class WIDGET_HOTKEY_CLIENT_DATA;
class WIDGET_HOTKEY_LIST : public wxTreeListCtrl
class WIDGET_HOTKEY_LIST : public TWO_COLUMN_TREE_LIST
{
HOTKEY_SECTIONS m_sections;
std::vector<HOTKEY_LIST> m_hotkeys;

View File

@ -303,6 +303,8 @@ set( PCBNEW_CLASS_SRCS
tools/grid_menu.cpp
tools/zoom_menu.cpp
tools/size_menu.cpp
footprint_preview_panel.cpp
)
set( PCBNEW_SRCS ${PCBNEW_AUTOROUTER_SRCS} ${PCBNEW_CLASS_SRCS} ${PCBNEW_DIALOGS} )

View File

@ -0,0 +1,316 @@
/*
* This program source code file is part of KiCad, a free EDA CAD application.
*
* Copyright (C) 2016-2017 KiCad Developers, see AUTHORS.txt for contributors.
* Copyright (C) 2017 Chris Pavlina <pavlina.chris@gmail.com>
* Copyright (C) 2016 Tomasz Wlostowski <tomasz.wlostowski@cern.ch>
*
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include <widgets/footprint_preview_panel.h>
#include <pcb_draw_panel_gal.h>
#include <kiway.h>
#include <io_mgr.h>
#include <fp_lib_table.h>
#include <view/view.h>
#include <math/box2.h>
#include <class_module.h>
#include <class_board.h>
#include <boost/bind.hpp>
#include <make_unique.h>
#include <wx/stattext.h>
FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::LOADER_THREAD ( FOOTPRINT_PREVIEW_PANEL* aParent ) :
wxThread ( wxTHREAD_JOINABLE ),
m_parent( aParent )
{
}
FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::~LOADER_THREAD ()
{
}
boost::optional<FOOTPRINT_PREVIEW_PANEL::CACHE_ENTRY>
FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::PopFromQueue()
{
wxMutexLocker lock( m_loaderLock );
if( m_loaderQueue.empty() )
{
return boost::none;
}
else
{
auto ent = m_loaderQueue.front();
m_loaderQueue.pop_front();
return ent;
}
}
FOOTPRINT_PREVIEW_PANEL::CACHE_ENTRY
FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::AddToQueue( LIB_ID const & aEntry )
{
wxMutexLocker lock( m_loaderLock );
CACHE_ENTRY ent = { aEntry, NULL, FPS_LOADING };
m_cachedFootprints[aEntry] = ent;
m_loaderQueue.push_back( ent );
return ent;
}
void FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::AddToCache(
FOOTPRINT_PREVIEW_PANEL::CACHE_ENTRY const & aEntry )
{
wxMutexLocker lock( m_loaderLock );
m_cachedFootprints[aEntry.fpid] = aEntry;
}
boost::optional<FOOTPRINT_PREVIEW_PANEL::CACHE_ENTRY>
FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::GetFromCache( LIB_ID const & aFPID )
{
wxMutexLocker lock( m_loaderLock );
auto it = m_cachedFootprints.find( aFPID );
if( it != m_cachedFootprints.end() )
return it->second;
else
return boost::none;
}
void* FOOTPRINT_PREVIEW_PANEL::LOADER_THREAD::Entry()
{
while(!TestDestroy())
{
auto ent = PopFromQueue();
if( ent )
{
FP_LIB_TABLE* fptbl = m_parent->Prj().PcbFootprintLibs();
if(!fptbl)
continue;
ent->module = NULL;
try {
ent->module = fptbl->FootprintLoadWithOptionalNickname( ent->fpid );
if(ent->module == NULL)
ent->status = FPS_NOT_FOUND;
} catch( const IO_ERROR& ioe )
{
ent->status = FPS_NOT_FOUND;
}
if(ent->status != FPS_NOT_FOUND )
ent->status = FPS_READY;
AddToCache( *ent );
if( ent->fpid == m_parent->m_currentFPID )
{
wxCommandEvent event( wxEVT_COMMAND_TEXT_UPDATED, 1 );
m_parent->GetEventHandler()->AddPendingEvent ( event );
}
} else {
wxMilliSleep(100);
}
}
return NULL;
}
FOOTPRINT_PREVIEW_PANEL::FOOTPRINT_PREVIEW_PANEL(
KIWAY* aKiway, wxWindow* aParent, KIGFX::GAL_DISPLAY_OPTIONS& aOpts, GAL_TYPE aGalType )
: PCB_DRAW_PANEL_GAL ( aParent, -1, wxPoint( 0, 0 ), wxSize(200, 200), aOpts, aGalType ),
KIWAY_HOLDER( aKiway ),
m_footprintDisplayed( true ),
m_label( NULL ),
m_hidesizer( NULL )
{
m_loader = std::make_unique<LOADER_THREAD>( this );
m_loader->Run();
ShowScrollbars( wxSHOW_SB_NEVER, wxSHOW_SB_NEVER );
EnableScrolling( false, false ); // otherwise Zoom Auto disables GAL canvas
m_dummyBoard = std::make_unique<BOARD>();
UseColorScheme( m_dummyBoard->GetColorsSettings() );
SyncLayersVisibility( &*m_dummyBoard );
Raise();
Show(true);
StartDrawing();
Connect( wxEVT_COMMAND_TEXT_UPDATED, wxCommandEventHandler( FOOTPRINT_PREVIEW_PANEL::OnLoaderThreadUpdate ), NULL, this );
}
FOOTPRINT_PREVIEW_PANEL::~FOOTPRINT_PREVIEW_PANEL( )
{
m_loader->Delete();
}
FOOTPRINT_PREVIEW_PANEL::CACHE_ENTRY
FOOTPRINT_PREVIEW_PANEL::CacheFootprint ( const LIB_ID& aFPID )
{
auto opt_ent = m_loader->GetFromCache( aFPID );
if( opt_ent )
return *opt_ent;
else
return m_loader->AddToQueue( aFPID );
}
void FOOTPRINT_PREVIEW_PANEL::renderFootprint( MODULE *module )
{
GetView()->Clear();
module->SetParent ( &*m_dummyBoard );
module->RunOnChildren( boost::bind( &KIGFX::VIEW::Add, GetView(), _1 ) );
GetView()->Add ( module );
GetView()->SetVisible( module, true );
GetView()->Update( module, KIGFX::ALL );
BOX2I bbox = module->ViewBBox();
bbox.Merge ( module->Value().ViewBBox() );
bbox.Merge ( module->Reference().ViewBBox() );
if( bbox.GetSize().x > 0 && bbox.GetSize().y > 0 )
{
// Autozoom
GetView()->SetViewport( BOX2D( bbox.GetOrigin(), bbox.GetSize() ) );
// Add a margin
GetView()->SetScale( GetView()->GetScale() * 0.7 );
Refresh();
}
}
void FOOTPRINT_PREVIEW_PANEL::DisplayFootprint ( const LIB_ID& aFPID )
{
m_currentFPID = aFPID;
m_footprintDisplayed = false;
CACHE_ENTRY fpe = CacheFootprint ( m_currentFPID );
switch( fpe.status )
{
case FPS_NOT_FOUND:
SetStatusText( _( "Footprint not found" ) );
break;
case FPS_LOADING:
SetStatusText( _( "Loading..." ) );
break;
case FPS_READY:
if ( !m_footprintDisplayed )
{
ClearStatus();
renderFootprint( fpe.module );
m_footprintDisplayed = true;
Refresh();
}
}
}
void FOOTPRINT_PREVIEW_PANEL::LinkErrorLabel( wxStaticText* aLabel )
{
m_label = aLabel;
}
void FOOTPRINT_PREVIEW_PANEL::SetHideSizer( wxSizer* aSizer )
{
m_hidesizer = aSizer;
}
void FOOTPRINT_PREVIEW_PANEL::OnLoaderThreadUpdate( wxCommandEvent& event )
{
DisplayFootprint( m_currentFPID );
}
void FOOTPRINT_PREVIEW_PANEL::SetStatusText( wxString const & aText )
{
if( m_label )
{
m_label->SetLabel( aText );
}
if( m_hidesizer )
{
m_hidesizer->ShowItems( true );
Hide();
}
GetParent()->Layout();
}
void FOOTPRINT_PREVIEW_PANEL::ClearStatus()
{
if( m_label )
{
m_label->SetLabel( wxEmptyString );
}
if( m_hidesizer )
{
Show();
m_hidesizer->ShowItems( false );
}
GetParent()->Layout();
}
FOOTPRINT_PREVIEW_PANEL* FOOTPRINT_PREVIEW_PANEL::New( KIWAY* aKiway, wxWindow* aParent )
{
KIGFX::GAL_DISPLAY_OPTIONS gal_opts;
return new FOOTPRINT_PREVIEW_PANEL(
aKiway, aParent, gal_opts, EDA_DRAW_PANEL_GAL::GAL_TYPE_CAIRO );
}

View File

@ -52,10 +52,12 @@
#include <hotkeys.h>
#include <wildcards_and_files_ext.h>
#include <class_board.h>
#include <class_draw_panel_gal.h>
#include <fp_lib_table.h>
#include <module_editor_frame.h>
#include <modview_frame.h>
#include <footprint_wizard_frame.h>
#include <widgets/footprint_preview_panel.h>
#include <gl_context_mgr.h>
extern bool IsWxPythonLoaded();
@ -144,6 +146,9 @@ static struct IFACE : public KIFACE_I
FRAME_T( aClassId ) ) );
break;
case FRAME_PCB_FOOTPRINT_PREVIEW:
frame = dynamic_cast< wxWindow* >( FOOTPRINT_PREVIEW_PANEL::New( aKiway, aParent ) );
default:
break;
}