42#include <idf_parser.h>
44#include <wx/stc/stc.h>
78 switch( aConstraintType )
89 default:
return false;
95 wxString* aConstraintTitle,
96 std::shared_ptr<DRC_RE_BASE_CONSTRAINT_DATA> aConstraintData ) :
124 wxBoxSizer* buttonSizer =
new wxBoxSizer( wxHORIZONTAL );
128 bContentSizer->Add( buttonSizer, 0, wxALIGN_RIGHT | wxALL, 2 );
139 [
this]( wxKeyEvent& aEvent )
144 [
this]( wxStyledTextEvent& aEvent )
171 m_netNameRegex.Compile(
"^NetName\\s*[!=]=\\s*$", wxRE_ADVANCED );
172 m_typeRegex.Compile(
"^Type\\s*[!=]=\\s*$", wxRE_ADVANCED );
173 m_viaTypeRegex.Compile(
"^Via_Type\\s*[!=]=\\s*$", wxRE_ADVANCED );
174 m_padTypeRegex.Compile(
"^Pad_Type\\s*[!=]=\\s*$", wxRE_ADVANCED );
175 m_pinTypeRegex.Compile(
"^Pin_Type\\s*[!=]=\\s*$", wxRE_ADVANCED );
176 m_fabPropRegex.Compile(
"^Fabrication_Property\\s*[!=]=\\s*$", wxRE_ADVANCED );
177 m_shapeRegex.Compile(
"^Shape\\s*[!=]=\\s*$", wxRE_ADVANCED );
182 m_hJustRegex.Compile(
"^Horizontal_Justification\\s*[!=]=\\s*$", wxRE_ADVANCED );
183 m_vJustRegex.Compile(
"^Vertical_Justification\\s*[!=]=\\s*$", wxRE_ADVANCED );
246 switch( aConstraintType )
250 dynamic_pointer_cast<DRC_RE_VIA_STYLE_CONSTRAINT_DATA>(
m_constraintData ) );
254 dynamic_pointer_cast<DRC_RE_MINIMUM_TEXT_HEIGHT_THICKNESS_CONSTRAINT_DATA>(
m_constraintData ) );
258 dynamic_pointer_cast<DRC_RE_ROUTING_DIFF_PAIR_CONSTRAINT_DATA>(
m_constraintData ) );
262 dynamic_pointer_cast<DRC_RE_ROUTING_WIDTH_CONSTRAINT_DATA>(
m_constraintData ) );
266 dynamic_pointer_cast<DRC_RE_PERMITTED_LAYERS_CONSTRAINT_DATA>(
m_constraintData ) );
270 dynamic_pointer_cast<DRC_RE_ALLOWED_ORIENTATION_CONSTRAINT_DATA>(
m_constraintData ) );
273 aParent, dynamic_pointer_cast<DRC_RE_CUSTOM_RULE_CONSTRAINT_DATA>(
m_constraintData ) );
277 dynamic_pointer_cast<DRC_RE_ABSOLUTE_LENGTH_TWO_CONSTRAINT_DATA>(
m_constraintData ) );
292 wxString customLabel;
294 switch( aConstraintType )
296 case VIAS_UNDER_SMD: customLabel =
"Allow Vias under SMD Pads";
break;
302 aConstraintType, customLabel );
396 if( aEvent.GetModifiers() == wxMOD_CONTROL && aEvent.GetKey() ==
' ' )
412 if( beginning.StartsWith( wxT(
"(condition " ) ) )
414 startPos = lineStart;
419 enum class EXPR_CONTEXT_T :
int
429 std::stack<wxString> sexprs;
432 wxString constraintType;
433 EXPR_CONTEXT_T context = EXPR_CONTEXT_T::NONE;
434 EXPR_CONTEXT_T expr_context = EXPR_CONTEXT_T::NONE;
436 for(
int i = startPos; i < currentPos; ++i )
444 else if( context == EXPR_CONTEXT_T::STRING )
448 context = EXPR_CONTEXT_T::NONE;
452 if( expr_context == EXPR_CONTEXT_T::STRING )
455 expr_context = EXPR_CONTEXT_T::NONE;
462 partial = wxEmptyString;
463 expr_context = EXPR_CONTEXT_T::STRING;
467 partial = wxEmptyString;
468 expr_context = EXPR_CONTEXT_T::STRUCT_REF;
479 partial = wxEmptyString;
480 context = EXPR_CONTEXT_T::STRING;
484 if( context == EXPR_CONTEXT_T::SEXPR_OPEN && !partial.IsEmpty() )
487 sexprs.push( partial );
490 partial = wxEmptyString;
491 context = EXPR_CONTEXT_T::SEXPR_OPEN;
495 context = EXPR_CONTEXT_T::NONE;
499 if( context == EXPR_CONTEXT_T::SEXPR_OPEN && !partial.IsEmpty() )
502 sexprs.push( partial );
504 if( partial == wxT(
"condition" ) )
506 context = EXPR_CONTEXT_T::SEXPR_STRING;
510 context = EXPR_CONTEXT_T::NONE;
513 partial = wxEmptyString;
517 context = EXPR_CONTEXT_T::NONE;
527 if( context == EXPR_CONTEXT_T::SEXPR_OPEN )
531 tokens = wxT(
"condition" );
534 else if( context == EXPR_CONTEXT_T::SEXPR_TOKEN )
541 else if( context == EXPR_CONTEXT_T::SEXPR_STRING && !sexprs.empty() && sexprs.top() == wxT(
"condition" ) )
545 else if( context == EXPR_CONTEXT_T::STRING && !sexprs.empty() && sexprs.top() == wxT(
"condition" ) )
547 if( expr_context == EXPR_CONTEXT_T::STRUCT_REF )
550 std::set<wxString> propNames;
554 const std::vector<PROPERTY_BASE*>& props = propMgr.
GetProperties( cls.type );
561 if( prop->IsHiddenFromRulesEditor() )
564 wxString ref( prop->Name() );
565 ref.Replace( wxT(
" " ), wxT(
"_" ) );
566 propNames.insert( ref );
570 for(
const wxString& propName : propNames )
571 tokens += wxT(
"|" ) + propName;
577 if( !funcSig.Contains(
"DEPRECATED" ) )
578 tokens += wxT(
"|" ) + funcSig;
581 else if( expr_context == EXPR_CONTEXT_T::STRING )
586 std::shared_ptr<NET_SETTINGS>& netSettings = bds.
m_NetSettings;
588 for(
const auto& [
name, netclass] : netSettings->GetNetclasses() )
589 tokens += wxT(
"|" ) +
name;
593 for(
const wxString& netnameCandidate :
m_board->GetNetClassAssignmentCandidates() )
594 tokens += wxT(
"|" ) + netnameCandidate;
598 tokens = wxT(
"Bitmap|"
614 tokens = wxT(
"Through|"
620 tokens = wxT(
"Through-hole|"
623 "NPTH, mechanical" );
627 tokens = wxT(
"Input|"
642 tokens = wxT(
"None|"
644 "Fiducial, global to board|"
645 "Fiducial, local to footprint|"
652 tokens = wxT(
"Segment|"
661 tokens = wxT(
"Circle|"
666 "Chamfered rectangle|"
671 tokens = wxT(
"Inherited|"
675 "Thermal reliefs for PTH" );
679 tokens = wxT(
"Inherited|"
686 tokens = wxT(
"Default|"
695 tokens = wxT(
"Left|"
708 if( !tokens.IsEmpty() )
721 std::vector<wxString> msg;
727 msg.emplace_back( t );
732 msg.emplace_back( t );
737 msg.emplace_back( t );
742 msg.emplace_back( t );
747 msg.emplace_back( t );
752 msg.emplace_back( t );
757 msg.emplace_back( t );
762 msg.emplace_back( t );
765 wxString msg_txt = wxEmptyString;
767 for( wxString i : msg )
768 msg_txt << wxGetTranslation( i );
771 msg_txt.Replace( wxT(
"Ctrl+" ), wxT(
"Cmd+" ) );
773 const wxString& msGg_txt = msg_txt;
778 wxString html_txt = wxEmptyString;
781 html_txt.Replace( wxS(
"<td" ), wxS(
"<td valign=top" ) );
795 if( condition.IsEmpty() )
797 wxString msg =
_(
"ERROR: No condition text provided for validation." );
805 std::vector<std::shared_ptr<DRC_RULE>> dummyRules;
806 wxString ruleTemplate =
L"(version 1)\n(rule default\n (condition \"%s\")\n)";
807 wxString formattedRule = wxString::Format( ruleTemplate, condition );
813 wxString msg = wxString::Format( wxT(
"%s <a href='%d:%d'>%s</a>" ),
826 wxString link =
event.GetLinkInfo().GetHref();
828 long line = 0, offset = 0;
832 if( parts.size() > 1 )
834 parts[0].ToLong( &line );
835 parts[1].ToLong( &offset );
850 menu.Append( wxID_UNDO,
_(
"Undo" ) );
851 menu.Append( wxID_REDO,
_(
"Redo" ) );
853 menu.AppendSeparator();
855 menu.Append( 1,
_(
"Cut" ) );
856 menu.Append( 2,
_(
"Copy" ) );
857 menu.Append( 3,
_(
"Paste" ) );
858 menu.Append( 4,
_(
"Delete" ) );
860 menu.AppendSeparator();
862 menu.Append( 5,
_(
"Select All" ) );
864 menu.AppendSeparator();
866 menu.Append( wxID_ZOOM_IN,
_(
"Zoom In" ) );
867 menu.Append( wxID_ZOOM_OUT,
_(
"Zoom Out" ) );
870 switch( GetPopupMenuSelectionFromUser( menu ) )
906 wxS(
"Show Matches clicked: nodeId=%d, rule='%s', code='%s'" ),
920 m_btnShowMatches->SetLabel( wxString::Format(
_(
"Show Matches (%d)" ), matchCount ) );
934 return wxEmptyString;
939 return wxEmptyString;
941 size_t index =
static_cast<size_t>( selection - 1 );
944 return wxEmptyString;
947 wxString clause = wxString::Format( wxS(
"(layer %s)" ),
m_board->GetLayerName( layerId ) );
964 if( aLayers.empty() )
972 for(
size_t i = 0; i <
m_layerIDs.size(); ++i )
wxBitmapBundle KiBitmapBundle(BITMAPS aBitmap, int aMinHeight)
Container for design settings for a BOARD object.
std::shared_ptr< NET_SETTINGS > m_NetSettings
Information pertinent to a Pcbnew printed circuit board.
Container panel that manages multiple condition rows with boolean operators.
Simple panel used for editing custom rule text.
void Parse(std::vector< std::shared_ptr< DRC_RULE > > &aRules, REPORTER *aReporter)
static bool IsNumericInputType(const DRC_RULE_EDITOR_CONSTRAINT_NAME &aConstraintType)
static std::string FormatErrorMessage(const int &aErrorCount, const std::string aErrorMessage)
static bool IsBoolInputType(const DRC_RULE_EDITOR_CONSTRAINT_NAME &aConstraintType)
static PAGED_DIALOG * GetDialog(wxWindow *aWindow)
wxBoxSizer * m_conditionControlsSizer
wxBoxSizer * bContentSizer
PANEL_DRC_RULE_EDITOR_BASE(wxWindow *parent, wxWindowID id=wxID_ANY, const wxPoint &pos=wxDefaultPosition, const wxSize &size=wxSize(-1,-1), long style=wxTAB_TRAVERSAL, const wxString &name=wxEmptyString)
wxStaticText * m_constraintHeaderTitle
wxTextCtrl * m_commentCtrl
wxBoxSizer * m_LayersComboBoxSizer
WX_HTML_REPORT_BOX * m_syntaxErrorReport
wxBoxSizer * m_constraintContentSizer
wxBitmapButton * m_checkSyntaxBtnCtrl
wxStyledTextCtrl * m_textConditionCtrl
std::shared_ptr< DRC_RE_BASE_CONSTRAINT_DATA > m_constraintData
void onCloseButtonClicked(wxCommandEvent &aEvent)
Handles the close button click event, invoking the close callback.
wxString GenerateRule(const RULE_GENERATION_CONTEXT &aContext) override
void ResetShowMatchesButton()
PANEL_DRC_RULE_EDITOR(wxWindow *aParent, BOARD *aBoard, DRC_RULE_EDITOR_CONSTRAINT_NAME aConstraintType, wxString *aConstraintTitle, std::shared_ptr< DRC_RE_BASE_CONSTRAINT_DATA > aConstraintData)
void onScintillaCharAdded(wxStyledTextEvent &aEvent)
Handles character addition in the Scintilla text control, performing auto-complete and context-sensit...
void onShowMatchesButtonClicked(wxCommandEvent &aEvent)
void onCheckSyntax(wxCommandEvent &aEvent) override
Checks the syntax of the DRC rule condition and reports any errors.
std::function< void(int aNodeId)> m_callBackSave
HTML_MESSAGE_BOX * m_helpWindow
bool ValidateInputs(int *aErrorCount, std::string *aValidationMessage) override
void onContextMenu(wxMouseEvent &aEvent) override
Handles right-click context menu actions for text editing (undo, redo, cut, copy, paste,...
bool TransferDataFromWindow() override
void onRemoveButtonClicked(wxCommandEvent &aEvent)
Handles the remove button click event, invoking the remove callback.
wxString * m_constraintTitle
wxButton * m_btnShowMatches
std::function< bool(int aNodeId, wxString aRuleName)> m_callBackRuleNameValidation
void onSyntaxHelp(wxHyperlinkEvent &aEvent) override
Displays a modeless help window with syntax and rule documentation.
~PANEL_DRC_RULE_EDITOR() override
wxChoice * m_layerListChoiceCtrl
wxRegEx m_zoneConnStyleRegex
void Cancel(wxCommandEvent &aEvent)
wxRegEx m_padConnectionsRegex
bool m_validationSucceeded
void onErrorLinkClicked(wxHtmlLinkEvent &aEvent) override
Handles clicks on error links in the syntax error report and navigates to the error location.
std::function< void(int aNodeId)> m_callBackRemove
std::function< int(int aNodeId)> m_callBackShowMatches
bool TransferDataToWindow() override
DRC_RE_CONDITION_GROUP_PANEL * m_conditionGroupPanel
std::unique_ptr< SCINTILLA_TRICKS > m_scintillaTricks
void Save(wxCommandEvent &aEvent)
std::vector< PCB_LAYER_ID > m_layerIDs
void onSaveButtonClicked(wxCommandEvent &aEvent)
Handles the save button click event, validating inputs and invoking the save callback if valid.
DRC_RULE_EDITOR_CONTENT_PANEL_BASE * getConstraintPanel(wxWindow *aParent, const DRC_RULE_EDITOR_CONSTRAINT_NAME &aConstraintType)
void setSelectedLayers(const std::vector< PCB_LAYER_ID > &aLayers)
std::vector< PCB_LAYER_ID > getSelectedLayers()
wxString buildLayerClause() const
std::function< void(int aNodeId)> m_callBackClose
std::string m_validationMessage
DRC_RULE_EDITOR_CONTENT_PANEL_BASE * m_constraintPanel
const wxArrayString GetSignatures() const
static PCBEXPR_BUILTIN_FUNCTIONS & Instance()
Provide class metadata.Helper macro to map type hashes to names.
const std::vector< PROPERTY_BASE * > & GetProperties(TYPE_ID aType) const
Return all properties for a specific type.
CLASSES_INFO GetAllClasses()
static PROPERTY_MANAGER & Instance()
This file is part of the common library.
DRC_RULE_EDITOR_CONSTRAINT_NAME
@ BOARD_OUTLINE_CLEARANCE
@ MINIMUM_THERMAL_RELIEF_SPOKE_COUNT
@ MINIMUM_TEXT_HEIGHT_AND_THICKNESS
@ COPPER_TO_HOLE_CLEARANCE
PCB_LAYER_ID
A quick note on layer IDs:
static bool constraintNeedsTwoObjects(DRC_RULE_EDITOR_CONSTRAINT_NAME aConstraintType)
static constexpr const wxChar * KI_TRACE_DRC_RULE_EDITOR
void wxStringSplit(const wxString &aText, wxArrayString &aStrings, wxChar aSplitter)
Split aString to a string list separated at aSplitter.
void ConvertMarkdown2Html(const wxString &aMarkdownInput, wxString &aHtmlOutput)
A filename or source description, a problem input line, a line number, a byte offset,...
int lineNumber
at which line number, 1 based index.
const wxString ParseProblem()
int byteIndex
at which byte offset within the line, 1 based index
wxString conditionExpression