KiCad PCB EDA Suite
Loading...
Searching...
No Matches
board_stackup_table.cpp
Go to the documentation of this file.
1/*
2 * This program source code file is part of KiCad, a free EDA CAD application.
3 *
4 * Copyright The KiCad Developers, see AUTHORS.txt for contributors.
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU General Public License
8 * as published by the Free Software Foundation; either version 2
9 * of the License, or (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program. If not, see <https://www.gnu.org/licenses/>.
18 */
19
20
21#include <board.h>
24#include <board_item.h>
25#include <pcb_table.h>
26#include <pcb_tablecell.h>
27#include <pcb_edit_frame.h>
28#include <units_provider.h>
30#include <string_utils.h>
31
33{
34 BOARD_DESIGN_SETTINGS& settings = aBoard->GetDesignSettings();
35 BOARD_STACKUP& stackup = settings.GetStackupDescriptor();
36 UNITS_PROVIDER units_provider( pcbIUScale, aDisplayUnits );
37
38 stackup.SynchronizeWithBoard( &settings );
39
40 std::vector<BOARD_STACKUP_ITEM*> layers = stackup.GetList();
41
42 PCB_TABLE* table = new PCB_TABLE( aBoard, pcbIUScale.mmToIU( DEFAULT_LINE_WIDTH ) );
43 table->SetColCount( 7 );
44
45 const auto addHeaderCell =
46 [&]( const wxString& text )
47 {
49 c->SetTextSize( VECTOR2I( pcbIUScale.mmToIU( 1.5 ), pcbIUScale.mmToIU( 1.5 ) ) );
50 c->SetTextThickness( pcbIUScale.mmToIU( 0.3 ) );
51 c->SetText( text );
52 table->AddCell( c );
53 };
54
55 const auto addDataCell =
56 [&]( const wxString& text, const char align = 'L' )
57 {
59 c->SetTextSize( VECTOR2I( pcbIUScale.mmToIU( 1.5 ), pcbIUScale.mmToIU( 1.5 ) ) );
60 c->SetTextThickness( pcbIUScale.mmToIU( 0.2 ) );
61
62 if( align == 'R' )
64
65 c->SetText( text );
66 table->AddCell( c );
67 };
68
69 const auto layerThicknessString =
70 [&]( const BOARD_STACKUP_ITEM& aStackupItem, int aSublayerId )
71 {
72 const int layerThickness = aStackupItem.GetThickness( aSublayerId );
73
74 // Layers like silkscreen, paste, etc. have no defined thickness, but that
75 // does not mean that they are specified as exactly 0mm
76 if( !aStackupItem.IsThicknessEditable() )
77 return NotSpecifiedPrm();
78
79 return units_provider.StringFromValue( layerThickness, true );
80 };
81
82 addHeaderCell( _( "Layer Name" ) );
83 addHeaderCell( _( "Type" ) );
84 addHeaderCell( _( "Material" ) );
85 addHeaderCell( _( "Thickness" ) );
86 addHeaderCell( _( "Color" ) );
87 addHeaderCell( _( "Epsilon R" ) );
88 addHeaderCell( _( "Loss Tangent" ) );
89
90 for( int i = 0; i < stackup.GetCount(); i++ )
91 {
92 BOARD_STACKUP_ITEM* stackup_item = layers.at( i );
93
94 for( int sublayer_id = 0; sublayer_id < stackup_item->GetSublayersCount(); sublayer_id++ )
95 {
96 // Layer names are empty until we close at least once the board setup dialog.
97 // If the user did not open the dialog, then get the names from the board.
98 // But dielectric layer names will be missing. And in stackup, the name is not very good
99 // So, for dielectric, a name will be used, similar to the name build in gerber job file
100 wxString layerName = stackup_item->GetLayerName();
101
102 if( layerName.IsEmpty() )
103 {
104 if( IsValidLayer( stackup_item->GetBrdLayerId() ) )
105 layerName = aBoard->GetLayerName( stackup_item->GetBrdLayerId() );
106 }
107
108 if( stackup_item->GetType() == BS_ITEM_TYPE_DIELECTRIC )
109 {
110 layerName = _( "Dielectric" );
111
112 if( stackup_item->GetSublayersCount() < 2 )
113 layerName << wxT( " " ) << stackup_item->GetDielectricLayerId();
114 else
115 layerName << wxString::Format( _( " %d (%d/%d)" ), stackup_item->GetDielectricLayerId(),
116 sublayer_id + 1, stackup_item->GetSublayersCount() );
117 }
118
119 addDataCell( layerName );
120
121 addDataCell( InitialCaps( stackup_item->GetTypeName() ) );
122 addDataCell( stackup_item->GetMaterial( sublayer_id ) );
123 addDataCell( layerThicknessString( *stackup_item, sublayer_id ), 'R' );
124 addDataCell( stackup_item->GetColor( sublayer_id ) );
126 stackup_item->GetEpsilonR( sublayer_id ) ), 'R' );
128 stackup_item->GetLossTangent( sublayer_id ) ), 'R' );
129 }
130 }
131
132 table->Autosize();
133 table->SetPosition( VECTOR2I( 0, 0 ) );
134
135 return table;
136}
constexpr EDA_IU_SCALE pcbIUScale
Definition base_units.h:128
constexpr EDA_IU_SCALE unityScale
Definition base_units.h:131
#define DEFAULT_LINE_WIDTH
@ BS_ITEM_TYPE_DIELECTRIC
PCB_TABLE * Build_Board_Stackup_Table(BOARD *aBoard, EDA_UNITS aDisplayUnits)
Container for design settings for a BOARD object.
BOARD_STACKUP & GetStackupDescriptor()
Manage one layer needed to make a physical board.
wxString GetTypeName() const
int GetSublayersCount() const
double GetEpsilonR(int aDielectricSubLayer=0) const
wxString GetColor(int aDielectricSubLayer=0) const
wxString GetLayerName() const
PCB_LAYER_ID GetBrdLayerId() const
bool IsThicknessEditable() const
int GetThickness(int aDielectricSubLayer=0) const
BOARD_STACKUP_ITEM_TYPE GetType() const
wxString GetMaterial(int aDielectricSubLayer=0) const
int GetDielectricLayerId() const
double GetLossTangent(int aDielectricSubLayer=0) const
Manage layers needed to make a physical board.
const std::vector< BOARD_STACKUP_ITEM * > & GetList() const
int GetCount() const
bool SynchronizeWithBoard(const BOARD_DESIGN_SETTINGS *aSettings)
Synchronize the BOARD_STACKUP_ITEM* list with the board.
Information pertinent to a Pcbnew printed circuit board.
Definition board.h:411
const wxString GetLayerName(PCB_LAYER_ID aLayer) const
Return the name of a aLayer.
Definition board.cpp:932
BOARD_DESIGN_SETTINGS & GetDesignSettings()
Definition board.cpp:1290
virtual void SetText(const wxString &aText)
Definition eda_text.cpp:236
void SetHorizJustify(GR_TEXT_H_ALIGN_T aType)
Definition eda_text.cpp:370
void SetTextThickness(int aWidth) override
The TextThickness is that set by the user.
void SetTextSize(VECTOR2I aNewSize, bool aEnforceMinTextSize=true) override
wxString StringFromValue(double aValue, bool aAddUnitLabel=false, EDA_DATA_TYPE aType=EDA_DATA_TYPE::DISTANCE) const
Converts aValue in internal units into a united string.
#define _(s)
EDA_UNITS
Definition eda_units.h:44
bool IsValidLayer(int aLayerId)
Test whether a given integer is a valid layer index, i.e.
Definition layer_ids.h:719
KICOMMON_API wxString StringFromValue(const EDA_IU_SCALE &aIuScale, EDA_UNITS aUnits, double aValue, bool aAddUnitsText=false, EDA_DATA_TYPE aType=EDA_DATA_TYPE::DISTANCE)
Return the string from aValue according to aUnits (inch, mm ...) for display.
wxString NotSpecifiedPrm()
wxString InitialCaps(const wxString &aString)
Capitalize only the first word.
@ GR_TEXT_H_ALIGN_RIGHT
VECTOR2< int32_t > VECTOR2I
Definition vector2d.h:708