65 for(
unsigned long letter : aText )
67 if( letter >=
' ' && letter <= 0x7F )
68 fmt_text += char( letter );
72 sprintf( buff,
"\\u%4.4lX", letter );
117 const char* value =
nullptr;
153 msg.Printf(
_(
"Failed to create file '%s'." ), aFullFilename );
159 msg.Printf(
_(
"Created Gerber job file '%s'." ), aFullFilename );
173 "GenerationSoftware",
175 {
"Vendor",
"KiCad" },
176 {
"Application",
"Pcbnew" },
192 std::ofstream file( aFullFilename.ToUTF8() );
196 m_json = nlohmann::ordered_json( {} );
213 file << std::setw( 2 ) <<
m_json << std::endl;
229 sscanf( buffer,
"%Lg", &output );
238 m_json[
"GeneralSpecs"] = nlohmann::ordered_json( {} );
239 m_json[
"GeneralSpecs"][
"ProjectId"] = nlohmann::ordered_json( {} );
251 wxString msg = fn.GetFullName();
266 m_json[
"GeneralSpecs"][
"ProjectId"][
"Name"] = msg.ToAscii();
267 m_json[
"GeneralSpecs"][
"ProjectId"][
"GUID"] = guid;
268 m_json[
"GeneralSpecs"][
"ProjectId"][
"Revision"] = rev.ToAscii();
282 m_json[
"GeneralSpecs"][
"BoardThickness"] =
288 if( !brd_stackup.m_FinishType.IsEmpty() )
289 m_json[
"GeneralSpecs"][
"Finish"] = brd_stackup.m_FinishType;
291 if( brd_stackup.m_HasDielectricConstrains )
292 m_json[
"GeneralSpecs"][
"ImpedanceControlled"] =
true;
294 if( brd_stackup.m_CastellatedPads )
295 m_json[
"GeneralSpecs"][
"Castellated"] =
true;
297 if( brd_stackup.m_EdgePlating )
298 m_json[
"GeneralSpecs"][
"EdgePlating"] =
true;
300 if( brd_stackup.m_EdgeConnectorConstraints )
302 m_json[
"GeneralSpecs"][
"EdgeConnector"] =
true;
304 m_json[
"GeneralSpecs"][
"EdgeConnectorBevelled"] =
308 #if 0 // Not yet in use 317 m_json[
"GeneralSpecs"][
"IPC-2221-Type"] = 4;
333 m_json[
"GeneralSpecs"][
"ViaProtection"] =
"Ib";
341 m_json[
"FilesAttributes"] = nlohmann::ordered_json::array();
347 wxString gbr_layer_id;
348 bool skip_file =
false;
349 const char* polarity =
"Positive";
351 nlohmann::ordered_json file_json;
355 gbr_layer_id = wxT(
"Copper,L" );
360 gbr_layer_id << layer + 1;
362 gbr_layer_id << wxT(
"," );
365 gbr_layer_id << wxT(
"Bot" );
366 else if( layer ==
F_Cu )
367 gbr_layer_id << wxT(
"Top" );
369 gbr_layer_id << wxT(
"Inr" );
377 gbr_layer_id = wxT(
"Glue,Bot" );
380 gbr_layer_id = wxT(
"Glue,Top" );
384 gbr_layer_id = wxT(
"SolderPaste,Bot" );
387 gbr_layer_id = wxT(
"SolderPaste,Top" );
391 gbr_layer_id = wxT(
"Legend,Bot" );
394 gbr_layer_id = wxT(
"Legend,Top" );
398 gbr_layer_id = wxT(
"SolderMask,Bot" );
399 polarity =
"Negative";
402 gbr_layer_id = wxT(
"SolderMask,Top" );
403 polarity =
"Negative";
407 gbr_layer_id = wxT(
"Profile" );
411 gbr_layer_id = wxT(
"AssemblyDrawing,Bot" );
414 gbr_layer_id = wxT(
"AssemblyDrawing,Top" );
436 gbr_layer_id = wxT(
"Other,User" );
455 file_json[
"Path"] = strname.c_str();
456 file_json[
"FileFunction"] = gbr_layer_id;
457 file_json[
"FilePolarity"] = polarity;
459 m_json[
"FilesAttributes"] += file_json;
475 for(
const std::pair<const wxString, NETCLASSPTR>& entry : dsnSettings.
GetNetClasses() )
476 minclearanceOuter = std::min( minclearanceOuter, entry.second->GetClearance() );
480 int minclearance_track2track = minclearanceOuter;
490 for(
PAD*
pad : footprint->Pads() )
494 int padClearance =
pad->GetOwnClearance( layer );
496 if( layer ==
B_Cu || layer ==
F_Cu )
497 minPadClearanceOuter = std::min( minPadClearanceOuter, padClearance );
499 minPadClearanceInner = std::min( minPadClearanceInner, padClearance );
504 m_json[
"DesignRules"] = { {
505 {
"Layers",
"Outer" },
506 {
"PadToPad",
mapValue( minPadClearanceOuter ) },
507 {
"PadToTrack",
mapValue( minPadClearanceOuter ) },
508 {
"TrackToTrack",
mapValue( minclearance_track2track ) }
512 int minclearanceInner = minclearanceOuter;
515 int mintrackWidthOuter = INT_MAX;
516 int mintrackWidthInner = INT_MAX;
523 if( track->GetLayer() ==
B_Cu || track->GetLayer() ==
F_Cu )
524 mintrackWidthOuter = std::min( mintrackWidthOuter, track->GetWidth() );
526 mintrackWidthInner = std::min( mintrackWidthInner, track->GetWidth() );
529 if( mintrackWidthOuter != INT_MAX )
530 m_json[
"DesignRules"][0][
"MinLineWidth"] =
mapValue( mintrackWidthOuter );
535 minclearanceOuter = INT_MAX;
536 minclearanceInner = INT_MAX;
540 if( zone->GetIsRuleArea() || !zone->IsOnCopperLayer() )
545 int zclerance = zone->GetOwnClearance( layer );
547 if( layer ==
B_Cu || layer ==
F_Cu )
548 minclearanceOuter = std::min( minclearanceOuter, zclerance );
550 minclearanceInner = std::min( minclearanceInner, zclerance );
554 if( minclearanceOuter != INT_MAX )
555 m_json[
"DesignRules"][0][
"TrackToRegion"] =
mapValue( minclearanceOuter );
557 if( minclearanceOuter != INT_MAX )
558 m_json[
"DesignRules"][0][
"RegionToRegion"] =
mapValue( minclearanceOuter );
562 m_json[
"DesignRules"] += nlohmann::ordered_json( {
563 {
"Layers",
"Inner" },
564 {
"PadToPad",
mapValue( minPadClearanceInner ) },
565 {
"PadToTrack",
mapValue( minPadClearanceInner ) },
566 {
"TrackToTrack",
mapValue( minclearance_track2track ) }
569 if( mintrackWidthInner != INT_MAX )
570 m_json[
"DesignRules"][1][
"MinLineWidth"] =
mapValue( mintrackWidthInner );
572 if( minclearanceInner != INT_MAX )
573 m_json[
"DesignRules"][1][
"TrackToRegion"] =
mapValue( minclearanceInner );
575 if( minclearanceInner != INT_MAX )
576 m_json[
"DesignRules"][1][
"RegionToRegion"] =
mapValue( minclearanceInner );
584 m_json[
"MaterialStackup"] = nlohmann::ordered_json::array();
599 for(
int ii = 0; ii < brd_stackup.
GetCount(); ++ii )
603 int sub_layer_count =
606 for(
int sub_idx = 0; sub_idx < sub_layer_count; sub_idx++ )
611 std::string layer_name;
613 nlohmann::ordered_json layer_json;
618 layer_type = wxT(
"Copper" );
624 layer_type = wxT(
"Legend" );
629 layer_type = wxT(
"SolderMask" );
634 layer_type = wxT(
"SolderPaste" );
639 layer_type = wxT(
"Dielectric" );
642 if( sub_layer_count > 1 )
657 layer_json[
"Type"] = layer_type;
663 wxString colorName = item->
GetColor();
665 if( colorName.StartsWith( wxT(
"#" ) ) )
669 colorName.Printf( wxT(
"R%dG%dB%d" ),
675 layer_json[
"Color"] = colorName;
680 layer_json[
"Thickness"] = thickness;
686 layer_json[
"Material"] = item->
GetMaterial( sub_idx );
697 layer_json[
"DielectricConstant"] = item->
FormatEpsilonR( sub_idx );
710 next_copper_layer =
B_Cu;
712 wxString subLayerName;
714 if( sub_layer_count > 1 )
715 subLayerName.Printf( wxT(
" (%d/%d)" ), sub_idx + 1, sub_layer_count );
722 layer_json[
"Name"] =
name;
733 layer_json[
"Notes"] = note;
759 layer_json[
"Name"] = layer_name.c_str();
763 layer_json[
"Name"] = layer_name.c_str();
766 m_json[
"MaterialStackup"].insert(
m_json[
"MaterialStackup"].end(), layer_json );
BOARD_STACKUP_ITEM_TYPE GetType() const
nlohmann::ordered_json m_json
std::string formatStringFromUTF32(const wxString &aText)
A helper function to convert a wxString ( therefore a Unicode text ) to a JSON compatible string (a e...
Plot settings, and plotting engines (PostScript, Gerber, HPGL and DXF)
BOARD_STACKUP_ITEM * GetStackupLayer(int aIndex)
const wxString GetLayerName(PCB_LAYER_ID aLayer) const
Return the name of a aLayer.
bool HasMaterialValue(int aDielectricSubLayer=0) const
double mapValue(double aUiValue)
A helper function to convert a double in Pcbnew internal units to a JSON double value (in mm),...
bool CreateJobFile(const wxString &aFullFilename)
Creates a Gerber job file.
Instantiate the current locale within a scope in which you are expecting exceptions to be thrown.
wxString ExpandTextVars(const wxString &aSource, const PROJECT *aProject)
Manage layers needed to make a physical board.
int GetSublayersCount() const
static constexpr double IU_PER_MM
Mock up a conversion function.
const EDA_RECT GetBoardEdgesBoundingBox() const
Return the board bounding box calculated using exclusively the board edges (graphics on Edge....
enum ONSIDE hasSolderMasks()
void addJSONHeader()
Add the job file header in JSON format to m_JSONbuffer.
const char * sideKeyValue(enum ONSIDE aValue)
PROJECT * GetProject() const
int GetBoardThickness() const
wxString GetColor() const
enum ONSIDE hasSilkLayers()
A pure virtual class used to derive REPORTER objects from.
const wxString & GetFileName() const
Classes used to generate a Gerber job file in JSON.
BOARD_DESIGN_SETTINGS & GetDesignSettings() const
void addJSONFilesAttributes()
Add the Files Attributes section in JSON format to m_JSONbuffer.
virtual REPORTER & Report(const wxString &aText, SEVERITY aSeverity=RPT_SEVERITY_UNDEFINED)=0
Report a string with a given severity.
double GetLossTangent(int aDielectricSubLayer=0) const
bool SynchronizeWithBoard(BOARD_DESIGN_SETTINGS *aSettings)
Synchronize the BOARD_STACKUP_ITEM* list with the board.
Board plot function definition file.
static LIB_SYMBOL * dummy()
Used to draw a dummy shape when a LIB_SYMBOL is not found in library.
wxArrayString m_GerberFileList
bool m_HasDielectricConstrains
True if some layers have impedance controlled tracks or have specific constrains for micro-wave appli...
BOARD_STACKUP & GetStackupDescriptor()
bool IsThicknessEditable() const
LSET is a set of PCB_LAYER_IDs.
wxString GetBuildVersion()
Get the full KiCad version string.
const wxString & GetRevision() const
int GetThickness(int aDielectricSubLayer=0) const
bool IsColorEditable() const
FOOTPRINTS & Footprints()
A collection of nets and the parameters used to route or test these nets.
double GetEpsilonR(int aDielectricSubLayer=0) const
wxString FormatEpsilonR(int aDielectricSubLayer=0) const
Definition of file extensions used in Kicad.
wxString GetTypeName() const
wxString FormatLossTangent(int aDielectricSubLayer=0) const
NETCLASSES & GetNetClasses() const
Handle a list of polygons defining a copper zone.
Manage one layer needed to make a physical board.
bool WriteJSONJobFile(const wxString &aFullFilename)
Creates an Gerber job file in JSON format.
PCB_LAYER_ID GetBrdLayerId() const
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
TITLE_BLOCK & GetTitleBlock()
bool IsPrmSpecified(const wxString &aPrmValue)
int GetDielectricLayerId() const
Information pertinent to a Pcbnew printed circuit board.
PCB_LAYER_ID
A quick note on layer IDs:
void addJSONDesignRules()
Add the Design Rules section in JSON format to m_JSONbuffer.
int GetCopperLayerCount() const
Handle the component boundary box.
NETCLASS * GetDefault() const
std::vector< PCB_LAYER_ID > m_LayerId
class PCB_VIA, a via (like a track segment on a copper layer)
void addJSONMaterialStackup()
Add the Material Stackup section in JSON format to m_JSONbuffer This is the ordered list of stackup l...
wxString GetMaterial(int aDielectricSubLayer=0) const
void addJSONGeneralSpecs()
Add the General Specs in JSON format to m_JSONbuffer.
GERBER_JOBFILE_WRITER(BOARD *aPcb, REPORTER *aReporter=nullptr)
Container for design settings for a BOARD object.
A color representation with 4 components: red, green, blue, alpha.