62 wxLogWarning( wxT(
"Attempting to call fromTo() with non-existent from-to cache, " 67 if( ftCache->IsOnFromToPath( static_cast<BOARD_CONNECTED_ITEM*>( item ),
96 wxT(
"existsOnLayer()" ) ) );
103 [item, arg, aCtx]() ->
double 105 const wxString& layerName = arg->
AsString();
114 bool anyMatch =
false;
116 for(
unsigned ii = 0; ii < layerMap.GetCount(); ++ii )
118 wxPGChoiceEntry& entry = layerMap[ ii ];
120 if( entry.GetText().Matches( layerName ))
142 std::unique_lock<std::mutex> cacheLock( board->
m_CachesMutex );
148 for(
unsigned ii = 0; ii < layerMap.GetCount(); ++ii )
150 wxPGChoiceEntry& entry = layerMap[ ii ];
152 if( entry.GetText().Matches( layerName ) )
177 aCtx->
Push( result );
206 return footprintCourtyard.
Collide( aItemShape.get() );
218 std::unique_lock<std::mutex> cacheLock( board->
m_CachesMutex );
219 std::pair<BOARD_ITEM*, BOARD_ITEM*> key( aFootprint, aItem );
221 std::map< std::pair<BOARD_ITEM*, BOARD_ITEM*>,
bool >* cache;
230 auto i = cache->find( key );
232 if( i != cache->end() )
237 (*cache)[ key ] = res;
249 aCtx->
Push( result );
256 wxT(
"insideCourtyard()" ) ) );
269 [item, arg, context]() ->
double 273 std::shared_ptr<SHAPE> itemShape;
276 itemBBox = static_cast<ZONE*>( item )->GetCachedBoundingBox();
287 else if( arg->
AsString() == wxT(
"B" ) )
296 if( fp->GetReference().Matches( arg->
AsString() ) )
315 aCtx->
Push( result );
322 wxT(
"insideFrontCourtyard()" ) ) );
335 [item, arg, context]() ->
double 339 std::shared_ptr<SHAPE> itemShape;
342 itemBBox = static_cast<ZONE*>( item )->GetCachedBoundingBox();
353 else if( arg->
AsString() == wxT(
"B" ) )
362 if( fp->GetReference().Matches( arg->
AsString() ) )
381 aCtx->
Push( result );
388 wxT(
"insideBackCourtyard()" ) ) );
400 [item, arg, context]() ->
double 404 std::shared_ptr<SHAPE> itemShape;
407 itemBBox = static_cast<ZONE*>( item )->GetCachedBoundingBox();
418 else if( arg->
AsString() == wxT(
"B" ) )
427 if( fp->GetReference().Matches( arg->
AsString() ) )
444 std::shared_ptr<SHAPE> shape;
460 PAD*
pad = static_cast<PAD*>( aItem );
463 return areaOutline.
Collide( holeShape );
467 PCB_VIA*
via = static_cast<PCB_VIA*>( aItem );
472 if( overlap.count() > 0 )
475 return areaOutline.
Collide( &holeShape );
484 FOOTPRINT* footprint = static_cast<FOOTPRINT*>( aItem );
490 aCtx->
ReportError(
_(
"Footprint's courtyard is not a single, closed shape." ) );
503 aCtx->
ReportError(
_(
"Footprint has no front courtyard." ) );
520 aCtx->
ReportError(
_(
"Footprint has no back courtyard." ) );
535 ZONE* zone = static_cast<ZONE*>( aItem );
542 std::vector<SHAPE*> shapes;
568 return areaOutline.
Collide( shape.get() );
576 if( !aArea || aArea == aItem || aArea->
GetParent() == aItem )
580 std::unique_lock<std::mutex> cacheLock( board->
m_CachesMutex );
581 std::pair<BOARD_ITEM*, BOARD_ITEM*> key( aArea, aItem );
601 aCtx->
Push( result );
608 wxT(
"insideArea()" ) ) );
621 [item, arg, context]() ->
double 627 itemBBox = static_cast<ZONE*>( item )->GetCachedBoundingBox();
633 ZONE* zone = dynamic_cast<ZONE*>( context->
GetItem( 0 ) );
634 return isInsideArea( item, itemBBox, context, zone ) ? 1.0 : 0.0;
636 else if( arg->
AsString() == wxT(
"B" ) )
638 ZONE* zone = dynamic_cast<ZONE*>( context->
GetItem( 1 ) );
639 return isInsideArea( item, itemBBox, context, zone ) ? 1.0 : 0.0;
649 if( area->m_Uuid == target )
650 return isInsideArea( item, itemBBox, context, area ) ? 1.0 : 0.0;
655 for(
ZONE* area : footprint->Zones() )
659 if( area->m_Uuid == target )
660 return isInsideArea( item, itemBBox, context, area ) ? 1.0 : 0.0;
670 if( area->GetZoneName().Matches( arg->
AsString() ) )
680 for(
ZONE* area : footprint->Zones() )
683 if( area->GetZoneName().Matches( arg->
AsString() ) )
703 aCtx->
Push( result );
710 wxT(
"memberOf()" ) ) );
722 [item, arg]() ->
double 749 aCtx->
Push( result );
765 aCtx->
Push( result );
782 aCtx->
Push( result );
784 result->SetDeferredEval(
785 [a, b, context]() ->
double 805 return b && b->GetNetname() == coupledNet;
818 aCtx->
Push( result );
825 wxT(
"inDiffPair()" ) ) );
835 [item, argv]() ->
double 839 NETINFO_ITEM* netinfo = static_cast<BOARD_CONNECTED_ITEM*>( item )->GetNet();
843 wxString baseName, coupledNet;
848 if( baseName.Matches( arg ) )
851 if( baseName.EndsWith(
"_" ) && baseName.BeforeLast(
'_' ).Matches( arg ) )
887 wxASSERT( dynamic_cast<const PCB_EXPR_CONTEXT*>( aCtx ) );
909 const wxString& layerName = b->AsString();
910 BOARD* board = static_cast<PCB_EXPR_CONTEXT*>( aCtx )->
GetBoard();
911 std::unique_lock<std::mutex> cacheLock( board->
m_CachesMutex );
917 for(
unsigned ii = 0; ii < layerMap.GetCount(); ++ii )
919 wxPGChoiceEntry& entry = layerMap[ii];
921 if( entry.GetText().Matches( layerName ) )
972 str = item->
Get<wxString>( it->second );
977 const wxAny& any = item->
Get( it->second );
978 bool valid = any.GetAs<wxString>( &str );
998 return LIBEVAL::VALUE( static_cast<BOARD_CONNECTED_ITEM*>( item )->GetNetClassName() );
1012 return LIBEVAL::VALUE( static_cast<BOARD_CONNECTED_ITEM*>( item )->GetNetname() );
1033 return registry.
Get( aName.Lower() );
1038 const wxString& aField )
1041 std::unique_ptr<PCB_EXPR_VAR_REF> vref;
1045 if( aField.CmpNoCase( wxT(
"NetClass" ) ) == 0 )
1047 if( aVar == wxT(
"A" ) )
1048 return std::make_unique<PCB_EXPR_NETCLASS_REF>( 0 );
1049 else if( aVar == wxT(
"B" ) )
1050 return std::make_unique<PCB_EXPR_NETCLASS_REF>( 1 );
1054 else if( aField.CmpNoCase( wxT(
"NetName" ) ) == 0 )
1056 if( aVar == wxT(
"A" ) )
1057 return std::make_unique<PCB_EXPR_NETNAME_REF>( 0 );
1058 else if( aVar == wxT(
"B" ) )
1059 return std::make_unique<PCB_EXPR_NETNAME_REF>( 1 );
1063 else if( aField.CmpNoCase( wxT(
"Type" ) ) == 0 )
1065 if( aVar == wxT(
"A" ) )
1066 return std::make_unique<PCB_EXPR_TYPE_REF>( 0 );
1067 else if( aVar == wxT(
"B" ) )
1068 return std::make_unique<PCB_EXPR_TYPE_REF>( 1 );
1073 if( aVar == wxT(
"A" ) || aVar == wxT(
"AB" ) )
1074 vref = std::make_unique<PCB_EXPR_VAR_REF>( 0 );
1075 else if( aVar == wxT(
"B" ) )
1076 vref = std::make_unique<PCB_EXPR_VAR_REF>( 1 );
1077 else if( aVar == wxT(
"L" ) )
1078 vref = std::make_unique<PCB_EXPR_VAR_REF>( 2 );
1082 if( aField.length() == 0 )
1084 return std::move( vref );
1087 wxString field( aField );
1088 field.Replace( wxT(
"_" ), wxT(
" " ) );
1098 vref->AddAllowedClass( cls.type, prop );
1111 vref->SetIsEnum (
true );
1115 wxFAIL_MSG( wxT(
"PCB_EXPR_UCODE::createVarRef: Unknown property type." ) );
1124 return std::move( vref );
1146 static const std::vector<wxString> pcbUnits = { wxT(
"mil" ), wxT(
"mm" ), wxT(
"in" ) };
1153 return _(
"must be mm, in, or mil" );
1156 virtual double Convert(
const wxString& aString,
int unitId )
const override 1158 double v = wxAtof( aString );
PCB_GROUP * GetParentGroup() const
BOARD_ITEM * GetItem(int index) const
NETINFO_ITEM * FindNet(int aNetcode) const
Search for a net with the given netcode.
virtual bool HasChoices() const
Return true if this PROPERTY has a limited set of possible values.
static PROPERTY_MANAGER & Instance()
bool isInsideCourtyard(BOARD_ITEM *aItem, const EDA_RECT &aItemBBox, std::shared_ptr< SHAPE > &aItemShape, PCB_EXPR_CONTEXT *aCtx, FOOTPRINT *aFootprint, PCB_LAYER_ID aSide)
int OutlineCount() const
Return the number of vertices in a given outline/hole.
std::unique_ptr< UNIT_RESOLVER > m_unitResolver
std::map< std::pair< BOARD_ITEM *, BOARD_ITEM * >, bool > m_InsideCourtyardCache
void SetDeferredEval(std::function< double()> aLambda)
A base class for any item which can be embedded within the BOARD container class, and therefore insta...
bool calcIsInsideArea(BOARD_ITEM *aItem, const EDA_RECT &aItemBBox, PCB_EXPR_CONTEXT *aCtx, ZONE *aArea)
NETINFO_ITEM * GetNet() const
Return #NET_INFO object for a given item.
virtual LIBEVAL::FUNC_CALL_REF CreateFuncCall(const wxString &aName) override
A set of BOARD_ITEMs (i.e., without duplicates).
virtual ~PCB_UNIT_RESOLVER()
virtual bool EqualTo(LIBEVAL::CONTEXT *aCtx, const VALUE *b) const override
void RegisterFunc(const wxString &funcSignature, LIBEVAL::FUNC_CALL_REF funcPtr)
SHAPE_POLY_SET * Outline()
bool Contains(PCB_LAYER_ID aLayer)
See if the layer set contains a PCB layer.
LIBEVAL::FUNC_CALL_REF Get(const wxString &name)
virtual LSET GetLayerSet() const override
Return a std::bitset of all layers on which the item physically resides.
virtual size_t TypeHash() const =0
Return type-id of the property type.
static ENUM_MAP< T > & Instance()
static void isPlated(LIBEVAL::CONTEXT *aCtx, void *self)
bool exprFromTo(LIBEVAL::CONTEXT *aCtx, void *self)
class PAD, a pad in a footprint
static void inDiffPair(LIBEVAL::CONTEXT *aCtx, void *self)
static int MatchDpSuffix(const wxString &aNetName, wxString &aComplementNet, wxString &aBaseDpName)
Check if the given net is a diff pair, returning its polarity and complement if so.
static void insideFrontCourtyard(LIBEVAL::CONTEXT *aCtx, void *self)
virtual wxString GetSupportedUnitsMessage() const override
LSEQ Seq(const PCB_LAYER_ID *aWishListSequence, unsigned aCount) const
Return an LSEQ from the union of this LSET and a desired sequence.
A base class derived from BOARD_ITEM for items that can be connected and have a net,...
BOARD_DESIGN_SETTINGS & GetDesignSettings() const
static LSET FrontMask()
Return a mask holding all technical layers and the external CU layer on front side.
virtual std::shared_ptr< SHAPE > GetEffectiveShape(PCB_LAYER_ID aLayer=UNDEFINED_LAYER, FLASHING aFlash=FLASHING::DEFAULT) const
Some pad shapes can be complex (rounded/chamfered rectangle), even without considering custom shapes.
bool Compile(const wxString &aString, UCODE *aCode, CONTEXT *aPreflightContext)
bool isInsideArea(BOARD_ITEM *aItem, const EDA_RECT &aItemBBox, PCB_EXPR_CONTEXT *aCtx, ZONE *aArea)
std::map< wxString, LIBEVAL::FUNC_CALL_REF > m_funcs
PROPERTY_BASE * GetProperty(TYPE_ID aType, const wxString &aProperty) const
Return a property for a specific type.
void RegisterAllFunctions()
static LIB_SYMBOL * dummy()
Used to draw a dummy shape when a LIB_SYMBOL is not found in library.
PCB_EXPR_COMPILER m_compiler
LSET is a set of PCB_LAYER_IDs.
#define HOLE_PROXY
Indicates the BOARD_ITEM is a proxy for its hole.
VAR_TYPE_T GetType() const
std::function< void(CONTEXT *, void *)> FUNC_CALL_REF
virtual bool IsOnLayer(PCB_LAYER_ID aLayer) const
Test to see if this object is on the given layer.
const EDA_RECT GetBoundingBox() const override
static void isBlindBuriedVia(LIBEVAL::CONTEXT *aCtx, void *self)
LIBEVAL::VAR_TYPE_T m_type
Represent a set of closed polygons.
SHAPE_LINE_CHAIN & Outline(int aIndex)
static bool SniffTest(const wxString &aCandidate)
Returns true if a string has the correct formatting to be a KIID.
static void existsOnLayer(LIBEVAL::CONTEXT *aCtx, void *self)
FOOTPRINTS & Footprints()
wxAny Get(PROPERTY_BASE *aProperty)
virtual std::unique_ptr< LIBEVAL::VAR_REF > CreateVarRef(const wxString &aVar, const wxString &aField) override
std::shared_ptr< CONNECTIVITY_DATA > GetConnectivity() const
Return a list of missing connections between components/tracks.
void Deflate(int aAmount, int aCircleSegmentsCount, CORNER_STRATEGY aCornerStrategy=ROUND_ALL_CORNERS)
const wxString & GetNetname() const
bool calcIsInsideCourtyard(BOARD_ITEM *aItem, const EDA_RECT &aItemBBox, std::shared_ptr< SHAPE > &aItemShape, PCB_EXPR_CONTEXT *aCtx, FOOTPRINT *aFootprint, PCB_LAYER_ID aSide)
Handle a list of polygons defining a copper zone.
class ZONE, a copper pour area
PCB_LAYER_VALUE(PCB_LAYER_ID aLayer)
static void insideArea(LIBEVAL::CONTEXT *aCtx, void *self)
static void insideBackCourtyard(LIBEVAL::CONTEXT *aCtx, void *self)
EDA_ITEM_FLAGS GetFlags() const
class FOOTPRINT, a footprint
LIBEVAL::VALUE GetValue(LIBEVAL::CONTEXT *aCtx) override
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, const CPTREE &aTree)
Output a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
PCB_EXPR_BUILTIN_FUNCTIONS()
std::map< wxString, LSET > m_LayerExpressionCache
bool Collide(const SHAPE *aShape, int aClearance=0, int *aActual=nullptr, VECTOR2I *aLocation=nullptr) const override
Check if the boundary of shape (this) lies closer to the shape aShape than aClearance,...
virtual LIBEVAL::VALUE GetValue(LIBEVAL::CONTEXT *aCtx) override
void ReportError(const wxString &aErrorMsg)
Handle the data for a net.
bool IsOfType(TYPE_ID aDerived, TYPE_ID aBase) const
Return true if aDerived is inherited from aBase.
int GetDRCEpsilon() const
virtual double AsDouble() const
Information pertinent to a Pcbnew printed circuit board.
static void memberOf(LIBEVAL::CONTEXT *aCtx, void *self)
PCB_LAYER_ID
A quick note on layer IDs:
virtual const wxString & AsString() const
class ZONE, managed by a footprint
static void insideCourtyard(LIBEVAL::CONTEXT *aCtx, void *self)
Handle the component boundary box.
constexpr ret_type KiROUND(fp_type v)
Round a floating point number to an integer using "round halfway cases away from zero".
bool Evaluate(const wxString &aExpr)
static void isMicroVia(LIBEVAL::CONTEXT *aCtx, void *self)
virtual double Convert(const wxString &aString, int unitId) const override
static LSET BackMask()
Return a mask holding all technical layers and the external CU layer on back side.
bool Intersects(const EDA_RECT &aRect) const
Test for a common area between rectangles.
std::map< ZONE *, std::unique_ptr< DRC_RTREE > > m_CopperZoneRTrees
virtual const std::vector< wxString > & GetSupportedUnits() const override
CLASSES_INFO GetAllClasses()
virtual bool IsConnected() const
Returns information if the object is derived from BOARD_CONNECTED_ITEM.
virtual const BOARD * GetBoard() const
Return the BOARD in which this BOARD_ITEM resides, or NULL if none.
Provide class metadata.Helper macro to map type hashes to names.
class PCB_VIA, a via (like a track segment on a copper layer)
static void isCoupledDiffPair(LIBEVAL::CONTEXT *aCtx, void *self)
VALUE * Run(CONTEXT *ctx)
virtual const EDA_RECT GetBoundingBox() const
Return the orthogonal bounding box of this object for display purposes.
std::map< std::pair< BOARD_ITEM *, BOARD_ITEM * >, bool > m_InsideBCourtyardCache
double DoubleValueFromString(EDA_UNITS aUnits, const wxString &aTextValue, EDA_DATA_TYPE aType)
Function DoubleValueFromString converts aTextValue to a double.
Implement an R-tree for fast spatial and layer indexing of connectable items.
int GetConstraint() const
BOARD_ITEM_CONTAINER * GetParent() const
#define MALFORMED_COURTYARDS
LIBEVAL::VALUE GetValue(LIBEVAL::CONTEXT *aCtx) override
std::map< std::pair< BOARD_ITEM *, BOARD_ITEM * >, bool > m_InsideAreaCache
just inflate the polygon. Acute angles create spikes
PCB_LAYER_ID ToLAYER_ID(int aLayer)
BOARD_ITEM * GetObject(const LIBEVAL::CONTEXT *aCtx) const
PCB_LAYER_ID GetLayer() const
virtual LSET GetLayerSet() const
Return a std::bitset of all layers on which the item physically resides.
std::unordered_map< TYPE_ID, PROPERTY_BASE * > m_matchingTypes
KICAD_T Type() const
Returns the type of object.
int QueryColliding(BOARD_ITEM *aRefItem, PCB_LAYER_ID aRefLayer, PCB_LAYER_ID aTargetLayer, std::function< bool(BOARD_ITEM *)> aFilter=nullptr, std::function< bool(BOARD_ITEM *)> aVisitor=nullptr, int aClearance=0) const
This is a fast test which essentially does bounding-box overlap given a worst-case clearance.
static PCB_EXPR_BUILTIN_FUNCTIONS & Instance()
std::map< std::pair< BOARD_ITEM *, BOARD_ITEM * >, bool > m_InsideFCourtyardCache
LIBEVAL::VALUE GetValue(LIBEVAL::CONTEXT *aCtx) override