35make_candidate(
const char* aRef,
int aUnit,
const std::vector<const char*>& aPins,
36 const std::initializer_list<std::pair<const char*, const char*>>& aNets )
39 candidate.
m_ref = wxString::FromUTF8( aRef );
42 for(
const char*
pin : aPins )
45 for(
const auto& [
pin, net] : aNets )
52static std::map<wxString, wxString>
53make_pin_map(
const std::initializer_list<std::pair<const char*, const char*>>& aNets )
55 std::map<wxString, wxString> pinMap;
57 for(
const auto& [
pin, net] : aNets )
58 pinMap[wxString::FromUTF8(
pin )] = wxString::FromUTF8( net );
69 std::initializer_list<size_t> aExpectedSwappedCandidateIndices )
75 for(
size_t candidateIdx : aExpectedSwappedCandidateIndices )
83static void check_final_units(
const std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>& aCandidates,
85 std::initializer_list<int> aExpectedUnits )
87 std::vector<int> finalUnits;
90 finalUnits.push_back( candidate.m_currentUnit );
95 BOOST_REQUIRE_EQUAL( finalUnits.size(), aExpectedUnits.size() );
99 for(
int expectedUnit : aExpectedUnits )
108 LIB_SYMBOL lib( wxS(
"MappedUnits" ),
nullptr );
111 for(
int number = 1; number <= 4; ++number )
114 pin->SetNumber( wxString::Format( wxS(
"%d" ), number ) );
115 pin->SetUnit( number <= 2 ? 1 : 2 );
121 PIN_MAP map( wxS(
"ReversedPads" ) );
122 map.
SetEntry( wxS(
"1" ), wxS(
"3" ) );
123 map.
SetEntry( wxS(
"2" ), wxS(
"4" ) );
124 map.
SetEntry( wxS(
"3" ), wxS(
"1" ) );
125 map.
SetEntry( wxS(
"4" ), wxS(
"2" ) );
129 footprint.
Parse( wxS(
"Test:MappedUnits" ) );
132 m_first = std::make_unique<SCH_SYMBOL>( lib, lib.
GetLibId(),
nullptr, 1 );
138 make_candidate(
"U1B", 2, {
"3",
"4" }, { {
"3",
"B_IN" }, {
"4",
"B_OUT" } } ) };
143 std::map<wxString, wxString> pcbNetsByLogicalPin;
148 BOOST_REQUIRE_EQUAL( pcbNetsByLogicalPin.size(), 4U );
164 std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>
candidates =
167 { {
"1",
"Aout" }, {
"2",
"Net-(U1A--)" }, {
"3",
"A+" } } ),
169 { {
"5",
"B+" }, {
"6",
"B-" }, {
"7",
"Bout" } } )
174 make_pin_map( { {
"1",
"Aout" }, {
"2",
"Net-(U1A--)" }, {
"3",
"A+" },
175 {
"5",
"B+" }, {
"6",
"B-" }, {
"7",
"Bout" } } ) );
184 std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>
candidates =
187 { {
"1",
"A1" }, {
"2",
"A2" }, {
"3",
"A3" } } ),
189 { {
"4",
"B1" }, {
"5",
"B2" }, {
"6",
"B3" } } )
194 make_pin_map( { {
"1",
"B1" }, {
"2",
"B2" }, {
"3",
"B3" },
195 {
"4",
"A1" }, {
"5",
"A2" }, {
"6",
"A3" } } ) );
204 std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>
candidates = {
205 make_candidate(
"D1", 1, {
"6",
"1" }, { {
"6",
"K1" }, {
"1",
"A1" } } ),
206 make_candidate(
"D1", 2, {
"5",
"2" }, { {
"5",
"K2" }, {
"2",
"A2" } } ),
207 make_candidate(
"D1", 3, {
"4",
"3" }, { {
"4",
"K3" }, {
"3",
"A3" } } )
213 { {
"6",
"K2" }, {
"1",
"A2" }, {
"5",
"K3" }, {
"2",
"A3" }, {
"4",
"K1" }, {
"3",
"A1" } } ) );
222 std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>
candidates = {
223 make_candidate(
"RN1", 1, {
"1",
"2" }, { {
"1",
"R1" }, {
"2",
"R1.2" } } ),
224 make_candidate(
"RN1", 2, {
"1",
"3" }, { {
"1",
"R1" }, {
"3",
"R2.2" } } ),
225 make_candidate(
"RN1", 3, {
"1",
"4" }, { {
"1",
"R1" }, {
"4",
"R3.2" } } )
231 { {
"1",
"R1" }, {
"2",
"R2.2" }, {
"3",
"R3.2" }, {
"4",
"R1.2" } } ) );
240 std::vector<BACKANNOTATE_UNIT_SWAP_CANDIDATE>
candidates = {
241 make_candidate(
"D1", 1, {
"6",
"1" }, { {
"6",
"K1" }, {
"1",
"A1" } } ),
242 make_candidate(
"D1", 2, {
"5",
"2" }, { {
"5",
"K2" }, {
"2",
"A2" } } ),
243 make_candidate(
"D1", 3, {
"4",
"3" }, { {
"4",
"K3" }, {
"3",
"A3" } } )
264 { {
"1",
"A1" }, {
"2",
"K3" }, {
"3",
"A2" }, {
"4",
"K2" }, {
"5",
"A3" }, {
"6",
"K1" } } ) );
266 BOOST_CHECK( !
plan.m_mappingOk );
267 BOOST_CHECK(
plan.m_steps.empty() );
268 BOOST_CHECK(
plan.m_swappedCandidateIndices.empty() );
275 const auto plan = Plan(
make_pin_map( { {
"1",
"B_IN" }, {
"2",
"B_OUT" }, {
"3",
"A_IN" }, {
"4",
"A_OUT" } } ) );
278 BOOST_CHECK(
plan.m_steps.empty() );
286 const auto plan = Plan(
make_pin_map( { {
"1",
"A_IN" }, {
"2",
"A_OUT" }, {
"3",
"B_IN" }, {
"4",
"B_OUT" } } ) );
297 m_first->SetPinMapOverride( pinOverride );
298 m_second->SetPinMapOverride( pinOverride );
300 const auto plan = Plan(
make_pin_map( { {
"1",
"A_IN" }, {
"2",
"A_OUT" }, {
"3",
"B_IN" }, {
"4",
"B_OUT" } } ) );
310 pinOverride.
m_Edits.push_back( { wxS(
"1" ), wxS(
"[3,5]" ) } );
311 m_first->SetPinMapOverride( pinOverride );
313 auto pcbNetsByPad =
make_pin_map( { {
"3",
"A_IN" }, {
"4",
"A_OUT" }, {
"5",
"A_IN" } } );
314 std::map<wxString, wxString> logicalNets;
320 pcbNetsByPad[wxS(
"5" )] = wxS(
"OTHER_NET" );
324 pcbNetsByPad.erase( wxS(
"5" ) );
332 LIB_SYMBOL lib( wxS(
"StackedUnit" ),
nullptr );
334 pin->SetNumber( wxS(
"[1,2]" ) );
340 pinOverride.
m_Edits.push_back( { wxS(
"[1,2]" ), wxS(
"[8,9]" ) } );
343 std::map<wxString, wxString> logicalNets;
346 symbol, sheet, wxEmptyString,
make_pin_map( { {
"8",
"SIGNAL" }, {
"9",
"SIGNAL" } } ), logicalNets ) );
347 BOOST_REQUIRE_EQUAL( logicalNets.size(), 2U );
bool CollectBackannotatePcbNets(const SCH_SYMBOL &aSymbol, const SCH_SHEET_PATH &aSheetPath, const wxString &aVariantName, const std::map< wxString, wxString > &aPcbNetsByPad, std::map< wxString, wxString > &aPcbNetsByLogicalPin)
Append this unit's PCB nets to a map keyed by logical pin number, resolving pin-to-pad mappings.
BACKANNOTATE_UNIT_SWAP_PLAN PlanBackannotateUnitSwaps(const std::vector< BACKANNOTATE_UNIT_SWAP_CANDIDATE > &aCandidates, const std::map< wxString, wxString > &aPcbPinMap)
Compute a pure unit-swap plan from schematic-side unit definitions and PCB nets keyed by logical pin ...
A logical library item identifier and consists of various portions much like a URI.
int Parse(const UTF8 &aId, bool aFix=false)
Parse LIB_ID with the information from aId.
Define a library symbol object.
const LIB_ID & GetLibId() const override
void SetAssociatedFootprints(std::vector< ASSOCIATED_FOOTPRINT > aList)
void SetUnitCount(int aCount, bool aDuplicateDrawItems)
Set the units per symbol count.
void AddDrawItem(SCH_ITEM *aItem, bool aSort=true)
Add a new draw aItem to the draw object list and sort according to aSort.
void AddOrReplace(PIN_MAP aMap)
Insert aMap, replacing any existing entry with the same name.
void SetEntry(const wxString &aPinNumber, const wxString &aPadNumber)
Set the pad number for a symbol pin.
Handle access to a stack of flattened SCH_SHEET objects by way of a path for creating a flattened sch...
void SetPinMapOverride(const PIN_MAP_INSTANCE_OVERRIDE &aOverride, const SCH_SHEET_PATH *aInstance=nullptr, const wxString &aVariantName=wxEmptyString)
Set the per-instance pin-to-pad map override (issue #2282).
static std::vector< PENDING_PROPERTY > plan(const EDA_ITEM &aSource, const EDA_ITEM &aTarget, const std::set< wxString > &aEnabledKeys)
Target properties to write, paired with values read off the source.
@ PT_PASSIVE
pin for passive symbols: must be connected, and can be connected to any pin.
Definition of the SCH_SHEET_PATH and SCH_SHEET_LIST classes for Eeschema.
std::vector< wxString > m_unitPinNumbers
std::map< wxString, wxString > m_schNetsByPin
std::vector< BACKANNOTATE_UNIT_SWAP_STEP > m_steps
std::set< size_t > m_swappedCandidateIndices
std::vector< BACKANNOTATE_UNIT_SWAP_CANDIDATE > m_candidates
std::unique_ptr< SCH_SYMBOL > m_first
BACKANNOTATE_UNIT_SWAP_PLAN Plan(const std::map< wxString, wxString > &aPcbNetsByPad)
std::unique_ptr< SCH_SYMBOL > m_second
MAPPED_UNIT_SWAP_FIXTURE()
Per-instance override of the active pin map and a sparse delta on top.
std::vector< PIN_MAP_ENTRY > m_Edits
PIN_MAP_OVERRIDE_MODE m_Mode
BOOST_AUTO_TEST_CASE(HorizontalAlignment)
BOOST_FIXTURE_TEST_CASE(MappedPadsAlreadyMatch, MAPPED_UNIT_SWAP_FIXTURE)
BOOST_AUTO_TEST_CASE(BackannotateUnitSwapPlanner_DetectsIdentityMapping)
static void check_final_units(const std::vector< BACKANNOTATE_UNIT_SWAP_CANDIDATE > &aCandidates, const BACKANNOTATE_UNIT_SWAP_PLAN &aPlan, std::initializer_list< int > aExpectedUnits)
static BACKANNOTATE_UNIT_SWAP_CANDIDATE make_candidate(const char *aRef, int aUnit, const std::vector< const char * > &aPins, const std::initializer_list< std::pair< const char *, const char * > > &aNets)
static std::map< wxString, wxString > make_pin_map(const std::initializer_list< std::pair< const char *, const char * > > &aNets)
static void check_plan(const BACKANNOTATE_UNIT_SWAP_PLAN &aPlan, bool aMappingOk, bool aIdentity, std::initializer_list< size_t > aExpectedSwappedCandidateIndices)
BOOST_AUTO_TEST_SUITE(CadstarPartParser)
BOOST_REQUIRE(intersection.has_value()==c.ExpectedIntersection.has_value())
BOOST_AUTO_TEST_SUITE_END()
static std::vector< int > candidates(const SEGMENT_INDEX &aIndex, const SEG &aQuery, int aPadding)
BOOST_CHECK_EQUAL(result, "25.4")
VECTOR2< int32_t > VECTOR2I