KiCad PCB EDA Suite
legacy_wx/eda_draw_frame.cpp
Go to the documentation of this file.
1 /*
2  * This program source code file is part of KiCad, a free EDA CAD application.
3  *
4  * Copyright (C) 2004-2017 Jean-Pierre Charras, jp.charras at wanadoo.fr
5  * Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com>
6  * Copyright (C) 2004-2018 KiCad Developers, see AUTHORS.txt for contributors.
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, you may find one here:
20  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21  * or you may search the http://www.gnu.org website for the version 2 license,
22  * or you may write to the Free Software Foundation, Inc.,
23  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25 
30 #include <fctsys.h>
31 #include <pgm_base.h>
32 #include <kiface_i.h>
33 #include <gr_basic.h>
34 #include <common.h>
35 #include <bitmaps.h>
36 #include <macros.h>
37 #include <id.h>
38 #include <class_drawpanel.h>
39 #include <base_screen.h>
40 #include <msgpanel.h>
41 #include <draw_frame.h>
42 #include <confirm.h>
43 #include <kicad_device_context.h>
44 #include <dialog_helpers.h>
45 #include <base_units.h>
46 #include <math/box2.h>
47 #include <lockfile.h>
48 #include <trace_helpers.h>
49 
50 #include <wx/clipbrd.h>
51 #include <fctsys.h>
52 #include <gr_basic.h>
53 #include <common.h>
54 #include <id.h>
55 #include <base_screen.h>
56 #include <confirm.h>
57 #include <draw_frame.h>
58 
59 
60 #include <wx/fontdlg.h>
61 #include <wx/snglinst.h>
62 #include <view/view.h>
63 #include <view/view_controls.h>
65 #include <tool/tool_manager.h>
66 #include <tool/tool_dispatcher.h>
67 #include <tool/actions.h>
68 
69 #include <advanced_config.h>
70 #include <menus_helpers.h>
71 #include <page_info.h>
72 #include <title_block.h>
74 
79 static const wxString traceScrollSettings( wxT( "KicadScrollSettings" ) );
80 
81 
84 
85 const wxChar EDA_DRAW_FRAME::CANVAS_TYPE_KEY[] = wxT( "canvas_type" );
86 
87 static const wxString FirstRunShownKeyword( wxT( "FirstRunShown" ) );
88 
90 
104 static const wxString MaxUndoItemsEntry(wxT( "DevelMaxUndoItems" ) );
105 
106 BEGIN_EVENT_TABLE( EDA_DRAW_FRAME, KIWAY_PLAYER )
107  EVT_CHAR_HOOK( EDA_DRAW_FRAME::OnCharHook )
108 
109  EVT_MOUSEWHEEL( EDA_DRAW_FRAME::OnMouseEvent )
110  EVT_MENU_OPEN( EDA_DRAW_FRAME::OnMenuOpen )
111  EVT_ACTIVATE( EDA_DRAW_FRAME::OnActivate )
113 
115  EDA_DRAW_FRAME::OnZoom )
116 
118  EDA_DRAW_FRAME::OnSelectGrid )
119 
120  EVT_TOOL( ID_TB_OPTIONS_SHOW_GRID, EDA_DRAW_FRAME::OnToggleGridState )
122  EDA_DRAW_FRAME::OnSelectUnits )
123 
124  EVT_TOOL( ID_TB_OPTIONS_SELECT_CURSOR, EDA_DRAW_FRAME::OnToggleCrossHairStyle )
125 
126  EVT_UPDATE_UI( wxID_UNDO, EDA_DRAW_FRAME::OnUpdateUndo )
127  EVT_UPDATE_UI( wxID_REDO, EDA_DRAW_FRAME::OnUpdateRedo )
128  EVT_UPDATE_UI( ID_TB_OPTIONS_SHOW_GRID, EDA_DRAW_FRAME::OnUpdateGrid )
129  EVT_UPDATE_UI( ID_TB_OPTIONS_SELECT_CURSOR, EDA_DRAW_FRAME::OnUpdateCrossHairStyle )
130  EVT_UPDATE_UI_RANGE( ID_TB_OPTIONS_SELECT_UNIT_MM, ID_TB_OPTIONS_SELECT_UNIT_INCH,
131  EDA_DRAW_FRAME::OnUpdateUnits )
132 END_EVENT_TABLE()
133 
134 
135 EDA_DRAW_FRAME::EDA_DRAW_FRAME( KIWAY* aKiway, wxWindow* aParent,
136  FRAME_T aFrameType,
137  const wxString& aTitle,
138  const wxPoint& aPos, const wxSize& aSize,
139  long aStyle, const wxString & aFrameName ) :
140  KIWAY_PLAYER( aKiway, aParent, aFrameType, aTitle, aPos, aSize, aStyle, aFrameName )
141 {
142  m_socketServer = nullptr;
143  m_drawToolBar = NULL;
144  m_optionsToolBar = NULL;
145  m_auxiliaryToolBar = NULL;
146  m_gridSelectBox = NULL;
147  m_zoomSelectBox = NULL;
148  m_hotkeysDescrList = NULL;
149 
150  m_canvas = NULL;
151  m_canvasType = EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE;
152  m_galCanvas = NULL;
153  m_galCanvasActive = false;
154  m_actions = NULL;
155  m_toolManager = NULL;
156  m_toolDispatcher = NULL;
157  m_messagePanel = NULL;
158  m_currentScreen = NULL;
159  m_toolId = ID_NO_TOOL_SELECTED;
160  m_lastDrawToolId = ID_NO_TOOL_SELECTED;
161  m_showAxis = false; // true to draw axis.
162  m_showBorderAndTitleBlock = false; // true to display reference sheet.
163  m_showGridAxis = false; // true to draw the grid axis
164  m_showOriginAxis = false; // true to draw the grid origin
165  m_LastGridSizeId = 0;
166  m_drawGrid = true; // hide/Show grid. default = show
167  m_gridColor = COLOR4D( DARKGRAY ); // Default grid color
168  m_showPageLimits = false;
169  m_drawBgColor = COLOR4D( BLACK ); // the background color of the draw canvas:
170  // BLACK for Pcbnew, BLACK or WHITE for eeschema
171  m_snapToGrid = true;
172  m_MsgFrameHeight = EDA_MSG_PANEL::GetRequiredHeight();
173  m_movingCursorWithKeyboard = false;
174  m_zoomLevelCoeff = 1.0;
175 
176  m_auimgr.SetFlags(wxAUI_MGR_DEFAULT);
177 
178  CreateStatusBar( 6 );
179 
180  // set the size of the status bar subwindows:
181 
182  wxWindow* stsbar = GetStatusBar();
183 
184  int dims[] = {
185 
186  // remainder of status bar on far left is set to a default or whatever is left over.
187  -1,
188 
189  // When using GetTextSize() remember the width of character '1' is not the same
190  // as the width of '0' unless the font is fixed width, and it usually won't be.
191 
192  // zoom:
193  GetTextSize( wxT( "Z 762000" ), stsbar ).x + 10,
194 
195  // cursor coords
196  GetTextSize( wxT( "X 0234.567890 Y 0234.567890" ), stsbar ).x + 10,
197 
198  // delta distances
199  GetTextSize( wxT( "dx 0234.567890 dx 0234.567890 d 0234.567890" ), stsbar ).x + 10,
200 
201  // units display, Inches is bigger than mm
202  GetTextSize( _( "Inches" ), stsbar ).x + 10,
203 
204  // Size for the panel used as "Current tool in play": will take longest string from
205  // void PCB_EDIT_FRAME::OnSelectTool( wxCommandEvent& aEvent ) in pcbnew/edit.cpp
206  GetTextSize( wxT( "Add layer alignment target" ), stsbar ).x + 10,
207  };
208 
209  SetStatusWidths( arrayDim( dims ), dims );
210 
211  // Create child subwindows.
212  GetClientSize( &m_FrameSize.x, &m_FrameSize.y );
213  m_FramePos.x = m_FramePos.y = 0;
214  m_FrameSize.y -= m_MsgFrameHeight;
215 
216  m_canvas = new EDA_DRAW_PANEL( this, -1, wxPoint( 0, 0 ), m_FrameSize );
217  m_messagePanel = new EDA_MSG_PANEL( this, -1, wxPoint( 0, m_FrameSize.y ),
218  wxSize( m_FrameSize.x, m_MsgFrameHeight ) );
219 
220  m_messagePanel->SetBackgroundColour( COLOR4D( LIGHTGRAY ).ToColour() );
221 }
222 
223 
225 {
226  delete m_socketServer;
227  for( auto socket : m_sockets )
228  {
229  socket->Shutdown();
230  socket->Destroy();
231  }
232 
234 
235  delete m_actions;
236  delete m_toolManager;
237  delete m_toolDispatcher;
238  delete m_galCanvas;
239 
240  delete m_currentScreen;
241  m_currentScreen = NULL;
242 
243  m_auimgr.UnInit();
244 
245  ReleaseFile();
246 }
247 
248 
249 void EDA_DRAW_FRAME::OnCharHook( wxKeyEvent& event )
250 {
251  wxLogTrace( kicadTraceKeyEvent, "EDA_DRAW_FRAME::OnCharHook %s", dump( event ) );
252  // Key events can be filtered here.
253  // Currently no filtering is made.
254  event.Skip();
255 }
256 
257 
259 {
260  m_file_checker = nullptr;
261 }
262 
263 
264 bool EDA_DRAW_FRAME::LockFile( const wxString& aFileName )
265 {
266  m_file_checker = ::LockFile( aFileName );
267 
268  return bool( m_file_checker );
269 }
270 
271 
273 {
274  UpdateStatusBar();
275  UpdateMsgPanel();
276 }
277 
279 {
281 
282  wxConfigBase* settings = Pgm().CommonSettings();
283 
284  int autosaveInterval;
285  settings->Read( AUTOSAVE_INTERVAL_KEY, &autosaveInterval );
286  SetAutoSaveInterval( autosaveInterval );
287 
288  int historySize;
289  settings->Read( FILE_HISTORY_SIZE_KEY, &historySize, DEFAULT_FILE_HISTORY_SIZE );
290  Kiface().GetFileHistory().SetMaxFiles( (unsigned) std::max( 0, historySize ) );
291 
292  bool option;
293  settings->Read( ENBL_MOUSEWHEEL_PAN_KEY, &option );
294  m_canvas->SetEnableMousewheelPan( option );
295 
296  settings->Read( ENBL_ZOOM_NO_CENTER_KEY, &option );
297  m_canvas->SetEnableZoomNoCenter( option );
298 
299  settings->Read( ENBL_AUTO_PAN_KEY, &option );
300  m_canvas->SetEnableAutoPan( option );
301 
302  int tmp;
305 
308 
310 }
311 
312 
314 {
315  if( m_messagePanel )
317 }
318 
319 
320 void EDA_DRAW_FRAME::OnActivate( wxActivateEvent& event )
321 {
322  if( m_canvas )
323  m_canvas->SetCanStartBlock( -1 );
324 
325  event.Skip(); // required under wxMAC
326 }
327 
328 
329 void EDA_DRAW_FRAME::OnMenuOpen( wxMenuEvent& event )
330 {
331  if( m_canvas )
332  m_canvas->SetCanStartBlock( -1 );
333 
334  event.Skip();
335 }
336 
337 
339 {
341 }
342 
343 
344 void EDA_DRAW_FRAME::OnToggleGridState( wxCommandEvent& aEvent )
345 {
347 
348  if( IsGalCanvasActive() )
349  {
352  }
353 
354  m_canvas->Refresh();
355 }
356 
357 
358 bool EDA_DRAW_FRAME::GetToolToggled( int aToolId )
359 {
360  // Checks all the toolbars and returns true if the given tool id is toggled.
361  return ( ( m_mainToolBar && m_mainToolBar->GetToolToggled( aToolId ) ) ||
362  ( m_optionsToolBar && m_optionsToolBar->GetToolToggled( aToolId ) ) ||
363  ( m_drawToolBar && m_drawToolBar->GetToolToggled( aToolId ) ) ||
364  ( m_auxiliaryToolBar && m_auxiliaryToolBar->GetToolToggled( aToolId ) )
365  );
366 }
367 
368 
369 wxAuiToolBarItem* EDA_DRAW_FRAME::GetToolbarTool( int aToolId )
370 {
371  // Checks all the toolbars and returns a reference to the given tool id
372  // (or the first tool found, but only one or 0 tool is expected, because on
373  // Windows, when different tools have the same ID, it creates issues)
374  if( m_mainToolBar && m_mainToolBar->FindTool( aToolId ) )
375  return m_mainToolBar->FindTool( aToolId );
376 
377  if( m_optionsToolBar && m_optionsToolBar->FindTool( aToolId ) )
378  return m_optionsToolBar->FindTool( aToolId );
379 
380  if( m_drawToolBar && m_drawToolBar->FindTool( aToolId ) )
381  return m_drawToolBar->FindTool( aToolId );
382 
383  if( m_auxiliaryToolBar && m_auxiliaryToolBar->FindTool( aToolId ) )
384  return m_auxiliaryToolBar->FindTool( aToolId );
385 
386  return nullptr;
387 }
388 
389 
390 void EDA_DRAW_FRAME::OnSelectUnits( wxCommandEvent& aEvent )
391 {
392  if( aEvent.GetId() == ID_TB_OPTIONS_SELECT_UNIT_MM && m_UserUnits != MILLIMETRES )
393  {
396  }
397  else if( aEvent.GetId() == ID_TB_OPTIONS_SELECT_UNIT_INCH && m_UserUnits != INCHES )
398  {
401  }
402 }
403 
404 
405 void EDA_DRAW_FRAME::OnToggleCrossHairStyle( wxCommandEvent& aEvent )
406 {
408  m_canvas->CrossHairOff( &dc );
409 
410  auto& galOpts = GetGalDisplayOptions();
411  galOpts.m_fullscreenCursor = !galOpts.m_fullscreenCursor;
412  galOpts.NotifyChanged();
413 
414  m_canvas->CrossHairOn( &dc );
415 }
416 
417 
418 void EDA_DRAW_FRAME::OnUpdateUndo( wxUpdateUIEvent& aEvent )
419 {
420  if( GetScreen() )
421  aEvent.Enable( GetScreen()->GetUndoCommandCount() > 0 );
422 }
423 
424 
425 void EDA_DRAW_FRAME::OnUpdateRedo( wxUpdateUIEvent& aEvent )
426 {
427  if( GetScreen() )
428  aEvent.Enable( GetScreen()->GetRedoCommandCount() > 0 );
429 }
430 
431 
432 void EDA_DRAW_FRAME::OnUpdateUnits( wxUpdateUIEvent& aEvent )
433 {
434  bool enable;
435 
436  enable = ( ((aEvent.GetId() == ID_TB_OPTIONS_SELECT_UNIT_MM) && (m_UserUnits == MILLIMETRES))
437  || ((aEvent.GetId() == ID_TB_OPTIONS_SELECT_UNIT_INCH) && (m_UserUnits == INCHES)) );
438 
439  aEvent.Check( enable );
440  DisplayUnitsMsg();
441 }
442 
443 
444 void EDA_DRAW_FRAME::OnUpdateGrid( wxUpdateUIEvent& aEvent )
445 {
446  wxString tool_tip = IsGridVisible() ? _( "Hide grid" ) : _( "Show grid" );
447 
448  aEvent.Check( IsGridVisible() );
449  m_optionsToolBar->SetToolShortHelp( ID_TB_OPTIONS_SHOW_GRID, tool_tip );
450 }
451 
452 
453 void EDA_DRAW_FRAME::OnUpdateSelectGrid( wxUpdateUIEvent& aEvent )
454 {
455  // No need to update the grid select box if it doesn't exist or the grid setting change
456  // was made using the select box.
457  if( m_gridSelectBox == NULL || m_auxiliaryToolBar == NULL )
458  return;
459 
460  int select = wxNOT_FOUND;
461 
462  for( size_t i = 0; i < GetScreen()->GetGridCount(); i++ )
463  {
464  if( GetScreen()->GetGridCmdId() == GetScreen()->GetGrid( i ).m_CmdId )
465  {
466  select = (int) i;
467  break;
468  }
469  }
470 
471  if( select != m_gridSelectBox->GetSelection() )
472  m_gridSelectBox->SetSelection( select );
473 }
474 
475 
476 void EDA_DRAW_FRAME::OnUpdateCrossHairStyle( wxUpdateUIEvent& aEvent )
477 {
478  aEvent.Check( GetGalDisplayOptions().m_fullscreenCursor );
479 }
480 
481 
483 {
484 }
485 
486 
488 {
489 }
490 
491 
492 bool EDA_DRAW_FRAME::OnHotKey( wxDC* aDC, int aHotKey, const wxPoint& aPosition, EDA_ITEM* aItem )
493 {
494  return false;
495 }
496 
498  wxString* aFullFileName )
499 {
500  int result = EDA_BASE_FRAME::WriteHotkeyConfig( aDescList, aFullFileName );
501 
502  if( IsGalCanvasActive() )
504 
505  return result;
506 }
507 
508 void EDA_DRAW_FRAME::ToolOnRightClick( wxCommandEvent& event )
509 {
510 }
511 
512 
513 void EDA_DRAW_FRAME::PrintPage( wxDC* aDC, LSET aPrintMask, bool aPrintMirrorMode, void* aData )
514 {
515  wxMessageBox( wxT("EDA_DRAW_FRAME::PrintPage() error") );
516 }
517 
518 
519 void EDA_DRAW_FRAME::OnSelectGrid( wxCommandEvent& event )
520 {
521  int* clientData;
522  int eventId = ID_POPUP_GRID_LEVEL_100;
523 
524  if( event.GetEventType() == wxEVT_COMBOBOX )
525  {
526  if( m_gridSelectBox == NULL ) // Should not happen
527  return;
528 
529  /*
530  * Don't use wxCommandEvent::GetClientData() here. It always
531  * returns NULL in GTK. This solution is not as elegant but
532  * it works.
533  */
534  int index = m_gridSelectBox->GetSelection();
535  wxASSERT( index != wxNOT_FOUND );
536 
537  if( index == int( m_gridSelectBox->GetCount() - 2 ) )
538  {
539  // this is the separator
540  wxUpdateUIEvent dummy;
541  OnUpdateSelectGrid( dummy );
542  return;
543  }
544  else if( index == int( m_gridSelectBox->GetCount() - 1 ) )
545  {
546  wxUpdateUIEvent dummy;
547  OnUpdateSelectGrid( dummy );
548  wxCommandEvent dummy2;
549  OnGridSettings( dummy2 );
550  return;
551  }
552 
553  clientData = (int*) m_gridSelectBox->wxItemContainer::GetClientData( index );
554 
555  if( clientData != NULL )
556  eventId = *clientData;
557  }
558  else
559  {
560  eventId = event.GetId();
561  }
562 
563  int idx = eventId - ID_POPUP_GRID_LEVEL_1000;
564 
565  // Notify GAL
566  TOOL_MANAGER* mgr = GetToolManager();
567 
568  if( mgr && IsGalCanvasActive() )
569  mgr->RunAction( "common.Control.gridPreset", true, idx );
570  else
571  SetPresetGrid( idx );
572 
573  m_canvas->Refresh();
574 }
575 
576 
577 void EDA_DRAW_FRAME::OnSelectZoom( wxCommandEvent& event )
578 {
579  if( m_zoomSelectBox == NULL )
580  return; // Should not happen!
581 
582  int id = m_zoomSelectBox->GetCurrentSelection();
583 
584  if( id < 0 || !( id < (int)m_zoomSelectBox->GetCount() ) )
585  return;
586 
587  if( IsGalCanvasActive() )
588  {
589  m_toolManager->RunAction( "common.Control.zoomPreset", true, id );
590  UpdateStatusBar();
591  m_galCanvas->Refresh();
592  }
593  else if( id == 0 ) // Auto zoom (Fit in Page)
594  {
595  Zoom_Automatique( true );
596  m_canvas->Refresh();
597  }
598  else
599  {
600  double selectedZoom = GetScreen()->m_ZoomList[id-1];
601 
602  if( GetScreen()->SetZoom( selectedZoom ) )
604  }
605 }
606 
607 
609 {
610  return GetScreen()->GetZoom();
611 }
612 
613 
614 void EDA_DRAW_FRAME::OnMouseEvent( wxMouseEvent& event )
615 {
616  event.Skip();
617 }
618 
619 
620 void EDA_DRAW_FRAME::OnLeftDClick( wxDC* DC, const wxPoint& MousePos )
621 {
622 }
623 
624 
625 void EDA_DRAW_FRAME::DisplayToolMsg( const wxString& msg )
626 {
627  SetStatusText( msg, 5 );
628 }
629 
630 
632 {
633  wxString msg;
634 
635  switch( m_UserUnits )
636  {
637  case INCHES:
638  msg = _( "Inches" );
639  break;
640 
641  case MILLIMETRES:
642  msg = _( "mm" );
643  break;
644 
645  default:
646  msg = _( "Units" );
647  break;
648  }
649 
650  SetStatusText( msg, 4 );
651 }
652 
653 
654 void EDA_DRAW_FRAME::OnSize( wxSizeEvent& SizeEv )
655 {
656  m_FrameSize = GetClientSize( );
657 
658  SizeEv.Skip();
659 }
660 
661 
662 void EDA_DRAW_FRAME::SetToolID( int aId, int aCursor, const wxString& aToolMsg )
663 {
664  // Keep default cursor in toolbars
665  SetCursor( wxNullCursor );
666 
667  // Change m_canvas cursor if requested.
668  if( m_canvas && aCursor >= 0 )
669  m_canvas->SetCurrentCursor( aCursor );
670 
671  // Change GAL canvas cursor if requested.
672  if( IsGalCanvasActive() && aCursor >= 0 )
673  GetGalCanvas()->SetCurrentCursor( aCursor );
674 
675  DisplayToolMsg( aToolMsg );
676 
677  if( aId < 0 )
678  return;
679 
680  wxCHECK2_MSG( aId >= ID_NO_TOOL_SELECTED, aId = ID_NO_TOOL_SELECTED,
681  wxString::Format( wxT( "Current tool ID cannot be set to %d." ), aId ) );
682 
683  m_toolId = aId;
684 }
685 
686 
688 {
689  // Select the ID_NO_TOOL_SELECTED id tool (Idle tool)
690 
691  int defaultCursor = wxCURSOR_DEFAULT;
692 
693  // Change GAL canvas cursor if requested.
694  if( IsGalCanvasActive() )
695  defaultCursor = GetGalCanvas()->GetDefaultCursor();
696  else if( m_canvas )
697  defaultCursor = m_canvas->GetDefaultCursor();
698 
699  SetToolID( ID_NO_TOOL_SELECTED, defaultCursor, wxEmptyString );
700 }
701 
702 
703 wxPoint EDA_DRAW_FRAME::GetGridPosition( const wxPoint& aPosition ) const
704 {
705  wxPoint pos = aPosition;
706 
707  if( m_currentScreen != NULL && m_snapToGrid )
708  pos = GetNearestGridPosition( aPosition );
709 
710  return pos;
711 }
712 
713 
715 {
716  BASE_SCREEN * screen = GetScreen();
717 
718  int new_grid_cmd = screen->GetGridCmdId();
719 
720  // if the grid id is the not the last, increment it
721  if( screen->GridExists( new_grid_cmd + 1 ) )
722  new_grid_cmd += 1;
723 
724  SetPresetGrid( new_grid_cmd - ID_POPUP_GRID_LEVEL_1000 );
725 }
726 
727 
729 {
730  BASE_SCREEN * screen = GetScreen();
731 
732  int new_grid_cmd = screen->GetGridCmdId();
733 
734  // if the grid id is the not the first, increment it
735  if( screen->GridExists( new_grid_cmd - 1 ) )
736  new_grid_cmd -= 1;
737 
738  SetPresetGrid( new_grid_cmd - ID_POPUP_GRID_LEVEL_1000 );
739 }
740 
741 
742 void EDA_DRAW_FRAME::SetPresetGrid( int aIndex )
743 {
744  BASE_SCREEN * screen = GetScreen();
745 
746  if( ! screen->GridExists( aIndex + ID_POPUP_GRID_LEVEL_1000 ) )
747  aIndex = screen->GetGrids()[0].m_CmdId;
748 
749  // aIndex is a Command Id relative to ID_POPUP_GRID_LEVEL_1000 comand id code.
750  // we need an index in grid list (the cmd id in list is is screen->GetGrids()[0].m_CmdId):
751  int glistIdx = aIndex + ID_POPUP_GRID_LEVEL_1000 - screen->GetGrids()[0].m_CmdId;
752 
753  if( m_gridSelectBox )
754  {
755  if( glistIdx < 0 || glistIdx >= (int) m_gridSelectBox->GetCount() - 2 )
756  {
757  wxASSERT_MSG( false, "Invalid grid index" );
758  return;
759  }
760 
761  m_gridSelectBox->SetSelection( glistIdx );
762  }
763 
764  // Be sure m_LastGridSizeId is up to date.
765  m_LastGridSizeId = aIndex;
767 
768  // Put cursor on new grid
769  SetCrossHairPosition( RefPos( true ) );
770 }
771 
772 
774 {
775  return 0;
776 }
777 
778 
780 {
783 }
784 
785 
786 void EDA_DRAW_FRAME::HandleBlockPlace( wxDC* DC )
787 {
788 }
789 
790 
791 bool EDA_DRAW_FRAME::HandleBlockEnd( wxDC* DC )
792 {
793  return false;
794 }
795 
796 
798 {
799  SetStatusText( GetZoomLevelIndicator(), 1 );
800 
801  // Absolute and relative cursor positions are handled by overloading this function and
802  // handling the internal to user units conversion at the appropriate level.
803 
804  // refresh units display
805  DisplayUnitsMsg();
806 }
807 
808 
809 const wxString EDA_DRAW_FRAME::GetZoomLevelIndicator() const
810 {
811  wxString Line;
812  double level = 0.0;
813 
814  if( IsGalCanvasActive() )
815  {
816  level = m_galCanvas->GetGAL()->GetZoomFactor();
817  }
818  else if( BASE_SCREEN* screen = GetScreen() )
819  {
820  level = m_zoomLevelCoeff / (double) screen->GetZoom();
821  }
822 
823  // returns a human readable value which can be displayed as zoom
824  // level indicator in dialogs.
825  Line.Printf( wxT( "Z %.2f" ), level );
826 
827  return Line;
828 }
829 
830 
831 void EDA_DRAW_FRAME::LoadSettings( wxConfigBase* aCfg )
832 {
834 
835  wxString baseCfgName = ConfigBaseName();
836  wxConfigBase* cmnCfg = Pgm().CommonSettings();
837 
838  // Read units used in dialogs and toolbars
839  EDA_UNITS_T unitsTmp;
840 
841  if( aCfg->Read( baseCfgName + UserUnitsEntryKeyword, (int*) &unitsTmp ) )
842  SetUserUnits( unitsTmp );
843  else
845 
846  // Read show/hide grid entry
847  bool btmp;
848  if( aCfg->Read( baseCfgName + ShowGridEntryKeyword, &btmp ) )
849  SetGridVisibility( btmp );
850 
851  // Read grid color:
852  COLOR4D wtmp = COLOR4D::UNSPECIFIED;
853 
854  if( wtmp.SetFromWxString( aCfg->Read( baseCfgName + GridColorEntryKeyword, wxT( "NONE" ) ) ) )
855  SetGridColor( wtmp );
856 
857  aCfg->Read( baseCfgName + LastGridSizeIdKeyword, &m_LastGridSizeId, 0L );
858 
859  // m_LastGridSizeId is an offset, expected to be >= 0
860  if( m_LastGridSizeId < 0 )
861  m_LastGridSizeId = 0;
862 
863  m_UndoRedoCountMax = aCfg->Read( baseCfgName + MaxUndoItemsEntry,
864  long( DEFAULT_MAX_UNDO_ITEMS ) );
865 
866  aCfg->Read( baseCfgName + FirstRunShownKeyword, &m_firstRunDialogSetting, 0L );
867 
869 
870  int temp;
873 
876 
878 }
879 
880 
881 void EDA_DRAW_FRAME::SaveSettings( wxConfigBase* aCfg )
882 {
884 
885  wxString baseCfgName = ConfigBaseName();
886 
887  aCfg->Write( baseCfgName + UserUnitsEntryKeyword, (int) m_UserUnits );
888  aCfg->Write( baseCfgName + ShowGridEntryKeyword, IsGridVisible() );
889  aCfg->Write( baseCfgName + GridColorEntryKeyword,
890  GetGridColor().ToColour().GetAsString( wxC2S_CSS_SYNTAX ) );
891  aCfg->Write( baseCfgName + LastGridSizeIdKeyword, ( long ) m_LastGridSizeId );
892  aCfg->Write( baseCfgName + FirstRunShownKeyword, m_firstRunDialogSetting );
893 
894  if( GetScreen() )
895  aCfg->Write( baseCfgName + MaxUndoItemsEntry, long( GetScreen()->GetMaxUndoItems() ) );
896 
898 }
899 
900 
901 void EDA_DRAW_FRAME::AppendMsgPanel( const wxString& textUpper,
902  const wxString& textLower,
903  COLOR4D color, int pad )
904 {
905  if( m_messagePanel == NULL )
906  return;
907 
908  m_messagePanel->AppendMessage( textUpper, textLower, color, pad );
909 }
910 
911 
913 {
914  if( m_messagePanel == NULL )
915  return;
916 
918 }
919 
920 
921 void EDA_DRAW_FRAME::SetMsgPanel( const MSG_PANEL_ITEMS& aList )
922 {
923  if( m_messagePanel == NULL )
924  return;
925 
926  ClearMsgPanel();
927 
928  for( unsigned i = 0; i < aList.size(); i++ )
929  m_messagePanel->AppendMessage( aList[i] );
930 }
931 
932 
934 {
935  wxCHECK_RET( aItem != NULL, wxT( "Invalid EDA_ITEM pointer. Bad programmer." ) );
936 
937  MSG_PANEL_ITEMS items;
938  aItem->GetMsgPanelInfo( m_UserUnits, items );
939  SetMsgPanel( items );
940 }
941 
942 
944 {
945  EDA_ITEM* item = GetScreen()->GetCurItem();
946 
947  if( item )
948  SetMsgPanel( item );
949 }
950 
951 
952 // FIXME: There needs to be a better way for child windows to load preferences.
953 // This function pushes four preferences from a parent window to a child window
954 // i.e. from eeschema to the schematic symbol editor
955 void EDA_DRAW_FRAME::PushPreferences( const EDA_DRAW_PANEL* aParentCanvas )
956 {
958  m_canvas->SetEnableAutoPan( aParentCanvas->GetEnableAutoPan() );
959 }
960 
961 
962 bool EDA_DRAW_FRAME::HandleBlockBegin( wxDC* aDC, EDA_KEY aKey, const wxPoint& aPosition,
963  int aExplicitCommand )
964 {
966 
967  if( ( block->GetCommand() != BLOCK_IDLE ) || ( block->GetState() != STATE_NO_BLOCK ) )
968  return false;
969 
970  if( aExplicitCommand == 0 )
971  block->SetCommand( (BLOCK_COMMAND_T) BlockCommand( aKey ) );
972  else
973  block->SetCommand( (BLOCK_COMMAND_T) aExplicitCommand );
974 
975  if( block->GetCommand() == 0 )
976  return false;
977 
978  switch( block->GetCommand() )
979  {
980  case BLOCK_IDLE:
981  break;
982 
983  case BLOCK_MOVE: // Move
984  case BLOCK_DRAG: // Drag (block defined)
985  case BLOCK_DRAG_ITEM: // Drag from a drag item command
986  case BLOCK_DUPLICATE: // Duplicate
987  case BLOCK_DUPLICATE_AND_INCREMENT: // Duplicate and increment relevant references
988  case BLOCK_DELETE: // Delete
989  case BLOCK_COPY: // Copy
990  case BLOCK_FLIP: // Flip
991  case BLOCK_ZOOM: // Window Zoom
992  case BLOCK_PRESELECT_MOVE: // Move with preselection list
993  block->InitData( m_canvas, aPosition );
994  break;
995 
996  case BLOCK_PASTE:
997  block->InitData( m_canvas, aPosition );
998  block->SetLastCursorPosition( wxPoint( 0, 0 ) );
1000 
1001  if( block->GetCount() == 0 ) // No data to paste
1002  {
1003  DisplayError( this, wxT( "No block to paste" ), 20 );
1006  block->SetState( STATE_NO_BLOCK );
1007  block->SetMessageBlock( this );
1008  return true;
1009  }
1010 
1011  if( !m_canvas->IsMouseCaptured() )
1012  {
1013  block->ClearItemsList();
1014  DisplayError( this,
1015  wxT( "EDA_DRAW_FRAME::HandleBlockBegin() Err: m_mouseCaptureCallback NULL" ) );
1016  block->SetState( STATE_NO_BLOCK );
1017  block->SetMessageBlock( this );
1018  return true;
1019  }
1020 
1021  block->SetState( STATE_BLOCK_MOVE );
1022  m_canvas->CallMouseCapture( aDC, aPosition, false );
1023  break;
1024 
1025  default:
1026  {
1027  wxString msg;
1028  msg << wxT( "EDA_DRAW_FRAME::HandleBlockBegin() error: Unknown command " ) <<
1029  block->GetCommand();
1030  DisplayError( this, msg );
1031  }
1032  break;
1033  }
1034 
1035  block->SetMessageBlock( this );
1036  return true;
1037 }
1038 
1039 
1040 // I am not seeing a problem with this size yet:
1041 static const double MAX_AXIS = INT_MAX - 100;
1042 
1043 #define VIRT_MIN (-MAX_AXIS/2.0)
1044 #define VIRT_MAX (MAX_AXIS/2.0)
1045 
1046 
1047 void EDA_DRAW_FRAME::AdjustScrollBars( const wxPoint& aCenterPositionIU )
1048 {
1049  BASE_SCREEN* screen = GetScreen();
1050 
1051  if( !screen || !m_canvas )
1052  return;
1053 
1054  double scale = screen->GetScalingFactor();
1055 
1056  wxLogTrace( traceScrollSettings, wxT( "Center Position = ( %d, %d ), scale = %.10g" ),
1057  aCenterPositionIU.x, aCenterPositionIU.y, scale );
1058 
1059  // Calculate the portion of the drawing that can be displayed in the
1060  // client area at the current zoom level.
1061 
1062  // visible viewport in device units ~ pixels
1063  wxSize clientSizeDU = m_canvas->GetClientSize();
1064 
1065  // Size of the client window in IU
1066  DSIZE clientSizeIU( clientSizeDU.x / scale, clientSizeDU.y / scale );
1067 
1068  // Full drawing or "page" rectangle in internal units
1069  DBOX pageRectIU( wxPoint( 0, 0 ), wxSize( GetPageSizeIU().x, GetPageSizeIU().y ) );
1070 
1071  // Remark: if something is modified here, perhaps EDA_DRAW_FRAME::RedrawScreen2()
1072  // will need changes accordint to the way the center is computed
1073  // Account for scrollbars
1074  wxSize scrollbarSizeDU = m_canvas->GetSize() - m_canvas->GetClientSize();
1075  wxSize scrollbarSizeIU = scrollbarSizeDU * (1 / scale);
1076  wxPoint centerAdjustedIU = aCenterPositionIU + scrollbarSizeIU / 2;
1077 
1078  // The upper left corner of the client rectangle in internal units.
1079  double xIU = centerAdjustedIU.x - clientSizeIU.x / 2.0;
1080  double yIU = centerAdjustedIU.y - clientSizeIU.y / 2.0;
1081 
1082  // If drawn around the center, adjust the client rectangle accordingly.
1083  if( screen->m_Center )
1084  {
1085  // half page offset.
1086  xIU += pageRectIU.GetWidth() / 2.0;
1087  yIU += pageRectIU.GetHeight() / 2.0;
1088  }
1089 
1090  DBOX clientRectIU( wxPoint( xIU, yIU ), wxSize( clientSizeIU.x, clientSizeIU.y ) );
1091  wxPoint centerPositionIU;
1092 
1093  // put "int" limits on the clientRect
1094  if( clientRectIU.GetLeft() < VIRT_MIN )
1095  clientRectIU.MoveLeftTo( VIRT_MIN );
1096  if( clientRectIU.GetTop() < VIRT_MIN )
1097  clientRectIU.MoveTopTo( VIRT_MIN );
1098  if( clientRectIU.GetRight() > VIRT_MAX )
1099  clientRectIU.MoveRightTo( VIRT_MAX );
1100  if( clientRectIU.GetBottom() > VIRT_MAX )
1101  clientRectIU.MoveBottomTo( VIRT_MAX );
1102 
1103  centerPositionIU.x = KiROUND( clientRectIU.GetX() + clientRectIU.GetWidth() / 2 );
1104  centerPositionIU.y = KiROUND( clientRectIU.GetY() + clientRectIU.GetHeight() / 2 );
1105 
1106  if( screen->m_Center )
1107  {
1108  centerPositionIU.x -= KiROUND( pageRectIU.GetWidth() / 2.0 );
1109  centerPositionIU.y -= KiROUND( pageRectIU.GetHeight() / 2.0 );
1110  }
1111 
1112  DSIZE virtualSizeIU;
1113 
1114  if( pageRectIU.GetLeft() < clientRectIU.GetLeft() && pageRectIU.GetRight() > clientRectIU.GetRight() )
1115  {
1116  virtualSizeIU.x = pageRectIU.GetSize().x;
1117  }
1118  else
1119  {
1120  double pageCenterX = pageRectIU.GetX() + ( pageRectIU.GetWidth() / 2 );
1121  double clientCenterX = clientRectIU.GetX() + ( clientRectIU.GetWidth() / 2 );
1122 
1123  if( clientRectIU.GetWidth() > pageRectIU.GetWidth() )
1124  {
1125  if( pageCenterX > clientCenterX )
1126  virtualSizeIU.x = ( pageCenterX - clientRectIU.GetLeft() ) * 2;
1127  else if( pageCenterX < clientCenterX )
1128  virtualSizeIU.x = ( clientRectIU.GetRight() - pageCenterX ) * 2;
1129  else
1130  virtualSizeIU.x = clientRectIU.GetWidth();
1131  }
1132  else
1133  {
1134  if( pageCenterX > clientCenterX )
1135  virtualSizeIU.x = pageRectIU.GetWidth() + ( (pageRectIU.GetLeft() - clientRectIU.GetLeft() ) * 2 );
1136  else if( pageCenterX < clientCenterX )
1137  virtualSizeIU.x = pageRectIU.GetWidth() + ( (clientRectIU.GetRight() - pageRectIU.GetRight() ) * 2 );
1138  else
1139  virtualSizeIU.x = pageRectIU.GetWidth();
1140  }
1141  }
1142 
1143  if( pageRectIU.GetTop() < clientRectIU.GetTop() && pageRectIU.GetBottom() > clientRectIU.GetBottom() )
1144  {
1145  virtualSizeIU.y = pageRectIU.GetSize().y;
1146  }
1147  else
1148  {
1149  double pageCenterY = pageRectIU.GetY() + ( pageRectIU.GetHeight() / 2 );
1150  double clientCenterY = clientRectIU.GetY() + ( clientRectIU.GetHeight() / 2 );
1151 
1152  if( clientRectIU.GetHeight() > pageRectIU.GetHeight() )
1153  {
1154  if( pageCenterY > clientCenterY )
1155  virtualSizeIU.y = ( pageCenterY - clientRectIU.GetTop() ) * 2;
1156  else if( pageCenterY < clientCenterY )
1157  virtualSizeIU.y = ( clientRectIU.GetBottom() - pageCenterY ) * 2;
1158  else
1159  virtualSizeIU.y = clientRectIU.GetHeight();
1160  }
1161  else
1162  {
1163  if( pageCenterY > clientCenterY )
1164  virtualSizeIU.y = pageRectIU.GetHeight() +
1165  ( ( pageRectIU.GetTop() - clientRectIU.GetTop() ) * 2 );
1166  else if( pageCenterY < clientCenterY )
1167  virtualSizeIU.y = pageRectIU.GetHeight() +
1168  ( ( clientRectIU.GetBottom() - pageRectIU.GetBottom() ) * 2 );
1169  else
1170  virtualSizeIU.y = pageRectIU.GetHeight();
1171  }
1172  }
1173 
1174  // put "int" limits on the virtualSizeIU
1175  virtualSizeIU.x = std::min( virtualSizeIU.x, MAX_AXIS );
1176  virtualSizeIU.y = std::min( virtualSizeIU.y, MAX_AXIS );
1177 
1178  if( screen->m_Center )
1179  {
1180  screen->m_DrawOrg.x = -KiROUND( virtualSizeIU.x / 2.0 );
1181  screen->m_DrawOrg.y = -KiROUND( virtualSizeIU.y / 2.0 );
1182  }
1183  else
1184  {
1185  screen->m_DrawOrg.x = -KiROUND( ( virtualSizeIU.x - pageRectIU.GetWidth() ) / 2.0 );
1186  screen->m_DrawOrg.y = -KiROUND( ( virtualSizeIU.y - pageRectIU.GetHeight() ) / 2.0 );
1187  }
1188 
1189  /* Always set scrollbar pixels per unit to 1 unless you want the zoom
1190  * around cursor to jump around. This reported problem occurs when the
1191  * zoom point is not on a pixel per unit increment. If you set the
1192  * pixels per unit to 10, you have potential for the zoom point to
1193  * jump around +/-5 pixels from the nearest grid point.
1194  */
1195  screen->m_ScrollPixelsPerUnitX = screen->m_ScrollPixelsPerUnitY = 1;
1196 
1197  // Number of scroll bar units for the given zoom level in device units.
1198  double unitsX = virtualSizeIU.x * scale;
1199  double unitsY = virtualSizeIU.y * scale;
1200 
1201  // Store the requested center position for later use
1202  SetScrollCenterPosition( aCenterPositionIU );
1203 
1204  // Calculate the scroll bar position in internal units to place the
1205  // center position at the center of client rectangle.
1206  double posX = centerPositionIU.x - clientRectIU.GetWidth() / 2.0 - screen->m_DrawOrg.x;
1207  double posY = centerPositionIU.y - clientRectIU.GetHeight() / 2.0 - screen->m_DrawOrg.y;
1208 
1209  // Convert scroll bar position to device units.
1210  posX = KiROUND( posX * scale );
1211  posY = KiROUND( posY * scale );
1212 
1213  if( posX < 0 )
1214  {
1215  wxLogTrace( traceScrollSettings, wxT( "Required scroll bar X position %.10g" ), posX );
1216  posX = 0;
1217  }
1218 
1219  if( posX > unitsX )
1220  {
1221  wxLogTrace( traceScrollSettings, wxT( "Required scroll bar X position %.10g" ), posX );
1222  posX = unitsX;
1223  }
1224 
1225  if( posY < 0 )
1226  {
1227  wxLogTrace( traceScrollSettings, wxT( "Required scroll bar Y position %.10g" ), posY );
1228  posY = 0;
1229  }
1230 
1231  if( posY > unitsY )
1232  {
1233  wxLogTrace( traceScrollSettings, wxT( "Required scroll bar Y position %.10g" ), posY );
1234  posY = unitsY;
1235  }
1236 
1237  screen->m_ScrollbarPos = wxPoint( KiROUND( posX ), KiROUND( posY ) );
1238  screen->m_ScrollbarNumber = wxSize( KiROUND( unitsX ), KiROUND( unitsY ) );
1239 
1240  wxLogTrace( traceScrollSettings,
1241  wxT( "Drawing = (%.10g, %.10g), Client = (%.10g, %.10g), Offset = (%d, %d), SetScrollbars(%d, %d, %d, %d, %d, %d)" ),
1242  virtualSizeIU.x, virtualSizeIU.y, clientSizeIU.x, clientSizeIU.y,
1243  screen->m_DrawOrg.x, screen->m_DrawOrg.y,
1245  screen->m_ScrollbarNumber.x, screen->m_ScrollbarNumber.y,
1246  screen->m_ScrollbarPos.x, screen->m_ScrollbarPos.y );
1247 
1248  bool noRefresh = true;
1249 
1250  m_canvas->SetScrollbars( screen->m_ScrollPixelsPerUnitX,
1251  screen->m_ScrollPixelsPerUnitY,
1252  screen->m_ScrollbarNumber.x,
1253  screen->m_ScrollbarNumber.y,
1254  screen->m_ScrollbarPos.x,
1255  screen->m_ScrollbarPos.y, noRefresh );
1256 }
1257 
1258 
1259 void EDA_DRAW_FRAME::UseGalCanvas( bool aEnable )
1260 {
1261  KIGFX::VIEW* view = GetGalCanvas()->GetView();
1262  KIGFX::GAL* gal = GetGalCanvas()->GetGAL();
1263 
1264  // Display the same view after canvas switching
1265  if( aEnable )
1266  {
1267  // Switch to GAL renderer from legacy
1268  if( !m_galCanvasActive )
1269  {
1270  // Set up viewport
1271  view->SetScale( GetZoomLevelCoeff() / m_canvas->GetZoom() );
1273  }
1274 
1275  // Set up grid settings
1276  gal->SetGridVisibility( IsGridVisible() );
1277  gal->SetGridSize( VECTOR2D( GetScreen()->GetGridSize() ) );
1278  gal->SetGridOrigin( VECTOR2D( GetGridOrigin() ) );
1279 
1280  // Transfer EDA_DRAW_PANEL settings
1281  KIGFX::VIEW_CONTROLS* viewControls = GetGalCanvas()->GetViewControls();
1282  viewControls->EnableCursorWarping( !m_canvas->GetEnableZoomNoCenter() );
1284  viewControls->EnableAutoPan( m_canvas->GetEnableAutoPan() );
1285  }
1286  else if( m_galCanvasActive )
1287  {
1288  // Switch to legacy renderer from GAL
1289  m_canvas->SetZoom( GetGalCanvas()->GetLegacyZoom() );
1290  VECTOR2D center = view->GetCenter();
1291  AdjustScrollBars( wxPoint( center.x, center.y ) );
1292  }
1293 
1294  m_canvas->SetEvtHandlerEnabled( !aEnable );
1295  GetGalCanvas()->SetEvtHandlerEnabled( aEnable );
1296 
1297  // Switch panes
1298  m_auimgr.GetPane( "DrawFrame" ).Show( !aEnable );
1299  m_auimgr.GetPane( "DrawFrameGal" ).Show( aEnable );
1300  m_auimgr.Update();
1301 
1302  // Reset current tool on switch();
1304 
1305  m_galCanvasActive = aEnable;
1306 }
1307 
1308 
1310 {
1311  auto galCanvas = GetGalCanvas();
1312  wxCHECK( galCanvas, false );
1313  bool use_gal = galCanvas->SwitchBackend( aCanvasType );
1314  use_gal &= aCanvasType != EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE;
1315  UseGalCanvas( use_gal );
1316  m_canvasType = use_gal ? aCanvasType : EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE;
1317 
1318  return use_gal;
1319 }
1320 
1321 
1323 {
1325  wxConfigBase* cfg = Kiface().KifaceSettings();
1326 
1327  if( cfg )
1328  canvasType = (EDA_DRAW_PANEL_GAL::GAL_TYPE) cfg->ReadLong( CANVAS_TYPE_KEY,
1330 
1331  if( canvasType < EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE
1332  || canvasType >= EDA_DRAW_PANEL_GAL::GAL_TYPE_LAST )
1333  {
1334  assert( false );
1335  canvasType = EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE;
1336  }
1337 
1338  // Coerce the value into a GAL type when Legacy is not available
1339  // Default to Cairo, and on the first, user will be prompted for OpenGL
1340  if( canvasType == EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE
1341  && !ADVANCED_CFG::GetCfg().AllowLegacyCanvas() )
1342  {
1344  }
1345 
1346  return canvasType;
1347 }
1348 
1349 
1351 {
1352  if( aCanvasType < EDA_DRAW_PANEL_GAL::GAL_TYPE_NONE
1353  || aCanvasType >= EDA_DRAW_PANEL_GAL::GAL_TYPE_LAST )
1354  {
1355  assert( false );
1356  return false;
1357  }
1358 
1359  wxConfigBase* cfg = Kiface().KifaceSettings();
1360 
1361  if( cfg )
1362  return cfg->Write( CANVAS_TYPE_KEY, (long) aCanvasType );
1363 
1364  return false;
1365 }
1366 
1367 //-----< BASE_SCREEN API moved here >--------------------------------------------
1368 
1369 wxPoint EDA_DRAW_FRAME::GetCrossHairPosition( bool aInvertY ) const
1370 {
1371  // subject to change, borrow from old BASE_SCREEN for now.
1372  if( IsGalCanvasActive() )
1373  {
1375 
1376  return wxPoint( cursor.x, cursor.y );
1377  }
1378  else
1379  {
1380  BASE_SCREEN* screen = GetScreen(); // virtual call
1381  return screen->getCrossHairPosition( aInvertY );
1382  }
1383 }
1384 
1385 
1386 void EDA_DRAW_FRAME::SetCrossHairPosition( const wxPoint& aPosition, bool aSnapToGrid )
1387 {
1388  BASE_SCREEN* screen = GetScreen(); // virtual call
1389  screen->setCrossHairPosition( aPosition, GetGridOrigin(), aSnapToGrid );
1390 }
1391 
1392 
1393 wxPoint EDA_DRAW_FRAME::GetCursorPosition( bool aOnGrid, wxRealPoint* aGridSize ) const
1394 {
1395  BASE_SCREEN* screen = GetScreen(); // virtual call
1396  return screen->getCursorPosition( aOnGrid, GetGridOrigin(), aGridSize );
1397 }
1398 
1399 
1400 wxPoint EDA_DRAW_FRAME::GetNearestGridPosition( const wxPoint& aPosition, wxRealPoint* aGridSize ) const
1401 {
1402  BASE_SCREEN* screen = GetScreen(); // virtual call
1403  return screen->getNearestGridPosition( aPosition, GetGridOrigin(), aGridSize );
1404 }
1405 
1406 
1408 {
1409  BASE_SCREEN* screen = GetScreen(); // virtual call
1410  return screen->getCrossHairScreenPosition();
1411 }
1412 
1413 
1414 void EDA_DRAW_FRAME::SetMousePosition( const wxPoint& aPosition )
1415 {
1416  BASE_SCREEN* screen = GetScreen(); // virtual call
1417  screen->setMousePosition( aPosition );
1418 }
1419 
1420 
1421 wxPoint EDA_DRAW_FRAME::RefPos( bool useMouse ) const
1422 {
1423  BASE_SCREEN* screen = GetScreen(); // virtual call
1424  return screen->refPos( useMouse );
1425 }
1426 
1427 
1428 const wxPoint& EDA_DRAW_FRAME::GetScrollCenterPosition() const
1429 {
1430  BASE_SCREEN* screen = GetScreen(); // virtual call
1431  return screen->getScrollCenterPosition();
1432 }
1433 
1434 
1435 void EDA_DRAW_FRAME::SetScrollCenterPosition( const wxPoint& aPoint )
1436 {
1437  BASE_SCREEN* screen = GetScreen(); // virtual call
1438  screen->setScrollCenterPosition( aPoint );
1439 }
1440 
1441 //-----</BASE_SCREEN API moved here >--------------------------------------------
1442 
1443 void EDA_DRAW_FRAME::RefreshCrossHair( const wxPoint &aOldPos, const wxPoint &aEvtPos, wxDC* aDC )
1444 {
1445  wxPoint newpos = GetCrossHairPosition();
1446 
1447  // Redraw the crosshair if it moved
1448  if( aOldPos != newpos )
1449  {
1450  SetCrossHairPosition( aOldPos, false );
1451  m_canvas->CrossHairOff( aDC );
1452  SetCrossHairPosition( newpos, false );
1453  m_canvas->CrossHairOn( aDC );
1454 
1455  if( m_canvas->IsMouseCaptured() )
1456  {
1457 #ifdef USE_WX_OVERLAY
1458  wxDCOverlay oDC( m_overlay, (wxWindowDC*)aDC );
1459  oDC.Clear();
1460  m_canvas->CallMouseCapture( aDC, aEvtPos, false );
1461 #else
1462  m_canvas->CallMouseCapture( aDC, aEvtPos, true );
1463 #endif
1464  }
1465 #ifdef USE_WX_OVERLAY
1466  else
1467  {
1468  m_overlay.Reset();
1469  }
1470 #endif
1471  }
1472 }
1473 
1474 
1475 bool EDA_DRAW_FRAME::LibraryFileBrowser( bool doOpen, wxFileName& aFilename,
1476  const wxString& wildcard, const wxString& ext,
1477  bool isDirectory )
1478 {
1479  wxString prompt = doOpen ? _( "Select Library" ) : _( "New Library" );
1480  aFilename.SetExt( ext );
1481 
1482 #ifndef __WXMAC__
1483  if( isDirectory )
1484  {
1485  wxDirDialog dlg( this, prompt, Prj().GetProjectPath(),
1486  doOpen ? wxDD_DEFAULT_STYLE | wxDD_DIR_MUST_EXIST : wxDD_DEFAULT_STYLE );
1487 
1488  if( dlg.ShowModal() == wxID_CANCEL )
1489  return false;
1490 
1491  aFilename = dlg.GetPath();
1492  aFilename.SetExt( ext );
1493  }
1494  else
1495 #endif
1496  {
1497  wxFileDialog dlg( this, prompt, Prj().GetProjectPath(), aFilename.GetFullName() ,
1498  wildcard, doOpen ? wxFD_OPEN | wxFD_FILE_MUST_EXIST
1499  : wxFD_SAVE | wxFD_CHANGE_DIR | wxFD_OVERWRITE_PROMPT );
1500 
1501  if( dlg.ShowModal() == wxID_CANCEL )
1502  return false;
1503 
1504  aFilename = dlg.GetPath();
1505  aFilename.SetExt( ext );
1506  }
1507 
1508  return true;
1509 }
1510 
1511 
1512 bool EDA_DRAW_FRAME::GeneralControlKeyMovement( int aHotKey, wxPoint *aPos, bool aSnapToGrid )
1513 {
1514  bool key_handled = false;
1515 
1516  // If requested snap the current position to the grid
1517  if( aSnapToGrid )
1518  *aPos = GetNearestGridPosition( *aPos );
1519 
1520  switch( aHotKey )
1521  {
1522  // All these keys have almost the same treatment
1523  case GR_KB_CTRL | WXK_NUMPAD8:
1524  case GR_KB_CTRL | WXK_UP:
1525  case GR_KB_CTRL | WXK_NUMPAD2:
1526  case GR_KB_CTRL | WXK_DOWN:
1527  case GR_KB_CTRL | WXK_NUMPAD4:
1528  case GR_KB_CTRL | WXK_LEFT:
1529  case GR_KB_CTRL | WXK_NUMPAD6:
1530  case GR_KB_CTRL | WXK_RIGHT:
1531  case WXK_NUMPAD8:
1532  case WXK_UP:
1533  case WXK_NUMPAD2:
1534  case WXK_DOWN:
1535  case WXK_NUMPAD4:
1536  case WXK_LEFT:
1537  case WXK_NUMPAD6:
1538  case WXK_RIGHT:
1539  key_handled = true;
1540  {
1541  /* Here's a tricky part: when doing cursor key movement, the
1542  * 'previous' point should be taken from memory, *not* from the
1543  * freshly computed position in the event. Otherwise you can't do
1544  * sub-pixel movement. The m_movingCursorWithKeyboard oneshot 'eats'
1545  * the automatic motion event generated by cursor warping */
1546  wxRealPoint gridSize = GetScreen()->GetGridSize();
1547  *aPos = GetCrossHairPosition();
1548 
1549  // Bonus: ^key moves faster (x10)
1550  switch( aHotKey )
1551  {
1552  case GR_KB_CTRL|WXK_NUMPAD8:
1553  case GR_KB_CTRL|WXK_UP:
1554  aPos->y -= KiROUND( 10 * gridSize.y );
1555  break;
1556 
1557  case GR_KB_CTRL|WXK_NUMPAD2:
1558  case GR_KB_CTRL|WXK_DOWN:
1559  aPos->y += KiROUND( 10 * gridSize.y );
1560  break;
1561 
1562  case GR_KB_CTRL|WXK_NUMPAD4:
1563  case GR_KB_CTRL|WXK_LEFT:
1564  aPos->x -= KiROUND( 10 * gridSize.x );
1565  break;
1566 
1567  case GR_KB_CTRL|WXK_NUMPAD6:
1568  case GR_KB_CTRL|WXK_RIGHT:
1569  aPos->x += KiROUND( 10 * gridSize.x );
1570  break;
1571 
1572  case WXK_NUMPAD8:
1573  case WXK_UP:
1574  aPos->y -= KiROUND( gridSize.y );
1575  break;
1576 
1577  case WXK_NUMPAD2:
1578  case WXK_DOWN:
1579  aPos->y += KiROUND( gridSize.y );
1580  break;
1581 
1582  case WXK_NUMPAD4:
1583  case WXK_LEFT:
1584  aPos->x -= KiROUND( gridSize.x );
1585  break;
1586 
1587  case WXK_NUMPAD6:
1588  case WXK_RIGHT:
1589  aPos->x += KiROUND( gridSize.x );
1590  break;
1591 
1592  default: /* Can't happen since we entered the statement */
1593  break;
1594  }
1595 
1596  m_canvas->MoveCursor( *aPos );
1598  }
1599  break;
1600 
1601  default:
1602  break;
1603  }
1604 
1605  return key_handled;
1606 }
1607 
1608 
1609 bool EDA_DRAW_FRAME::isBusy() const
1610 {
1611  const BASE_SCREEN* screen = const_cast< BASE_SCREEN* >( GetScreen() );
1612 
1613  if( !screen )
1614  return false;
1615 
1616  return ( screen->GetCurItem() && screen->GetCurItem()->GetFlags() )
1617  || ( screen->m_BlockLocate.GetState() != STATE_NO_BLOCK );
1618 }
1619 
1620 
1621 void EDA_DRAW_FRAME::RedrawScreen( const wxPoint& aCenterPoint, bool aWarpPointer )
1622 {
1623  if( IsGalCanvasActive() )
1624  return;
1625 
1626  AdjustScrollBars( aCenterPoint );
1627 
1628  // Move the mouse cursor to the on grid graphic cursor position
1629  if( aWarpPointer )
1631 
1632  m_canvas->Refresh();
1633  m_canvas->Update();
1634 }
1635 
1636 
1637 void EDA_DRAW_FRAME::RedrawScreen2( const wxPoint& posBefore )
1638 {
1639  if( IsGalCanvasActive() )
1640  return;
1641 
1642  // Account for scrollbars (see EDA_DRAW_FRAME::AdjustScrollBars that takes
1643  // in account scroolbars area to adjust scroll bars)
1644  wxSize scrollbarSize = m_canvas->GetSize() - m_canvas->GetClientSize();
1645  wxSize sizeAdjusted = m_canvas->GetClientSize() - scrollbarSize;
1646 
1647  wxPoint dPos = posBefore - sizeAdjusted / 2;
1648 
1649  // screen position of crosshair after zoom
1650  wxPoint newScreenPos = m_canvas->ToDeviceXY( GetCrossHairPosition() );
1651  wxPoint newCenter = m_canvas->ToLogicalXY( newScreenPos - dPos );
1652 
1653  AdjustScrollBars( newCenter );
1654 
1655  m_canvas->Refresh();
1656  m_canvas->Update();
1657 }
1658 
1659 
1661 {
1662  m_canvas->Refresh();
1663  m_canvas->Update();
1664 }
1665 
1666 
1667 // Factor out the calculation portion of the various BestZoom() implementations.
1668 //
1669 // Note that like it's forerunners this routine has an intentional side-effect: it
1670 // sets the scroll centre position. While I'm not happy about that, it's probably
1671 // not worth fixing as its days are numbered (GAL canvases use a different method).
1672 double EDA_DRAW_FRAME::bestZoom( double sizeX, double sizeY, double scaleFactor, wxPoint centre )
1673 {
1674  double bestzoom = std::max( sizeX * scaleFactor / (double) m_canvas->GetClientSize().x,
1675  sizeY * scaleFactor / (double) m_canvas->GetClientSize().y );
1676 
1677  // Take scrollbars into account
1678  DSIZE scrollbarSize = m_canvas->GetSize() - m_canvas->GetClientSize();
1679  centre.x -= int( bestzoom * scrollbarSize.x / 2.0 );
1680  centre.y -= int( bestzoom * scrollbarSize.y / 2.0 );
1681 
1682  SetScrollCenterPosition( centre );
1683 
1684  return bestzoom;
1685 }
1686 
1687 
1688 void EDA_DRAW_FRAME::Zoom_Automatique( bool aWarpPointer )
1689 {
1690  BASE_SCREEN* screen = GetScreen();
1691 
1692  // Set the best zoom and get center point.
1693 
1694  // BestZoom() can compute an illegal zoom if the client window size
1695  // is small, say because frame is not maximized. So use the clamping form
1696  // of SetZoom():
1697  double bestzoom = BestZoom();
1698  screen->SetScalingFactor( bestzoom );
1699 
1700  if( !screen->m_Initialized )
1702 
1703  if( !IsGalCanvasActive() )
1704  RedrawScreen( GetScrollCenterPosition(), aWarpPointer );
1705  else
1706  m_toolManager->RunAction( "common.Control.zoomFitScreen", true );
1707 }
1708 
1709 
1711 {
1712  // Compute the best zoom
1713  Rect.Normalize();
1714 
1715  wxSize size = m_canvas->GetClientSize();
1716 
1717  // Use ceil to at least show the full rect
1718  double scalex = (double) Rect.GetSize().x / size.x;
1719  double bestscale = (double) Rect.GetSize().y / size.y;
1720 
1721  bestscale = std::max( bestscale, scalex );
1722 
1723  GetScreen()->SetScalingFactor( bestscale );
1724  RedrawScreen( Rect.Centre(), true );
1725 }
1726 
1727 
1728 void EDA_DRAW_FRAME::OnZoom( wxCommandEvent& event )
1729 {
1730  if( m_canvas == NULL )
1731  return;
1732 
1733  int id = event.GetId();
1734  bool zoom_at_cursor = false;
1735  BASE_SCREEN* screen = GetScreen();
1736  wxPoint center = GetScrollCenterPosition();
1737 
1738  if ( id == ID_KEY_ZOOM_IN )
1739  {
1740  id = GetCanvas()->GetEnableZoomNoCenter() ?
1742  }
1743  else if ( id == ID_KEY_ZOOM_OUT )
1744  {
1745  id = GetCanvas()->GetEnableZoomNoCenter() ?
1747  }
1748 
1749  switch( id )
1750  {
1751  case ID_OFFCENTER_ZOOM_IN:
1752  center = m_canvas->ToDeviceXY( GetCrossHairPosition() );
1753 
1754  if( screen->SetPreviousZoom() )
1755  RedrawScreen2( center );
1756  break;
1757 
1758  case ID_POPUP_ZOOM_IN:
1759  zoom_at_cursor = true;
1760  center = GetCrossHairPosition();
1761 
1762  // fall thru
1763  case ID_VIEWER_ZOOM_IN:
1764  case ID_ZOOM_IN:
1765  if( screen->SetPreviousZoom() )
1766  RedrawScreen( center, zoom_at_cursor );
1767  break;
1768 
1769  case ID_OFFCENTER_ZOOM_OUT:
1770  center = m_canvas->ToDeviceXY( GetCrossHairPosition() );
1771 
1772  if( screen->SetNextZoom() )
1773  RedrawScreen2( center );
1774  break;
1775 
1776  case ID_POPUP_ZOOM_OUT:
1777  zoom_at_cursor = true;
1778  center = GetCrossHairPosition();
1779 
1780  // fall thru
1781  case ID_VIEWER_ZOOM_OUT:
1782  case ID_ZOOM_OUT:
1783  if( screen->SetNextZoom() )
1784  RedrawScreen( center, zoom_at_cursor );
1785  break;
1786 
1787  case ID_VIEWER_ZOOM_REDRAW:
1788  case ID_POPUP_ZOOM_REDRAW:
1789  case ID_ZOOM_REDRAW:
1790  // This usually means something went wrong. Do a hard refresh.
1791  SetScreen( GetScreen() );
1792  break;
1793 
1794  case ID_POPUP_ZOOM_CENTER:
1795  center = GetCrossHairPosition();
1796  RedrawScreen( center, true );
1797  break;
1798 
1799  case ID_POPUP_ZOOM_PAGE:
1800  case ID_VIEWER_ZOOM_PAGE:
1801  case ID_ZOOM_PAGE:
1802  Zoom_Automatique( false );
1803  break;
1804 
1805  case ID_POPUP_ZOOM_SELECT:
1806  break;
1807 
1808  case ID_POPUP_CANCEL:
1810  break;
1811 
1812  default:
1814  }
1815 
1816  UpdateStatusBar();
1817 }
1818 
1819 
1821 {
1822  GetScreen()->SetNextZoom();
1823 }
1824 
1825 
1827 {
1829 }
1830 
1831 
1832 void EDA_DRAW_FRAME::SetPresetZoom( int aIndex )
1833 {
1834  BASE_SCREEN* screen = GetScreen();
1835 
1836  if( aIndex >= (int) screen->m_ZoomList.size() )
1837  {
1838  wxLogDebug( wxT( "%s %d: index %d is outside the bounds of the zoom list." ),
1839  __TFILE__, __LINE__, aIndex );
1840  return;
1841  }
1842 
1843  if( m_zoomSelectBox )
1844  m_zoomSelectBox->SetSelection( aIndex );
1845 
1846  if( screen->SetZoom( screen->m_ZoomList[aIndex] ) )
1848 
1849  UpdateStatusBar();
1850 }
1851 
1852 
1853 void EDA_DRAW_FRAME::AddMenuZoomAndGrid( wxMenu* MasterMenu )
1854 {
1855  int maxZoomIds;
1856  double zoom;
1857  wxString msg;
1858  BASE_SCREEN* screen = m_canvas->GetScreen();
1859 
1860  msg = AddHotkeyName( _( "Center" ), m_hotkeysDescrList, HK_ZOOM_CENTER );
1861  AddMenuItem( MasterMenu, ID_POPUP_ZOOM_CENTER, msg, KiBitmap( zoom_center_on_screen_xpm ) );
1862  msg = AddHotkeyName( _( "Zoom In" ), m_hotkeysDescrList, HK_ZOOM_IN );
1863  AddMenuItem( MasterMenu, ID_POPUP_ZOOM_IN, msg, KiBitmap( zoom_in_xpm ) );
1864  msg = AddHotkeyName( _( "Zoom Out" ), m_hotkeysDescrList, HK_ZOOM_OUT );
1865  AddMenuItem( MasterMenu, ID_POPUP_ZOOM_OUT, msg, KiBitmap( zoom_out_xpm ) );
1866  msg = AddHotkeyName( _( "Redraw View" ), m_hotkeysDescrList, HK_ZOOM_REDRAW );
1867  AddMenuItem( MasterMenu, ID_POPUP_ZOOM_REDRAW, msg, KiBitmap( zoom_redraw_xpm ) );
1868  msg = AddHotkeyName( _( "Zoom to Fit" ), m_hotkeysDescrList, HK_ZOOM_AUTO );
1869  AddMenuItem( MasterMenu, ID_POPUP_ZOOM_PAGE, msg, KiBitmap( zoom_fit_in_page_xpm ) );
1870 
1871 
1872  wxMenu* zoom_choice = new wxMenu;
1873  AddMenuItem( MasterMenu, zoom_choice,
1874  ID_POPUP_ZOOM_SELECT, _( "Zoom" ),
1875  KiBitmap( zoom_selection_xpm ) );
1876 
1877  zoom = screen->GetZoom();
1879  maxZoomIds = ( (size_t) maxZoomIds < screen->m_ZoomList.size() ) ?
1880  maxZoomIds : screen->m_ZoomList.size();
1881 
1882  // Populate zoom submenu.
1883  for( int i = 0; i < maxZoomIds; i++ )
1884  {
1885  msg.Printf( wxT( "%.2f" ), m_zoomLevelCoeff / screen->m_ZoomList[i] );
1886 
1887  zoom_choice->Append( ID_POPUP_ZOOM_LEVEL_START + i, _( "Zoom: " ) + msg,
1888  wxEmptyString, wxITEM_CHECK );
1889  if( zoom == screen->m_ZoomList[i] )
1890  zoom_choice->Check( ID_POPUP_ZOOM_LEVEL_START + i, true );
1891  }
1892 
1893  // Create grid submenu as required.
1894  if( screen->GetGridCount() )
1895  {
1896  wxMenu* gridMenu = new wxMenu;
1897  AddMenuItem( MasterMenu, gridMenu, ID_POPUP_GRID_SELECT,
1898  _( "Grid" ), KiBitmap( grid_select_xpm ) );
1899 
1900  wxArrayString gridsList;
1901  int icurr = screen->BuildGridsChoiceList( gridsList, GetUserUnits() != INCHES );
1902 
1903  for( unsigned i = 0; i < gridsList.GetCount(); i++ )
1904  {
1905  GRID_TYPE& grid = screen->GetGrid( i );
1906  gridMenu->Append( grid.m_CmdId, gridsList[i], wxEmptyString, wxITEM_CHECK );
1907 
1908  if( (int)i == icurr )
1909  gridMenu->Check( grid.m_CmdId, true );
1910  }
1911  }
1912 
1913  MasterMenu->AppendSeparator();
1914  AddMenuItem( MasterMenu, ID_POPUP_CANCEL, _( "Close" ), KiBitmap( cancel_xpm ) );
1915 }
1916 
1917 
1918 // Find the first child dialog.
1919 wxWindow* findDialog( wxWindowList& aList )
1920 {
1921  for( wxWindow* window : aList )
1922  {
1923  if( dynamic_cast<DIALOG_SHIM*>( window ) )
1924  return window;
1925  }
1926  return NULL;
1927 }
1928 
1929 
1930 void EDA_DRAW_FRAME::FocusOnLocation( const wxPoint& aPos, bool aWarpCursor, bool aCenterView )
1931 {
1932  if( IsGalCanvasActive() )
1933  {
1934  if( aCenterView )
1935  {
1936  wxWindow* dialog = findDialog( GetChildren() );
1937 
1938  // If a dialog partly obscures the window, then center on the uncovered area.
1939  if( dialog )
1940  {
1941  wxRect dialogRect( GetGalCanvas()->ScreenToClient( dialog->GetScreenPosition() ),
1942  dialog->GetSize() );
1943  GetGalCanvas()->GetView()->SetCenter( aPos, dialogRect );
1944  }
1945  else
1946  GetGalCanvas()->GetView()->SetCenter( aPos );
1947  }
1948 
1949  if( aWarpCursor )
1951  else
1953  }
1954  else
1955  {
1957 
1958  // There may be need to reframe the drawing.
1959  if( aCenterView || !m_canvas->IsPointOnDisplay( aPos ) )
1960  {
1961  SetCrossHairPosition( aPos );
1962  RedrawScreen( aPos, aWarpCursor );
1963  }
1964  else
1965  {
1966  // Put cursor on item position
1967  m_canvas->CrossHairOff( &dc );
1968  SetCrossHairPosition( aPos );
1969 
1970  if( aWarpCursor )
1972  }
1973 
1974  // Be sure cross hair cursor is ON:
1975  m_canvas->CrossHairOn( &dc );
1976  m_canvas->CrossHairOn( &dc );
1977  }
1978 }
1979 
1980 
1981 static bool DrawPageOnClipboard( EDA_DRAW_FRAME* aFrame );
1982 
1983 
1984 void EDA_DRAW_FRAME::CopyToClipboard( wxCommandEvent& event )
1985 {
1986  DrawPageOnClipboard( this );
1987 
1988  if( event.GetId() == ID_GEN_COPY_BLOCK_TO_CLIPBOARD )
1989  {
1990  if( GetScreen()->IsBlockActive() )
1991  m_canvas->SetCursor( wxCursor( (wxStockCursor) m_canvas->GetDefaultCursor() ) );
1992 
1994  }
1995 }
1996 
1997 
1998 /* copy the current page or block to the clipboard ,
1999  * to export drawings to other applications (word processing ...)
2000  * This is not suitable for copy command within Eeschema or Pcbnew
2001  */
2003 {
2004  bool DrawBlock = false;
2005  wxRect DrawArea;
2006  BASE_SCREEN* screen = aFrame->GetCanvas()->GetScreen();
2007 
2008  if( screen->IsBlockActive() )
2009  {
2010  DrawBlock = true;
2011  DrawArea.SetX( screen->m_BlockLocate.GetX() );
2012  DrawArea.SetY( screen->m_BlockLocate.GetY() );
2013  DrawArea.SetWidth( screen->m_BlockLocate.GetWidth() );
2014  DrawArea.SetHeight( screen->m_BlockLocate.GetHeight() );
2015  }
2016  else
2017  DrawArea.SetSize( aFrame->GetPageSizeIU() );
2018 
2019  // Calculate a reasonable dc size, in pixels, and the dc scale to fit
2020  // the drawings into the dc size
2021  // scale is the ratio resolution (in PPI) / internal units
2022  double ppi = 300; // Use 300 pixels per inch to create bitmap images on start
2023  double inch2Iu = 1000.0 * (double) screen->MilsToIuScalar();
2024  double scale = ppi / inch2Iu;
2025 
2026  wxSize dcsize = DrawArea.GetSize();
2027 
2028  int maxdim = std::max( dcsize.x, dcsize.y );
2029 
2030  // the max size in pixels of the bitmap used to byuild the sheet copy
2031  const int maxbitmapsize = 3000;
2032 
2033  while( int( maxdim * scale ) > maxbitmapsize )
2034  {
2035  ppi = ppi / 1.5;
2036  scale = ppi / inch2Iu;
2037  }
2038 
2039  dcsize.x *= scale;
2040  dcsize.y *= scale;
2041 
2042  // Set draw offset, zoom... to values needed to draw in the memory DC
2043  // after saving initial values:
2044  wxPoint tmp_startvisu = screen->m_StartVisu;
2045  double tmpzoom = screen->GetZoom();
2046  wxPoint old_org = screen->m_DrawOrg;
2047  screen->m_DrawOrg.x = screen->m_DrawOrg.y = 0;
2048  screen->m_StartVisu.x = screen->m_StartVisu.y = 0;
2049 
2050  screen->SetZoom( 1 ); // we use zoom = 1 in draw functions.
2051 
2052  wxMemoryDC dc;
2053  wxBitmap image( dcsize );
2054  dc.SelectObject( image );
2055 
2056  EDA_RECT tmp = *aFrame->GetCanvas()->GetClipBox();
2057  GRResetPenAndBrush( &dc );
2058  GRForceBlackPen( false );
2059  screen->m_IsPrinting = true;
2060  dc.SetUserScale( scale, scale );
2061 
2062  aFrame->GetCanvas()->SetClipBox( EDA_RECT( wxPoint( 0, 0 ),
2063  wxSize( 0x7FFFFF0, 0x7FFFFF0 ) ) );
2064 
2065  if( DrawBlock )
2066  {
2067  dc.SetClippingRegion( DrawArea );
2068  }
2069 
2070  dc.Clear();
2071  aFrame->GetCanvas()->EraseScreen( &dc );
2072  const LSET allLayersMask = LSET().set();
2073  aFrame->PrintPage( &dc, allLayersMask, false );
2074  screen->m_IsPrinting = false;
2075  aFrame->GetCanvas()->SetClipBox( tmp );
2076 
2077  bool success = true;
2078 
2079  if( wxTheClipboard->Open() )
2080  {
2081  // This data objects are held by the clipboard,
2082  // so do not delete them in the app.
2083  wxBitmapDataObject* clipbrd_data = new wxBitmapDataObject( image );
2084  wxTheClipboard->SetData( clipbrd_data );
2085  wxTheClipboard->Close();
2086  }
2087  else
2088  success = false;
2089 
2090  // Deselect Bitmap from DC in order to delete the MemoryDC safely
2091  // without deleting the bitmap
2092  dc.SelectObject( wxNullBitmap );
2093 
2094  GRForceBlackPen( false );
2095 
2096  screen->m_StartVisu = tmp_startvisu;
2097  screen->m_DrawOrg = old_org;
2098  screen->SetZoom( tmpzoom );
2099 
2100  return success;
2101 }
2102 
2103 
2104 void DrawPageLayout( wxDC* aDC, EDA_RECT* aClipBox,
2105  const PAGE_INFO& aPageInfo,
2106  const wxString &aFullSheetName,
2107  const wxString& aFileName,
2108  TITLE_BLOCK& aTitleBlock,
2109  int aSheetCount, int aSheetNumber,
2110  int aPenWidth, double aScalar,
2111  COLOR4D aColor, COLOR4D aAltColor,
2112  const wxString& aSheetLayer )
2113 {
2114  WS_DRAW_ITEM_LIST drawList;
2115 
2116  drawList.SetPenSize( aPenWidth );
2117  drawList.SetMilsToIUfactor( aScalar );
2118  drawList.SetSheetNumber( aSheetNumber );
2119  drawList.SetSheetCount( aSheetCount );
2120  drawList.SetFileName( aFileName );
2121  drawList.SetSheetName( aFullSheetName );
2122  drawList.SetSheetLayer( aSheetLayer );
2123 
2124  drawList.BuildWorkSheetGraphicList( aPageInfo,
2125  aTitleBlock, aColor, aAltColor );
2126 
2127  // Draw item list
2128  drawList.Draw( aClipBox, aDC );
2129 }
2130 
2131 
2132 void EDA_DRAW_FRAME::DrawWorkSheet( wxDC* aDC, BASE_SCREEN* aScreen, int aLineWidth,
2133  double aScalar, const wxString &aFilename,
2134  const wxString &aSheetLayer )
2135 {
2137  return;
2138 
2139  const PAGE_INFO& pageInfo = GetPageSettings();
2140  wxSize pageSize = pageInfo.GetSizeMils();
2141 
2142  // if not printing, draw the page limits:
2143  if( !aScreen->m_IsPrinting && m_showPageLimits )
2144  {
2145  GRSetDrawMode( aDC, GR_COPY );
2146  GRRect( m_canvas->GetClipBox(), aDC, 0, 0,
2147  pageSize.x * aScalar, pageSize.y * aScalar, aLineWidth,
2149  }
2150 
2151  TITLE_BLOCK t_block = GetTitleBlock();
2152  COLOR4D color = COLOR4D( RED );
2153 
2154  wxPoint origin = aDC->GetDeviceOrigin();
2155 
2156  if( aScreen->m_IsPrinting && origin.y > 0 )
2157  {
2158  aDC->SetDeviceOrigin( 0, 0 );
2159  aDC->SetAxisOrientation( true, false );
2160  }
2161 
2162  DrawPageLayout( aDC, m_canvas->GetClipBox(), pageInfo,
2163  GetScreenDesc(), aFilename, t_block,
2164  aScreen->m_NumberOfScreens, aScreen->m_ScreenNumber,
2165  aLineWidth, aScalar, color, color, aSheetLayer );
2166 
2167  if( aScreen->m_IsPrinting && origin.y > 0 )
2168  {
2169  aDC->SetDeviceOrigin( origin.x, origin.y );
2170  aDC->SetAxisOrientation( true, true );
2171  }
2172 }
2173 
2174 
2175 wxString EDA_DRAW_FRAME::GetScreenDesc() const
2176 {
2177  // Virtual function. In basic class, returns
2178  // an empty string.
2179  return wxEmptyString;
2180 }
2181 
2182 
2184 {
2185  BOX2I rv;
2186  rv.SetMaximum();
2187  return rv;
2188 }
2189 
2190 
2191 bool EDA_DRAW_FRAME::saveCanvasImageToFile( const wxString& aFileName, wxBitmapType aBitmapType )
2192 {
2193  return SaveCanvasImageToFile( this, aFileName, aBitmapType );
2194 }
virtual BASE_SCREEN * GetScreen()=0
TOOL_MANAGER * m_toolManager
Definition: draw_frame.h:125
virtual void ReCreateMenuBar() override
Function ReCreateMenuBar Creates recreates the menu bar.
void GRResetPenAndBrush(wxDC *DC)
Definition: gr_basic.cpp:123
const VECTOR2D & GetCenter() const
Function GetCenter() Returns the center point of this VIEW (in world space coordinates) ...
Definition: view.h:339
coord_type GetY() const
Definition: box2.h:189
wxPoint getCursorPosition(bool aOnGrid, const wxPoint &aGridOrigin, wxRealPoint *aGridSize) const
Function getCursorPosition returns the current cursor position in logical (drawing) units...
STATUS_FLAGS GetFlags() const
Definition: base_struct.h:258
void CommonSettingsChanged() override
Function CommonSettingsChanged Notification event that some of the common (suite-wide) settings have ...
Class KIWAY_PLAYER is a wxFrame capable of the OpenProjectFiles function, meaning it can load a porti...
Definition: kiway_player.h:120
virtual wxPoint GetScreenCenterLogicalPosition()
Update the board display after modifying it by a python script (note: it is automatically called by a...
void AdjustScrollBars(const wxPoint &aCenterPosition)
int m_ScreenNumber
Definition: base_screen.h:216
void OnToggleCrossHairStyle(wxCommandEvent &aEvent)
BLOCK_SELECTOR m_BlockLocate
Block description for block commands.
Definition: base_screen.h:214
FOOTPRINT_EDIT_FRAME::OnVerticalToolbar FOOTPRINT_EDIT_FRAME::ProcessPreferences FOOTPRINT_EDIT_FRAME::Process_Special_Functions FOOTPRINT_EDIT_FRAME::Process_Special_Functions FOOTPRINT_EDIT_FRAME::Process_Special_Functions EVT_UPDATE_UI(ID_MODEDIT_LOAD_MODULE_FROM_BOARD, FOOTPRINT_EDIT_FRAME::OnUpdateLoadModuleFromBoard) EVT_UPDATE_UI(ID_MODEDIT_INSERT_MODULE_IN_BOARD
Structure EDA_HOTKEY_CONFIG contains the information required to save hot key information to a config...
Definition: hotkeys_basic.h:94
bool m_galCanvasActive
whether to use new GAL engine
Definition: draw_frame.h:97
void SetCurrentCursor(int aCursor)
Function SetCurrentCursor Set the current cursor shape for drawpanel.
void SetFileName(const wxString &aFileName)
Set the filename to draw/plot.
void SetPenSize(int aPenSize)
Function SetPenSize Set the default pen size to draw/plot lines and texts.
wxSize m_ScrollbarNumber
Current virtual draw area size in scroll units.
Definition: base_screen.h:192
virtual EDA_DRAW_PANEL * GetCanvas() const
Definition: draw_frame.h:385
void GRSetDrawMode(wxDC *DC, GR_DRAWMODE draw_mode)
Definition: gr_basic.cpp:223
virtual const TITLE_BLOCK & GetTitleBlock() const =0
int m_ScrollPixelsPerUnitY
Pixels per scroll unit in the vertical direction.
Definition: base_screen.h:190
KIGFX::GAL_DISPLAY_OPTIONS & GetGalDisplayOptions()
Return a reference to the gal rendering options used by GAL for rendering.
Definition: draw_frame.h:943
static int KiROUND(double v)
Round a floating point number to an integer using "round halfway cases away from zero".
Definition: common.h:121
virtual const wxString GetZoomLevelIndicator() const
Return a human readable value which can be displayed as zoom level indicator in dialogs.
void setScrollCenterPosition(const wxPoint &aPoint)
Definition: base_screen.h:174
EDA_ITEM * GetCurItem() const
Definition: base_screen.h:233
virtual void HandleBlockPlace(wxDC *DC)
Called after HandleBlockEnd, when a block command needs to be executed after the block is moved to it...
bool SaveCanvasImageToFile(EDA_DRAW_FRAME *aFrame, const wxString &aFileName, wxBitmapType aBitmapType)
Save the current view as an image file.
Definition: bitmap.cpp:195
virtual wxPoint ToDeviceXY(const wxPoint &pos)
Function ToDeviceXY transforms logical to device coordinates.
double GetScalingFactor() const
Function GetScalingFactor returns the inverse of the current scale used to draw items on screen...
Definition: base_screen.cpp:95
Implementation of conversion functions that require both schematic and board internal units...
This file is part of the common library.
wxPoint GetGridPosition(const wxPoint &aPosition) const
Return the nearest grid position to aPosition if a screen is defined and snap to grid is enabled...
virtual int BlockCommand(EDA_KEY aKey)
Return the block command code (BLOCK_MOVE, BLOCK_COPY...) corresponding to the keys pressed (ALT...
TOOL_DISPATCHER * m_toolDispatcher
Definition: draw_frame.h:126
virtual void SetEnableZoomNoCenter(bool aEnable)
const wxSize GetSize() const
Definition: eda_rect.h:101
#define DEFAULT_MAX_UNDO_ITEMS
Definition: draw_frame.h:47
virtual void SetScreen(BASE_SCREEN *aScreen)
Definition: draw_frame.h:178
double bestZoom(double sizeX, double sizeY, double scaleFactor, wxPoint centre)
int GetGridCmdId() const
Return the command ID of the currently selected grid.
Definition: base_screen.h:403
wxMenuItem * AddMenuItem(wxMenu *aMenu, int aId, const wxString &aText, const wxBitmap &aImage, wxItemKind aType=wxITEM_NORMAL)
Function AddMenuItem is an inline helper function to create and insert a menu item with an icon into ...
Definition: bitmap.cpp:223
VIEW_CONTROLS class definition.
FRAME_T
Enum FRAME_T is the set of EDA_BASE_FRAME derivatives, typically stored in EDA_BASE_FRAME::m_Ident.
Definition: frame_type.h:34
EDA_DRAW_PANEL_GAL::GAL_TYPE m_canvasType
The current canvas type.
Definition: draw_frame.h:176
virtual double BestZoom()=0
Return the zoom level which displays the full page on screen.
virtual void OnGridSettings(wxCommandEvent &event)
Definition: draw_frame.h:594
double GetZoom() const
Function GetZoom returns the current "zoom factor", which is a measure of "internal units per device ...
Definition: base_screen.h:340
void SetScrollCenterPosition(const wxPoint &aPoint)
wxPoint getCrossHairScreenPosition() const
Function getCursorScreenPosition returns the cross hair position in device (display) units...
void OnMouseEvent(wxMouseEvent &event)
virtual void SaveSettings(wxConfigBase *aCfg)
Function SaveSettings saves common frame parameters to a configuration data file. ...
int color
Definition: DXF_plotter.cpp:62
void MoveBottomTo(coord_type aBottom)
Definition: box2.h:204
void SetMessageBlock(EDA_DRAW_FRAME *frame)
Function SetMessageBlock Displays the type of block command in the status bar of the window...
void SetSheetLayer(const wxString &aSheetLayer)
Set the sheet layer to draw/plot.
Definition: id.h:241
virtual bool OnHotKey(wxDC *aDC, int aHotKey, const wxPoint &aPosition, EDA_ITEM *aItem=NULL)
std::vector< wxSocketBase * > m_sockets
interprocess communication
Definition: draw_frame.h:101
int GetHeight() const
Definition: eda_rect.h:118
void SetSheetName(const wxString &aSheetName)
Set the sheet name to draw/plot.
virtual void EnableMousewheelPan(bool aEnable)
Function EnableMousewheelPan() Enables or disables mousewheel panning.
wxString ConfigBaseName()
Function ConfigBaseName.
coord_type GetRight() const
Definition: box2.h:197
virtual void EndMouseCapture(int aId=-1, int aCursorId=-1, const wxString &aTitle=wxEmptyString, bool aCallEndFunc=true)
Function EndMouseCapture ends mouse a capture.
const GRIDS & GetGrids() const
Function GetGrids().
Definition: base_screen.h:472
EVT_MENU_RANGE(ID_POPUP_ZOOM_START_RANGE, ID_POPUP_ZOOM_END_RANGE, EDA_DRAW_FRAME::OnZoom) EVT_MENU_RANGE(ID_POPUP_GRID_LEVEL_1000
BLOCK_COMMAND_T
wxPoint GetCursorPosition(bool aOnGrid, wxRealPoint *aGridSize=NULL) const
Return the current cursor position in logical (drawing) units.
bool RunAction(const std::string &aActionName, bool aNow=false, T aParam=NULL)
Function RunAction() Runs the specified action.
Definition: tool_manager.h:125
#define GR_KB_CTRL
void SetCanStartBlock(int aStartBlock)
void ReleaseFile()
Release the current file marked in use.
const wxPoint & GetScrollCenterPosition() const
static EDA_DRAW_PANEL_GAL::GAL_TYPE LoadCanvasTypeSetting()
Returns the canvas type stored in the application settings.
virtual void ToolOnRightClick(wxCommandEvent &event)
PGM_BASE & Pgm()
The global Program "get" accessor.
Definition: kicad.cpp:66
wxAuiManager m_auimgr
virtual EDA_RECT * GetClipBox()
void BuildWorkSheetGraphicList(const PAGE_INFO &aPageInfo, const TITLE_BLOCK &aTitleBlock, COLOR4D aColor, COLOR4D aAltColor)
Function BuildWorkSheetGraphicList is a core function for drawing or plotting the page layout with th...
virtual void OnZoom(wxCommandEvent &event)
KIGFX::VIEW * GetView() const
Function GetView() Returns a pointer to the VIEW instance used in the panel.
void OnMenuOpen(wxMenuEvent &event)
void SkipNextLeftButtonReleaseEvent()
After calling this function, if the left mouse button is down, the next left mouse button release eve...
virtual void SetGridColor(COLOR4D aColor)
Definition: draw_frame.h:550
void CopyToClipboard(wxCommandEvent &event)
Copy the current page or the current block to the clipboard.
virtual void MoveCursor(const wxPoint &aPosition)
Function MoveCursor moves the mouse pointer to aPosition in logical (drawing) units.
class EDA_MSG_PANEL is a panel to display various information messages.
Definition: msgpanel.h:111
Sentinel, do not use as a parameter.
virtual void SetPrevGrid()
Change the grid size settings to the previous one available.
The base class for create windows for drawing purpose.
Definition: draw_frame.h:78
virtual void MoveCursorToCrossHair()
Function MoveCursorToCrossHair warps the cursor to the current cross hair position.
void SetGridOrigin(const VECTOR2D &aGridOrigin)
Set the origin point for the grid.
void PushPreferences(const EDA_DRAW_PANEL *aParentCanvas)
Push preferences from a parent window to a child window.
const Vec & GetSize() const
Definition: box2.h:187
void FocusOnLocation(const wxPoint &aPos, bool aWarpCursor=true, bool aCenterView=false)
Useful to focus on a particular location, in find functions Move the graphic cursor (crosshair cursor...
COLOR4D m_drawBgColor
the background color of the draw canvas BLACK for Pcbnew, BLACK or WHITE for eeschema ...
Definition: draw_frame.h:113
OPENGL_ANTIALIASING_MODE gl_antialiasing_mode
Class TITLE_BLOCK holds the information shown in the lower right corner of a plot, printout, or editing view.
Definition: title_block.h:40
bool SetPreviousZoom()
wxComboBox * m_zoomSelectBox
Definition: draw_frame.h:149
void SetScale(double aScale)
Function SetScale() Sets the scaling factor.
Definition: view.h:250
static const wxChar CANVAS_TYPE_KEY[]
Key in KifaceSettings to store the canvas type.
Definition: draw_frame.h:234
virtual void UseGalCanvas(bool aEnable)
Use to switch between standard and GAL-based canvas.
std::unique_ptr< wxSingleInstanceChecker > m_file_checker
prevents opening same file multiple times.
Definition: draw_frame.h:103
void SaveSettings(wxConfigBase *aCfg) override
Function SaveSettings saves common frame parameters to a configuration data file. ...
virtual void InitBlockPasteInfos()
coord_type GetTop() const
Definition: box2.h:202
static const double MAX_AXIS
virtual const wxSize GetPageSizeIU() const =0
Works off of GetPageSettings() to return the size of the paper page in the internal units of this par...
wxPoint refPos(bool useMouse) const
Function RefPos Return the reference position, coming from either the mouse position or the cursor po...
Definition: base_screen.h:168
double GetZoomLevelCoeff() const
Return the coefficient to convert internal display scale factor to zoom level.
Definition: draw_frame.h:461
KIFACE_I & Kiface()
Global KIFACE_I "get" accessor.
Definition: kicad.cpp:52
virtual bool IsGridVisible() const
Definition: draw_frame.h:525
size_t GetGridCount() const
Function GetGridCount().
Definition: base_screen.h:457
#define ENBL_ZOOM_NO_CENTER_KEY
Definition: pgm_base.h:48
#define VIRT_MIN
min X or Y coordinate in virtual space
bool SetNextZoom()
Auxiliary rendering target (noncached)
Definition: definitions.h:42
void SetClipBox(const EDA_RECT &aRect)
static const wxString MaxUndoItemsEntry(wxT("DevelMaxUndoItems"))
Integer to set the maximum number of undo items on the stack.
This file contains miscellaneous commonly used macros and functions.
void ClearItemsList()
Function ClearItemsList clear only the list of EDA_ITEM pointers, it does NOT delete the EDA_ITEM obj...
wxSize GetTextSize(const wxString &aSingleLine, wxWindow *aWindow)
Return the size of aSingleLine of text when it is rendered in aWindow using whatever font is currentl...
Definition: common.cpp:111
void DisplayUnitsMsg()
Display current unit pane on the status bar.
const wxSize & GetSizeMils() const
Definition: page_info.h:142
bool saveCanvasImageToFile(const wxString &aFileName, wxBitmapType aBitmapType=wxBITMAP_TYPE_PNG)
void OnUpdateUndo(wxUpdateUIEvent &aEvent)
bool GeneralControlKeyMovement(int aHotKey, wxPoint *aPos, bool aSnapToGrid)
Handle the common part of GeneralControl dedicated to global cursor keys (i.e.
coord_type GetWidth() const
Definition: box2.h:195
CAIRO_ANTIALIASING_MODE cairo_antialiasing_mode
void SetState(BLOCK_STATE_T aState)
int BuildGridsChoiceList(wxArrayString &aGridsList, bool aMmFirst) const
Function BuildGridsChoiceList().
virtual wxPoint ToLogicalXY(const wxPoint &pos)
Function ToLogicalXY transforms device to logical coordinates.
Class TOOL_MANAGER.
Definition: tool_manager.h:49
virtual bool HandleBlockBegin(wxDC *aDC, EDA_KEY aKey, const wxPoint &aPosition, int aExplicitCommand=0)
Initialize a block command.
void EnableCursorWarping(bool aEnable)
Function EnableCursorWarping() Enables or disables warping the cursor.
wxBitmap KiBitmap(BITMAP_DEF aBitmap)
Construct a wxBitmap from a memory record, held in a BITMAP_DEF.
Definition: bitmap.cpp:79
PROJECT & Prj() const
Function Prj returns a reference to the PROJECT "associated with" this KIWAY.
virtual const PAGE_INFO & GetPageSettings() const =0
virtual void Zoom_Automatique(bool aWarpPointer)
Redraw the screen with best zoom level and the best centering that shows all the page or the board...
#define GAL_DISPLAY_OPTIONS_KEY
Definition: pgm_base.h:53
wxPoint m_StartVisu
Coordinates in drawing units of the current view position (upper left corner of device) ...
Definition: base_screen.h:198
void MoveLeftTo(coord_type aLeft)
Definition: box2.h:205
void ReadConfig(wxConfigBase *aCfg, const wxString &aBaseName)
bool IsBlockActive() const
Definition: base_screen.h:499
static const wxString traceScrollSettings(wxT("KicadScrollSettings"))
Definition for enabling and disabling scroll bar setting trace output.
KIGFX::GAL * GetGAL() const
Function GetGAL() Returns a pointer to the GAL instance used in the panel.
virtual bool IsPointOnDisplay(const wxPoint &aPosition)
Function IsPointOnDisplay.
void GRRect(EDA_RECT *aClipBox, wxDC *aDC, int x1, int y1, int x2, int y2, COLOR4D aColor)
Definition: gr_basic.cpp:1003
#define ENBL_AUTO_PAN_KEY
Definition: pgm_base.h:51
wxAuiToolBar * m_auxiliaryToolBar
Auxiliary tool bar typically shown below the main tool bar at the top of the main window...
Definition: draw_frame.h:153
#define DEFAULT_FILE_HISTORY_SIZE
The default file history size is 9.
Definition: pgm_base.h:60
virtual BASE_SCREEN * GetScreen() const
Return a pointer to a BASE_SCREEN or one of its derivatives.
Definition: draw_frame.h:394
Class LSET is a set of PCB_LAYER_IDs.
a helper to handle the real device context used in KiCad
wxAuiToolBar * m_optionsToolBar
The options tool bar typcially located on the left edge of the main window.
Definition: draw_frame.h:160
void SetCenter(const VECTOR2D &aCenter)
Function SetCenter() Sets the center point of the VIEW (i.e.
Definition: view.cpp:600
void OnUpdateRedo(wxUpdateUIEvent &aEvent)
BASE_SCREEN * m_currentScreen
current used SCREEN
Definition: draw_frame.h:87
static bool DrawPageOnClipboard(EDA_DRAW_FRAME *aFrame)
virtual void PrintPage(wxDC *aDC, LSET aPrintMask, bool aPrintMirrorMode, void *aData=NULL)
Print the page pointed by current screen, set by the calling print function.
EDA_HOTKEY_CONFIG * m_hotkeysDescrList
Definition: draw_frame.h:105
void RefreshCrossHair(const wxPoint &aOldPos, const wxPoint &aEvtPos, wxDC *aDC)
Move and refresh the crosshair after movement and call the mouse capture function.
VECTOR2< double > VECTOR2D
Definition: vector2d.h:586
wxPoint getCrossHairPosition(bool aInvertY) const
Function getCrossHairPosition return the current cross hair position in logical (drawing) coordinates...
Definition: base_screen.h:107
wxString dump(const wxArrayString &aArray)
Debug helper for printing wxArrayString contents.
virtual wxString GetScreenDesc() const
const GRID_TYPE & GetGrid() const
Return the grid object of the currently selected grid.
Definition: base_screen.h:417
void SetMsgPanel(const std::vector< MSG_PANEL_ITEM > &aList)
Clear the message panel and populates it with the contents of aList.
EDA_DRAW_FRAME::OnSelectGrid EVT_TOOL_RANGE(ID_TB_OPTIONS_SELECT_UNIT_MM, ID_TB_OPTIONS_SELECT_UNIT_INCH, EDA_DRAW_FRAME::OnSelectUnits) EVT_UPDATE_UI_RANGE(ID_TB_OPTIONS_SELECT_UNIT_MM
wxPoint getNearestGridPosition(const wxPoint &aPosition, const wxPoint &aGridOrigin, wxRealPoint *aGridSize) const
Function getNearestGridPosition returns the nearest aGridSize location to aPosition.
void GRForceBlackPen(bool flagforce)
Function GRForceBlackPen.
Definition: gr_basic.cpp:204
void MarkTargetDirty(int aTarget)
Function MarkTargetDirty() Sets or clears target &#39;dirty&#39; flag.
Definition: view.h:596
void SetSheetCount(int aSheetCount)
Function SetSheetCount Set the value of the count of sheets, for basic inscriptions.
wxComboBox * m_gridSelectBox
Definition: draw_frame.h:148
bool m_Center
Center on screen.
Definition: base_screen.h:202
bool m_Initialized
Definition: base_screen.h:207
EDA_MSG_PANEL * m_messagePanel
Panel used to display information at the bottom of the main window.
Definition: draw_frame.h:163
virtual void CrossHairOn(wxDC *DC=nullptr)
void OnUpdateSelectGrid(wxUpdateUIEvent &aEvent)
Class PAGE_INFO describes the page size and margins of a paper page on which to eventually print or p...
Definition: page_info.h:54
bool m_showBorderAndTitleBlock
True shows the drawing border and title block.
Definition: draw_frame.h:143
FOOTPRINT_EDIT_FRAME::OnVerticalToolbar FOOTPRINT_EDIT_FRAME::ProcessPreferences FOOTPRINT_EDIT_FRAME::Process_Special_Functions FOOTPRINT_EDIT_FRAME::Process_Special_Functions FOOTPRINT_EDIT_FRAME::Process_Special_Functions FOOTPRINT_EDIT_FRAME::OnUpdateInsertModuleInBoard EVT_UPDATE_UI_RANGE(ID_MODEDIT_PAD_TOOL, ID_MODEDIT_MEASUREMENT_TOOL, FOOTPRINT_EDIT_FRAME::OnUpdateVerticalToolbar) EVT_UPDATE_UI(ID_TB_OPTIONS_SHOW_HIGH_CONTRAST_MODE
Class BASE_SCREEN handles how to draw a screen (a board, a schematic ...)
Definition: base_screen.h:76
EDA_UNITS_T GetUserUnits() const override
Return the user units currently in use.
Definition: draw_frame.h:281
void SetScalingFactor(double iu_per_du)
Function SetScalingFactor sets the scaling factor of "internal unit per device unit".
VECTOR2D GetCursorPosition() const
Returns the current cursor position in world coordinates.
Definition: common.h:161
virtual void LoadSettings(wxConfigBase *aCfg)
Function LoadSettings loads common frame parameters from a configuration file.
void SetMaximum()
Definition: box2.h:71
bool GetEnableZoomNoCenter() const
virtual void CallMouseCapture(wxDC *aDC, const wxPoint &aPosition, bool aErase)
Function CallMouseCapture calls the mouse capture callback.
void SetMilsToIUfactor(double aScale)
Function SetMilsToIUfactor Set the scalar to convert pages units ( mils) to draw/plot units...
virtual const BOX2I GetDocumentExtents() const
coord_type GetBottom() const
Definition: box2.h:198
virtual void SetZoom(double mode)
static const wxString ShowGridEntryKeyword(wxT("ShowGrid"))
Nonzero to show grid (suffix)
#define ENBL_MOUSEWHEEL_PAN_KEY
Definition: pgm_base.h:49
int m_ScrollPixelsPerUnitX
Pixels per scroll unit in the horizontal direction.
Definition: base_screen.h:189
virtual void ReCreateAuxiliaryToolbar()
Helper dialog and control classes.
#define FILE_HISTORY_SIZE_KEY
Definition: pgm_base.h:52
Class KIWAY is a minimalistic software bus for communications between various DLLs/DSOs (DSOs) within...
Definition: kiway.h:258
Class VIEW_CONTROLS is an interface for classes handling user events controlling the view behaviour (...
wxConfigBase * KifaceSettings() const
Definition: kiface_i.h:103
virtual void CrossHairOff(wxDC *DC=nullptr)
uint32_t EDA_KEY
Definition: common.h:74
wxAuiToolBarItem * GetToolbarTool(int aToolId)
Checks all the toolbars and returns a reference to the given tool id or nullptr if not found...
void OnUpdateUnits(wxUpdateUIEvent &aEvent)
wxLogTrace helper definitions.
void setMousePosition(const wxPoint &aPosition)
Definition: base_screen.h:156
bool IsGalCanvasActive() const
Function IsGalCanvasActive is used to check which canvas (GAL-based or standard) is currently in use...
Definition: draw_frame.h:918
static const wxString UserUnitsEntryKeyword(wxT("Units"))
User units.
Definition: colors.h:60
virtual void OnSize(wxSizeEvent &event)
Recalculate the size of toolbars and display panel when the frame size changes.
void OnToggleGridState(wxCommandEvent &aEvent)
virtual bool SwitchCanvas(EDA_DRAW_PANEL_GAL::GAL_TYPE aCanvasType)
Changes the current rendering backend.
virtual int MilsToIuScalar()
Function MilsToIuScalar returns the scalar required to convert mils to internal units.
Definition: base_screen.h:245
void SetPresetZoom(int aIndex)
Change zoom to one of the preset values.
const wxPoint & getScrollCenterPosition() const
Definition: base_screen.h:173
virtual void EnableAutoPan(bool aEnabled)
Function EnableAutoPan Turns on/off auto panning (user setting to disable it entirely).
virtual bool SetZoom(double iu_per_du)
Function SetZoom adjusts the current zoom factor.
void SetPresetGrid(int aIndex)
Change the grid size to one of the preset values.
int m_UndoRedoCountMax
default Undo/Redo command Max depth, to be handed
Definition: draw_frame.h:118
virtual void SetCrossHairCursorPosition(const VECTOR2D &aPosition, bool aWarpView=true)=0
Moves the graphic crosshair cursor to the requested position expressed in world coordinates.
void EraseMsgBox()
Definition: msgpanel.cpp:216
EVT_TOOL(ID_FOOTPRINT_WIZARD_SELECT_WIZARD, FOOTPRINT_WIZARD_FRAME::SelectCurrentWizard) EVT_TOOL(ID_FOOTPRINT_WIZARD_RESET_TO_DEFAULT
wxPoint Centre() const
Definition: eda_rect.h:60
virtual void SetToolID(int aId, int aCursor, const wxString &aToolMsg)
Set the tool command ID to aId and sets the cursor to aCursor.
virtual void GetMsgPanelInfo(EDA_UNITS_T aUnits, std::vector< MSG_PANEL_ITEM > &aList)
Function GetMsgPanelInfo populates aList of MSG_PANEL_ITEM objects with it&#39;s internal state for displ...
Definition: base_struct.h:297
virtual void SetCurrentCursor(int aCursor)
Function SetCurrentCursor Set the current cursor shape for this panel.
virtual int GetDefaultCursor() const
Function GetDefaultCursor.
virtual const wxPoint & GetGridOrigin() const =0
Return the absolute coordinates of the origin of the snap grid.
int m_LastGridSizeId
Definition: draw_frame.h:107
virtual COLOR4D GetGridColor()
Definition: draw_frame.h:542
virtual void RedrawScreen2(const wxPoint &posBefore)
Put the crosshair back to the screen position it had before zooming.
bool LibraryFileBrowser(bool doOpen, wxFileName &aFilename, const wxString &wildcard, const wxString &ext, bool isDirectory)
void SetGridSize(const VECTOR2D &aGridSize)
Set the grid size.
wxAuiToolBar * m_drawToolBar
The tool bar that contains the buttons for quick access to the application draw tools.
Definition: draw_frame.h:157
wxAuiToolBar * m_mainToolBar
Standard horizontal Toolbar.
EDA_DRAW_FRAME::OnSelectGrid ID_TB_OPTIONS_SELECT_UNIT_INCH
bool m_IsPrinting
Definition: base_screen.h:220
Definition: solve.cpp:178
void LoadSettings(wxConfigBase *aCfg) override
Function LoadSettings loads common frame parameters from a configuration file.
virtual void HardRedraw()
Rebuild the GAL and redraws the screen.
#define AUTOSAVE_INTERVAL_KEY
Definition: pgm_base.h:47
virtual void Refresh(bool aEraseBackground=true, const wxRect *aRect=NULL) override
Update the board display after modifying it by a python script (note: it is automatically called by a...
wxPoint m_ScrollbarPos
Current scroll bar position in scroll units.
Definition: base_screen.h:196
void AppendMessage(const wxString &aUpperText, const wxString &aLowerText, COLOR4D aColor, int aPad=6)
Function AppendMessage appends a message to the message panel.
Definition: msgpanel.cpp:110
void DrawPageLayout(wxDC *aDC, EDA_RECT *aClipBox, const PAGE_INFO &aPageInfo, const wxString &aFullSheetName, const wxString &aFileName, TITLE_BLOCK &aTitleBlock, int aSheetCount, int aSheetNumber, int aPenWidth, double aScalar, COLOR4D aColor, COLOR4D aAltColor, const wxString &aSheetLayer)
Function DrawPageLayout is a core function to draw the page layout with the frame and the basic inscr...
virtual void SetNextGrid()
Change the grid size settings to the next one available.
EDA_DRAW_PANEL_GAL * m_galCanvas
GAL display options - this is the frame&#39;s interface to setting GAL display options.
Definition: draw_frame.h:91
virtual bool HandleBlockEnd(wxDC *DC)
Handle the "end" of a block command, i.e.
constexpr std::size_t arrayDim(T const (&)[N]) noexcept
of elements in an array. This implements type-safe compile time checking
Definition: macros.h:99
wxSocketServer * m_socketServer
Definition: draw_frame.h:100
static const wxString LastGridSizeIdKeyword(wxT("_LastGridSize"))
Most recently used grid size (suffix)
void Normalize()
Function Normalize ensures that the height ant width are positive.
wxPoint RefPos(bool useMouse) const
Return the reference position, coming from either the mouse position or the cursor position...
virtual void SetNoToolSelected()
Select the ID_NO_TOOL_SELECTED id tool (Idle tool)
coord_type GetHeight() const
Definition: box2.h:196
EDA_DRAW_PANEL * m_canvas
The area to draw on.
Definition: draw_frame.h:123
void AppendMsgPanel(const wxString &textUpper, const wxString &textLower, COLOR4D color, int pad=6)
Append a message to the message panel.
wxWindow * findDialog(wxWindowList &aList)
void OnUpdateCrossHairStyle(wxUpdateUIEvent &aEvent)
void WriteConfig(wxConfigBase *aCfg, const wxString &aBaseName)
virtual void RedrawScreen(const wxPoint &aCenterPoint, bool aWarpPointer)
Redraw the entire screen area by updating the scroll bars and mouse pointer in order to have aCenterP...
void SetMaxFiles(size_t aMaxFiles)
Definition: pgm_base.cpp:79
TOOL_MANAGER * GetToolManager() const
Return the tool manager instance, if any.
Definition: draw_frame.h:931
void setCrossHairPosition(const wxPoint &aPosition, const wxPoint &aGridOrigin, bool aSnapToGrid)
Function setCrossHairPosition sets the screen cross hair position to aPosition in logical (drawing) u...
#define GAL_ANTIALIASING_MODE_KEY
Definition: pgm_base.h:54
void SetAutoSaveInterval(int aInterval)
double m_zoomLevelCoeff
a suitable value to convert the internal zoom scaling factor
Definition: draw_frame.h:115
wxPoint GetNearestGridPosition(const wxPoint &aPosition, wxRealPoint *aGridSize=NULL) const
Return the nearest aGridSize location to aPosition.
const int scale
void DisplayToolMsg(const wxString &msg)
bool GridExists(int aCommandId)
Function GridExists tests for grid command ID (not an index in grid list, but a wxID) exists in grid ...
wxString AddHotkeyName(const wxString &aText, EDA_HOTKEY **aList, int aCommandId, HOTKEY_ACTION_TYPE aShortCutType)
Function AddHotkeyName Add the key name from the Command id value ( m_Idcommand member value) ...
see class PGM_BASE
virtual void OnSelectGrid(wxCommandEvent &event)
Command event handler for selecting grid sizes.
void OnUpdateGrid(wxUpdateUIEvent &aEvent)
void SetMousePosition(const wxPoint &aPosition)
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, CPTREE &aTree)
Function Format outputs a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:205
Class GRID_TYPE is for grid arrays.
Definition: base_screen.h:45
BLOCK_STATE_T GetState() const
void SetSheetNumber(int aSheetNumber)
Function SetSheetNumber Set the value of the sheet number, for basic inscriptions.
static LIB_PART * dummy()
Used when a LIB_PART is not found in library to draw a dummy shape This component is a 400 mils squar...
#define max(a, b)
Definition: auxiliary.h:86
bool GetEnableMousewheelPan() const
#define INSTALL_UNBUFFERED_DC(name, parent)
virtual int WriteHotkeyConfig(struct EDA_HOTKEY_CONFIG *aDescList, wxString *aFullFileName=NULL)
Function WriteHotkeyConfig Store the current hotkey list It is stored using the standard wxConfig mec...
KIGFX::GAL_DISPLAY_OPTIONS m_galDisplayOptions
Definition: draw_frame.h:94
FILE_HISTORY & GetFileHistory()
Definition: kiface_i.h:123
VTBL_ENTRY wxConfigBase * CommonSettings() const
Definition: pgm_base.h:189
size_t i
Definition: json11.cpp:597
const wxRealPoint & GetGridSize() const
Return the grid size of the currently selected grid.
Definition: base_screen.h:410
Class EDA_RECT handles the component boundary box.
Definition: eda_rect.h:44
wxPoint m_DrawOrg
offsets for drawing the circuit on the screen
Definition: base_screen.h:183
virtual void SetEnableMousewheelPan(bool aEnable)
int GetX() const
Definition: eda_rect.h:109
void SetNextZoom()
Change the zoom to the next one available.
const wxChar *const kicadTraceKeyEvent
Flag to enable wxKeyEvent debug tracing.
Class EDA_ITEM is a base class for most all the KiCad significant classes, used in schematics and boa...
Definition: base_struct.h:154
#define CAIRO_ANTIALIASING_MODE_KEY
Definition: pgm_base.h:55
static const wxString FirstRunShownKeyword(wxT("FirstRunShown"))
The common library.
int GetWidth() const
Definition: eda_rect.h:117
double GetZoomFactor() const
Get the zoom factor.
std::vector< MSG_PANEL_ITEM > MSG_PANEL_ITEMS
Definition: msgpanel.h:102
bool m_showPageLimits
true to display the page limits
Definition: draw_frame.h:111
void SetGridVisibility(bool aVisibility)
Sets the visibility setting of the grid.
Definition: colors.h:49
int GetY() const
Definition: eda_rect.h:110
KIGFX::VIEW_CONTROLS * GetViewControls() const
Function GetViewControls() Returns a pointer to the VIEW_CONTROLS instance used in the panel...
int WriteHotkeyConfig(struct EDA_HOTKEY_CONFIG *aDescList, wxString *aFullFileName=NULL) override
>
virtual void Window_Zoom(EDA_RECT &Rect)
int m_NumberOfScreens
Definition: base_screen.h:217
BLOCK_COMMAND_T GetCommand() const
static const ADVANCED_CFG & GetCfg()
Get the singleton instance&#39;s config, which is shared by all consumers of advanced config...
EDA_DRAW_PANEL_GAL * GetGalCanvas() const
Return a pointer to GAL-based canvas of given EDA draw frame.
Definition: draw_frame.h:925
virtual void CommonSettingsChanged()
Function CommonSettingsChanged Notification event that some of the common (suite-wide) settings have ...
virtual void AddMenuZoomAndGrid(wxMenu *aMasterMenu)
Add standard zoom commands and submenu zoom and grid selection to a popup menu uses zoom hotkeys info...
classes and function to generate graphics to plt or draw titles blocks and frame references ...
virtual void SetGridVisibility(bool aVisible)
It may be overloaded by derived classes.
Definition: draw_frame.h:534
void DrawWorkSheet(wxDC *aDC, BASE_SCREEN *aScreen, int aLineWidth, double aScale, const wxString &aFilename, const wxString &aSheetLayer=wxEmptyString)
Draws on screen the page layout with the frame and the basic inscriptions.
static const wxString GridColorEntryKeyword(wxT("GridColor"))
Grid color ID (suffix)
coord_type GetLeft() const
Definition: box2.h:201
void Draw(EDA_RECT *aClipBox, wxDC *aDC)
Draws the item list created by BuildWorkSheetGraphicList.
Definition: colors.h:45
virtual void OnCharHook(wxKeyEvent &event)
Capture the key event before it is sent to the GUI.
void InitData(EDA_DRAW_PANEL *Panel, const wxPoint &startpos)
Function InitData sets the initial values of a BLOCK_SELECTOR, before starting a block command...
void OnSelectUnits(wxCommandEvent &aEvent)
virtual void unitsChangeRefresh()
Called when when the units setting has changed to allow for any derived classes to handle refreshing ...
Class VIEW.
Definition: view.h:61
virtual void Refresh(bool eraseBackground=true, const wxRect *rect=NULL)
bool GetToolToggled(int aToolId)
Checks all the toolbars and returns true if the given tool id is toggled.
bool saveCanvasTypeSetting(EDA_DRAW_PANEL_GAL::GAL_TYPE aCanvasType)
Stores the canvas type in the application settings.
void MoveTopTo(coord_type aTop)
Definition: box2.h:203
void SetCrossHairPosition(const wxPoint &aPosition, bool aSnapToGrid=true)
Set the screen cross hair position to aPosition in logical (drawing) units.
int SetGrid(const wxRealPoint &size)
set the current grid size m_Grid.
coord_type GetX() const
Definition: box2.h:188
int m_CmdId
Definition: base_screen.h:48
BASE_SCREEN class implementation.
Message panel definition file.
wxPoint GetCrossHairScreenPosition() const
Return the cross hair position in device (display) units.b.
void SetLastCursorPosition(const wxPoint &aPosition)
Function SetLastCursorPosition sets the last cursor position to aPosition.
int GetDefaultCursor() const
Function GetDefaultCursor.
virtual void EraseScreen(wxDC *DC)
Function OnMouseWheel handles mouse wheel events.
EDA_UNITS_T m_UserUnits
Definition: draw_frame.h:120
ACTIONS * m_actions
Definition: draw_frame.h:127
virtual void OnLeftDClick(wxDC *DC, const wxPoint &MousePos)
static int GetRequiredHeight()
Function GetRequiredHeight returns the required height (in pixels) of a EDA_MSG_PANEL.
Definition: msgpanel.cpp:71
void SetPrevZoom()
Change the zoom to the previous one available.
virtual void SetEnableAutoPan(bool aEnable)
#define VIRT_MAX
max X or Y coordinate in virtual space
virtual void UpdateStatusBar()
Update the status bar information.
void DisplayError(wxWindow *parent, const wxString &text, int displaytime)
Function DisplayError displays an error or warning message box with aMessage.
Definition: confirm.cpp:245
wxPoint GetCrossHairPosition(bool aInvertY=false) const
Return the current cross hair position in logical (drawing) coordinates.
unsigned GetCount() const
virtual void OnActivate(wxActivateEvent &event)
Called when activating the frame.
bool m_movingCursorWithKeyboard
One-shot to avoid a recursive mouse event during hotkey movement.
Definition: draw_frame.h:173
void ClearMsgPanel(void)
Clear all messages from the message panel.
void UpdateHotKeys()
>
EDA_UNITS_T
Definition: common.h:160
virtual void SetMouseCaptureCallback(MOUSE_CAPTURE_CALLBACK aMouseCaptureCallback)
long m_firstRunDialogSetting
Key to control whether first run dialog is shown on startup.
Definition: draw_frame.h:146
void SetUserUnits(EDA_UNITS_T aUnits)
Definition: draw_frame.h:282
virtual void OnSelectZoom(wxCommandEvent &event)
Set the zoom factor when selected by the zoom list box in the main tool bar.
virtual void SetCursorPosition(const VECTOR2D &aPosition, bool aWarpView=true, bool aTriggeredByArrows=false)=0
Moves cursor to the requested position expressed in world coordinates.
std::vector< double > m_ZoomList
standard zoom (i.e. scale) coefficients.
Definition: base_screen.h:219
bool m_snapToGrid
Indicates if cursor should be snapped to grid.
Definition: draw_frame.h:89
bool LockFile(const wxString &aFileName)
Mark a schematic file as being in use.
void SetCommand(BLOCK_COMMAND_T aCommand)
#define min(a, b)
Definition: auxiliary.h:85
Class GAL is the abstract interface for drawing on a 2D-surface.
virtual void UpdateMsgPanel()
Redraw the message panel.
Class COLOR4D is the color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:39
void MoveRightTo(coord_type aRight)
Definition: box2.h:206
void SetIgnoreLeftButtonReleaseEvent(bool aIgnore)
File locking utilities.