Code cleanup related to zoom:

- remove outdated code or comment coming from old drawing code using wxDC
- move zoom values lists to zoom_defines.h
- fix incorrect zoom max and min values (gal scaling factor limits).
This commit is contained in:
jean-pierre charras 2020-12-02 18:33:59 +01:00
parent fcce62f0a4
commit 64f555079a
15 changed files with 90 additions and 79 deletions

View File

@ -357,7 +357,7 @@ void EDA_DRAW_FRAME::UpdateZoomSelectBox()
if( m_zoomSelectBox == NULL ) if( m_zoomSelectBox == NULL )
return; return;
double zoom = m_canvas->GetGAL()->GetZoomFactor() / ZOOM_COEFF; double zoom = m_canvas->GetGAL()->GetZoomFactor();
m_zoomSelectBox->Clear(); m_zoomSelectBox->Clear();
m_zoomSelectBox->Append( _( "Zoom Auto" ) ); m_zoomSelectBox->Append( _( "Zoom Auto" ) );
@ -383,7 +383,7 @@ void EDA_DRAW_FRAME::OnUpdateSelectZoom( wxUpdateUIEvent& aEvent )
int current = 0; // display Auto if no match found int current = 0; // display Auto if no match found
// check for a match within 1% // check for a match within 1%
double zoom = GetCanvas()->GetGAL()->GetZoomFactor() / ZOOM_COEFF; double zoom = GetCanvas()->GetGAL()->GetZoomFactor();
for( unsigned i = 0; i < config()->m_Window.zoom_factors.size(); i++ ) for( unsigned i = 0; i < config()->m_Window.zoom_factors.size(); i++ )
{ {
@ -520,7 +520,7 @@ const wxString EDA_DRAW_FRAME::GetZoomLevelIndicator() const
{ {
// returns a human readable value which can be displayed as zoom // returns a human readable value which can be displayed as zoom
// level indicator in dialogs. // level indicator in dialogs.
double zoom = m_canvas->GetGAL()->GetZoomFactor() / ZOOM_COEFF; double zoom = m_canvas->GetGAL()->GetZoomFactor();
return wxString::Format( wxT( "Z %.2f" ), zoom ); return wxString::Format( wxT( "Z %.2f" ), zoom );
} }

View File

@ -219,7 +219,7 @@ int COMMON_TOOLS::ZoomInOutCenter( const TOOL_EVENT& aEvent )
int COMMON_TOOLS::doZoomInOut( bool aDirection, bool aCenterOnCursor ) int COMMON_TOOLS::doZoomInOut( bool aDirection, bool aCenterOnCursor )
{ {
double zoom = getView()->GetGAL()->GetZoomFactor() / ZOOM_COEFF; double zoom = getView()->GetGAL()->GetZoomFactor();
// Step must be AT LEAST 1.3 // Step must be AT LEAST 1.3
if( aDirection ) if( aDirection )
@ -254,6 +254,7 @@ int COMMON_TOOLS::doZoomInOut( bool aDirection, bool aCenterOnCursor )
idx = 0; // if we ran off the end then peg to the end idx = 0; // if we ran off the end then peg to the end
} }
// Note: idx == 0 is Auto; idx == 1 is first entry in zoomList
return doZoomToPreset( idx + 1, aCenterOnCursor ); return doZoomToPreset( idx + 1, aCenterOnCursor );
} }
@ -401,7 +402,7 @@ int COMMON_TOOLS::doZoomToPreset( int idx, bool aCenterOnCursor )
idx--; idx--;
} }
double scale = zoomList[idx] * ZOOM_COEFF; double scale = zoomList[idx];
if( aCenterOnCursor ) if( aCenterOnCursor )
{ {

View File

@ -60,7 +60,7 @@ OPT_TOOL_EVENT ZOOM_MENU::eventHandler( const wxMenuEvent& aEvent )
void ZOOM_MENU::update() void ZOOM_MENU::update()
{ {
double zoom = m_parent->GetCanvas()->GetGAL()->GetZoomFactor() / ZOOM_COEFF; double zoom = m_parent->GetCanvas()->GetGAL()->GetZoomFactor();
const std::vector<double>& zoomList = m_parent->config()->m_Window.zoom_factors; const std::vector<double>& zoomList = m_parent->config()->m_Window.zoom_factors;

View File

@ -200,11 +200,6 @@ void SCH_BASE_FRAME::LoadSettings( APP_SETTINGS_BASE* aCfg )
{ {
aCfg->m_Window.zoom_factors = { ZOOM_LIST_EESCHEMA }; aCfg->m_Window.zoom_factors = { ZOOM_LIST_EESCHEMA };
} }
// ensure factors < MAX_ZOOM_FACTOR (useful only when the user will be
// able to change/edit the factor list
for( double& factor : aCfg->m_Window.zoom_factors )
factor = std::min( factor, MAX_ZOOM_FACTOR );
} }

View File

@ -48,6 +48,7 @@
#include <sch_base_frame.h> #include <sch_base_frame.h>
#include <sch_painter.h> #include <sch_painter.h>
#include <zoom_defines.h>
SCH_DRAW_PANEL::SCH_DRAW_PANEL( wxWindow* aParentWindow, wxWindowID aWindowId, SCH_DRAW_PANEL::SCH_DRAW_PANEL( wxWindow* aParentWindow, wxWindowID aWindowId,
@ -74,7 +75,8 @@ SCH_DRAW_PANEL::SCH_DRAW_PANEL( wxWindow* aParentWindow, wxWindowID aWindowId,
m_painter->GetSettings()->LoadColors( cs ); m_painter->GetSettings()->LoadColors( cs );
m_view->SetPainter( m_painter.get() ); m_view->SetPainter( m_painter.get() );
m_view->SetScaleLimits( 1000.0, 0.0001 ); // This fixes the zoom in and zoom out limits // This fixes the zoom in and zoom out limits:
m_view->SetScaleLimits( ZOOM_MAX_LIMIT_EESCHEMA, ZOOM_MIN_LIMIT_EESCHEMA );
m_view->SetMirror( false, false ); m_view->SetMirror( false, false );
// Early initialization of the canvas background color, // Early initialization of the canvas background color,

View File

@ -33,6 +33,7 @@
#include <sch_edit_frame.h> #include <sch_edit_frame.h>
#include <settings/settings_manager.h> #include <settings/settings_manager.h>
#include <preview_items/selection_area.h> #include <preview_items/selection_area.h>
#include <zoom_defines.h>
#include <functional> #include <functional>
@ -55,7 +56,8 @@ SCH_PREVIEW_PANEL::SCH_PREVIEW_PANEL( wxWindow* aParentWindow, wxWindowID aWindo
m_painter->GetSettings()->LoadColors( Pgm().GetSettingsManager().GetColorSettings() ); m_painter->GetSettings()->LoadColors( Pgm().GetSettingsManager().GetColorSettings() );
m_view->SetPainter( m_painter.get() ); m_view->SetPainter( m_painter.get() );
m_view->SetScaleLimits( 20000.0, 0.002 ); // This fixes the zoom in and zoom out limits:
m_view->SetScaleLimits( ZOOM_MAX_LIMIT_EESCHEMA_PREVIEW, ZOOM_MIN_LIMIT_EESCHEMA_PREVIEW );
m_view->SetMirror( false, false ); m_view->SetMirror( false, false );
setDefaultLayerOrder(); setDefaultLayerOrder();

View File

@ -22,6 +22,7 @@
#include <view/wx_view_controls.h> #include <view/wx_view_controls.h>
#include <gerbview_painter.h> #include <gerbview_painter.h>
#include <page_layout/ws_proxy_view_item.h> #include <page_layout/ws_proxy_view_item.h>
#include <zoom_defines.h>
#include <gerbview_frame.h> #include <gerbview_frame.h>
#include <gal/graphics_abstraction_layer.h> #include <gal/graphics_abstraction_layer.h>
@ -29,9 +30,11 @@
#include <gerber_file_image.h> #include <gerber_file_image.h>
#include <gerber_file_image_list.h> #include <gerber_file_image_list.h>
#include <zoom_defines.h>
#include <functional> #include <functional>
#include <memory> #include <memory>
using namespace std::placeholders; using namespace std::placeholders;
@ -46,6 +49,8 @@ EDA_DRAW_PANEL_GAL( aParentWindow, aWindowId, aPosition, aSize, aOptions, aGalTy
m_painter = std::make_unique<KIGFX::GERBVIEW_PAINTER>( m_gal ); m_painter = std::make_unique<KIGFX::GERBVIEW_PAINTER>( m_gal );
m_view->SetPainter( m_painter.get() ); m_view->SetPainter( m_painter.get() );
// This fixes the zoom in and zoom out limits:
m_view->SetScaleLimits( ZOOM_MAX_LIMIT_GERBVIEW, ZOOM_MIN_LIMIT_GERBVIEW );
m_viewControls = new KIGFX::WX_VIEW_CONTROLS( m_view, this ); m_viewControls = new KIGFX::WX_VIEW_CONTROLS( m_view, this );

View File

@ -301,12 +301,9 @@ void GERBVIEW_FRAME::LoadSettings( APP_SETTINGS_BASE* aCfg )
if( aCfg->m_Window.zoom_factors.empty() ) if( aCfg->m_Window.zoom_factors.empty() )
{ {
aCfg->m_Window.zoom_factors = { ZOOM_LIST_GERBER }; aCfg->m_Window.zoom_factors = { ZOOM_LIST_GERBVIEW };
} }
for( double& factor : aCfg->m_Window.zoom_factors )
factor = std::min( factor, MAX_ZOOM_FACTOR );
GERBVIEW_SETTINGS* cfg = dynamic_cast<GERBVIEW_SETTINGS*>( aCfg ); GERBVIEW_SETTINGS* cfg = dynamic_cast<GERBVIEW_SETTINGS*>( aCfg );
wxCHECK( cfg, /*void*/ ); wxCHECK( cfg, /*void*/ );

View File

@ -24,6 +24,42 @@
#pragma once #pragma once
/* Note about internal units and max size for boards and items
The largest distance that we (and Kicad) can support is INT_MAX, since it represents
distance often in a wxCoord or wxSize. As a scalar, a distance is always
positive. Because int is 32 bits and INT_MAX is
2147483647. The most difficult distance for a virtual (world) cartesian
space is the hypotenuse, or diagonal measurement at a 45 degree angle. This
puts the most stress on the distance magnitude within the bounded virtual
space. So if we allow this distance to be our constraint of <= INT_MAX, this
constraint then propagates to the maximum distance in X and in Y that can be
supported on each axis. Remember that the hypotenuse of a 1x1 square is
sqrt( 1x1 + 1x1 ) = sqrt(2) = 1.41421356.
hypotenuse of any square = sqrt(2) * deltaX;
Let maximum supported hypotenuse be INT_MAX, then:
MAX_AXIS = INT_MAX / sqrt(2) = 2147483647 / 1.41421356 = 1518500251
The next choice is what to use for internal units (IU), sometimes called
world units. If nanometers, then the virtual space must be limited to
about 1.5 x 1.5 meters square. This is 1518500251 divided by 1e9 nm/meter.
The maximum zoom factor then depends on the client window size. If we ask
wx to handle something outside INT_MIN to INT_MAX, there are unreported
problems in the non-Debug build because wxRound() goes silent.
Pcbnew uses nanometers because we ned to convert coordintes and size between
milimeters and inches. using a iu = 1 nm avoid rounding issues
Gerbview uses iu = 10 nm because we can have coordintes far from origin, and
1 nm is too small to avoid int overflow.
(Conversions between milimeters and inches are not critical)
*/
/** /**
* @brief some define and functions to convert a value in mils, decimils or mm * @brief some define and functions to convert a value in mils, decimils or mm
* to the internal unit used in pcbnew, cvpcb or gerbview (nanometer or deci-mil) * to the internal unit used in pcbnew, cvpcb or gerbview (nanometer or deci-mil)

View File

@ -24,58 +24,10 @@
#pragma once #pragma once
/* ZOOM LIMITS // List of predefined zooms used in zoom in/out from hotkeys, context menu and toolbar
// Zooming using mouse wheel can have different limits
The largest distance that we (and Kicad) can support is INT_MAX, since it represents #define ZOOM_LIST_GERBVIEW 0.022, 0.035, 0.05, 0.08, 0.13, 0.22, 0.35, 0.6, 1.0,\
distance often in a wxCoord or wxSize. As a scalar, a distance is always 2.2, 3.5, 5.0, 8.0, 13.0, 22.0, 35.0, 50.0, 80.0, 130.0, 220.0
positive. Because int is 32 bits and INT_MAX is
2147483647. The most difficult distance for a virtual (world) cartesian
space is the hypotenuse, or diagonal measurement at a 45 degree angle. This
puts the most stress on the distance magnitude within the bounded virtual
space. So if we allow this distance to be our constraint of <= INT_MAX, this
constraint then propagates to the maximum distance in X and in Y that can be
supported on each axis. Remember that the hypotenuse of a 1x1 square is
sqrt( 1x1 + 1x1 ) = sqrt(2) = 1.41421356.
hypotenuse of any square = sqrt(2) * deltaX;
Let maximum supported hypotenuse be INT_MAX, then:
MAX_AXIS = INT_MAX / sqrt(2) = 2147483647 / 1.41421356 = 1518500251
This maximum distance is imposed by wxWidgets, not by KiCad. The imposition
comes in the form of the data structures used in the graphics API at the
wxDC level. Obviously when we are not interacting with wx we can use double
to compute distances larger than this. For example the computation of the
total length of a net, can and should be done in double, since it might
actually be longer than a single diagonal line.
The next choice is what to use for internal units (IU), sometimes called
world units. If nanometers, then the virtual space must be limited to
about 1.5 x 1.5 meters square. This is 1518500251 divided by 1e9 nm/meter.
The maximum zoom factor then depends on the client window size. If we ask
wx to handle something outside INT_MIN to INT_MAX, there are unreported
problems in the non-Debug build because wxRound() goes silent.
Let:
const double MAX_AXIS = 1518500251;
Then a maximum zoom factor for a screen of 1920 pixels wide is
1518500251 / 1920 = 790885.
The largest zoom factor allowed is therefore ~ 300 (which computes to 762000).
*/
#define MAX_ZOOM_FACTOR 300.0
// Adjusted to display zoom level ~ 1 when the screen shows a 1:1 image.
// Obviously depends on the monitor, but this is an acceptable value.
#define ZOOM_COEFF 1.1
// List of predefined zooms used in zoom in/out from hotkeys and toolbar
#define ZOOM_LIST_GERBER 0.022, 0.035, 0.05, 0.08, 0.13, 0.22, 0.35, 0.6, 1.0,\
2.2, 3.5, 5.0, 8.0, 13.0, 22.0, 35.0, 50.0, 80.0, 130.0, 220.0
#define ZOOM_LIST_PCBNEW 0.13, 0.22, 0.35, 0.6, 1.0, 1.5, 2.2, 3.5, 5.0, 8.0, 13.0,\ #define ZOOM_LIST_PCBNEW 0.13, 0.22, 0.35, 0.6, 1.0, 1.5, 2.2, 3.5, 5.0, 8.0, 13.0,\
20.0, 35.0, 50.0, 80.0, 130.0, 220.0, 300.0 20.0, 35.0, 50.0, 80.0, 130.0, 220.0, 300.0
@ -85,3 +37,27 @@
#define ZOOM_LIST_EESCHEMA 0.05, 0.07, 0.1, 0.15, 0.2, 0.3, 0.5, 0.7, 1.0, 1.5, 2.0,\ #define ZOOM_LIST_EESCHEMA 0.05, 0.07, 0.1, 0.15, 0.2, 0.3, 0.5, 0.7, 1.0, 1.5, 2.0,\
3.0, 4.5, 6.5, 10.0, 15.0, 20.0, 30.0, 45.0, 65.0, 100.0 3.0, 4.5, 6.5, 10.0, 15.0, 20.0, 30.0, 45.0, 65.0, 100.0
// Zoom scale limits for zoom (especially mouse wheel)
// the limits can differ from zoom list because the zoom list cannot be as long as
// we want because the zoom list is displayed in menus.
// But zoom by mouse wheel is limited mainly by the usability
// Scale limits for zoom for Eeschema
#define ZOOM_MAX_LIMIT_EESCHEMA 100
#define ZOOM_MIN_LIMIT_EESCHEMA 0.01
#define ZOOM_MAX_LIMIT_EESCHEMA_PREVIEW 20
#define ZOOM_MIN_LIMIT_EESCHEMA_PREVIEW 0.5
// Scale limits for zoom for pl_editor
#define ZOOM_MAX_LIMIT_PLEDITOR 20
#define ZOOM_MIN_LIMIT_PLEDITOR 0.05
// Scale limits for zoom for gerbview
#define ZOOM_MAX_LIMIT_GERBVIEW 220
#define ZOOM_MIN_LIMIT_GERBVIEW 0.02
// Scale limits for zoom (especially mouse wheel) for Pcbnew
#define ZOOM_MAX_LIMIT_PCBNEW 5000
#define ZOOM_MIN_LIMIT_PCBNEW 0.1

View File

@ -37,6 +37,7 @@
#include "pl_editor_settings.h" #include "pl_editor_settings.h"
#include "tools/pl_actions.h" #include "tools/pl_actions.h"
#include "tools/pl_selection_tool.h" #include "tools/pl_selection_tool.h"
#include <zoom_defines.h>
using namespace std::placeholders; using namespace std::placeholders;
@ -58,7 +59,8 @@ PL_DRAW_PANEL_GAL::PL_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWindo
m_painter->GetSettings()->LoadColors( settingsManager.GetColorSettings( cfg->m_ColorTheme ) ); m_painter->GetSettings()->LoadColors( settingsManager.GetColorSettings( cfg->m_ColorTheme ) );
m_view->SetPainter( m_painter.get() ); m_view->SetPainter( m_painter.get() );
m_view->SetScaleLimits( 20.0, 0.05 ); // This fixes the zoom in and zoom out limits // This fixes the zoom in and zoom out limits
m_view->SetScaleLimits( ZOOM_MAX_LIMIT_PLEDITOR, ZOOM_MIN_LIMIT_PLEDITOR );
setDefaultLayerDeps(); setDefaultLayerDeps();

View File

@ -489,9 +489,6 @@ void PL_EDITOR_FRAME::LoadSettings( APP_SETTINGS_BASE* aCfg )
aCfg->m_Window.zoom_factors = { ZOOM_LIST_PL_EDITOR }; aCfg->m_Window.zoom_factors = { ZOOM_LIST_PL_EDITOR };
} }
for( double& factor : aCfg->m_Window.zoom_factors )
factor = std::min( factor, MAX_ZOOM_FACTOR );
PL_EDITOR_SETTINGS* cfg = dynamic_cast<PL_EDITOR_SETTINGS*>( aCfg ); PL_EDITOR_SETTINGS* cfg = dynamic_cast<PL_EDITOR_SETTINGS*>( aCfg );
wxCHECK( cfg, /*void*/ ); wxCHECK( cfg, /*void*/ );

View File

@ -449,9 +449,6 @@ FOOTPRINT_PREVIEW_PANEL* FOOTPRINT_PREVIEW_PANEL::New( KIWAY* aKiway, wxWindow*
cfg->m_Window.zoom_factors = { ZOOM_LIST_PCBNEW }; cfg->m_Window.zoom_factors = { ZOOM_LIST_PCBNEW };
} }
for( double& factor : cfg->m_Window.zoom_factors )
factor = std::min( factor, MAX_ZOOM_FACTOR );
std::unique_ptr<KIGFX::GAL_DISPLAY_OPTIONS> gal_opts; std::unique_ptr<KIGFX::GAL_DISPLAY_OPTIONS> gal_opts;
gal_opts = std::make_unique<KIGFX::GAL_DISPLAY_OPTIONS>(); gal_opts = std::make_unique<KIGFX::GAL_DISPLAY_OPTIONS>();

View File

@ -603,9 +603,6 @@ void PCB_BASE_FRAME::LoadSettings( APP_SETTINGS_BASE* aCfg )
aCfg->m_Window.zoom_factors = { ZOOM_LIST_PCBNEW }; aCfg->m_Window.zoom_factors = { ZOOM_LIST_PCBNEW };
} }
for( double& factor : aCfg->m_Window.zoom_factors )
factor = std::min( factor, MAX_ZOOM_FACTOR );
// Some, but not all derived classes have a PCBNEW_SETTINGS. // Some, but not all derived classes have a PCBNEW_SETTINGS.
PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( aCfg ); PCBNEW_SETTINGS* cfg = dynamic_cast<PCBNEW_SETTINGS*>( aCfg );

View File

@ -43,10 +43,12 @@
#include <confirm.h> #include <confirm.h>
#include <gal/graphics_abstraction_layer.h> #include <gal/graphics_abstraction_layer.h>
#include <zoom_defines.h>
#include <functional> #include <functional>
#include <memory> #include <memory>
#include <thread> #include <thread>
using namespace std::placeholders; using namespace std::placeholders;
const LAYER_NUM GAL_LAYER_ORDER[] = const LAYER_NUM GAL_LAYER_ORDER[] =
@ -135,6 +137,8 @@ PCB_DRAW_PANEL_GAL::PCB_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
m_painter = std::make_unique<KIGFX::PCB_PAINTER>( m_gal ); m_painter = std::make_unique<KIGFX::PCB_PAINTER>( m_gal );
m_view->SetPainter( m_painter.get() ); m_view->SetPainter( m_painter.get() );
// This fixes the zoom in and zoom out limits:
m_view->SetScaleLimits( ZOOM_MAX_LIMIT_PCBNEW, ZOOM_MIN_LIMIT_PCBNEW );
setDefaultLayerOrder(); setDefaultLayerOrder();
setDefaultLayerDeps(); setDefaultLayerDeps();