Properly handle incremental bus connections

- Incremental extraction needs the newly created items.  The modified
  items are already set in the connection graph but the newly created
  items don't exist yet, so we need to add those explicitly
- Bus parents need to ensure that the bus children exist because we
  iterate on the updates from the top of the graph down
This commit is contained in:
Seth Hillbrand 2023-09-16 12:42:48 -07:00
parent e603ba4f3e
commit 9fc45eb08c
2 changed files with 29 additions and 3 deletions

View File

@ -233,13 +233,20 @@ void CONNECTION_SUBGRAPH::getAllConnectedItems( std::set<std::pair<SCH_SHEET_PAT
CONNECTION_SUBGRAPH* sg = this;
while( sg->m_absorbed_by )
{
wxASSERT( sg->m_graph == sg->m_absorbed_by->m_graph );
sg = sg->m_absorbed_by;
}
aSubgraphs.insert( sg );
aSubgraphs.insert( sg->m_absorbed_subgraphs.begin(), sg->m_absorbed_subgraphs.end() );
for( SCH_ITEM* item : sg->m_items )
{
item->Connection( &m_sheet )->Reset();
item->ConnectedItems( m_sheet ).clear();
aItems.emplace( m_sheet, item );
}
for( CONNECTION_SUBGRAPH* child_sg : sg->m_hier_children )
child_sg->getAllConnectedItems( aItems, aSubgraphs );
@ -604,8 +611,11 @@ void CONNECTION_GRAPH::Recalculate( const SCH_SHEET_LIST& aSheetList, bool aUnco
for( SCH_ITEM* item : sheet.LastScreen()->Items() )
{
if( item->IsConnectable() && ( aUnconditional || item->IsConnectivityDirty() ) )
{
wxLogTrace( ConnTrace, wxT( "Adding item %s to connectivity graph update" ),
item->GetTypeDesc() );
items.push_back( item );
}
// Ensure the hierarchy info stored in SCREENS is built and up to date
// (multi-unit symbols)
if( item->Type() == SCH_SYMBOL_T )
@ -663,11 +673,17 @@ std::set<std::pair<SCH_SHEET_PATH, SCH_ITEM*>> CONNECTION_GRAPH::ExtractAffected
{
// Find the primary subgraph on this sheet
while( aSubgraph->m_absorbed_by )
{
wxASSERT( aSubgraph->m_graph == aSubgraph->m_absorbed_by->m_graph );
aSubgraph = aSubgraph->m_absorbed_by;
}
// Find the top most connected subgraph on all sheets
while( aSubgraph->m_hier_parent )
{
wxASSERT( aSubgraph->m_graph == aSubgraph->m_hier_parent->m_graph );
aSubgraph = aSubgraph->m_hier_parent;
}
// Recurse through all subsheets to collect connected items
aSubgraph->getAllConnectedItems( retvals, subgraphs );
@ -2229,6 +2245,9 @@ void CONNECTION_GRAPH::propagateToNeighbors( CONNECTION_SUBGRAPH* aSubgraph, boo
candidate->m_code, candidate->m_driver_connection->Name() );
candidate->m_hier_parent = aParent;
aParent->m_hier_children.insert( candidate );
wxASSERT( candidate->m_graph == aParent->m_graph );
search_list.push_back( candidate );
break;

View File

@ -1686,9 +1686,10 @@ void SCH_EDIT_FRAME::RecalculateConnections( SCH_COMMIT* aCommit, SCH_CLEANUP_FL
}
else
{
auto& changed_list = m_undoList.m_CommandsList.back();
PICKED_ITEMS_LIST* changed_list = m_undoList.m_CommandsList.back();
std::set<SCH_ITEM*> changed_items;
std::vector<VECTOR2I> pts;
std::set<std::pair<SCH_SHEET_PATH, SCH_ITEM*>> item_paths;
for( unsigned ii = 0; ii < changed_list->GetCount(); ++ii )
{
@ -1697,11 +1698,16 @@ void SCH_EDIT_FRAME::RecalculateConnections( SCH_COMMIT* aCommit, SCH_CLEANUP_FL
if( !item || !IsEeschemaType( item->Type() ) )
continue;
SCH_SCREEN* screen = static_cast<SCH_SCREEN*>( changed_list->GetScreenForItem( ii ) );
SCH_ITEM* sch_item = static_cast<SCH_ITEM*>( item );
SCH_SHEET_PATHS& paths = screen->GetClientSheetPaths();
std::vector<VECTOR2I> tmp_pts = sch_item->GetConnectionPoints();
pts.insert( pts.end(), tmp_pts.begin(), tmp_pts.end() );
changed_items.insert( sch_item );
for( SCH_SHEET_PATH& path : paths )
item_paths.insert( std::make_pair( path, sch_item ) );
}
for( VECTOR2I& pt: pts )
@ -1731,6 +1737,8 @@ void SCH_EDIT_FRAME::RecalculateConnections( SCH_COMMIT* aCommit, SCH_CLEANUP_FL
std::set<std::pair<SCH_SHEET_PATH, SCH_ITEM*>> all_items =
Schematic().ConnectionGraph()->ExtractAffectedItems( changed_items );
all_items.insert( item_paths.begin(), item_paths.end() );
CONNECTION_GRAPH new_graph( &Schematic() );
new_graph.SetLastCodes( Schematic().ConnectionGraph() );
@ -1741,7 +1749,6 @@ void SCH_EDIT_FRAME::RecalculateConnections( SCH_COMMIT* aCommit, SCH_CLEANUP_FL
{
case SCH_FIELD_T:
case SCH_PIN_T:
case SCH_SHEET_PIN_T:
static_cast<SCH_ITEM*>( item->GetParent() )->SetConnectivityDirty();
break;