44#include <unordered_map>
46using CODE_MAP = std::unordered_map<DRC_RULE_EDITOR_CONSTRAINT_NAME, const char*>;
47using REVERSE_CODE_MAP = std::unordered_map<wxString, DRC_RULE_EDITOR_CONSTRAINT_NAME, wxStringHash, wxStringEqual>;
86 for(
const auto& [type, code] :
sCodeMap )
87 map.emplace( wxString::FromUTF8( code ), type );
93 static std::vector<DRC_RULE_EDITOR_UTILS::RuleConverter> converters;
146 static bool initialized =
false;
153 [](
const std::shared_ptr<DRC_RULE>& aRule ) -> std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA>
155 if( aRule->m_Constraints.empty() )
return nullptr;
157 const auto& constraint = aRule->m_Constraints[0];
160 if( code.IsEmpty() )
return nullptr;
168 double val = constraint.GetValue().Min() / 1000000.0;
170 data->SetRuleName( aRule->m_Name );
171 data->SetNumericInputValue( val );
172 data->SetConstraintCode( code );
177 auto data = std::make_shared<DRC_RE_BOOL_INPUT_CONSTRAINT_DATA>( 0, 0,
true, aRule->m_Name );
178 data->SetConstraintCode( code );
181 else if( code ==
"track_width" )
183 double minW = constraint.GetValue().Min() / 1000000.0;
184 double optW = constraint.GetValue().Opt() / 1000000.0;
185 double maxW = constraint.GetValue().Max() / 1000000.0;
187 auto data = std::make_shared<DRC_RE_ROUTING_WIDTH_CONSTRAINT_DATA>( 0, 0, aRule->m_Name, minW, optW, maxW );
188 data->SetConstraintCode( code );
197 [](
const std::shared_ptr<DRC_RULE>& aRule ) -> std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA>
202 if( diaConstraint && holeConstraint )
204 double minDia = diaConstraint->GetValue().Min() / 1000000.0;
205 double optDia = diaConstraint->GetValue().Opt() / 1000000.0;
206 double maxDia = diaConstraint->GetValue().Max() / 1000000.0;
208 double minDrill = holeConstraint->GetValue().Min() / 1000000.0;
209 double optDrill = holeConstraint->GetValue().Opt() / 1000000.0;
210 double maxDrill = holeConstraint->GetValue().Max() / 1000000.0;
212 auto data = std::make_shared<DRC_RE_VIA_STYLE_CONSTRAINT_DATA>( 0, 0, aRule->m_Name,
213 minDia, maxDia, optDia, minDrill, maxDrill, optDrill );
214 data->SetConstraintCode(
"via_style" );
224 auto it =
sCodeMap.find( aConstraintType );
226 return wxString::FromUTF8( it->second );
267 switch( aConstraintType )
270 default:
return false;
277 switch( aConstraintType )
312 int* aErrorCount, wxString* aValidationMessage )
315 aTextCtrl->SetValidator( validator );
317 if( !aTextCtrl->Validate() )
326 *aValidationMessage +=
328 wxString::Format(
_(
"%s should not be empty." ), aLabel ) );
335 *aErrorCount, wxString::Format(
_(
"The value of %s must be a valid number." ), aLabel ) );
342 *aErrorCount, wxString::Format(
_(
"The value of %s must be greater than 0." ), aLabel ) );
354 int* aErrorCount, wxString* aValidationMessage )
357 aTextCtrl->SetValidator( validator );
359 if( !aTextCtrl->Validate() )
368 *aValidationMessage +=
370 wxString::Format(
_(
"%s should not be empty." ), aLabel ) );
377 *aErrorCount, wxString::Format(
_(
"The value of %s must be a valid integer." ), aLabel ) );
384 *aErrorCount, wxString::Format(
_(
"The value of %s must be greater than 0." ), aLabel ) );
396 wxString* aValidationMessage )
399 aComboBox->SetValidator( cmbCtrlValidator );
401 if( !aComboBox->Validate() )
411 wxString::Format(
_(
"Please choose %s." ), aLabel ) );
423 const wxString& aMinLabel,
const wxString& aMaxLabel,
424 int* aErrorCount, wxString* aValidationMessage )
426 aMinTextCtrl->SetName(
"min" );
427 aMaxTextCtrl->SetName(
"max" );
431 if( !aMinTextCtrl->Validate() )
441 *aErrorCount, wxString::Format(
_(
"%s value cannot be greater than %s value." ),
442 aMinLabel, aMaxLabel ) );
449 aMinTextCtrl->SetName(
"text" );
450 aMaxTextCtrl->SetName(
"text" );
457 wxTextCtrl* aMaxTextCtrl,
const wxString& aMinLabel,
458 const wxString& aPreferredLabel,
const wxString& aMaxLabel,
459 int* aErrorCount, wxString* aValidationMessage )
461 aMinTextCtrl->SetName(
"min" );
462 aPreferredTextCtrl->SetName(
"preferred" );
463 aMaxTextCtrl->SetName(
"max" );
467 if( !aMinTextCtrl->Validate() )
478 *aErrorCount, wxString::Format(
_(
"%s value cannot be greater than %s value." ),
479 aMinLabel, aPreferredLabel ) );
486 *aErrorCount, wxString::Format(
_(
"%s value cannot be greater than %s value." ),
487 aPreferredLabel, aMaxLabel ) );
494 *aErrorCount, wxString::Format(
_(
"%s value cannot be greater than %s value." ),
495 aMinLabel, aMaxLabel ) );
502 aMinTextCtrl->SetName(
"text" );
503 aPreferredTextCtrl->SetName(
"text" );
504 aMaxTextCtrl->SetName(
"text" );
511 int* aErrorCount, wxString* aValidationMessage )
515 aCheckboxes[0]->SetValidator( validator );
517 if( !aCheckboxes[0]->Validate() )
527 *aErrorCount, wxString::Format(
_(
"Please select at least one option from %s list." ), aLabel ));
540 return wxString::Format( wxS(
"%d. %s\n" ), aErrorCount, aErrorMessage );
549 if( !aCanBeZero && aValue <= 0.0 )
551 aResult->
AddError( wxString::Format(
_(
"The value of %s must be greater than 0." ), aLabel ) );
560 bool aIntegerOnly,
const wxString& aLabel,
563 if( aValueStr.IsEmpty() )
565 aResult->
AddError( wxString::Format(
_(
"%s should not be empty." ), aLabel ) );
573 std::string stdStr = aValueStr.ToStdString();
575 long intVal = std::stol( stdStr, &pos );
577 if( pos != stdStr.length() )
579 aResult->
AddError( wxString::Format(
_(
"The value of %s must be a valid integer." ), aLabel ) );
583 if( !aCanBeZero && intVal <= 0 )
585 aResult->
AddError( wxString::Format(
_(
"The value of %s must be greater than 0." ), aLabel ) );
591 std::string stdStr = aValueStr.ToStdString();
593 double floatVal = std::stod( stdStr, &pos );
595 if( pos != stdStr.length() )
597 aResult->
AddError( wxString::Format(
_(
"The value of %s must be a valid number." ), aLabel ) );
601 if( !aCanBeZero && floatVal <= 0.0 )
603 aResult->
AddError( wxString::Format(
_(
"The value of %s must be greater than 0." ), aLabel ) );
608 catch(
const std::exception& )
611 aResult->
AddError( wxString::Format(
_(
"The value of %s must be a valid integer." ), aLabel ) );
613 aResult->
AddError( wxString::Format(
_(
"The value of %s must be a valid number." ), aLabel ) );
627 aResult->
AddError( wxString::Format(
_(
"%s value cannot be greater than %s value." ), aMinLabel, aMaxLabel ));
636 const wxString& aMinLabel,
637 const wxString& aPrefLabel,
638 const wxString& aMaxLabel,
643 if( aMin > aPreferred )
645 aResult->
AddError( wxString::Format(
_(
"%s value cannot be greater than %s value." ), aMinLabel, aPrefLabel ));
649 if( aPreferred > aMax )
651 aResult->
AddError( wxString::Format(
_(
"%s value cannot be greater than %s value." ), aPrefLabel, aMaxLabel ));
657 aResult->
AddError( wxString::Format(
_(
"%s value cannot be greater than %s value." ), aMinLabel, aMaxLabel ));
666 const wxString& aLabel,
669 for(
bool selected : aSelected )
675 aResult->
AddError( wxString::Format(
_(
"Please select at least one option from %s list." ), aLabel ) );
683 if( aSelectionIndex < 0 )
685 aResult->
AddError( wxString::Format(
_(
"Please choose %s." ), aLabel ) );
697 std::vector<std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA>> rules;
698 std::vector<std::shared_ptr<DRC_RULE>> parsedRules;
700 wxString rulesText = aRules;
701 if( !rulesText.Contains(
"(version" ) )
702 rulesText.Prepend(
"(version 1)\n" );
707 parser.
Parse( parsedRules,
nullptr );
713 for(
const auto& rule : parsedRules )
715 std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA> data;
719 data = converter( rule );
726 auto customData = std::make_shared<DRC_RE_CUSTOM_RULE_CONSTRAINT_DATA>( 0, 0, rule->m_Name );
727 customData->SetRuleText( wxString::Format(
"(rule \"%s\" ...)", rule->m_Name ) );
731 if( rule->m_Condition )
732 data->SetRuleCondition( rule->m_Condition->GetExpression() );
734 rules.push_back( data );
741 const std::vector<std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA>>& aRules,
742 const BOARD* aBoard )
744 wxFFile file( aFilename,
"w" );
746 if( !file.IsOpened() )
749 file.Write(
"(version 1)\n" );
751 for(
const auto& data : aRules )
758 ctx.
comment = data->GetComment();
762 std::vector<PCB_LAYER_ID> layers = data->GetLayers();
764 if( !layers.empty() && aBoard )
766 wxString layerStr =
"(layer";
769 layerStr +=
" \"" + aBoard->
GetLayerName( layer ) +
"\"";
775 wxString ruleText = data->GenerateRule( ctx );
776 file.Write( ruleText +
"\n" );
789 switch( aConstraintType )
855 switch( aConstraintType )
858 return wxString::Format( wxS(
"(layer \"%s\")" ),
859 aIsTop ? wxS(
"F.CrtYd" ) : wxS(
"B.CrtYd" ) );
863 return wxString::Format( wxS(
"(condition \"A.Layer == '%s' && B.Layer == '%s'\")" ),
864 aIsTop ? wxS(
"F.SilkS" ) : wxS(
"B.SilkS" ),
865 aIsTop ? wxS(
"F.Mask" ) : wxS(
"B.Mask" ) );
869 return wxString::Format( wxS(
"(layer \"%s\")" ), aIsTop ? wxS(
"F.Cu" ) : wxS(
"B.Cu" ) );
872 return wxEmptyString;
877std::shared_ptr<DRC_RE_NUMERIC_INPUT_CONSTRAINT_DATA>
884 case COURTYARD_CLEARANCE:
return std::make_shared<DRC_RE_COURTYARD_CLEARANCE_CONSTRAINT_DATA>();
885 case PHYSICAL_CLEARANCE:
return std::make_shared<DRC_RE_PHYSICAL_CLEARANCE_CONSTRAINT_DATA>();
886 case CREEPAGE_DISTANCE:
return std::make_shared<DRC_RE_CREEPAGE_DISTANCE_CONSTRAINT_DATA>();
887 case HOLE_SIZE:
return std::make_shared<DRC_RE_HOLE_SIZE_CONSTRAINT_DATA>();
891 case MAXIMUM_VIA_COUNT:
return std::make_shared<DRC_RE_MAXIMUM_VIA_COUNT_CONSTRAINT_DATA>();
892 case MINIMUM_ANGULAR_RING:
return std::make_shared<DRC_RE_MINIMUM_ANGULAR_RING_CONSTRAINT_DATA>();
894 case MINIMUM_CLEARANCE:
return std::make_shared<DRC_RE_MINIMUM_CLEARANCE_CONSTRAINT_DATA>();
898 case MINIMUM_THROUGH_HOLE:
return std::make_shared<DRC_RE_MINIMUM_THROUGH_HOLE_CONSTRAINT_DATA>();
900 case MINIMUM_UVIA_HOLE:
return std::make_shared<DRC_RE_MINIMUM_UVIA_HOLE_CONSTRAINT_DATA>();
901 case MINIMUM_VIA_DIAMETER:
return std::make_shared<DRC_RE_MINIMUM_VIA_DIAMETER_CONSTRAINT_DATA>();
904 case SOLDERMASK_EXPANSION:
return std::make_shared<DRC_RE_SOLDERMASK_EXPANSION_CONSTRAINT_DATA>();
906 default:
return std::make_shared<DRC_RE_NUMERIC_INPUT_CONSTRAINT_DATA>();
911std::shared_ptr<DRC_RE_NUMERIC_INPUT_CONSTRAINT_DATA>
919 case COURTYARD_CLEARANCE:
return std::make_shared<DRC_RE_COURTYARD_CLEARANCE_CONSTRAINT_DATA>( aBase );
920 case PHYSICAL_CLEARANCE:
return std::make_shared<DRC_RE_PHYSICAL_CLEARANCE_CONSTRAINT_DATA>( aBase );
921 case CREEPAGE_DISTANCE:
return std::make_shared<DRC_RE_CREEPAGE_DISTANCE_CONSTRAINT_DATA>( aBase );
922 case HOLE_SIZE:
return std::make_shared<DRC_RE_HOLE_SIZE_CONSTRAINT_DATA>( aBase );
923 case HOLE_TO_HOLE_CLEARANCE:
return std::make_shared<DRC_RE_HOLE_TO_HOLE_CLEARANCE_CONSTRAINT_DATA>( aBase );
924 case HOLE_TO_HOLE_DISTANCE:
return std::make_shared<DRC_RE_HOLE_TO_HOLE_DISTANCE_CONSTRAINT_DATA>( aBase );
926 case MAXIMUM_VIA_COUNT:
return std::make_shared<DRC_RE_MAXIMUM_VIA_COUNT_CONSTRAINT_DATA>( aBase );
927 case MINIMUM_ANGULAR_RING:
return std::make_shared<DRC_RE_MINIMUM_ANGULAR_RING_CONSTRAINT_DATA>( aBase );
928 case MINIMUM_ANNULAR_WIDTH:
return std::make_shared<DRC_RE_MINIMUM_ANNULAR_WIDTH_CONSTRAINT_DATA>( aBase );
929 case MINIMUM_CLEARANCE:
return std::make_shared<DRC_RE_MINIMUM_CLEARANCE_CONSTRAINT_DATA>( aBase );
933 case MINIMUM_THROUGH_HOLE:
return std::make_shared<DRC_RE_MINIMUM_THROUGH_HOLE_CONSTRAINT_DATA>( aBase );
934 case MINIMUM_UVIA_DIAMETER:
return std::make_shared<DRC_RE_MINIMUM_UVIA_DIAMETER_CONSTRAINT_DATA>( aBase );
935 case MINIMUM_UVIA_HOLE:
return std::make_shared<DRC_RE_MINIMUM_UVIA_HOLE_CONSTRAINT_DATA>( aBase );
936 case MINIMUM_VIA_DIAMETER:
return std::make_shared<DRC_RE_MINIMUM_VIA_DIAMETER_CONSTRAINT_DATA>( aBase );
937 case SILK_TO_SILK_CLEARANCE:
return std::make_shared<DRC_RE_SILK_TO_SILK_CLEARANCE_CONSTRAINT_DATA>( aBase );
939 case SOLDERMASK_EXPANSION:
return std::make_shared<DRC_RE_SOLDERMASK_EXPANSION_CONSTRAINT_DATA>( aBase );
940 case SOLDERPASTE_EXPANSION:
return std::make_shared<DRC_RE_SOLDERPASTE_EXPANSION_CONSTRAINT_DATA>( aBase );
941 default:
return std::make_shared<DRC_RE_NUMERIC_INPUT_CONSTRAINT_DATA>( aBase );
Information pertinent to a Pcbnew printed circuit board.
const wxString GetLayerName(PCB_LAYER_ID aLayer) const
Return the name of a aLayer.
void SetConstraintCode(wxString aCode)
void Parse(std::vector< std::shared_ptr< DRC_RULE > > &aRules, REPORTER *aReporter)
static bool IsNumericInputType(const DRC_RULE_EDITOR_CONSTRAINT_NAME &aConstraintType)
static wxString ConstraintToKicadDrc(DRC_RULE_EDITOR_CONSTRAINT_NAME aType)
Convert a constraint type into the keyword used in a .kicad_drc file.
static bool ValidateNumericValue(double aValue, bool aCanBeZero, const wxString &aLabel, VALIDATION_RESULT *aResult)
Validates a numeric value.
static bool ValidateAtLeastOneSelected(const std::vector< bool > &aSelected, const wxString &aLabel, VALIDATION_RESULT *aResult)
Validates that at least one option is selected.
static bool ValidateSelection(int aSelectionIndex, const wxString &aLabel, VALIDATION_RESULT *aResult)
Validates that a selection has been made (index >= 0).
static wxString GetConstraintCode(DRC_RULE_EDITOR_CONSTRAINT_NAME aConstraintType)
Translate a rule tree node type into the keyword used by the rules file for that constraint.
static bool ValidateNumericCtrl(wxTextCtrl *aTextCtrl, const wxString &aLabel, bool aCanBeZero, int *aErrorCount, wxString *aValidationMessage)
Validates a numeric input control, checking if the value is valid, non-empty, and greater than zero.
static bool ValidateMinMax(double aMin, double aMax, const wxString &aMinLabel, const wxString &aMaxLabel, VALIDATION_RESULT *aResult)
Validates that min <= max.
static bool ConstraintFromKicadDrc(const wxString &aCode, DRC_RE_BASE_CONSTRAINT_DATA *aData)
Populate a constraint data object using a keyword from a .kicad_drc file.
static bool ValidateMinPreferredMaxCtrl(wxTextCtrl *aMinTextCtrl, wxTextCtrl *aPreferredTextCtrl, wxTextCtrl *aMaxTextCtrl, const wxString &aMinLabel, const wxString &aPreferredLabel, const wxString &aMaxLabel, int *aErrorCount, wxString *aValidationMessage)
Validates the minimum, preferred, and maximum value controls, ensuring that:
static wxString FormatErrorMessage(int aErrorCount, const wxString &aErrorMessage)
static std::optional< DRC_RULE_EDITOR_CONSTRAINT_NAME > GetConstraintTypeFromCode(const wxString &aCode)
Resolve a constraint keyword from a rules file into the corresponding rule tree enumeration value.
static bool ValidateComboCtrl(wxComboBox *aComboBox, const wxString &aLabel, int *aErrorCount, wxString *aValidationMessage)
Validates a combo box control, ensuring that a selection has been made.
static bool SaveRules(const wxString &aFilename, const std::vector< std::shared_ptr< DRC_RE_BASE_CONSTRAINT_DATA > > &aRules, const BOARD *aBoard)
static void RegisterRuleConverter(RuleConverter aConverter)
static wxString TranslateTopBottomLayer(DRC_RULE_EDITOR_CONSTRAINT_NAME aConstraintType, bool aIsTop)
Translate a top/bottom selection to the appropriate layer clause or condition.
static bool ValidateCheckBoxCtrls(const std::vector< wxCheckBox * > &aCheckboxes, const wxString &aLabel, int *aErrorCount, wxString *aValidationMessage)
Validates a list of checkboxes, ensuring that at least one option is selected.
static bool ValidateNumericString(const wxString &aValueStr, bool aCanBeZero, bool aIntegerOnly, const wxString &aLabel, VALIDATION_RESULT *aResult)
Validates that a string represents a valid numeric value.
static bool ValidateMinMaxCtrl(wxTextCtrl *aMinTextCtrl, wxTextCtrl *aMaxTextCtrl, const wxString &aMinLabel, const wxString &aMaxLabel, int *aErrorCount, wxString *aValidationMessage)
Validates the minimum and maximum value controls, ensuring that the minimum value is not greater than...
std::function< std::shared_ptr< DRC_RE_BASE_CONSTRAINT_DATA >(const std::shared_ptr< DRC_RULE > &)> RuleConverter
static std::shared_ptr< DRC_RE_NUMERIC_INPUT_CONSTRAINT_DATA > CreateNumericConstraintData(DRC_RULE_EDITOR_CONSTRAINT_NAME aType)
static DRC_LAYER_CATEGORY GetLayerCategoryForConstraint(DRC_RULE_EDITOR_CONSTRAINT_NAME aConstraintType)
Get the layer category for a constraint type.
static bool ValidateMinPreferredMax(double aMin, double aPreferred, double aMax, const wxString &aMinLabel, const wxString &aPrefLabel, const wxString &aMaxLabel, VALIDATION_RESULT *aResult)
Validates that min <= preferred <= max.
static bool ValidateIntegerCtrl(wxTextCtrl *aTextCtrl, const wxString &aLabel, bool aCanBeZero, int *aErrorCount, wxString *aValidationMessage)
Validates an integer input control, ensuring the value is a valid integer, non-empty,...
static bool IsBoolInputType(const DRC_RULE_EDITOR_CONSTRAINT_NAME &aConstraintType)
static std::vector< std::shared_ptr< DRC_RE_BASE_CONSTRAINT_DATA > > ParseRules(const wxString &aRules)
Hold an error message and may be used when throwing exceptions containing meaningful error messages.
VALIDATION_STATE GetValidationState() const
VALIDATION_STATE GetValidationState() const
VALIDATION_STATE GetValidationState() const
@ PreferredGreaterThanMax
@ MinGreaterThanPreferred
VALIDATION_STATE GetValidationState() const
VALIDATION_STATE GetValidationState() const
@ ANNULAR_WIDTH_CONSTRAINT
@ BRIDGED_MASK_CONSTRAINT
@ COURTYARD_CLEARANCE_CONSTRAINT
@ VIA_DIAMETER_CONSTRAINT
@ ZONE_CONNECTION_CONSTRAINT
@ DIFF_PAIR_GAP_CONSTRAINT
@ VIA_DANGLING_CONSTRAINT
@ SOLDER_MASK_SLIVER_CONSTRAINT
@ SILK_CLEARANCE_CONSTRAINT
@ EDGE_CLEARANCE_CONSTRAINT
@ MIN_RESOLVED_SPOKES_CONSTRAINT
@ TRACK_SEGMENT_LENGTH_CONSTRAINT
@ TEXT_THICKNESS_CONSTRAINT
@ PHYSICAL_HOLE_CLEARANCE_CONSTRAINT
@ THERMAL_SPOKE_WIDTH_CONSTRAINT
@ CONNECTION_WIDTH_CONSTRAINT
@ THERMAL_RELIEF_GAP_CONSTRAINT
@ MAX_UNCOUPLED_CONSTRAINT
@ HOLE_CLEARANCE_CONSTRAINT
@ SOLDER_PASTE_ABS_MARGIN_CONSTRAINT
@ SOLDER_MASK_EXPANSION_CONSTRAINT
@ PHYSICAL_CLEARANCE_CONSTRAINT
@ SOLDER_PASTE_REL_MARGIN_CONSTRAINT
@ HOLE_TO_HOLE_CONSTRAINT
DRC_RULE_EDITOR_CONSTRAINT_NAME
@ MINIMUM_SOLDERMASK_SILVER
@ SILK_TO_SOLDERMASK_CLEARANCE
@ MINIMUM_CONNECTION_WIDTH
@ MINIMUM_THERMAL_RELIEF_SPOKE_COUNT
@ MINIMUM_TEXT_HEIGHT_AND_THICKNESS
@ COPPER_TO_HOLE_CLEARANCE
@ MAXIMUM_ALLOWED_DEVIATION
@ MATCHED_LENGTH_DIFF_PAIR
@ COPPER_TO_EDGE_CLEARANCE
DRC_LAYER_CATEGORY
Layer categories for filtering the layer selector dropdown.
@ NO_LAYER_SELECTOR
Hide layer selector entirely.
@ TOP_BOTTOM_ANY
Simplified top/bottom/any selector with custom translation.
@ SOLDERMASK_ONLY
F_Mask, B_Mask.
@ GENERAL_ANY_LAYER
All layers + inner/outer synthetic.
@ SOLDERPASTE_ONLY
F_Paste, B_Paste.
@ COPPER_ONLY
Copper layers + inner/outer synthetic.
@ SILKSCREEN_ONLY
F_SilkS, B_SilkS.
static wxString GetConstraintCodeFromType(DRC_CONSTRAINT_T aType)
std::unordered_map< DRC_RULE_EDITOR_CONSTRAINT_NAME, const char * > CODE_MAP
static void RegisterDefaultConverters()
static const CODE_MAP sCodeMap
static const REVERSE_CODE_MAP sCodeReverse
std::unordered_map< wxString, DRC_RULE_EDITOR_CONSTRAINT_NAME, wxStringHash, wxStringEqual > REVERSE_CODE_MAP
static std::vector< DRC_RULE_EDITOR_UTILS::RuleConverter > & GetRuleConverters()
PCB_LAYER_ID
A quick note on layer IDs:
wxString conditionExpression
Result of a validation operation.
void AddError(const wxString &aError)