diff --git a/qa/pns/CMakeLists.txt b/qa/pns/CMakeLists.txt index 8825692c03..0e35cd9ed8 100644 --- a/qa/pns/CMakeLists.txt +++ b/qa/pns/CMakeLists.txt @@ -92,12 +92,11 @@ target_link_libraries( test_pns tinyspline_lib nanosvg idf3 - unit_test_utils ${PCBNEW_IO_LIBRARIES} ${wxWidgets_LIBRARIES} ${GDI_PLUS_LIBRARIES} ${PYTHON_LIBRARIES} - ${Boost_LIBRARIES} # must follow GITHUB + ${Boost_LIBRARIES} ${PCBNEW_EXTRA_LIBS} # -lrt must follow Boost ) diff --git a/qa/pns/pns_log.cpp b/qa/pns/pns_log.cpp index 9dffbf4e7b..0a8c4fe292 100644 --- a/qa/pns/pns_log.cpp +++ b/qa/pns/pns_log.cpp @@ -129,8 +129,10 @@ void PNS_TEST_ENVIRONMENT::createRouter() m_router->SetMode( m_mode ); m_router->SyncWorld(); m_router->LoadSettings( new PNS::ROUTING_SETTINGS (nullptr, "")); - m_router->Settings().SetMode( PNS::RM_Shove ); - m_router->Settings().SetOptimizeDraggedTrack( true ); + m_router->Settings().SetMode( PNS::RM_Walkaround ); + m_router->Sizes().SetTrackWidth( 250000 ); + + //m_router->Settings().SetOptimizeDraggedTrack( true ); m_debugDecorator.Clear(); m_iface->SetDebugDecorator( &m_debugDecorator ); @@ -305,6 +307,7 @@ void PNS_TEST_DEBUG_DECORATOR::AddPoint( VECTOR2I aP, int aColor, int aSize, con ent->m_width = 30000; ent->m_iter = m_iter; ent->m_name = aName; + ent->m_hasLabels = false; addEntry( ent ); } @@ -379,7 +382,6 @@ void PNS_TEST_DEBUG_DECORATOR::NewStage(const std::string& name, int iter) void PNS_TEST_DEBUG_DECORATOR::DEBUG_ENT::IterateTree( std::function visitor, int depth ) { - printf("LOG D:%d iter: %p\n", depth, this ); if( ! visitor( this ) ) return; diff --git a/qa/pns/pns_log.h b/qa/pns/pns_log.h index 35ffa79fe1..1ec6f257e5 100644 --- a/qa/pns/pns_log.h +++ b/qa/pns/pns_log.h @@ -173,6 +173,7 @@ public: std::vector m_children; int m_color; int m_width; + bool m_hasLabels = true; int m_iter; std::string m_name; std::string m_msg; diff --git a/qa/pns/pns_log_viewer.cpp b/qa/pns/pns_log_viewer.cpp index 491377de27..d7885bc25d 100644 --- a/qa/pns/pns_log_viewer.cpp +++ b/qa/pns/pns_log_viewer.cpp @@ -38,6 +38,8 @@ #include "pns_log.h" #include "router/pns_diff_pair.h" +#include "router/pns_utils.h" + #include "pns_log_viewer_frame_base.h" #include "qa/drc_proto/drc_proto.h" @@ -46,6 +48,195 @@ #define ID_LIST_SHOW_ALL 10002 #define ID_LIST_SHOW_NONE 10003 +#define TOM_EXTRA_DEBUG + +class LABEL_MANAGER +{ +public: + struct LABEL + { + COLOR4D m_color; + std::string m_msg; + VECTOR2I m_target; + BOX2I m_bbox; + }; + + LABEL_MANAGER( KIGFX::GAL* aGal ) : + m_gal( aGal ) {}; + + + void Add( VECTOR2I target, std::string msg, COLOR4D color ) + { + LABEL lbl; + + lbl.m_target = target; + lbl.m_msg = msg; + lbl.m_color = color; + m_gal->SetGlyphSize( VECTOR2D(m_textSize, m_textSize) ); + + VECTOR2I textDims = m_gal->GetTextLineSize( msg ); + + lbl.m_bbox.SetOrigin( lbl.m_target - textDims - VECTOR2I( m_textSize, m_textSize ) ); + lbl.m_bbox.SetSize( textDims ); + m_labels.push_back( lbl ); + } + + void Add( const SHAPE_LINE_CHAIN& aL, COLOR4D color ) + { + for( int i = 0; i < aL.PointCount(); i++ ) + { + char msg[10]; + snprintf(msg, sizeof(msg), "%d", i ); + Add( aL.CPoint(i), msg, color ); + } + } + + void Redraw( std::shared_ptr aOvl ) + { + recalculate(); + for ( auto & lbl : m_labels ) + { + //printf("Draw lbl %d %d '%s'\n", lbl.m_bbox.GetOrigin().x, lbl.m_bbox.GetOrigin().y, lbl.m_msg.c_str() ); + aOvl->SetIsFill( false ); + aOvl->SetIsStroke( true ); + aOvl->SetLineWidth( 10000 ); + aOvl->SetStrokeColor( lbl.m_color.Brighten( 0.7 ) ); + aOvl->Rectangle( lbl.m_bbox.GetOrigin(), lbl.m_bbox.GetEnd() ); + aOvl->BitmapText( lbl.m_msg, lbl.m_bbox.Centre(), 0.0 ); + VECTOR2I nearest = nearestBoxCorner( lbl.m_bbox, lbl.m_target ); + aOvl->Line( lbl.m_target, nearest ); + } + } + +private: + + VECTOR2I nearestBoxCorner( BOX2I b, VECTOR2I p ) + { + VECTOR2I ptest[4] = + { + b.GetPosition(), + b.GetPosition() + VECTOR2I( b.GetWidth(), 0 ), + b.GetPosition() + VECTOR2I( b.GetWidth(), b.GetHeight() ), + b.GetPosition() + VECTOR2I( 0, b.GetHeight() ) + }; + + int bestDist = INT_MAX; + VECTOR2I rv; + + for(int i = 0; i< 4;i++) + { + int dist = ( ptest[i] - p ).EuclideanNorm(); + if(dist < bestDist) + { + bestDist = dist; + rv = ptest[i]; + } + } + + return rv; + } + + VECTOR2I boxMtv( BOX2I b1, BOX2I b2 ) + { + VECTOR2I rv(0, 0); + + b1.Normalize(); + b2.Normalize(); + + if( !b1.Intersects(b2) ) + return rv; + + int bestDist = INT_MAX; + + VECTOR2I p[4] = + { + b2.GetPosition(), + b2.GetPosition() + VECTOR2I( b2.GetWidth(), 0 ), + b2.GetPosition() + VECTOR2I( b2.GetWidth(), b2.GetHeight() ), + b2.GetPosition() + VECTOR2I( 0, b2.GetHeight() ) + }; + + for (int i = 0; i < 4 ; i++ ) + { + if ( b1.Contains( p[i] )) + { + // printf("CONT %d\n", i ); + VECTOR2I dp[4] = + { + VECTOR2I( b1.GetEnd().x - p[i].x + 1, 0 ), + VECTOR2I( b1.GetPosition().x - p[i].x - 1, 0 ), + VECTOR2I( 0, b1.GetEnd().y - p[i].y + 1 ), + VECTOR2I( 0, b1.GetPosition().y - p[i].y - 1 ) + }; + + for(int j = 0; j < 4; j++ ) + { + BOX2I btest(b2); + btest.Move( dp[j] ); + if( !b1.Intersects(btest) ) + { + int dist = dp[j].EuclideanNorm(); + if( dist < bestDist ) + { + bestDist = dist; + rv = dp[j]; + } + } + } + } + } + + return rv; + } + + void recalculate() + { + int iterLimit = 5; + while ( iterLimit > 0 ) + { + printf("Iter %d\n", iterLimit ); + bool collisionsFound = false; + for(int i = 0; i < m_labels.size(); i++ ) + { + for(int j = 0; j < m_labels.size(); j++ ) + { + if (i == j ) + continue; + + + auto bb_i = m_labels[i].m_bbox; + auto bb_j = m_labels[j].m_bbox; + + bb_i.Inflate(100000); + bb_j.Inflate(100000); + VECTOR2I mtv = boxMtv(bb_i, bb_j); + + + if( mtv.x || mtv.y ) + { +// printf("%d %d mtv %d %d\n", i, j, mtv.x, mtv.y ); + + m_labels[i].m_bbox.Move( -mtv ); + collisionsFound = true; + } + } + } + + if( ! collisionsFound ) + break; + + iterLimit--; + } + } + + KIGFX::GAL* m_gal; + int m_textSize = 100000; + std::vector