Rewrite intersheet refs resolution to be sheet-path aware.

Fixes https://gitlab.com/kicad/code/kicad/-/issues/17533
This commit is contained in:
Jeff Young 2024-03-23 16:50:00 +00:00
parent fc572bfbc6
commit a6e2746a08
6 changed files with 40 additions and 45 deletions

View File

@ -351,13 +351,14 @@ SCH_FIELD::GetRenderCache( const wxString& forResolvedText, const VECTOR2I& forP
void SCH_FIELD::Print( const RENDER_SETTINGS* aSettings, const VECTOR2I& aOffset )
{
wxDC* DC = aSettings->GetPrintDC();
COLOR4D color = aSettings->GetLayerColor( IsForceVisible() ? LAYER_HIDDEN : m_layer );
bool blackAndWhiteMode = GetGRForceBlackPenState();
VECTOR2I textpos;
int penWidth = GetEffectiveTextPenWidth( aSettings->GetDefaultPenWidth() );
SCH_SHEET_PATH* sheet = &Schematic()->CurrentSheet();
wxDC* DC = aSettings->GetPrintDC();
COLOR4D color = aSettings->GetLayerColor( IsForceVisible() ? LAYER_HIDDEN : m_layer );
bool blackAndWhiteMode = GetGRForceBlackPenState();
VECTOR2I textpos;
int penWidth = GetEffectiveTextPenWidth( aSettings->GetDefaultPenWidth() );
if( ( !IsVisible() && !IsForceVisible() ) || GetShownText( true ).IsEmpty() )
if( ( !IsVisible() && !IsForceVisible() ) || GetShownText( sheet, true ).IsEmpty() )
return;
COLOR4D bg = aSettings->GetBackgroundColor();
@ -416,7 +417,7 @@ void SCH_FIELD::Print( const RENDER_SETTINGS* aSettings, const VECTOR2I& aOffset
textpos += label->GetSchematicTextOffset( aSettings );
}
GRPrintText( DC, textpos, color, GetShownText( true ), orient, GetTextSize(),
GRPrintText( DC, textpos, color, GetShownText( sheet, true ), orient, GetTextSize(),
GR_TEXT_H_ALIGN_CENTER, GR_TEXT_V_ALIGN_CENTER, penWidth, IsItalic(), IsBold(),
font, GetFontMetrics() );
}
@ -950,12 +951,14 @@ void SCH_FIELD::DoHypertextAction( EDA_DRAW_FRAME* aFrame ) const
if( IsHypertext() )
{
SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( m_parent );
std::vector<std::pair<wxString, wxString>> pages;
wxMenu menu;
wxString href;
SCH_LABEL_BASE* label = static_cast<SCH_LABEL_BASE*>( m_parent );
SCH_SHEET_PATH* sheet = &label->Schematic()->CurrentSheet();
wxMenu menu;
wxString href;
label->GetIntersheetRefs( &pages );
std::vector<std::pair<wxString, wxString>> pages;
label->GetIntersheetRefs( sheet, &pages );
for( int i = 0; i < (int) pages.size(); ++i )
{
@ -1148,7 +1151,9 @@ bool SCH_FIELD::HitTest( const BOX2I& aRect, bool aContained, int aAccuracy ) co
void SCH_FIELD::Plot( PLOTTER* aPlotter, bool aBackground,
const SCH_PLOT_SETTINGS& aPlotSettings ) const
{
if( GetShownText( true ).IsEmpty() || aBackground )
SCH_SHEET_PATH* sheet = &Schematic()->CurrentSheet();
if( GetShownText( sheet, true ).IsEmpty() || aBackground )
return;
RENDER_SETTINGS* settings = aPlotter->RenderSettings();
@ -1228,7 +1233,7 @@ void SCH_FIELD::Plot( PLOTTER* aPlotter, bool aBackground,
attrs.m_Angle = orient;
attrs.m_Multiline = false;
aPlotter->PlotText( textpos, color, GetShownText( true ), attrs, font, GetFontMetrics() );
aPlotter->PlotText( textpos, color, GetShownText( sheet, true ), attrs, font, GetFontMetrics() );
if( IsHypertext() )
{
@ -1239,7 +1244,7 @@ void SCH_FIELD::Plot( PLOTTER* aPlotter, bool aBackground,
wxCHECK( label, /* void */ );
label->GetIntersheetRefs( &pages );
label->GetIntersheetRefs( sheet, &pages );
for( const std::pair<wxString, wxString>& page : pages )
pageHrefs.push_back( wxT( "#" ) + page.first );

View File

@ -706,13 +706,15 @@ void SCH_LABEL_BASE::AutoplaceFields( SCH_SCREEN* aScreen, bool aManual )
}
void SCH_LABEL_BASE::GetIntersheetRefs( std::vector<std::pair<wxString, wxString>>* pages )
void SCH_LABEL_BASE::GetIntersheetRefs( const SCH_SHEET_PATH* aPath,
std::vector<std::pair<wxString, wxString>>* pages )
{
wxCHECK( pages, /* void */ );
if( Schematic() )
{
auto it = Schematic()->GetPageRefsMap().find( GetText() );
wxString resolvedLabel = GetShownText( &Schematic()->CurrentSheet(), false );
auto it = Schematic()->GetPageRefsMap().find( resolvedLabel );
if( it != Schematic()->GetPageRefsMap().end() )
{
@ -1308,6 +1310,7 @@ void SCH_LABEL_BASE::Plot( PLOTTER* aPlotter, bool aBackground,
{
static std::vector<VECTOR2I> s_poly;
SCH_SHEET_PATH* sheet = &Schematic()->CurrentSheet();
RENDER_SETTINGS* settings = aPlotter->RenderSettings();
SCH_CONNECTION* connection = Connection();
int layer = ( connection && connection->IsBus() ) ? LAYER_BUS : m_layer;
@ -1338,7 +1341,8 @@ void SCH_LABEL_BASE::Plot( PLOTTER* aPlotter, bool aBackground,
}
else
{
aPlotter->PlotText( textpos, color, GetShownText( true ), attrs, font, GetFontMetrics() );
aPlotter->PlotText( textpos, color, GetShownText( sheet, true ), attrs, font,
GetFontMetrics() );
if( GetShape() == LABEL_FLAG_SHAPE::F_DOT )
{
@ -1840,7 +1844,7 @@ bool SCH_GLOBALLABEL::ResolveTextVar( const SCH_SHEET_PATH* aPath, wxString* tok
{
SCHEMATIC_SETTINGS& settings = schematic->Settings();
wxString ref;
auto it = schematic->GetPageRefsMap().find( GetText() );
auto it = schematic->GetPageRefsMap().find( GetShownText( aPath ) );
if( it == schematic->GetPageRefsMap().end() )
{

View File

@ -238,7 +238,8 @@ public:
* Builds an array of { pageNumber, pageName } pairs.
* @param pages [out] Array of { pageNumber, pageName } pairs.
*/
void GetIntersheetRefs( std::vector<std::pair<wxString, wxString>>* pages );
void GetIntersheetRefs( const SCH_SHEET_PATH* aPath,
std::vector<std::pair<wxString, wxString>>* pages );
/**
* Return the list of system text vars & fields for this label.

View File

@ -342,6 +342,7 @@ void SCH_TEXT::Plot( PLOTTER* aPlotter, bool aBackground,
if( aBackground )
return;
SCH_SHEET_PATH* sheet = &Schematic()->CurrentSheet();
RENDER_SETTINGS* settings = aPlotter->RenderSettings();
SCH_CONNECTION* connection = Connection();
int layer = ( connection && connection->IsBus() ) ? LAYER_BUS : m_layer;
@ -375,7 +376,7 @@ void SCH_TEXT::Plot( PLOTTER* aPlotter, bool aBackground,
std::vector<VECTOR2I> positions;
wxArrayString strings_list;
wxStringSplit( GetShownText( true ), strings_list, '\n' );
wxStringSplit( GetShownText( sheet, true ), strings_list, '\n' );
positions.reserve( strings_list.Count() );
GetLinePositions( positions, (int) strings_list.Count() );

View File

@ -419,6 +419,7 @@ void SCH_TEXTBOX::Plot( PLOTTER* aPlotter, bool aBackground,
return;
}
SCH_SHEET_PATH* sheet = &Schematic()->CurrentSheet();
RENDER_SETTINGS* settings = aPlotter->RenderSettings();
int penWidth = GetPenWidth();
COLOR4D color = GetStroke().GetColor();
@ -456,7 +457,7 @@ void SCH_TEXTBOX::Plot( PLOTTER* aPlotter, bool aBackground,
std::vector<VECTOR2I> positions;
wxArrayString strings_list;
wxStringSplit( GetShownText( true ), strings_list, '\n' );
wxStringSplit( GetShownText( sheet, true ), strings_list, '\n' );
positions.reserve( strings_list.Count() );
GetLinePositions( positions, (int) strings_list.Count() );

View File

@ -659,37 +659,20 @@ void SCHEMATIC::RecomputeIntersheetRefs( const std::function<void( SCH_GLOBALLAB
pageRefsMap.clear();
SCH_SCREENS screens( Root() );
std::vector<int> virtualPageNumbers;
/* Iterate over screens */
for( SCH_SCREEN* screen = screens.GetFirst(); screen != nullptr; screen = screens.GetNext() )
for( const SCH_SHEET_PATH& sheet : GetSheets() )
{
virtualPageNumbers.clear();
/* Find in which sheets this screen is used */
for( const SCH_SHEET_PATH& sheet : GetSheets() )
for( SCH_ITEM* item : sheet.LastScreen()->Items().OfType( SCH_GLOBAL_LABEL_T ) )
{
if( sheet.LastScreen() == screen )
virtualPageNumbers.push_back( sheet.GetVirtualPageNumber() );
}
SCH_GLOBALLABEL* global = static_cast<SCH_GLOBALLABEL*>( item );
wxString resolvedLabel = global->GetShownText( &sheet, false );
for( SCH_ITEM* item : screen->Items() )
{
if( item->Type() == SCH_GLOBAL_LABEL_T )
{
SCH_GLOBALLABEL* globalLabel = static_cast<SCH_GLOBALLABEL*>( item );
std::set<int>& virtualpageList = pageRefsMap[globalLabel->GetText()];
for( const int& pageNo : virtualPageNumbers )
virtualpageList.insert( pageNo );
}
pageRefsMap[ resolvedLabel ].insert( sheet.GetVirtualPageNumber() );
}
}
bool show = Settings().m_IntersheetRefsShow;
// Refresh all global labels. Note that we have to collect them first as the
// Refresh all visible global labels. Note that we have to collect them first as the
// SCH_SCREEN::Update() call is going to invalidate the RTree iterator.
std::vector<SCH_GLOBALLABEL*> currentSheetGlobalLabels;