Improve algorithm for calculating net length; use it for netinfo message panel

Fixes https://gitlab.com/kicad/code/kicad/-/issues/4258
This commit is contained in:
Jon Evans 2021-04-04 12:27:09 -04:00
parent 6b24abac8f
commit 80728f8d78
2 changed files with 48 additions and 28 deletions

View File

@ -1675,22 +1675,42 @@ std::tuple<int, double, double> BOARD::GetTrackLength( const TRACK& aTrack ) con
if( TRACK* track = dyn_cast<TRACK*>( item ) )
{
bool inPad = false;
bool inPad = false;
double segLen = track->GetLength();
for( auto pad_it : connectivity->GetConnectedPads( item ) )
{
PAD* pad = static_cast<PAD*>( pad_it );
if( pad->HitTest( track->GetStart(), track->GetWidth() / 2 )
&& pad->HitTest( track->GetEnd(), track->GetWidth() / 2 ) )
bool hitStart = pad->HitTest( track->GetStart(), track->GetWidth() / 2 );
bool hitEnd = pad->HitTest( track->GetEnd(), track->GetWidth() / 2 );
if( hitStart && hitEnd )
{
inPad = true;
break;
}
else if( hitStart || hitEnd )
{
VECTOR2I loc;
SEG trackSeg( track->GetStart(), track->GetEnd() );
// We may not collide even if we passed the bounding-box hit test
if( pad->GetEffectivePolygon()->Collide( trackSeg, 0, nullptr, &loc ) )
{
// Part 1: length of the seg to the intersection with the pad poly
segLen = hitStart ? ( VECTOR2I( track->GetEnd() ) - loc ).EuclideanNorm() :
( VECTOR2I( track->GetStart() ) - loc ).EuclideanNorm();
// Part 2: length from the interesection to the pad anchor
segLen += ( loc - pad->GetPosition() ).EuclideanNorm();
break;
}
}
}
if( !inPad )
length += track->GetLength();
length += segLen;
}
else if( PAD* pad = dyn_cast<PAD*>( item ) )
{

View File

@ -81,53 +81,53 @@ void NETINFO_ITEM::GetMsgPanelInfo( EDA_DRAW_FRAME* aFrame, std::vector<MSG_PANE
if( board )
{
int count = 0;
double lengthNet = 0.0; // This is the length of tracks on pcb
double lengthPadToDie = 0.0; // this is the length of internal ICs connections
int count = 0;
TRACK* startTrack = nullptr;
for( FOOTPRINT* footprint : board->Footprints() )
{
for( PAD* pad : footprint->Pads() )
{
if( pad->GetNetCode() == GetNetCode() )
{
count++;
lengthPadToDie += pad->GetPadToDieLength();
}
}
}
aList.emplace_back( _( "Pads" ), wxString::Format( "%d", count ) );
count = 0;
count = 0;
for( TRACK* track : board->Tracks() )
{
if( track->Type() == PCB_VIA_T )
if( track->GetNetCode() == GetNetCode() )
{
if( track->GetNetCode() == GetNetCode() )
if( track->Type() == PCB_VIA_T )
count++;
}
if( track->Type() == PCB_TRACE_T )
{
if( track->GetNetCode() == GetNetCode() )
lengthNet += track->GetLength();
else if( !startTrack )
startTrack = track;
}
}
aList.emplace_back( _( "Vias" ), wxString::Format( "%d", count ) );
// Displays the full net length (tracks on pcb + internal ICs connections ):
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthNet + lengthPadToDie );
aList.emplace_back( _( "Net Length" ), msg );
if( startTrack )
{
double lengthNet = 0.0; // This is the length of tracks on pcb
double lengthPadToDie = 0.0; // this is the length of internal ICs connections
// Displays the net length of tracks only:
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthNet );
aList.emplace_back( _( "On Board" ), msg );
std::tie( count, lengthNet, lengthPadToDie ) = board->GetTrackLength( *startTrack );
// Displays the net length of internal ICs connections (wires inside ICs):
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthPadToDie );
aList.emplace_back( _( "In Package" ), msg );
// Displays the full net length (tracks on pcb + internal ICs connections ):
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthNet + lengthPadToDie );
aList.emplace_back( _( "Net Length" ), msg );
// Displays the net length of tracks only:
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthNet );
aList.emplace_back( _( "On Board" ), msg );
// Displays the net length of internal ICs connections (wires inside ICs):
msg = MessageTextFromValue( aFrame->GetUserUnits(), lengthPadToDie );
aList.emplace_back( _( "In Package" ), msg );
}
}
}