KiCad PCB EDA Suite
Loading...
Searching...
No Matches
test_ee_item.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, you may find one here:
18 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
19 * or you may search the http://www.gnu.org website for the version 2 license,
20 * or you may write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
22 */
23
24#include <properties/property.h>
26#include <eda_item_test_utils.h>
27#include <core/typeinfo.h>
28
29#include <eda_item.h>
30#include <sch_item.h>
31
32#include <sch_marker.h>
33#include <sch_junction.h>
34#include <sch_no_connect.h>
35#include <sch_bus_entry.h>
36#include <sch_line.h>
37#include <sch_rule_area.h>
38#include <sch_shape.h>
39#include <sch_bitmap.h>
40#include <sch_text.h>
41#include <sch_textbox.h>
42#include <sch_table.h>
43#include <sch_tablecell.h>
44#include <sch_field.h>
45#include <sch_group.h>
46#include <sch_symbol.h>
47#include <sch_sheet_pin.h>
48#include <sch_sheet.h>
49#include <sch_pin.h>
50
51#include <erc/erc_settings.h>
53
55{
56public:
61 std::shared_ptr<ERC_ITEM> m_ercItem;
62
64 m_sheet(),
65 m_symbol( "test symbol" ),
66 m_pin( &m_symbol ),
68 {
69 m_sheet.SetPosition( VECTOR2I( schIUScale.mmToIU( 5 ), schIUScale.mmToIU( 10 ) ) );
70 m_sheet.SetSize( VECTOR2I( schIUScale.mmToIU( 50 ), schIUScale.mmToIU( 100 ) ) );
71 }
72
74 {
75 m_text.SetParentGroup( nullptr );
76 }
77
79 {
80 if( !IsEeschemaType( aType ) )
81 return nullptr;
82
83 if( !IsInstantiableType( aType ) )
84 return nullptr;
85
86 switch( aType )
87 {
88 case SCH_MARKER_T: return new SCH_MARKER( m_ercItem, VECTOR2I( 0, 0 ) );
89 case SCH_JUNCTION_T: return new SCH_JUNCTION();
90 case SCH_NO_CONNECT_T: return new SCH_NO_CONNECT();
92 case SCH_BUS_BUS_ENTRY_T: return new SCH_BUS_BUS_ENTRY();
93 case SCH_LINE_T: return new SCH_LINE();
94
95 case SCH_RULE_AREA_T:
96 {
97 SHAPE_POLY_SET ruleShape;
98
99 ruleShape.NewOutline();
100 auto& outline = ruleShape.Outline( 0 );
101 outline.Append( VECTOR2I( 20000, 20000) );
102 outline.Append( VECTOR2I( 22000, 20000) );
103 outline.Append( VECTOR2I( 22000, 22000) );
104 outline.Append( VECTOR2I( 20000, 22000) );
105 outline.SetClosed( true );
106 outline.Simplify( true );
107
108 SCH_RULE_AREA* ruleArea = new SCH_RULE_AREA();
109 ruleArea->SetPolyShape( ruleShape );
110
111 return ruleArea;
112 }
113
114 case SCH_SHAPE_T: return new SCH_SHAPE( SHAPE_T::ARC, LAYER_NOTES );
115 case SCH_BITMAP_T: return new SCH_BITMAP();
116 case SCH_TEXT_T: return new SCH_TEXT( VECTOR2I( 0, 0 ), "test text" );
117 case SCH_TEXTBOX_T: return new SCH_TEXTBOX( LAYER_NOTES, 0, FILL_T::NO_FILL, "test textbox" );
118 case SCH_TABLECELL_T: return new SCH_TABLECELL();
119
120 case SCH_TABLE_T:
121 {
122 SCH_TABLE* table = new SCH_TABLE( schIUScale.mmToIU( 0.1 ) );
123
124 table->SetColCount( 2 );
125
126 for( int ii = 0; ii < 4; ++ii )
127 table->InsertCell( ii, new SCH_TABLECELL() );
128
129 return table;
130 }
131
132 case SCH_LABEL_T: return new SCH_LABEL( VECTOR2I( 0, 0 ), "test label" );
133 case SCH_DIRECTIVE_LABEL_T: return new SCH_DIRECTIVE_LABEL( VECTOR2I( 0, 0 ) );
134 case SCH_GLOBAL_LABEL_T: return new SCH_GLOBALLABEL();
135 case SCH_HIER_LABEL_T: return new SCH_HIERLABEL();
136 case SCH_FIELD_T: return new SCH_FIELD( nullptr, FIELD_T::USER );
137 case SCH_SYMBOL_T: return new SCH_SYMBOL();
138
139 case SCH_SHEET_PIN_T:
140 // XXX: m_sheet pins currently have to have their initial positions calculated manually.
141 return new SCH_SHEET_PIN( &m_sheet,
142 VECTOR2I( m_sheet.GetPosition().x,
143 m_sheet.GetPosition().y + schIUScale.mmToIU( 40 ) ),
144 "test aPin" );
145
146 case SCH_SHEET_T: return new SCH_SHEET();
147 case SCH_PIN_T: return new SCH_PIN( &m_symbol );
148
149 case SCH_GROUP_T:
150 {
151 SCH_GROUP* group = new SCH_GROUP();
152
153 // Group position only makes sense if there's at least one item in the group.
154 group->AddItem( &m_text );
155
156 return group;
157 }
158
159 case SCHEMATIC_T:
160 case LIB_SYMBOL_T: return nullptr;
161
162 default:
163 BOOST_FAIL( wxString::Format(
164 "Unhandled type: %d "
165 "(if you created a new type you need to handle it in this switch statement)",
166 aType ) );
167 return nullptr;
168 }
169 }
170
171 static void CompareItems( EDA_ITEM* aItem, EDA_ITEM* aOriginalItem )
172 {
173 BOOST_CHECK_EQUAL( aItem->GetPosition(), aOriginalItem->GetPosition() );
175 aOriginalItem->GetBoundingBox().GetTop() );
177 aOriginalItem->GetBoundingBox().GetLeft() );
179 aOriginalItem->GetBoundingBox().GetBottom() );
181 aOriginalItem->GetBoundingBox().GetRight() );
182 }
183};
184
185
186BOOST_FIXTURE_TEST_SUITE( EeItem, TEST_EE_ITEM_FIXTURE )
187
188
190{
191 for( int i = 0; i < MAX_STRUCT_TYPE_ID; i++ )
192 {
193 KICAD_T type = static_cast<KICAD_T>( i );
194
195 auto item = std::unique_ptr<EDA_ITEM>( Instantiate( type ) );
196
197 if( item == nullptr )
198 continue;
199
200 BOOST_TEST_CONTEXT( "Class: " << item->GetClass() )
201 {
203 item.get(),
204 []( EDA_ITEM* aOriginalItem, VECTOR2I aRef )
205 {
206 auto item = std::unique_ptr<EDA_ITEM>( aOriginalItem->Clone() );
207 VECTOR2I originalPos = item->GetPosition();
208
209 SCH_ITEM* schItem = dynamic_cast<SCH_ITEM*>( item.get() );
210
211 // Move to a point, then go back.
212 // This has to be an identity transformation.
213
214 if( schItem != nullptr )
215 {
216 schItem->Move( aRef );
217 BOOST_CHECK_EQUAL( schItem->GetPosition(), originalPos + aRef );
218
219 schItem->Move( -aRef );
220 }
221
222 CompareItems( item.get(), aOriginalItem );
223 } );
224 }
225 }
226}
227
228
230{
231 for( int i = 0; i < MAX_STRUCT_TYPE_ID; i++ )
232 {
233 KICAD_T type = static_cast<KICAD_T>( i );
234
235 auto item = std::unique_ptr<EDA_ITEM>( Instantiate( type ) );
236
237 if( item == nullptr )
238 continue;
239
240 BOOST_TEST_CONTEXT( "Class: " << item->GetClass() )
241 {
242 // Four equivalent 90 degree rotations are an identity.
243 // (warning: only for items having no autoplaced fields).
244
245 if( item->GetClass() == "SCH_SHEET_PIN" )
246 {
247 auto newItem = std::unique_ptr<EDA_ITEM>( item->Clone() );
248
249 SCH_ITEM* schItem = dynamic_cast<SCH_ITEM*>( newItem.get() );
250
251 if( schItem != nullptr )
252 {
254 // Only rotating pins around the center of parent sheet works.
255 schItem->Rotate( m_sheet.GetBodyBoundingBox().GetCenter(), false );
256 schItem->Rotate( m_sheet.GetBodyBoundingBox().GetCenter(), false );
257 schItem->Rotate( m_sheet.GetBodyBoundingBox().GetCenter(), false );
258 schItem->Rotate( m_sheet.GetBodyBoundingBox().GetCenter(), false );
259 }
260
261 CompareItems( newItem.get(), item.get() );
262 }
263 else
264 {
266 item.get(),
267 []( EDA_ITEM* aOriginalItem, VECTOR2I aRef )
268 {
269 auto item = std::unique_ptr<EDA_ITEM>( aOriginalItem->Clone() );
270
271 SCH_ITEM* schItem = dynamic_cast<SCH_ITEM*>( item.get() );
272
273 if( schItem != nullptr )
274 {
275 schItem->SetFieldsAutoplaced( AUTOPLACE_NONE );
276 schItem->Rotate( aRef, false );
277 schItem->Rotate( aRef, false );
278 schItem->Rotate( aRef, false );
279 schItem->Rotate( aRef, false );
280 }
281
282 CompareItems( item.get(), aOriginalItem );
283 } );
284 }
285 }
286 }
287}
288
289
290BOOST_AUTO_TEST_CASE( MirrorHorizontally )
291{
292 for( int i = 0; i < MAX_STRUCT_TYPE_ID; i++ )
293 {
294 KICAD_T type = static_cast<KICAD_T>( i );
295
296 auto item = std::unique_ptr<EDA_ITEM>( Instantiate( type ) );
297
298 if( item == nullptr )
299 continue;
300
301 BOOST_TEST_CONTEXT( "Class: " << item->GetClass() )
302 {
304 item.get(),
305 []( EDA_ITEM* aOriginalItem, VECTOR2I aRef )
306 {
307 auto item = std::unique_ptr<EDA_ITEM>( aOriginalItem->Clone() );
308
309 SCH_ITEM* schItem = dynamic_cast<SCH_ITEM*>( item.get() );
310
311 // Two mirrorings are an identity
312 // (warning: only for text items having no autoplaced fields).
313 if( schItem != nullptr )
314 {
315 schItem->SetFieldsAutoplaced( AUTOPLACE_NONE );
316 schItem->MirrorHorizontally( aRef.x );
317 schItem->MirrorHorizontally( aRef.x );
318 }
319
320 CompareItems( item.get(), aOriginalItem );
321 } );
322 }
323 }
324}
325
326
327BOOST_AUTO_TEST_CASE( MirrorVertically )
328{
329 for( int i = 0; i < MAX_STRUCT_TYPE_ID; i++ )
330 {
331 KICAD_T type = static_cast<KICAD_T>( i );
332
333 auto item = std::unique_ptr<EDA_ITEM>( Instantiate( type ) );
334
335 if( item == nullptr )
336 continue;
337
338 BOOST_TEST_CONTEXT( "Class: " << item->GetClass() )
339 {
341 item.get(),
342 []( EDA_ITEM* aOriginalItem, VECTOR2I aRef )
343 {
344 auto item = std::unique_ptr<EDA_ITEM>( aOriginalItem->Clone() );
345
346 SCH_ITEM* schItem = dynamic_cast<SCH_ITEM*>( item.get() );
347
348 // Two mirrorings are an identity
349 // (warning only for text items having no autoplaced fields).
350
351 if( schItem != nullptr )
352 {
353 schItem->SetFieldsAutoplaced( AUTOPLACE_NONE );
354 schItem->MirrorVertically( aRef.y );
355 schItem->MirrorVertically( aRef.y );
356 }
357
358 CompareItems( item.get(), aOriginalItem );
359 } );
360 }
361 }
362}
363
constexpr EDA_IU_SCALE schIUScale
Definition base_units.h:114
constexpr coord_type GetLeft() const
Definition box2.h:228
constexpr coord_type GetRight() const
Definition box2.h:217
constexpr coord_type GetTop() const
Definition box2.h:229
constexpr coord_type GetBottom() const
Definition box2.h:222
A base class for most all the KiCad significant classes used in schematics and boards.
Definition eda_item.h:99
virtual VECTOR2I GetPosition() const
Definition eda_item.h:278
virtual const BOX2I GetBoundingBox() const
Return the orthogonal bounding box of this object for display purposes.
Definition eda_item.cpp:120
void SetPolyShape(const SHAPE_POLY_SET &aShape)
Definition eda_shape.h:345
Define a library symbol object.
Definition lib_symbol.h:83
Object to handle a bitmap image that can be inserted in a schematic.
Definition sch_bitmap.h:40
Class for a bus to bus entry.
Class for a wire to bus entry.
A set of SCH_ITEMs (i.e., without duplicates).
Definition sch_group.h:52
Base class for any item which can be embedded within the SCHEMATIC container class,...
Definition sch_item.h:168
void SetFieldsAutoplaced(AUTOPLACE_ALGO aAlgo)
Definition sch_item.h:627
virtual void Rotate(const VECTOR2I &aCenter, bool aRotateCCW)
Rotate the item around aCenter 90 degrees in the clockwise direction.
Definition sch_item.h:423
Segment description base class to describe items which have 2 end points (track, wire,...
Definition sch_line.h:42
Define a sheet pin (label) used in sheets to create hierarchical schematics.
Sheet symbol placed in a schematic, and is the entry point for a sub schematic.
Definition sch_sheet.h:48
Schematic symbol object.
Definition sch_symbol.h:76
void Append(int aX, int aY, bool aAllowDuplication=false)
Append a new point at the end of the line chain.
Represent a set of closed polygons.
SHAPE_LINE_CHAIN & Outline(int aIndex)
Return the reference to aIndex-th outline in the set.
int NewOutline()
Creates a new empty polygon in the set and returns its index.
EDA_ITEM * Instantiate(KICAD_T aType)
static void CompareItems(EDA_ITEM *aItem, EDA_ITEM *aOriginalItem)
std::shared_ptr< ERC_ITEM > m_ercItem
static void IterateOverPositionsAndReferences(T *aItem, void(*aCallback)(T *, VECTOR2I))
@ NO_FILL
Definition eda_shape.h:57
@ ERCE_DRIVER_CONFLICT
Conflicting drivers (labels, etc) on a subgraph.
@ LAYER_NOTES
Definition layer_ids.h:467
Class to handle a set of SCH_ITEMs.
@ AUTOPLACE_NONE
Definition sch_item.h:70
@ USER
The field ID hasn't been set yet; field is invalid.
BOOST_AUTO_TEST_CASE(HorizontalAlignment)
BOOST_AUTO_TEST_CASE(Move)
BOOST_AUTO_TEST_SUITE_END()
BOOST_TEST_CONTEXT("Test Clearance")
BOOST_CHECK_EQUAL(result, "25.4")
KICAD_T
The set of class identification values stored in EDA_ITEM::m_structType.
Definition typeinfo.h:78
@ SCH_GROUP_T
Definition typeinfo.h:177
@ SCH_TABLE_T
Definition typeinfo.h:169
@ SCH_LINE_T
Definition typeinfo.h:167
@ LIB_SYMBOL_T
Definition typeinfo.h:152
@ SCH_NO_CONNECT_T
Definition typeinfo.h:164
@ MAX_STRUCT_TYPE_ID
Definition typeinfo.h:242
@ SCH_SYMBOL_T
Definition typeinfo.h:176
@ SCH_TABLECELL_T
Definition typeinfo.h:170
@ SCH_FIELD_T
Definition typeinfo.h:154
@ SCH_DIRECTIVE_LABEL_T
Definition typeinfo.h:175
@ SCH_LABEL_T
Definition typeinfo.h:171
@ SCH_SHEET_T
Definition typeinfo.h:179
@ SCH_MARKER_T
Definition typeinfo.h:162
@ SCH_SHAPE_T
Definition typeinfo.h:153
@ SCH_RULE_AREA_T
Definition typeinfo.h:174
@ SCH_HIER_LABEL_T
Definition typeinfo.h:173
@ SCH_BUS_BUS_ENTRY_T
Definition typeinfo.h:166
@ SCHEMATIC_T
Definition typeinfo.h:208
@ SCH_SHEET_PIN_T
Definition typeinfo.h:178
@ SCH_TEXT_T
Definition typeinfo.h:155
@ SCH_BUS_WIRE_ENTRY_T
Definition typeinfo.h:165
@ SCH_BITMAP_T
Definition typeinfo.h:168
@ SCH_TEXTBOX_T
Definition typeinfo.h:156
@ SCH_GLOBAL_LABEL_T
Definition typeinfo.h:172
@ SCH_JUNCTION_T
Definition typeinfo.h:163
@ SCH_PIN_T
Definition typeinfo.h:157
constexpr bool IsInstantiableType(const KICAD_T aType)
Definition typeinfo.h:313
constexpr bool IsEeschemaType(const KICAD_T aType)
Definition typeinfo.h:373
VECTOR2< int32_t > VECTOR2I
Definition vector2d.h:695