KiCad PCB EDA Suite
Loading...
Searching...
No Matches
sch_io_easyedapro.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 (C) 2023 Alex Shvartzkop <[email protected]>
5 * Copyright (C) 2023-2024 KiCad Developers, see AUTHORS.txt for contributors.
6 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
11 *
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
16 *
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, you may find one here:
19 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
20 * or you may search the http://www.gnu.org website for the version 2 license,
21 * or you may write to the Free Software Foundation, Inc.,
22 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
23 */
24
26#include "sch_io_easyedapro.h"
27
28#include <schematic.h>
29#include <sch_sheet.h>
30#include <sch_screen.h>
32
33#include <fstream>
34#include <wx/txtstrm.h>
35#include <wx/wfstream.h>
36#include <wx/mstream.h>
37#include <wx/zipstrm.h>
38#include <wx/fs_zip.h>
39#include <wx/log.h>
40
41#include <nlohmann/json.hpp>
42#include <string_utils.h>
46#include <core/map_helpers.h>
47#include <project_sch.h>
48
49
51{
52 std::map<wxString, EASYEDAPRO::SYM_INFO> m_Symbols;
53 std::map<wxString, EASYEDAPRO::BLOB> m_Blobs;
54};
55
56
57SCH_IO_EASYEDAPRO::SCH_IO_EASYEDAPRO() : SCH_IO( wxS( "EasyEDA Pro (JLCEDA) Schematic" ) )
58{
60}
61
62
64{
65 if( m_projectData )
66 delete m_projectData;
67}
68
69
70bool SCH_IO_EASYEDAPRO::CanReadSchematicFile( const wxString& aFileName ) const
71{
72 if( aFileName.Lower().EndsWith( wxS( ".epro" ) ) )
73 {
74 return true;
75 }
76 else if( aFileName.Lower().EndsWith( wxS( ".zip" ) ) )
77 {
78 std::shared_ptr<wxZipEntry> entry;
79 wxFFileInputStream in( aFileName );
80 wxZipInputStream zip( in );
81
82 if( !zip.IsOk() )
83 return false;
84
85 while( entry.reset( zip.GetNextEntry() ), entry.get() != NULL )
86 {
87 wxString name = entry->GetName();
88
89 if( name == wxS( "project.json" ) )
90 return true;
91 }
92
93 return false;
94 }
95
96 return false;
97}
98
99
101{
102 return 0;
103}
104
105
106static LIB_SYMBOL* loadSymbol( nlohmann::json project, const wxString& aLibraryPath,
107 const wxString& aAliasName, const STRING_UTF8_MAP* aProperties )
108{
109 SCH_EASYEDAPRO_PARSER parser( nullptr, nullptr );
110 LIB_SYMBOL* symbol = nullptr;
111 wxFileName libFname( aLibraryPath );
112 wxString symLibName = LIB_ID::FixIllegalChars( libFname.GetName(), true );
113
114 /*if( libFname.GetExt() == wxS( "esym" ) )
115 {
116 wxFFileInputStream ffis( aLibraryPath );
117 wxTextInputStream txt( ffis, wxS( " " ), wxConvUTF8 );
118
119 bool loadThis = false;
120 std::vector<nlohmann::json> lines;
121 while( ffis.CanRead() )
122 {
123 nlohmann::json js = nlohmann::json::parse( txt.ReadLine() );
124 lines.emplace_back( js );
125
126 if( js.at( 0 ) == "ATTR" && js.at( 3 ) == "Symbol" )
127 {
128 if( js.at( 4 ).get<wxString>() == aAliasName )
129 {
130 loadThis = true;
131 }
132 }
133 }
134
135 if( loadThis )
136 {
137 EASYEDAPRO::SYM_INFO symInfo = parser.ParseSymbol( lines );
138 return symInfo.libSymbol.release();
139 }
140 }
141 else */
142 if( libFname.GetExt() == wxS( "elibz" ) || libFname.GetExt() == wxS( "epro" )
143 || libFname.GetExt() == wxS( "zip" ) )
144 {
145 std::map<wxString, EASYEDAPRO::PRJ_SYMBOL> prjSymbols = project.at( "symbols" );
146 std::map<wxString, EASYEDAPRO::PRJ_FOOTPRINT> prjFootprints = project.at( "footprints" );
147 std::map<wxString, EASYEDAPRO::PRJ_DEVICE> prjDevices = project.at( "devices" );
148
149 auto prjSymIt = std::find_if( prjSymbols.begin(), prjSymbols.end(),
150 [&]( const auto& pair )
151 {
152 return pair.second.title == aAliasName;
153 } );
154
155 if( prjSymIt == prjSymbols.end() )
156 return nullptr;
157
158 wxString prjSymUuid = prjSymIt->first;
159
160 wxString description;
161 wxString customTags;
162 std::map<wxString, wxString> deviceAttributes;
163 wxString fpTitle;
164
165 for( auto& [key, device] : prjDevices )
166 {
167 auto val = get_opt( device.attributes, "Symbol" );
168
169 if( val && *val == prjSymUuid )
170 {
171 description = device.description;
172 deviceAttributes = device.attributes;
173
174 if( device.custom_tags.is_string() )
175 customTags = device.custom_tags.get<wxString>();
176
177 if( auto fpUuid = get_opt( device.attributes, "Footprint" ) )
178 {
179 if( auto prjFp = get_opt( prjFootprints, *fpUuid ) )
180 {
181 fpTitle = prjFp->title;
182 break;
183 }
184 }
185 }
186 }
187
188 auto cb = [&]( const wxString& name, const wxString& symUuid, wxInputStream& zip ) -> bool
189 {
190 if( !name.EndsWith( wxS( ".esym" ) ) )
192
193 if( symUuid != prjSymUuid )
195
196 wxTextInputStream txt( zip, wxS( " " ), wxConvUTF8 );
197
198 std::vector<nlohmann::json> lines;
199 while( zip.CanRead() )
200 {
201 nlohmann::json js = nlohmann::json::parse( txt.ReadLine() );
202 lines.emplace_back( js );
203 }
204
205 EASYEDAPRO::SYM_INFO symInfo = parser.ParseSymbol( lines, deviceAttributes );
206
207 if( !symInfo.libSymbol )
209
210 LIB_ID libID = EASYEDAPRO::ToKiCadLibID( symLibName, aAliasName );
211 symInfo.libSymbol->SetLibId( libID );
212 symInfo.libSymbol->SetName( aAliasName );
213 symInfo.libSymbol->GetFootprintField().SetText( symLibName + wxS( ":" ) + fpTitle );
214
215 wxString keywords = customTags;
216 keywords.Replace( wxS( ":" ), wxS( " " ), true );
217
218 symInfo.libSymbol->SetKeyWords( keywords );
219
220 description.Replace( wxS( "\u2103" ), wxS( "\u00B0C" ), true ); // ℃ -> °C
221
222 symInfo.libSymbol->SetDescription( description );
223
224 symbol = symInfo.libSymbol.release();
225
227 };
228 EASYEDAPRO::IterateZipFiles( aLibraryPath, cb );
229 }
230
231 return symbol;
232}
233
234
235void SCH_IO_EASYEDAPRO::EnumerateSymbolLib( wxArrayString& aSymbolNameList,
236 const wxString& aLibraryPath,
237 const STRING_UTF8_MAP* aProperties )
238{
239 wxFileName fname( aLibraryPath );
240
241 if( fname.GetExt() == wxS( "esym" ) )
242 {
243 wxFFileInputStream ffis( aLibraryPath );
244 wxTextInputStream txt( ffis, wxS( " " ), wxConvUTF8 );
245
246 while( ffis.CanRead() )
247 {
248 wxString line = txt.ReadLine();
249
250 if( !line.Contains( wxS( "ATTR" ) ) )
251 continue; // Don't bother parsing
252
253 nlohmann::json js = nlohmann::json::parse( line );
254 if( js.at( 0 ) == "ATTR" && js.at( 3 ) == "Symbol" )
255 {
256 aSymbolNameList.Add( js.at( 4 ).get<wxString>() );
257 }
258 }
259 }
260 else if( fname.GetExt() == wxS( "elibz" ) || fname.GetExt() == wxS( "epro" )
261 || fname.GetExt() == wxS( "zip" ) )
262 {
263 nlohmann::json project = EASYEDAPRO::ReadProjectOrDeviceFile( aLibraryPath );
264 std::map<wxString, nlohmann::json> symbolMap = project.at( "symbols" );
265
266 for( auto& [key, value] : symbolMap )
267 {
268 wxString title;
269
270 if( value.contains( "display_title" ) )
271 title = value.at( "display_title" ).get<wxString>();
272 else
273 title = value.at( "title" ).get<wxString>();
274
275 aSymbolNameList.Add( title );
276 }
277 }
278}
279
280
281void SCH_IO_EASYEDAPRO::EnumerateSymbolLib( std::vector<LIB_SYMBOL*>& aSymbolList,
282 const wxString& aLibraryPath,
283 const STRING_UTF8_MAP* aProperties )
284{
285 wxFileName libFname( aLibraryPath );
286 wxArrayString symbolNameList;
287 nlohmann::json project;
288
289 EnumerateSymbolLib( symbolNameList, aLibraryPath, aProperties );
290
291 if( libFname.GetExt() == wxS( "elibz" ) || libFname.GetExt() == wxS( "epro" )
292 || libFname.GetExt() == wxS( "zip" ) )
293 {
295 }
296
297 for( const wxString& symbolName : symbolNameList )
298 {
299 LIB_SYMBOL* sym = loadSymbol( project, aLibraryPath, symbolName, aProperties );
300
301 if( sym )
302 aSymbolList.push_back( sym );
303 }
304}
305
306
307void SCH_IO_EASYEDAPRO::LoadAllDataFromProject( const wxString& aProjectPath )
308{
309 if( m_projectData )
310 delete m_projectData;
311
313
314 SCH_EASYEDAPRO_PARSER parser( nullptr, nullptr );
315 wxFileName fname( aProjectPath );
316 wxString symLibName = EASYEDAPRO::ShortenLibName( fname.GetName() );
317
318 if( fname.GetExt() != wxS( "epro" ) && fname.GetExt() != wxS( "zip" ) )
319 return;
320
321 nlohmann::json project = EASYEDAPRO::ReadProjectOrDeviceFile( aProjectPath );
322
323 std::map<wxString, EASYEDAPRO::PRJ_SYMBOL> prjSymbols = project.at( "symbols" );
324 std::map<wxString, EASYEDAPRO::PRJ_FOOTPRINT> prjFootprints = project.at( "footprints" );
325 std::map<wxString, EASYEDAPRO::PRJ_DEVICE> prjDevices = project.at( "devices" );
326
327 auto cb = [&]( const wxString& name, const wxString& baseName, wxInputStream& zip ) -> bool
328 {
329 if( !name.EndsWith( wxS( ".esym" ) ) && !name.EndsWith( wxS( ".eblob" ) ) )
331
332 std::vector<nlohmann::json> lines = EASYEDAPRO::ParseJsonLines( zip, name );
333
334 if( name.EndsWith( wxS( ".esym" ) ) )
335 {
336 wxString description;
337 wxString customTags;
338 std::map<wxString, wxString> deviceAttributes;
339 wxString fpTitle;
340
341 for( auto& [key, device] : prjDevices )
342 {
343 auto val = get_opt( device.attributes, "Symbol" );
344
345 if( val && *val == baseName )
346 {
347 description = device.description;
348 deviceAttributes = device.attributes;
349
350 if( device.custom_tags.is_string() )
351 customTags = device.custom_tags.get<wxString>();
352
353 if( auto fpUuid = get_opt( device.attributes, "Footprint" ) )
354 {
355 if( auto prjFp = get_opt( prjFootprints, *fpUuid ) )
356 {
357 fpTitle = prjFp->title;
358 break;
359 }
360 }
361 }
362 }
363
364 EASYEDAPRO::PRJ_SYMBOL symData = prjSymbols.at( baseName );
365 EASYEDAPRO::SYM_INFO symInfo = parser.ParseSymbol( lines, deviceAttributes );
366
367 if( !symInfo.libSymbol )
369
370 LIB_ID libID = EASYEDAPRO::ToKiCadLibID( symLibName, symData.title );
371 symInfo.libSymbol->SetLibId( libID );
372 symInfo.libSymbol->SetName( symData.title );
373 symInfo.libSymbol->GetFootprintField().SetText( symLibName + wxS( ":" ) + fpTitle );
374
375 wxString keywords = customTags;
376 keywords.Replace( wxS( ":" ), wxS( " " ), true );
377
378 symInfo.libSymbol->SetKeyWords( keywords );
379
380 description.Replace( wxS( "\u2103" ), wxS( "\u00B0C" ), true ); // ℃ -> °C
381
382 symInfo.libSymbol->SetDescription( description );
383
384 m_projectData->m_Symbols.emplace( baseName, std::move( symInfo ) );
385 }
386 else if( name.EndsWith( wxS( ".eblob" ) ) )
387 {
388 for( const nlohmann::json& line : lines )
389 {
390 if( line.at( 0 ) == "BLOB" )
391 {
392 EASYEDAPRO::BLOB blob = line;
393 m_projectData->m_Blobs[blob.objectId] = blob;
394 }
395 }
396 }
397
399 };
400 EASYEDAPRO::IterateZipFiles( aProjectPath, cb );
401}
402
403
404LIB_SYMBOL* SCH_IO_EASYEDAPRO::LoadSymbol( const wxString& aLibraryPath, const wxString& aAliasName,
405 const STRING_UTF8_MAP* aProperties )
406{
407 wxFileName libFname( aLibraryPath );
408 nlohmann::json project;
409
410 if( libFname.GetExt() == wxS( "elibz" ) || libFname.GetExt() == wxS( "epro" )
411 || libFname.GetExt() == wxS( "zip" ) )
412 {
414 }
415
416 return loadSymbol( project, aLibraryPath, aAliasName, aProperties );
417}
418
419
421 SCHEMATIC* aSchematic, SCH_SHEET* aAppendToMe,
422 const STRING_UTF8_MAP* aProperties )
423{
424 wxCHECK( !aFileName.IsEmpty() && aSchematic, nullptr );
425
426 SCH_SHEET* rootSheet = nullptr;
427
428 if( aAppendToMe )
429 {
430 wxCHECK_MSG( aSchematic->IsValid(), nullptr,
431 wxS( "Can't append to a schematic with no root!" ) );
432
433 rootSheet = &aSchematic->Root();
434 }
435 else
436 {
437 rootSheet = new SCH_SHEET( aSchematic );
438 rootSheet->SetFileName( aFileName );
439 aSchematic->SetRoot( rootSheet );
440 }
441
442 if( !rootSheet->GetScreen() )
443 {
444 SCH_SCREEN* screen = new SCH_SCREEN( aSchematic );
445
446 screen->SetFileName( aFileName );
447 rootSheet->SetScreen( screen );
448 }
449
450 SYMBOL_LIB_TABLE* libTable = PROJECT_SCH::SchSymbolLibTable( &aSchematic->Prj() );
451 wxCHECK_MSG( libTable, nullptr, wxS( "Could not load symbol lib table." ) );
452
453 SCH_EASYEDAPRO_PARSER parser( nullptr, nullptr );
454 wxFileName fname( aFileName );
455 wxString libName = EASYEDAPRO::ShortenLibName( fname.GetName() );
456
457 wxFileName libFileName( fname.GetPath(), libName, FILEEXT::KiCadSymbolLibFileExtension );
458
459 if( fname.GetExt() != wxS( "epro" ) && fname.GetExt() != wxS( "zip" ) )
460 return rootSheet;
461
462 nlohmann::json project = EASYEDAPRO::ReadProjectOrDeviceFile( aFileName );
463
464 std::map<wxString, EASYEDAPRO::PRJ_SCHEMATIC> prjSchematics = project.at( "schematics" );
465
466 wxString schematicToLoad;
467
468 if( aProperties && aProperties->Exists( "sch_id" ) )
469 {
470 schematicToLoad = wxString::FromUTF8( aProperties->at( "sch_id" ) );
471 }
472 else
473 {
474 if( prjSchematics.size() == 1 )
475 {
476 schematicToLoad = prjSchematics.begin()->first;
477 }
478 else
479 {
480 std::vector<IMPORT_PROJECT_DESC> chosen = m_choose_project_handler(
482
483 if( chosen.size() > 0 )
484 schematicToLoad = chosen[0].SchematicId;
485 }
486 }
487
488 if( schematicToLoad.empty() )
489 return nullptr;
490
491 wxString rootBaseName = EscapeString( prjSchematics[schematicToLoad].name, CTX_FILENAME );
492
493 wxFileName rootFname( aFileName );
494 rootFname.SetFullName( rootBaseName + wxS( "." )
495 + wxString::FromUTF8( FILEEXT::KiCadSchematicFileExtension ) );
496
497 rootSheet->SetName( prjSchematics[schematicToLoad].name );
498 rootSheet->SetFileName( rootFname.GetFullPath() );
499 rootSheet->GetScreen()->SetFileName( rootFname.GetFullPath() );
500
501 const std::vector<EASYEDAPRO::PRJ_SHEET>& prjSchematicSheets =
502 prjSchematics[schematicToLoad].sheets;
503
504 LoadAllDataFromProject( aFileName );
505
506 if( !m_projectData )
507 return nullptr;
508
509 const int schSheetsCount = prjSchematicSheets.size();
510
511 auto cbs = [&]( const wxString& name, const wxString& baseName, wxInputStream& zip ) -> bool
512 {
513 if( !name.EndsWith( wxS( ".esch" ) ) )
515
516 wxArrayString nameParts = wxSplit( name, '\\', '\0' );
517
518 if( nameParts.size() == 1 )
519 nameParts = wxSplit( name, '/', '\0' );
520
521 if( nameParts.size() < 3 )
523
524 wxString schematicUuid = nameParts[1];
525 wxString sheetFileName = nameParts[2];
526 wxString sheetId = sheetFileName.BeforeLast( '.' );
527 int sheetId_i;
528 sheetId.ToInt( &sheetId_i );
529
530 if( schematicUuid != schematicToLoad )
532
533 auto prjSheetIt = std::find_if( prjSchematicSheets.begin(), prjSchematicSheets.end(),
534 [&]( const EASYEDAPRO::PRJ_SHEET& s )
535 {
536 return s.id == sheetId_i;
537 } );
538
539 if( prjSheetIt == prjSchematicSheets.end() )
541
542 std::vector<nlohmann::json> lines = EASYEDAPRO::ParseJsonLines( zip, name );
543
544 if( schSheetsCount > 1 )
545 {
546 wxString sheetBaseName =
547 sheetId + wxS( "_" ) + EscapeString( prjSheetIt->name, CTX_FILENAME );
548
549 wxFileName sheetFname( aFileName );
550 sheetFname.SetFullName( sheetBaseName + wxS( "." )
551 + wxString::FromUTF8( FILEEXT::KiCadSchematicFileExtension ) );
552
553 wxFileName relSheetPath( sheetFname );
554 relSheetPath.MakeRelativeTo( rootFname.GetPath() );
555
556 std::unique_ptr<SCH_SHEET> subSheet = std::make_unique<SCH_SHEET>( aSchematic );
557 subSheet->SetFileName( relSheetPath.GetFullPath() );
558 subSheet->SetName( prjSheetIt->name );
559
560 SCH_SCREEN* screen = new SCH_SCREEN( aSchematic );
561 screen->SetFileName( sheetFname.GetFullPath() );
562 screen->SetPageNumber( sheetId );
563 subSheet->SetScreen( screen );
564
565 VECTOR2I pos;
566 pos.x = schIUScale.MilsToIU( 200 );
567 pos.y = schIUScale.MilsToIU( 200 )
568 + ( subSheet->GetSize().y + schIUScale.MilsToIU( 200 ) ) * ( sheetId_i - 1 );
569
570 subSheet->SetPosition( pos );
571
572 SCH_SHEET_PATH sheetPath;
573 sheetPath.push_back( rootSheet );
574 sheetPath.push_back( subSheet.get() );
575 sheetPath.SetPageNumber( sheetId );
576 aSchematic->SetCurrentSheet( sheetPath );
577
578 parser.ParseSchematic( aSchematic, subSheet.get(), project, m_projectData->m_Symbols,
579 m_projectData->m_Blobs, lines, libName );
580
581 rootSheet->GetScreen()->Append( subSheet.release() );
582 }
583 else
584 {
585 parser.ParseSchematic( aSchematic, rootSheet, project, m_projectData->m_Symbols,
586 m_projectData->m_Blobs, lines, libName );
587 }
588
590 };
591 EASYEDAPRO::IterateZipFiles( aFileName, cbs );
592
593 IO_RELEASER<SCH_IO> sch_plugin( SCH_IO_MGR::FindPlugin( SCH_IO_MGR::SCH_KICAD ) );
594
595 if( !libTable->HasLibrary( libName ) )
596 {
597 // Create a new empty symbol library.
598 sch_plugin->CreateLibrary( libFileName.GetFullPath() );
599 wxString libTableUri = wxS( "${KIPRJMOD}/" ) + libFileName.GetFullName();
600
601 // Add the new library to the project symbol library table.
602 libTable->InsertRow( new SYMBOL_LIB_TABLE_ROW( libName, libTableUri, wxS( "KiCad" ) ) );
603
604 // Save project symbol library table.
605 wxFileName fn( aSchematic->Prj().GetProjectPath(),
607
608 // So output formatter goes out of scope and closes the file before reloading.
609 {
610 FILE_OUTPUTFORMATTER formatter( fn.GetFullPath() );
611 libTable->Format( &formatter, 0 );
612 }
613
614 // Relaod the symbol library table.
615 aSchematic->Prj().SetElem( PROJECT::ELEM_SYMBOL_LIB_TABLE, NULL );
616 PROJECT_SCH::SchSymbolLibTable( &aSchematic->Prj() );
617 }
618
619 // set properties to prevent save file on every symbol save
620 STRING_UTF8_MAP properties;
621 properties.emplace( SCH_IO_KICAD_SEXPR::PropBuffering, wxEmptyString );
622
623 for( auto& [symbolUuid, symInfo] : m_projectData->m_Symbols )
624 sch_plugin->SaveSymbol( libFileName.GetFullPath(), symInfo.libSymbol.release(),
625 &properties );
626
627 sch_plugin->SaveLibrary( libFileName.GetFullPath() );
628
630 aSchematic->FixupJunctions();
631
632 return rootSheet;
633}
const char * name
Definition: DXF_plotter.cpp:57
constexpr EDA_IU_SCALE schIUScale
Definition: base_units.h:110
void SetPageNumber(const wxString &aPageNumber)
Definition: base_screen.h:79
Used for text file output.
Definition: richio.h:475
REPORTER * m_reporter
Reporter to log errors/warnings to, may be nullptr.
Definition: io_base.h:210
A logical library item identifier and consists of various portions much like a URI.
Definition: lib_id.h:49
static UTF8 FixIllegalChars(const UTF8 &aLibItemName, bool aLib)
Replace illegal LIB_ID item name characters with underscores '_'.
Definition: lib_id.cpp:191
Define a library symbol object.
Definition: lib_symbol.h:77
bool HasLibrary(const wxString &aNickname, bool aCheckEnabled=false) const
Test for the existence of aNickname in the library table.
bool InsertRow(LIB_TABLE_ROW *aRow, bool doReplace=false)
Adds aRow if it does not already exist or if doReplace is true.
CHOOSE_PROJECT_HANDLER m_choose_project_handler
Callback to choose projects to import.
static SYMBOL_LIB_TABLE * SchSymbolLibTable(PROJECT *aProject)
Accessor for project symbol library table.
virtual const wxString GetProjectPath() const
Return the full path of the project.
Definition: project.cpp:135
virtual void SetElem(ELEM_T aIndex, _ELEM *aElem)
Definition: project.cpp:309
@ ELEM_SYMBOL_LIB_TABLE
Definition: project.h:228
Holds all the data relating to one schematic.
Definition: schematic.h:75
SCH_SHEET_PATH & CurrentSheet() const override
Definition: schematic.h:136
void SetCurrentSheet(const SCH_SHEET_PATH &aPath) override
Definition: schematic.h:141
void FixupJunctions()
Add junctions to this schematic where required.
Definition: schematic.cpp:723
void SetRoot(SCH_SHEET *aRootSheet)
Initialize the schematic with a new root sheet.
Definition: schematic.cpp:186
bool IsValid() const
A simple test if the schematic is loaded, not a complete one.
Definition: schematic.h:121
SCH_SHEET & Root() const
Definition: schematic.h:105
PROJECT & Prj() const override
Return a reference to the project this schematic is part of.
Definition: schematic.h:90
EASYEDAPRO::SYM_INFO ParseSymbol(const std::vector< nlohmann::json > &aLines, const std::map< wxString, wxString > &aDeviceAttributes)
void ParseSchematic(SCHEMATIC *aSchematic, SCH_SHEET *aRootSheet, const nlohmann::json &aProject, std::map< wxString, EASYEDAPRO::SYM_INFO > &aSymbolMap, const std::map< wxString, EASYEDAPRO::BLOB > &aBlobMap, const std::vector< nlohmann::json > &aLines, const wxString &aLibName)
SCH_SHEET * LoadSchematicFile(const wxString &aFileName, SCHEMATIC *aSchematic, SCH_SHEET *aAppendToMe=nullptr, const STRING_UTF8_MAP *aProperties=nullptr) override
Load information from some input file format that this SCH_IO implementation knows about,...
void EnumerateSymbolLib(wxArrayString &aSymbolNameList, const wxString &aLibraryPath, const STRING_UTF8_MAP *aProperties=nullptr) override
Populate a list of LIB_SYMBOL alias names contained within the library aLibraryPath.
PRJ_DATA * m_projectData
void LoadAllDataFromProject(const wxString &aLibraryPath)
int GetModifyHash() const override
Return the modification hash from the library cache.
bool CanReadSchematicFile(const wxString &aFileName) const override
Checks if this SCH_IO can read the specified schematic file.
LIB_SYMBOL * LoadSymbol(const wxString &aLibraryPath, const wxString &aAliasName, const STRING_UTF8_MAP *aProperties=nullptr) override
Load a LIB_SYMBOL object having aPartName from the aLibraryPath containing a library format that this...
static const char * PropBuffering
The property used internally by the plugin to enable cache buffering which prevents the library file ...
Base class that schematic file and library loading and saving plugins should derive from.
Definition: sch_io.h:57
void Append(SCH_ITEM *aItem, bool aUpdateLibSymbol=true)
Definition: sch_screen.cpp:151
void SetFileName(const wxString &aFileName)
Set the file name for this screen to aFileName.
Definition: sch_screen.cpp:116
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
void UpdateAllScreenReferences() const
Update all the symbol references for this sheet path.
void SetPageNumber(const wxString &aPageNumber)
Set the sheet instance user definable page number.
void push_back(SCH_SHEET *aSheet)
Forwarded method from std::vector.
Sheet symbol placed in a schematic, and is the entry point for a sub schematic.
Definition: sch_sheet.h:57
void SetFileName(const wxString &aFilename)
Definition: sch_sheet.h:312
void SetName(const wxString &aName)
Definition: sch_sheet.h:108
SCH_SCREEN * GetScreen() const
Definition: sch_sheet.h:110
void SetScreen(SCH_SCREEN *aScreen)
Set the SCH_SCREEN associated with this sheet to aScreen.
Definition: sch_sheet.cpp:162
A name/value tuple with unique names and optional values.
bool Exists(const std::string &aProperty) const
Hold a record identifying a symbol library accessed by the appropriate symbol library SCH_IO object i...
static const wxString & GetSymbolLibTableFileName()
virtual void Format(OUTPUTFORMATTER *aOutput, int aIndentLevel) const override
Generate the table in s-expression format to aOutput with an indentation level of aIndentLevel.
static REPORTER & GetInstance()
Definition: reporter.cpp:203
#define EASY_IT_BREAK
#define EASY_IT_CONTINUE
static const std::string KiCadSchematicFileExtension
static const std::string KiCadSymbolLibFileExtension
std::unique_ptr< T > IO_RELEASER
Helper to hold and release an IO_BASE object when exceptions are thrown.
Definition: io_mgr.h:33
std::optional< V > get_opt(const std::map< wxString, V > &aMap, const wxString &aKey)
Definition: map_helpers.h:34
LIB_ID ToKiCadLibID(const wxString &aLibName, const wxString &aLibReference)
void IterateZipFiles(const wxString &aFileName, std::function< bool(const wxString &, const wxString &, wxInputStream &)> aCallback)
std::vector< nlohmann::json > ParseJsonLines(wxInputStream &aInput, const wxString &aSource)
std::vector< IMPORT_PROJECT_DESC > ProjectToSelectorDialog(const nlohmann::json &aProject, bool aPcbOnly=false, bool aSchOnly=false)
nlohmann::json ReadProjectOrDeviceFile(const wxString &aZipFileName)
wxString ShortenLibName(wxString aProjectName)
LIB_SYMBOL * loadSymbol(const wxString &aLibraryPath, nlohmann::json aFileData, const wxString &aAliasName, const STRING_UTF8_MAP *aProperties)
static LIB_SYMBOL * loadSymbol(nlohmann::json project, const wxString &aLibraryPath, const wxString &aAliasName, const STRING_UTF8_MAP *aProperties)
wxString EscapeString(const wxString &aSource, ESCAPE_CONTEXT aContext)
The Escape/Unescape routines use HTML-entity-reference-style encoding to handle characters which are:...
@ CTX_FILENAME
Definition: string_utils.h:61
std::unique_ptr< LIB_SYMBOL > libSymbol
constexpr int MilsToIU(int mils) const
Definition: base_units.h:93
std::map< wxString, EASYEDAPRO::BLOB > m_Blobs
std::map< wxString, EASYEDAPRO::SYM_INFO > m_Symbols
Definition of file extensions used in Kicad.