void SCH_EDIT_FRAME::OnSelectUnit( wxCommandEvent& aEvent ) { SCH_SCREEN* screen = GetScreen(); SCH_ITEM* item = screen->GetCurItem(); wxCHECK_RET( item != NULL && item->Type() == SCH_COMPONENT_T, wxT( "Cannot select unit of invalid schematic item." ) ); INSTALL_UNBUFFERED_DC( dc, m_canvas ); m_canvas->MoveCursorToCrossHair(); SCH_COMPONENT* component = (SCH_COMPONENT*) item; int unit = aEvent.GetId() + 1 - ID_POPUP_SCH_SELECT_UNIT1; LIB_PART* part = GetLibPart( component->GetLibId() ); if( !part ) return; int unitCount = part->GetUnitCount(); wxCHECK_RET( (unit >= 1) && (unit <= unitCount), wxString::Format( wxT( "Cannot select unit %d from component " ), unit ) + part->GetName() ); if( unitCount <= 1 || component->GetUnit() == unit ) return; if( unit > unitCount ) unit = unitCount; STATUS_FLAGS flags = component->GetFlags(); if( !flags ) // No command in progress: save in undo list SaveCopyInUndoList( component, UR_CHANGED ); if( flags ) component->Draw( m_canvas, &dc, wxPoint( 0, 0 ), g_XorMode, g_GhostColor ); else component->Draw( m_canvas, &dc, wxPoint( 0, 0 ), g_XorMode ); /* Update the unit number. */ component->SetUnitSelection( m_CurrentSheet, unit ); component->SetUnit( unit ); component->ClearFlags(); component->SetFlags( flags ); // Restore m_Flag modified by SetUnit() if( m_autoplaceFields ) component->AutoAutoplaceFields( GetScreen() ); if( screen->TestDanglingEnds() ) m_canvas->Refresh(); OnModify(); }
void SCH_EDIT_FRAME::OnSelectUnit( wxCommandEvent& aEvent ) { SCH_SCREEN* screen = GetScreen(); SCH_ITEM* item = screen->GetCurItem(); SCH_COMPONENT* component = (SCH_COMPONENT*) item; GetCanvas()->MoveCursorToCrossHair(); int unit = aEvent.GetId() + 1 - ID_POPUP_SCH_SELECT_UNIT1; LIB_PART* part = GetLibPart( component->GetLibId() ); if( !part ) return; int unitCount = part->GetUnitCount(); if( unitCount <= 1 || component->GetUnit() == unit ) return; if( unit > unitCount ) unit = unitCount; STATUS_FLAGS flags = component->GetFlags(); if( !flags ) // No command in progress: save in undo list SaveCopyInUndoList( component, UR_CHANGED ); /* Update the unit number. */ component->SetUnitSelection( g_CurrentSheet, unit ); component->SetUnit( unit ); component->ClearFlags(); component->SetFlags( flags ); // Restore m_Flag modified by SetUnit() if( m_autoplaceFields ) component->AutoAutoplaceFields( GetScreen() ); TestDanglingEnds(); RefreshItem( component ); OnModify(); }
void SCH_EDIT_FRAME::OnRotate( wxCommandEvent& aEvent ) { SCH_SCREEN* screen = GetScreen(); SCH_ITEM* item = screen->GetCurItem(); INSTALL_UNBUFFERED_DC( dc, m_canvas ); // Allows block rotate operation on hot key. if( screen->m_BlockLocate.GetState() != STATE_NO_BLOCK ) { screen->m_BlockLocate.SetCommand( BLOCK_ROTATE ); HandleBlockEnd( &dc ); return; } if( item == NULL ) { // If we didn't get here by a hot key, then something has gone wrong. if( aEvent.GetInt() == 0 ) return; EDA_HOTKEY_CLIENT_DATA* data = (EDA_HOTKEY_CLIENT_DATA*) aEvent.GetClientObject(); wxCHECK_RET( data != NULL, wxT( "Invalid hot key client object." ) ); item = LocateAndShowItem( data->GetPosition(), SCH_COLLECTOR::RotatableItems, aEvent.GetInt() ); // Exit if no item found at the current location or the item is already being edited. if( (item == NULL) || (item->GetFlags() != 0) ) return; } switch( item->Type() ) { case SCH_COMPONENT_T: { SCH_COMPONENT* component = static_cast<SCH_COMPONENT*>( item ); if( aEvent.GetId() == ID_SCH_ROTATE_CLOCKWISE ) OrientComponent( CMP_ROTATE_CLOCKWISE ); else if( aEvent.GetId() == ID_SCH_ROTATE_COUNTERCLOCKWISE ) OrientComponent( CMP_ROTATE_COUNTERCLOCKWISE ); else wxFAIL_MSG( wxT( "Unknown rotate item command ID." ) ); if( m_autoplaceFields ) component->AutoAutoplaceFields( GetScreen() ); m_canvas->Refresh(); break; } case SCH_TEXT_T: case SCH_LABEL_T: case SCH_GLOBAL_LABEL_T: case SCH_HIERARCHICAL_LABEL_T: m_canvas->MoveCursorToCrossHair(); ChangeTextOrient( (SCH_TEXT*) item ); m_canvas->Refresh(); break; case SCH_FIELD_T: m_canvas->MoveCursorToCrossHair(); RotateField( (SCH_FIELD*) item ); if( item->GetParent()->Type() == SCH_COMPONENT_T ) { // Now that we're moving a field, they're no longer autoplaced. SCH_COMPONENT *parent = static_cast<SCH_COMPONENT*>( item->GetParent() ); parent->ClearFieldsAutoplaced(); } m_canvas->Refresh(); break; case SCH_BITMAP_T: RotateImage( (SCH_BITMAP*) item ); break; case SCH_SHEET_T: if( !item->IsNew() ) // rotate a sheet during its creation has no sense { bool retCCW = ( aEvent.GetId() == ID_SCH_ROTATE_COUNTERCLOCKWISE ); RotateHierarchicalSheet( static_cast<SCH_SHEET*>( item ), retCCW ); } break; case SCH_JUNCTION_T: case SCH_NO_CONNECT_T: // these items are not rotated, because rotation does not change them. break; default: // Other items (wires...) cannot be rotated, at least during creation if( item->IsNew() ) break; wxFAIL_MSG( wxString::Format( wxT( "Cannot rotate schematic item type %s." ), GetChars( item->GetClass() ) ) ); } if( item->GetFlags() == 0 ) screen->SetCurItem( NULL ); }
void SCH_EDIT_FRAME::EditComponentFieldText( SCH_FIELD* aField ) { wxCHECK_RET( aField != NULL && aField->Type() == SCH_FIELD_T, wxT( "Cannot edit invalid schematic field." ) ); int fieldNdx; SCH_COMPONENT* component = (SCH_COMPONENT*) aField->GetParent(); wxCHECK_RET( component != NULL && component->Type() == SCH_COMPONENT_T, wxT( "Invalid schematic field parent item." ) ); LIB_PART* part = Prj().SchLibs()->FindLibPart( component->GetPartName() ); wxCHECK_RET( part, wxT( "Library part for component <" ) + component->GetPartName() + wxT( "> could not be found." ) ); fieldNdx = aField->GetId(); // Save old component in undo list if not already in edit, or moving. if( aField->GetFlags() == 0 ) SaveCopyInUndoList( component, UR_CHANGED ); // Don't use GetText() here. If the field is the reference designator and it's parent // component has multiple parts, we don't want the part suffix added to the field. m_canvas->SetIgnoreMouseEvents( true ); wxString title; title.Printf( _( "Edit %s Field" ), GetChars( aField->GetName() ) ); DIALOG_SCH_EDIT_ONE_FIELD dlg( this, title, aField ); // Value fields of power components cannot be modified. This will grey out // the text box and display an explanation. if( fieldNdx == VALUE && part->IsPower() ) { dlg.SetPowerWarning( true ); } //The diag may invoke a kiway player for footprint fields //so we must use a quasimodal int response = dlg.ShowQuasiModal(); m_canvas->MoveCursorToCrossHair(); m_canvas->SetIgnoreMouseEvents( false ); wxString newtext = dlg.GetTextField( ); if ( response != wxID_OK ) return; // canceled by user // make some tests bool can_update = true; if( !newtext.IsEmpty() ) { if( fieldNdx == REFERENCE ) { // Test if the reference string is valid: if( SCH_COMPONENT::IsReferenceStringValid( newtext ) ) { component->SetRef( m_CurrentSheet, newtext ); } else { DisplayError( this, _( "Illegal reference string! No change" ) ); can_update = false; } } } else { if( fieldNdx == REFERENCE ) { DisplayError( this, _( "The reference field cannot be empty! No change" ) ); can_update = false; } else if( fieldNdx == VALUE && ! part->IsPower() ) { // Note that power components also should not have empty value fields - but // since the user is forbidden from changing the value field here, if it // were to happen somehow, it'd be awfully confusing if an error were to // be displayed! DisplayError( this, _( "The value field cannot be empty! No change" ) ); can_update = false; } else if ( !( fieldNdx == VALUE && part->IsPower() ) ) { dlg.SetTextField( wxT( "~" ) ); } } if( can_update ) { dlg.TransfertDataToField( /* aIncludeText = */ !( fieldNdx == VALUE && part->IsPower() ) ); OnModify(); if( m_autoplaceFields ) component->AutoAutoplaceFields( GetScreen() ); m_canvas->Refresh(); } MSG_PANEL_ITEMS items; component->SetCurrentSheetPath( &GetCurrentSheet() ); component->GetMsgPanelInfo( items ); SetMsgPanel( items ); }
void SCH_EDIT_FRAME::OnOrient( wxCommandEvent& aEvent ) { SCH_SCREEN* screen = GetScreen(); SCH_ITEM* item = screen->GetCurItem(); INSTALL_UNBUFFERED_DC( dc, m_canvas ); // Allows block rotate operation on hot key. if( screen->m_BlockLocate.GetState() != STATE_NO_BLOCK ) { if( aEvent.GetId() == ID_SCH_MIRROR_X ) { m_canvas->MoveCursorToCrossHair(); screen->m_BlockLocate.SetMessageBlock( this ); screen->m_BlockLocate.SetCommand( BLOCK_MIRROR_X ); HandleBlockEnd( &dc ); } else if( aEvent.GetId() == ID_SCH_MIRROR_Y ) { m_canvas->MoveCursorToCrossHair(); screen->m_BlockLocate.SetMessageBlock( this ); screen->m_BlockLocate.SetCommand( BLOCK_MIRROR_Y ); HandleBlockEnd( &dc ); } else { wxFAIL_MSG( wxT( "Unknown block oriention command ID." ) ); } return; } if( item == NULL ) { // If we didn't get here by a hot key, then something has gone wrong. if( aEvent.GetInt() == 0 ) return; EDA_HOTKEY_CLIENT_DATA* data = (EDA_HOTKEY_CLIENT_DATA*) aEvent.GetClientObject(); wxCHECK_RET( data != NULL, wxT( "Invalid hot key client object." ) ); item = LocateAndShowItem( data->GetPosition(), SCH_COLLECTOR::OrientableItems, aEvent.GetInt() ); // Exit if no item found at the current location or the item is already being edited. if( (item == NULL) || (item->GetFlags() != 0) ) return; } switch( item->Type() ) { case SCH_COMPONENT_T: { SCH_COMPONENT *component = static_cast<SCH_COMPONENT*>( item ); if( aEvent.GetId() == ID_SCH_MIRROR_X ) OrientComponent( CMP_MIRROR_X ); else if( aEvent.GetId() == ID_SCH_MIRROR_Y ) OrientComponent( CMP_MIRROR_Y ); else if( aEvent.GetId() == ID_SCH_ORIENT_NORMAL ) OrientComponent( CMP_NORMAL ); else wxFAIL_MSG( wxT( "Invalid orient schematic component command ID." ) ); if( m_autoplaceFields ) component->AutoAutoplaceFields( GetScreen() ); m_canvas->Refresh(); break; } case SCH_BITMAP_T: if( aEvent.GetId() == ID_SCH_MIRROR_X ) MirrorImage( (SCH_BITMAP*) item, true ); else if( aEvent.GetId() == ID_SCH_MIRROR_Y ) MirrorImage( (SCH_BITMAP*) item, false ); break; case SCH_SHEET_T: if( aEvent.GetId() == ID_SCH_MIRROR_X ) MirrorSheet( (SCH_SHEET*) item, true ); else if( aEvent.GetId() == ID_SCH_MIRROR_Y ) MirrorSheet( (SCH_SHEET*) item, false ); break; default: // This object cannot be oriented. ; } if( item->GetFlags() == 0 ) screen->SetCurItem( NULL ); }