Commit 009d28d4 authored by Maciej Suminski's avatar Maciej Suminski

Merged lp:~cern-kicad/kicad/drawing_tool branch.

parents 402c7d21 2ed804b8
...@@ -477,6 +477,8 @@ if( KICAD_SKIP_BOOST ) ...@@ -477,6 +477,8 @@ if( KICAD_SKIP_BOOST )
message( FATAL_ERROR "Boost 1.54+ libraries are required." ) message( FATAL_ERROR "Boost 1.54+ libraries are required." )
endif() endif()
add_custom_target( boost ) # it is required to meet some further dependencies
message( WARNING " message( WARNING "
WARNING: You decided to skip building boost library. WARNING: You decided to skip building boost library.
KiCad developers strongly advise you to build the bundled boost library, as it is known to work with KiCad. KiCad developers strongly advise you to build the bundled boost library, as it is known to work with KiCad.
......
...@@ -29,7 +29,7 @@ add_custom_target( ...@@ -29,7 +29,7 @@ add_custom_target(
set( GAL_SRCS set( GAL_SRCS
# Common part # Common part
drawpanel_gal.cpp draw_panel_gal.cpp
painter.cpp painter.cpp
worksheet_viewitem.cpp worksheet_viewitem.cpp
gal/graphics_abstraction_layer.cpp gal/graphics_abstraction_layer.cpp
......
...@@ -175,13 +175,6 @@ void BASE_SCREEN::SetGridList( GRIDS& gridlist ) ...@@ -175,13 +175,6 @@ void BASE_SCREEN::SetGridList( GRIDS& gridlist )
} }
void BASE_SCREEN::GetGrids( GRIDS& aList )
{
for( size_t i = 0; i < m_grids.size(); i++ )
aList.push_back( m_grids[ i ] );
}
int BASE_SCREEN::SetGrid( const wxRealPoint& size ) int BASE_SCREEN::SetGrid( const wxRealPoint& size )
{ {
wxASSERT( !m_grids.empty() ); wxASSERT( !m_grids.empty() );
......
...@@ -19,8 +19,8 @@ ...@@ -19,8 +19,8 @@
// Default marquer shape: // Default marquer shape:
#define M_SHAPE_SCALE 6 // default scaling factor for MarkerShapeCorners coordinates const int M_SHAPE_SCALE = 6; // default scaling factor for MarkerShapeCorners coordinates
#define CORNERS_COUNT 8 const int CORNERS_COUNT = 8;
/* corners of the default shape /* corners of the default shape
* actual coordinates are these values * .m_ScalingFactor * actual coordinates are these values * .m_ScalingFactor
*/ */
...@@ -46,10 +46,10 @@ void MARKER_BASE::init() ...@@ -46,10 +46,10 @@ void MARKER_BASE::init()
m_Color = RED; m_Color = RED;
wxPoint start = MarkerShapeCorners[0]; wxPoint start = MarkerShapeCorners[0];
wxPoint end = MarkerShapeCorners[0]; wxPoint end = MarkerShapeCorners[0];
for( unsigned ii = 0; ii < CORNERS_COUNT; ii++ ) for( unsigned ii = 0; ii < CORNERS_COUNT; ii++ )
{ {
wxPoint corner = MarkerShapeCorners[ii]; wxPoint corner = MarkerShapeCorners[ii];
m_Corners.push_back( corner );
start.x = std::min( start.x, corner.x); start.x = std::min( start.x, corner.x);
start.y = std::min( start.y, corner.y); start.y = std::min( start.y, corner.y);
end.x = std::max( end.x, corner.x); end.x = std::max( end.x, corner.x);
...@@ -64,7 +64,6 @@ void MARKER_BASE::init() ...@@ -64,7 +64,6 @@ void MARKER_BASE::init()
MARKER_BASE::MARKER_BASE( const MARKER_BASE& aMarker ) MARKER_BASE::MARKER_BASE( const MARKER_BASE& aMarker )
{ {
m_Pos = aMarker.m_Pos; m_Pos = aMarker.m_Pos;
m_Corners = aMarker.m_Corners;
m_MarkerType = aMarker.m_MarkerType; m_MarkerType = aMarker.m_MarkerType;
m_Color = aMarker.m_Color; m_Color = aMarker.m_Color;
m_ShapeBoundingBox = aMarker.m_ShapeBoundingBox; m_ShapeBoundingBox = aMarker.m_ShapeBoundingBox;
...@@ -154,9 +153,9 @@ void MARKER_BASE::DrawMarker( EDA_DRAW_PANEL* aPanel, wxDC* aDC, GR_DRAWMODE aDr ...@@ -154,9 +153,9 @@ void MARKER_BASE::DrawMarker( EDA_DRAW_PANEL* aPanel, wxDC* aDC, GR_DRAWMODE aDr
GRSetDrawMode( aDC, aDrawMode ); GRSetDrawMode( aDC, aDrawMode );
for( unsigned ii = 0; ii < m_Corners.size(); ii++ ) for( unsigned ii = 0; ii < CORNERS_COUNT; ii++ )
{ {
corners[ii] = m_Corners[ii]; corners[ii] = MarkerShapeCorners[ii];
corners[ii].x *= m_ScalingFactor; corners[ii].x *= m_ScalingFactor;
corners[ii].y *= m_ScalingFactor; corners[ii].y *= m_ScalingFactor;
corners[ii] += m_Pos + aOffset; corners[ii] += m_Pos + aOffset;
......
...@@ -36,7 +36,7 @@ ...@@ -36,7 +36,7 @@
#include <macros.h> #include <macros.h>
#include <id.h> #include <id.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <class_base_screen.h> #include <class_base_screen.h>
#include <msgpanel.h> #include <msgpanel.h>
#include <draw_frame.h> #include <draw_frame.h>
...@@ -48,6 +48,7 @@ ...@@ -48,6 +48,7 @@
#include <wx/fontdlg.h> #include <wx/fontdlg.h>
#include <view/view.h> #include <view/view.h>
#include <view/view_controls.h>
#include <gal/graphics_abstraction_layer.h> #include <gal/graphics_abstraction_layer.h>
/** /**
...@@ -395,7 +396,7 @@ void EDA_DRAW_FRAME::OnSelectGrid( wxCommandEvent& event ) ...@@ -395,7 +396,7 @@ void EDA_DRAW_FRAME::OnSelectGrid( wxCommandEvent& event )
if( IsGalCanvasActive() ) if( IsGalCanvasActive() )
{ {
GetGalCanvas()->GetGAL()->SetGridSize( VECTOR2D( screen->GetGrid().m_Size.x, GetGalCanvas()->GetGAL()->SetGridSize( VECTOR2D( screen->GetGrid().m_Size.x,
screen->GetGrid().m_Size.y ) ); screen->GetGrid().m_Size.y ) );
GetGalCanvas()->GetView()->MarkTargetDirty( KIGFX::TARGET_NONCACHED ); GetGalCanvas()->GetView()->MarkTargetDirty( KIGFX::TARGET_NONCACHED );
} }
...@@ -532,6 +533,38 @@ wxPoint EDA_DRAW_FRAME::GetGridPosition( const wxPoint& aPosition ) const ...@@ -532,6 +533,38 @@ wxPoint EDA_DRAW_FRAME::GetGridPosition( const wxPoint& aPosition ) const
} }
void EDA_DRAW_FRAME::SetNextGrid()
{
if( m_gridSelectBox )
{
m_gridSelectBox->SetSelection( ( m_gridSelectBox->GetSelection() + 1 ) %
m_gridSelectBox->GetCount() );
wxCommandEvent cmd( wxEVT_COMMAND_COMBOBOX_SELECTED );
// cmd.SetEventObject( this );
OnSelectGrid( cmd );
}
}
void EDA_DRAW_FRAME::SetPrevGrid()
{
if( m_gridSelectBox )
{
int cnt = m_gridSelectBox->GetSelection();
if( --cnt < 0 )
cnt = m_gridSelectBox->GetCount() - 1;
m_gridSelectBox->SetSelection( cnt );
wxCommandEvent cmd( wxEVT_COMMAND_COMBOBOX_SELECTED );
// cmd.SetEventObject( this );
OnSelectGrid( cmd );
}
}
int EDA_DRAW_FRAME::BlockCommand( int key ) int EDA_DRAW_FRAME::BlockCommand( int key )
{ {
return 0; return 0;
...@@ -1007,9 +1040,17 @@ void EDA_DRAW_FRAME::UseGalCanvas( bool aEnable ) ...@@ -1007,9 +1040,17 @@ void EDA_DRAW_FRAME::UseGalCanvas( bool aEnable )
wxPoint EDA_DRAW_FRAME::GetCrossHairPosition( bool aInvertY ) const wxPoint EDA_DRAW_FRAME::GetCrossHairPosition( bool aInvertY ) const
{ {
// subject to change, borrow from old BASE_SCREEN for now. // subject to change, borrow from old BASE_SCREEN for now.
if( IsGalCanvasActive() )
{
VECTOR2I cursor = GetGalCanvas()->GetViewControls()->GetCursorPosition();
BASE_SCREEN* screen = GetScreen(); // virtual call return wxPoint( cursor.x, cursor.y );
return screen->getCrossHairPosition( aInvertY ); }
else
{
BASE_SCREEN* screen = GetScreen(); // virtual call
return screen->getCrossHairPosition( aInvertY );
}
} }
......
...@@ -35,7 +35,7 @@ ...@@ -35,7 +35,7 @@
#include <macros.h> #include <macros.h>
#include <id.h> #include <id.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <class_base_screen.h> #include <class_base_screen.h>
#include <draw_frame.h> #include <draw_frame.h>
......
...@@ -29,7 +29,7 @@ ...@@ -29,7 +29,7 @@
#include <wx/colour.h> #include <wx/colour.h>
#include <wx/filename.h> #include <wx/filename.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <view/view.h> #include <view/view.h>
#include <view/wx_view_controls.h> #include <view/wx_view_controls.h>
#include <pcb_painter.h> #include <pcb_painter.h>
...@@ -45,8 +45,6 @@ ...@@ -45,8 +45,6 @@
#include <profile.h> #include <profile.h>
#endif /* __WXDEBUG__ */ #endif /* __WXDEBUG__ */
#define METRIC_UNIT_LENGTH (1e9)
EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWindowId, EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWindowId,
const wxPoint& aPosition, const wxSize& aSize, const wxPoint& aPosition, const wxSize& aSize,
GalType aGalType ) : GalType aGalType ) :
...@@ -61,11 +59,6 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin ...@@ -61,11 +59,6 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
SwitchBackend( aGalType ); SwitchBackend( aGalType );
SetBackgroundStyle( wxBG_STYLE_CUSTOM ); SetBackgroundStyle( wxBG_STYLE_CUSTOM );
// Initial display settings
m_gal->SetLookAtPoint( VECTOR2D( 0, 0 ) );
m_gal->SetZoomFactor( 1.0 );
m_gal->ComputeWorldScreenMatrix();
m_painter = new KIGFX::PCB_PAINTER( m_gal ); m_painter = new KIGFX::PCB_PAINTER( m_gal );
m_view = new KIGFX::VIEW( true ); m_view = new KIGFX::VIEW( true );
...@@ -90,8 +83,7 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin ...@@ -90,8 +83,7 @@ EDA_DRAW_PANEL_GAL::EDA_DRAW_PANEL_GAL( wxWindow* aParentWindow, wxWindowID aWin
Connect( wxEVT_MIDDLE_DCLICK, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this ); Connect( wxEVT_MIDDLE_DCLICK, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this );
Connect( wxEVT_MOUSEWHEEL, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this ); Connect( wxEVT_MOUSEWHEEL, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this );
Connect( wxEVT_CHAR_HOOK, wxEventHandler( EDA_DRAW_PANEL_GAL::skipEvent ) ); Connect( wxEVT_CHAR_HOOK, wxEventHandler( EDA_DRAW_PANEL_GAL::skipEvent ) );
Connect( wxEVT_KEY_UP, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this ); Connect( wxEVT_CHAR, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this );
Connect( wxEVT_KEY_DOWN, wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this );
Connect( wxEVT_ENTER_WINDOW, wxEventHandler( EDA_DRAW_PANEL_GAL::onEnter ), NULL, this ); Connect( wxEVT_ENTER_WINDOW, wxEventHandler( EDA_DRAW_PANEL_GAL::onEnter ), NULL, this );
Connect( KIGFX::WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE, Connect( KIGFX::WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE,
wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this ); wxEventHandler( EDA_DRAW_PANEL_GAL::onEvent ), NULL, this );
...@@ -131,17 +123,22 @@ void EDA_DRAW_PANEL_GAL::onPaint( wxPaintEvent& WXUNUSED( aEvent ) ) ...@@ -131,17 +123,22 @@ void EDA_DRAW_PANEL_GAL::onPaint( wxPaintEvent& WXUNUSED( aEvent ) )
{ {
m_drawing = true; m_drawing = true;
m_view->UpdateItems();
m_gal->BeginDrawing(); m_gal->BeginDrawing();
m_gal->SetBackgroundColor( KIGFX::COLOR4D( 0.0, 0.0, 0.0, 1.0 ) );
m_gal->ClearScreen(); m_gal->ClearScreen();
m_view->ClearTargets(); if( m_view->IsDirty() )
// Grid has to be redrawn only when the NONCACHED target is redrawn {
if( m_view->IsTargetDirty( KIGFX::TARGET_NONCACHED ) ) m_view->ClearTargets();
m_gal->DrawGrid();
m_view->Redraw(); // Grid has to be redrawn only when the NONCACHED target is redrawn
m_gal->DrawCursor( m_viewControls->GetCursorPosition() ); if( m_view->IsTargetDirty( KIGFX::TARGET_NONCACHED ) )
m_gal->DrawGrid();
m_view->Redraw();
}
m_gal->DrawCursor( m_viewControls->GetCursorPosition() );
m_gal->EndDrawing(); m_gal->EndDrawing();
m_drawing = false; m_drawing = false;
...@@ -196,14 +193,14 @@ void EDA_DRAW_PANEL_GAL::StopDrawing() ...@@ -196,14 +193,14 @@ void EDA_DRAW_PANEL_GAL::StopDrawing()
void EDA_DRAW_PANEL_GAL::SwitchBackend( GalType aGalType ) void EDA_DRAW_PANEL_GAL::SwitchBackend( GalType aGalType )
{ {
// Protect from refreshing during backend switch
m_pendingRefresh = true;
m_refreshTimer.Stop();
// Do not do anything if the currently used GAL is correct // Do not do anything if the currently used GAL is correct
if( aGalType == m_currentGal && m_gal != NULL ) if( aGalType == m_currentGal && m_gal != NULL )
return; return;
// Prevent refreshing canvas during backend switch
m_pendingRefresh = true;
m_refreshTimer.Stop();
delete m_gal; delete m_gal;
switch( aGalType ) switch( aGalType )
...@@ -220,21 +217,15 @@ void EDA_DRAW_PANEL_GAL::SwitchBackend( GalType aGalType ) ...@@ -220,21 +217,15 @@ void EDA_DRAW_PANEL_GAL::SwitchBackend( GalType aGalType )
return; return;
} }
m_gal->SetWorldUnitLength( 1.0 / METRIC_UNIT_LENGTH * 2.54 ); // 1 inch in nanometers
m_gal->SetScreenDPI( 106 ); // Display resolution setting
m_gal->ComputeWorldScreenMatrix();
wxSize size = GetClientSize(); wxSize size = GetClientSize();
m_gal->ResizeScreen( size.GetX(), size.GetY() ); m_gal->ResizeScreen( size.GetX(), size.GetY() );
m_gal->SetBackgroundColor( KIGFX::COLOR4D( 0.0, 0.0, 0.0, 1.0 ) );
if( m_painter ) if( m_painter )
m_painter->SetGAL( m_gal ); m_painter->SetGAL( m_gal );
if( m_view ) if( m_view )
{
m_view->SetGAL( m_gal ); m_view->SetGAL( m_gal );
m_view->RecacheAllItems( true );
}
m_currentGal = aGalType; m_currentGal = aGalType;
m_pendingRefresh = false; m_pendingRefresh = false;
......
...@@ -35,9 +35,6 @@ ...@@ -35,9 +35,6 @@
using namespace KIGFX; using namespace KIGFX;
///> Opacity of a single layer
const float LAYER_ALPHA = 0.8;
CAIRO_GAL::CAIRO_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener, CAIRO_GAL::CAIRO_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener,
wxEvtHandler* aPaintListener, const wxString& aName ) : wxEvtHandler* aPaintListener, const wxString& aName ) :
wxWindow( aParent, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxEXPAND, aName ) wxWindow( aParent, wxID_ANY, wxDefaultPosition, wxDefaultSize, wxEXPAND, aName )
...@@ -73,14 +70,16 @@ CAIRO_GAL::CAIRO_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener, ...@@ -73,14 +70,16 @@ CAIRO_GAL::CAIRO_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener,
#endif #endif
SetSize( aParent->GetSize() ); SetSize( aParent->GetSize() );
screenSize = VECTOR2D( aParent->GetSize() ); screenSize = VECTOR2I( aParent->GetSize() );
initCursor( 20 ); initCursor();
// Grid color settings are different in Cairo and OpenGL // Grid color settings are different in Cairo and OpenGL
SetGridColor( COLOR4D( 0.1, 0.1, 0.1, 0.8 ) ); SetGridColor( COLOR4D( 0.1, 0.1, 0.1, 0.8 ) );
// Allocate memory for pixel storage // Allocate memory for pixel storage
allocateBitmaps(); allocateBitmaps();
initSurface();
} }
...@@ -139,7 +138,7 @@ void CAIRO_GAL::EndDrawing() ...@@ -139,7 +138,7 @@ void CAIRO_GAL::EndDrawing()
*wxOutputPtr++ = value & 0xff; // Blue pixel *wxOutputPtr++ = value & 0xff; // Blue pixel
} }
wxImage img( (int) screenSize.x, (int) screenSize.y, (unsigned char*) wxOutput, true ); wxImage img( screenSize.x, screenSize.y, (unsigned char*) wxOutput, true );
wxBitmap bmp( img ); wxBitmap bmp( img );
wxClientDC client_dc( this ); wxClientDC client_dc( this );
wxBufferedDC dc; wxBufferedDC dc;
...@@ -284,7 +283,7 @@ void CAIRO_GAL::DrawCurve( const VECTOR2D& aStartPoint, const VECTOR2D& aControl ...@@ -284,7 +283,7 @@ void CAIRO_GAL::DrawCurve( const VECTOR2D& aStartPoint, const VECTOR2D& aControl
void CAIRO_GAL::ResizeScreen( int aWidth, int aHeight ) void CAIRO_GAL::ResizeScreen( int aWidth, int aHeight )
{ {
screenSize = VECTOR2D( aWidth, aHeight ); screenSize = VECTOR2I( aWidth, aHeight );
// Recreate the bitmaps // Recreate the bitmaps
deleteBitmaps(); deleteBitmaps();
...@@ -431,7 +430,7 @@ void CAIRO_GAL::SetLayerDepth( double aLayerDepth ) ...@@ -431,7 +430,7 @@ void CAIRO_GAL::SetLayerDepth( double aLayerDepth )
} }
void CAIRO_GAL::Transform( MATRIX3x3D aTransformation ) void CAIRO_GAL::Transform( const MATRIX3x3D& aTransformation )
{ {
cairo_matrix_t cairoTransformation; cairo_matrix_t cairoTransformation;
...@@ -885,11 +884,10 @@ void CAIRO_GAL::skipMouseEvent( wxMouseEvent& aEvent ) ...@@ -885,11 +884,10 @@ void CAIRO_GAL::skipMouseEvent( wxMouseEvent& aEvent )
} }
void CAIRO_GAL::initCursor( int aCursorSize ) void CAIRO_GAL::initCursor()
{ {
cursorPixels = new wxBitmap( aCursorSize, aCursorSize ); cursorPixels = new wxBitmap( cursorSize, cursorSize );
cursorPixelsSaved = new wxBitmap( aCursorSize, aCursorSize ); cursorPixelsSaved = new wxBitmap( cursorSize, cursorSize );
cursorSize = aCursorSize;
wxMemoryDC cursorShape( *cursorPixels ); wxMemoryDC cursorShape( *cursorPixels );
...@@ -900,8 +898,8 @@ void CAIRO_GAL::initCursor( int aCursorSize ) ...@@ -900,8 +898,8 @@ void CAIRO_GAL::initCursor( int aCursorSize )
cursorShape.SetPen( pen ); cursorShape.SetPen( pen );
cursorShape.Clear(); cursorShape.Clear();
cursorShape.DrawLine( 0, aCursorSize / 2, aCursorSize, aCursorSize / 2 ); cursorShape.DrawLine( 0, cursorSize / 2, cursorSize, cursorSize / 2 );
cursorShape.DrawLine( aCursorSize / 2, 0, aCursorSize / 2, aCursorSize ); cursorShape.DrawLine( cursorSize / 2, 0, cursorSize / 2, cursorSize );
} }
...@@ -925,14 +923,15 @@ void CAIRO_GAL::blitCursor( wxBufferedDC& clientDC ) ...@@ -925,14 +923,15 @@ void CAIRO_GAL::blitCursor( wxBufferedDC& clientDC )
} }
// Store pixels that are going to be overpainted // Store pixels that are going to be overpainted
cursorSave.Blit( 0, 0, cursorSize, cursorSize, &clientDC, cursorPosition.x, cursorPosition.y ); VECTOR2D cursorScreen = ToScreen( cursorPosition ) - cursorSize / 2;
cursorSave.Blit( 0, 0, cursorSize, cursorSize, &clientDC, cursorScreen.x, cursorScreen.y );
// Draw the cursor // Draw the cursor
clientDC.Blit( cursorPosition.x, cursorPosition.y, cursorSize, cursorSize, clientDC.Blit( cursorScreen.x, cursorScreen.y, cursorSize, cursorSize,
&cursorShape, 0, 0, wxOR ); &cursorShape, 0, 0, wxOR );
savedCursorPosition.x = (wxCoord) cursorPosition.x; savedCursorPosition.x = (wxCoord) cursorScreen.x;
savedCursorPosition.y = (wxCoord) cursorPosition.y; savedCursorPosition.y = (wxCoord) cursorScreen.y;
} }
...@@ -958,7 +957,8 @@ void CAIRO_GAL::deleteBitmaps() ...@@ -958,7 +957,8 @@ void CAIRO_GAL::deleteBitmaps()
void CAIRO_GAL::initSurface() void CAIRO_GAL::initSurface()
{ {
wxASSERT( !isInitialized ); if( isInitialized )
return;
// Create the Cairo surface // Create the Cairo surface
surface = cairo_image_surface_create_for_data( (unsigned char*) bitmapBuffer, GAL_FORMAT, surface = cairo_image_surface_create_for_data( (unsigned char*) bitmapBuffer, GAL_FORMAT,
......
...@@ -39,7 +39,10 @@ GAL::GAL() : ...@@ -39,7 +39,10 @@ GAL::GAL() :
SetIsStroke( true ); SetIsStroke( true );
SetFillColor( COLOR4D( 0.0, 0.0, 0.0, 0.0 ) ); SetFillColor( COLOR4D( 0.0, 0.0, 0.0, 0.0 ) );
SetStrokeColor( COLOR4D( 1.0, 1.0, 1.0, 1.0 ) ); SetStrokeColor( COLOR4D( 1.0, 1.0, 1.0, 1.0 ) );
SetLookAtPoint( VECTOR2D( 0, 0 ) );
SetZoomFactor( 1.0 ); SetZoomFactor( 1.0 );
SetWorldUnitLength( 1.0 / METRIC_UNIT_LENGTH * 2.54 ); // 1 inch in nanometers
SetScreenDPI( 106 ); // Display resolution setting
SetDepthRange( VECTOR2D( GAL::MIN_DEPTH, GAL::MAX_DEPTH ) ); SetDepthRange( VECTOR2D( GAL::MIN_DEPTH, GAL::MAX_DEPTH ) );
SetFlip( false, false ); SetFlip( false, false );
SetLineWidth( 1.0 ); SetLineWidth( 1.0 );
...@@ -85,7 +88,7 @@ void GAL::ComputeWorldScreenMatrix() ...@@ -85,7 +88,7 @@ void GAL::ComputeWorldScreenMatrix()
MATRIX3x3D translation; MATRIX3x3D translation;
translation.SetIdentity(); translation.SetIdentity();
translation.SetTranslation( 0.5 * screenSize ); translation.SetTranslation( 0.5 * VECTOR2D( screenSize ) );
MATRIX3x3D scale; MATRIX3x3D scale;
scale.SetIdentity(); scale.SetIdentity();
...@@ -112,23 +115,23 @@ void GAL::DrawGrid() ...@@ -112,23 +115,23 @@ void GAL::DrawGrid()
SetTarget( TARGET_NONCACHED ); SetTarget( TARGET_NONCACHED );
// Draw the origin marker // Draw the origin marker
double origSize = static_cast<double>( gridOriginMarkerSize ) / worldScale; double originSize = gridOriginMarkerSize / worldScale;
SetLayerDepth( GAL::GRID_DEPTH ); SetLayerDepth( GAL::GRID_DEPTH );
SetIsFill( false ); SetIsFill( false );
SetIsStroke( true ); SetIsStroke( true );
SetStrokeColor( COLOR4D( 1.0, 1.0, 1.0, 1.0 ) ); SetStrokeColor( COLOR4D( 1.0, 1.0, 1.0, 1.0 ) );
SetLineWidth( gridLineWidth / worldScale ); SetLineWidth( gridLineWidth / worldScale );
DrawLine( gridOrigin + VECTOR2D( -origSize, -origSize ), DrawLine( gridOrigin + VECTOR2D( -originSize, -originSize ),
gridOrigin + VECTOR2D( origSize, origSize ) ); gridOrigin + VECTOR2D( originSize, originSize ) );
DrawLine( gridOrigin + VECTOR2D( -origSize, origSize ), DrawLine( gridOrigin + VECTOR2D( -originSize, originSize ),
gridOrigin + VECTOR2D( origSize, -origSize ) ); gridOrigin + VECTOR2D( originSize, -originSize ) );
DrawCircle( gridOrigin, origSize * 0.7 ); DrawCircle( gridOrigin, originSize * 0.7 );
// Draw the grid // Draw the grid
// For the drawing the start points, end points and increments have // For the drawing the start points, end points and increments have
// to be calculated in world coordinates // to be calculated in world coordinates
VECTOR2D worldStartPoint = screenWorldMatrix * VECTOR2D( 0.0, 0.0 ); VECTOR2D worldStartPoint = screenWorldMatrix * VECTOR2D( 0.0, 0.0 );
VECTOR2D worldEndPoint = screenWorldMatrix * screenSize; VECTOR2D worldEndPoint = screenWorldMatrix * VECTOR2D( screenSize );
int gridScreenSizeDense = round( gridSize.x * worldScale ); int gridScreenSizeDense = round( gridSize.x * worldScale );
int gridScreenSizeCoarse = round( gridSize.x * static_cast<double>( gridTick ) * worldScale ); int gridScreenSizeCoarse = round( gridSize.x * static_cast<double>( gridTick ) * worldScale );
...@@ -232,12 +235,12 @@ void GAL::DrawGrid() ...@@ -232,12 +235,12 @@ void GAL::DrawGrid()
} }
VECTOR2D GAL::GetGridPoint( VECTOR2D aPoint ) const VECTOR2D GAL::GetGridPoint( const VECTOR2D& aPoint ) const
{ {
VECTOR2D pointWorld = ToWorld( aPoint ); VECTOR2D gridPoint;
pointWorld.x = round( pointWorld.x / gridSize.x ) * gridSize.x; gridPoint.x = round( aPoint.x / gridSize.x ) * gridSize.x;
pointWorld.y = round( pointWorld.y / gridSize.y ) * gridSize.y; gridPoint.y = round( aPoint.y / gridSize.y ) * gridSize.y;
return ToScreen( pointWorld ); return gridPoint;
} }
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
* You should have received a copy of the GNU General Public License * You should have received a copy of the GNU General Public License
* along with this program; if not, you may find one here: * along with this program; if not, you may find one here:
* http://www.gnu.org/licenses/old-licenses/gpl-2.0.html * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
* or you may search the http:O//www.gnu.org website for the version 2 license, * or you may search the http://www.gnu.org website for the version 2 license,
* or you may write to the Free Software Foundation, Inc., * or you may write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
*/ */
......
...@@ -86,8 +86,7 @@ OPENGL_GAL::OPENGL_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener, ...@@ -86,8 +86,7 @@ OPENGL_GAL::OPENGL_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener,
#endif #endif
SetSize( aParent->GetSize() ); SetSize( aParent->GetSize() );
screenSize = VECTOR2D( aParent->GetSize() ); screenSize = VECTOR2I( aParent->GetSize() );
initCursor( 80 );
// Grid color settings are different in Cairo and OpenGL // Grid color settings are different in Cairo and OpenGL
SetGridColor( COLOR4D( 0.8, 0.8, 0.8, 0.1 ) ); SetGridColor( COLOR4D( 0.8, 0.8, 0.8, 0.1 ) );
...@@ -103,6 +102,8 @@ OPENGL_GAL::OPENGL_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener, ...@@ -103,6 +102,8 @@ OPENGL_GAL::OPENGL_GAL( wxWindow* aParent, wxEvtHandler* aMouseListener,
} }
gluTessProperty( tesselator, GLU_TESS_WINDING_RULE, GLU_TESS_WINDING_POSITIVE ); gluTessProperty( tesselator, GLU_TESS_WINDING_RULE, GLU_TESS_WINDING_POSITIVE );
currentManager = &nonCachedManager;
} }
...@@ -250,6 +251,8 @@ void OPENGL_GAL::DrawLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoin ...@@ -250,6 +251,8 @@ void OPENGL_GAL::DrawLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoin
const VECTOR2D startEndVector = aEndPoint - aStartPoint; const VECTOR2D startEndVector = aEndPoint - aStartPoint;
double lineAngle = startEndVector.Angle(); double lineAngle = startEndVector.Angle();
currentManager->Color( strokeColor.r, strokeColor.g, strokeColor.b, strokeColor.a );
drawLineQuad( aStartPoint, aEndPoint ); drawLineQuad( aStartPoint, aEndPoint );
// Line caps // Line caps
...@@ -467,10 +470,15 @@ void OPENGL_GAL::DrawRectangle( const VECTOR2D& aStartPoint, const VECTOR2D& aEn ...@@ -467,10 +470,15 @@ void OPENGL_GAL::DrawRectangle( const VECTOR2D& aStartPoint, const VECTOR2D& aEn
void OPENGL_GAL::DrawPolyline( std::deque<VECTOR2D>& aPointList ) void OPENGL_GAL::DrawPolyline( std::deque<VECTOR2D>& aPointList )
{ {
if( aPointList.empty() )
return;
currentManager->Color( strokeColor.r, strokeColor.g, strokeColor.b, strokeColor.a );
std::deque<VECTOR2D>::const_iterator it = aPointList.begin(); std::deque<VECTOR2D>::const_iterator it = aPointList.begin();
// Start from the second point // Start from the second point
for( it++; it != aPointList.end(); it++ ) for( ++it; it != aPointList.end(); ++it )
{ {
const VECTOR2D startEndVector = ( *it - *( it - 1 ) ); const VECTOR2D startEndVector = ( *it - *( it - 1 ) );
double lineAngle = startEndVector.Angle(); double lineAngle = startEndVector.Angle();
...@@ -554,7 +562,7 @@ void OPENGL_GAL::DrawCurve( const VECTOR2D& aStartPoint, const VECTOR2D& aContro ...@@ -554,7 +562,7 @@ void OPENGL_GAL::DrawCurve( const VECTOR2D& aStartPoint, const VECTOR2D& aContro
void OPENGL_GAL::ResizeScreen( int aWidth, int aHeight ) void OPENGL_GAL::ResizeScreen( int aWidth, int aHeight )
{ {
screenSize = VECTOR2D( aWidth, aHeight ); screenSize = VECTOR2I( aWidth, aHeight );
// Resize framebuffers // Resize framebuffers
compositor.Resize( aWidth, aHeight ); compositor.Resize( aWidth, aHeight );
...@@ -589,16 +597,7 @@ void OPENGL_GAL::ClearScreen() ...@@ -589,16 +597,7 @@ void OPENGL_GAL::ClearScreen()
} }
void OPENGL_GAL::SetStrokeColor( const COLOR4D& aColor ) void OPENGL_GAL::Transform( const MATRIX3x3D& aTransformation )
{
strokeColor = aColor;
// This is the default drawing color
currentManager->Color( aColor.r, aColor.g, aColor.b, aColor.a );
}
void OPENGL_GAL::Transform( MATRIX3x3D aTransformation )
{ {
GLdouble matrixData[16] = { 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1 }; GLdouble matrixData[16] = { 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1 };
...@@ -767,8 +766,8 @@ void OPENGL_GAL::DrawCursor( const VECTOR2D& aCursorPosition ) ...@@ -767,8 +766,8 @@ void OPENGL_GAL::DrawCursor( const VECTOR2D& aCursorPosition )
{ {
// Now we should only store the position of the mouse cursor // Now we should only store the position of the mouse cursor
// The real drawing routines are in blitCursor() // The real drawing routines are in blitCursor()
cursorPosition = VECTOR2D( aCursorPosition.x, VECTOR2D screenCursor = worldScreenMatrix * aCursorPosition;
screenSize.y - aCursorPosition.y ); // invert Y axis cursorPosition = screenWorldMatrix * VECTOR2D( screenCursor.x, screenSize.y - screenCursor.y );
} }
...@@ -778,13 +777,9 @@ void OPENGL_GAL::drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEnd ...@@ -778,13 +777,9 @@ void OPENGL_GAL::drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEnd
// We do not need a very precise comparison here (the lineWidth is set by GAL::DrawGrid()) // We do not need a very precise comparison here (the lineWidth is set by GAL::DrawGrid())
if( fabs( lineWidth - 2.0 * gridLineWidth / worldScale ) < 0.1 ) if( fabs( lineWidth - 2.0 * gridLineWidth / worldScale ) < 0.1 )
{
glLineWidth( 1.0 ); glLineWidth( 1.0 );
}
else else
{
glLineWidth( 2.0 ); glLineWidth( 2.0 );
}
glColor4d( gridColor.r, gridColor.g, gridColor.b, gridColor.a ); glColor4d( gridColor.r, gridColor.g, gridColor.b, gridColor.a );
...@@ -798,8 +793,23 @@ void OPENGL_GAL::drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEnd ...@@ -798,8 +793,23 @@ void OPENGL_GAL::drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEnd
} }
inline void OPENGL_GAL::drawLineQuad( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint ) void OPENGL_GAL::drawLineQuad( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint )
{ {
/* Helper drawing: ____--- v3 ^
* ____---- ... \ \
* ____---- ... \ end \
* v1 ____---- ... ____---- \ width
* ---- ...___---- \ \
* \ ___...-- \ v
* \ ____----... ____---- v2
* ---- ... ____----
* start \ ... ____----
* \... ____----
* ----
* v0
* dots mark triangles' hypotenuses
*/
VECTOR2D startEndVector = aEndPoint - aStartPoint; VECTOR2D startEndVector = aEndPoint - aStartPoint;
double lineLength = startEndVector.EuclideanNorm(); double lineLength = startEndVector.EuclideanNorm();
double scale = 0.5 * lineWidth / lineLength; double scale = 0.5 * lineWidth / lineLength;
...@@ -857,8 +867,8 @@ void OPENGL_GAL::drawFilledSemiCircle( const VECTOR2D& aCenterPoint, double aRad ...@@ -857,8 +867,8 @@ void OPENGL_GAL::drawFilledSemiCircle( const VECTOR2D& aCenterPoint, double aRad
/* Draw a triangle that contains the semicircle, then shade it to leave only /* Draw a triangle that contains the semicircle, then shade it to leave only
* the semicircle. Parameters given to setShader are indices of the triangle's vertices * the semicircle. Parameters given to setShader are indices of the triangle's vertices
* (if you want to understand more, check the vertex shader source [shader.vert]). * (if you want to understand more, check the vertex shader source [shader.vert]).
* Shader uses this coordinates to determine if fragments are inside the semicircle or not. * Shader uses these coordinates to determine if fragments are inside the semicircle or not.
* v2 * v2
* /\ * /\
* /__\ * /__\
...@@ -888,9 +898,9 @@ void OPENGL_GAL::drawStrokedSemiCircle( const VECTOR2D& aCenterPoint, double aRa ...@@ -888,9 +898,9 @@ void OPENGL_GAL::drawStrokedSemiCircle( const VECTOR2D& aCenterPoint, double aRa
/* Draw a triangle that contains the semicircle, then shade it to leave only /* Draw a triangle that contains the semicircle, then shade it to leave only
* the semicircle. Parameters given to setShader are indices of the triangle's vertices * the semicircle. Parameters given to setShader are indices of the triangle's vertices
* (if you want to understand more, check the vertex shader source [shader.vert]), the * (if you want to understand more, check the vertex shader source [shader.vert]), the
* radius and the line width. Shader uses this coordinates to determine if fragments are * radius and the line width. Shader uses these coordinates to determine if fragments are
* inside the semicircle or not. * inside the semicircle or not.
* v2 * v2
* /\ * /\
* /__\ * /__\
...@@ -968,12 +978,6 @@ void OPENGL_GAL::initGlew() ...@@ -968,12 +978,6 @@ void OPENGL_GAL::initGlew()
} }
void OPENGL_GAL::initCursor( int aCursorSize )
{
cursorSize = aCursorSize;
}
void OPENGL_GAL::blitCursor() void OPENGL_GAL::blitCursor()
{ {
if( !isCursorEnabled ) if( !isCursorEnabled )
...@@ -981,11 +985,9 @@ void OPENGL_GAL::blitCursor() ...@@ -981,11 +985,9 @@ void OPENGL_GAL::blitCursor()
compositor.SetBuffer( OPENGL_COMPOSITOR::DIRECT_RENDERING ); compositor.SetBuffer( OPENGL_COMPOSITOR::DIRECT_RENDERING );
VECTOR2D cursorBegin = ToWorld( cursorPosition - VECTOR2D cursorBegin = cursorPosition - cursorSize / ( 2 * worldScale );
VECTOR2D( cursorSize / 2, cursorSize / 2 ) ); VECTOR2D cursorEnd = cursorPosition + cursorSize / ( 2 * worldScale );
VECTOR2D cursorEnd = ToWorld( cursorPosition + VECTOR2D cursorCenter = ( cursorBegin + cursorEnd ) / 2;
VECTOR2D( cursorSize / 2, cursorSize / 2 ) );
VECTOR2D cursorCenter = ( cursorBegin + cursorEnd ) / 2.0;
glDisable( GL_TEXTURE_2D ); glDisable( GL_TEXTURE_2D );
glLineWidth( 1.0 ); glLineWidth( 1.0 );
......
This diff is collapsed.
...@@ -59,7 +59,7 @@ RENDER_SETTINGS::~RENDER_SETTINGS() ...@@ -59,7 +59,7 @@ RENDER_SETTINGS::~RENDER_SETTINGS()
void RENDER_SETTINGS::update() void RENDER_SETTINGS::update()
{ {
m_hiContrastColor = COLOR4D( m_hiContrastFactor, m_hiContrastFactor, m_highlightFactor, m_hiContrastColor = COLOR4D( m_hiContrastFactor, m_hiContrastFactor, m_hiContrastFactor,
m_layerOpacity ); m_layerOpacity );
} }
......
...@@ -26,6 +26,7 @@ ...@@ -26,6 +26,7 @@
#include <tool/tool_manager.h> #include <tool/tool_manager.h>
#include <tool/tool_event.h> #include <tool/tool_event.h>
#include <tool/tool_action.h> #include <tool/tool_action.h>
#include <boost/foreach.hpp>
#include <cassert> #include <cassert>
ACTION_MANAGER::ACTION_MANAGER( TOOL_MANAGER* aToolManager ) : ACTION_MANAGER::ACTION_MANAGER( TOOL_MANAGER* aToolManager ) :
...@@ -43,7 +44,12 @@ ACTION_MANAGER::~ACTION_MANAGER() ...@@ -43,7 +44,12 @@ ACTION_MANAGER::~ACTION_MANAGER()
void ACTION_MANAGER::RegisterAction( TOOL_ACTION* aAction ) void ACTION_MANAGER::RegisterAction( TOOL_ACTION* aAction )
{ {
assert( aAction->GetId() == -1 ); // Check if the TOOL_ACTION was not registered before // Check if the TOOL_ACTION was not registered before
assert( aAction->GetId() == -1 );
// TOOL_ACTIONs are supposed to be named [appName.]toolName.actionName (with dots between)
// action name without specifying at least toolName is not valid
assert( aAction->GetName().find( '.', 0 ) != std::string::npos );
assert( m_actionNameIndex.find( aAction->m_name ) == m_actionNameIndex.end() ); assert( m_actionNameIndex.find( aAction->m_name ) == m_actionNameIndex.end() );
assert( m_actionIdIndex.find( aAction->m_id ) == m_actionIdIndex.end() ); assert( m_actionIdIndex.find( aAction->m_id ) == m_actionIdIndex.end() );
...@@ -53,15 +59,7 @@ void ACTION_MANAGER::RegisterAction( TOOL_ACTION* aAction ) ...@@ -53,15 +59,7 @@ void ACTION_MANAGER::RegisterAction( TOOL_ACTION* aAction )
m_actionIdIndex[aAction->m_id] = aAction; m_actionIdIndex[aAction->m_id] = aAction;
if( aAction->HasHotKey() ) if( aAction->HasHotKey() )
{ m_actionHotKeys[aAction->m_currentHotKey].push_back( aAction );
// Duplication of hot keys leads to unexpected behaviour
// The right way to change a hotkey is to use ACTION_MANAGER::ClearHotKey() first
assert( m_actionHotKeys.find( aAction->m_currentHotKey ) == m_actionHotKeys.end() );
m_actionHotKeys[aAction->m_currentHotKey] = aAction;
}
aAction->setActionMgr( this );
} }
...@@ -71,11 +69,18 @@ void ACTION_MANAGER::UnregisterAction( TOOL_ACTION* aAction ) ...@@ -71,11 +69,18 @@ void ACTION_MANAGER::UnregisterAction( TOOL_ACTION* aAction )
m_actionIdIndex.erase( aAction->m_id ); m_actionIdIndex.erase( aAction->m_id );
// Indicate that the ACTION_MANAGER no longer care about the object // Indicate that the ACTION_MANAGER no longer care about the object
aAction->setActionMgr( NULL );
aAction->setId( -1 ); aAction->setId( -1 );
if( aAction->HasHotKey() ) if( aAction->HasHotKey() )
m_actionHotKeys.erase( aAction->m_currentHotKey ); {
std::list<TOOL_ACTION*>& actions = m_actionHotKeys[aAction->m_currentHotKey];
std::list<TOOL_ACTION*>::iterator action = std::find( actions.begin(), actions.end(), aAction );
if( action != actions.end() )
actions.erase( action );
else
assert( false );
}
} }
...@@ -94,34 +99,80 @@ bool ACTION_MANAGER::RunAction( const std::string& aActionName ) const ...@@ -94,34 +99,80 @@ bool ACTION_MANAGER::RunAction( const std::string& aActionName ) const
if( it == m_actionNameIndex.end() ) if( it == m_actionNameIndex.end() )
return false; // no action with given name found return false; // no action with given name found
runAction( it->second ); RunAction( it->second );
return true; return true;
} }
void ACTION_MANAGER::RunAction( const TOOL_ACTION* aAction ) const
{
TOOL_EVENT event = aAction->MakeEvent();
m_toolMgr->ProcessEvent( event );
}
bool ACTION_MANAGER::RunHotKey( int aHotKey ) const bool ACTION_MANAGER::RunHotKey( int aHotKey ) const
{ {
std::map<int, TOOL_ACTION*>::const_iterator it = m_actionHotKeys.find( aHotKey ); int key = std::toupper( aHotKey & ~MD_MODIFIER_MASK );
int mod = aHotKey & MD_MODIFIER_MASK;
HOTKEY_LIST::const_iterator it = m_actionHotKeys.find( key | mod );
// If no luck, try without modifier, to handle keys that require a modifier
// e.g. to get ? you need to press Shift+/ without US keyboard layout
// Hardcoding ? as Shift+/ is a bad idea, as on another layout you may need to press a
// different combination
if( it == m_actionHotKeys.end() ) if( it == m_actionHotKeys.end() )
return false; // no appropriate action found for the hotkey {
it = m_actionHotKeys.find( key );
runAction( it->second ); if( it == m_actionHotKeys.end() )
return false; // no appropriate action found for the hotkey
}
return true; const std::list<TOOL_ACTION*>& actions = it->second;
}
// Choose the action that has the highest priority on the active tools stack
// If there is none, run the global action associated with the hot key
int highestPriority = -1, priority = -1;
const TOOL_ACTION* context = NULL; // pointer to context action of the highest priority tool
const TOOL_ACTION* global = NULL; // pointer to global action, if there is no context action
void ACTION_MANAGER::ClearHotKey( int aHotKey ) BOOST_FOREACH( const TOOL_ACTION* action, actions )
{ {
m_actionHotKeys.erase( aHotKey ); if( action->GetScope() == AS_GLOBAL )
} {
// Store the global action for the hot key in case there was no possible
// context actions to run
assert( global == NULL ); // there should be only one global action per hot key
global = action;
continue;
}
TOOL_BASE* tool = m_toolMgr->FindTool( action->GetToolName() );
if( tool )
{
priority = m_toolMgr->GetPriority( tool->GetId() );
if( priority >= 0 && priority > highestPriority )
{
highestPriority = priority;
context = action;
}
}
}
if( !global && !context ) // currently there is no valid action to run
return false;
void ACTION_MANAGER::runAction( const TOOL_ACTION* aAction ) const if( context )
{ RunAction( context );
TOOL_EVENT event = aAction->MakeEvent(); else if( global )
RunAction( global );
m_toolMgr->ProcessEvent( event ); return true;
} }
...@@ -27,18 +27,16 @@ ...@@ -27,18 +27,16 @@
#include <tool/tool_manager.h> #include <tool/tool_manager.h>
#include <tool/tool_dispatcher.h> #include <tool/tool_dispatcher.h>
#include <tools/common_actions.h>
#include <view/view.h> #include <view/view.h>
#include <view/wx_view_controls.h> #include <view/wx_view_controls.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <pcbnew_id.h> #include <pcbnew_id.h>
#include <boost/optional.hpp> #include <boost/optional.hpp>
#include <boost/foreach.hpp> #include <boost/foreach.hpp>
using boost::optional;
///> Stores information about a mouse button state ///> Stores information about a mouse button state
struct TOOL_DISPATCHER::BUTTON_STATE struct TOOL_DISPATCHER::BUTTON_STATE
{ {
...@@ -128,7 +126,7 @@ bool TOOL_DISPATCHER::handleMouseButton( wxEvent& aEvent, int aIndex, bool aMoti ...@@ -128,7 +126,7 @@ bool TOOL_DISPATCHER::handleMouseButton( wxEvent& aEvent, int aIndex, bool aMoti
{ {
BUTTON_STATE* st = m_buttons[aIndex]; BUTTON_STATE* st = m_buttons[aIndex];
wxEventType type = aEvent.GetEventType(); wxEventType type = aEvent.GetEventType();
optional<TOOL_EVENT> evt; boost::optional<TOOL_EVENT> evt;
bool isClick = false; bool isClick = false;
bool up = type == st->upEvent; bool up = type == st->upEvent;
...@@ -207,7 +205,7 @@ bool TOOL_DISPATCHER::handleMouseButton( wxEvent& aEvent, int aIndex, bool aMoti ...@@ -207,7 +205,7 @@ bool TOOL_DISPATCHER::handleMouseButton( wxEvent& aEvent, int aIndex, bool aMoti
void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent ) void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent )
{ {
bool motion = false, buttonEvents = false; bool motion = false, buttonEvents = false;
optional<TOOL_EVENT> evt; boost::optional<TOOL_EVENT> evt;
int type = aEvent.GetEventType(); int type = aEvent.GetEventType();
...@@ -221,6 +219,9 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent ) ...@@ -221,6 +219,9 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent )
// but changes in world coordinates (e.g. autopanning) // but changes in world coordinates (e.g. autopanning)
type == KIGFX::WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE ) type == KIGFX::WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE )
{ {
wxMouseEvent* me = static_cast<wxMouseEvent*>( &aEvent );
int mods = decodeModifiers<wxMouseEvent>( me );
VECTOR2D screenPos = m_toolMgr->GetViewControls()->GetMousePosition(); VECTOR2D screenPos = m_toolMgr->GetViewControls()->GetMousePosition();
VECTOR2D pos = getView()->ToWorld( screenPos ); VECTOR2D pos = getView()->ToWorld( screenPos );
...@@ -228,6 +229,7 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent ) ...@@ -228,6 +229,7 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent )
{ {
motion = true; motion = true;
m_lastMousePos = pos; m_lastMousePos = pos;
m_editFrame->UpdateStatusBar();
} }
for( unsigned int i = 0; i < m_buttons.size(); i++ ) for( unsigned int i = 0; i < m_buttons.size(); i++ )
...@@ -235,29 +237,38 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent ) ...@@ -235,29 +237,38 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent )
if( !buttonEvents && motion ) if( !buttonEvents && motion )
{ {
evt = TOOL_EVENT( TC_MOUSE, TA_MOUSE_MOTION ); evt = TOOL_EVENT( TC_MOUSE, TA_MOUSE_MOTION, mods );
evt->SetMousePosition( pos ); evt->SetMousePosition( pos );
} }
} }
// Keyboard handling // Keyboard handling
else if( type == wxEVT_KEY_UP || type == wxEVT_KEY_DOWN ) else if( type == wxEVT_CHAR )
{ {
wxKeyEvent* ke = static_cast<wxKeyEvent*>( &aEvent ); wxKeyEvent* ke = static_cast<wxKeyEvent*>( &aEvent );
int key = ke->GetKeyCode(); int key = ke->GetKeyCode();
int mods = decodeModifiers<wxKeyEvent>( ke ); int mods = decodeModifiers<wxKeyEvent>( ke );
if( type == wxEVT_KEY_UP ) if( mods & MD_CTRL )
{ {
if( key == WXK_ESCAPE ) // ESC is the special key for cancelling tools #if !wxCHECK_VERSION( 2, 9, 0 )
evt = TOOL_EVENT( TC_COMMAND, TA_CANCEL_TOOL ); // I really look forward to the day when we will use only one version of wxWidgets..
else const int WXK_CONTROL_A = 1;
evt = TOOL_EVENT( TC_KEYBOARD, TA_KEY_UP, key | mods ); const int WXK_CONTROL_Z = 26;
#endif
// wxWidgets have a quirk related to Ctrl+letter hot keys handled by CHAR_EVT
// http://docs.wxwidgets.org/trunk/classwx_key_event.html:
// "char events for ASCII letters in this case carry codes corresponding to the ASCII
// value of Ctrl-Latter, i.e. 1 for Ctrl-A, 2 for Ctrl-B and so on until 26 for Ctrl-Z."
if( key >= WXK_CONTROL_A && key <= WXK_CONTROL_Z )
key += 'A' - 1;
} }
if( key == WXK_ESCAPE ) // ESC is the special key for cancelling tools
evt = TOOL_EVENT( TC_COMMAND, TA_CANCEL_TOOL );
else else
{ evt = TOOL_EVENT( TC_KEYBOARD, TA_KEY_PRESSED, key | mods );
evt = TOOL_EVENT( TC_KEYBOARD, TA_KEY_DOWN, key | mods );
}
} }
if( evt ) if( evt )
...@@ -268,21 +279,29 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent ) ...@@ -268,21 +279,29 @@ void TOOL_DISPATCHER::DispatchWxEvent( wxEvent& aEvent )
} }
void TOOL_DISPATCHER::DispatchWxCommand( const wxCommandEvent& aEvent ) void TOOL_DISPATCHER::DispatchWxCommand( wxCommandEvent& aEvent )
{ {
bool activateTool = false; boost::optional<TOOL_EVENT> evt;
std::string toolName;
// fixme: use TOOL_ACTIONs here
switch( aEvent.GetId() ) switch( aEvent.GetId() )
{ {
case ID_PNS_ROUTER_TOOL: case ID_ZOOM_IN: // toolbar button "Zoom In"
toolName = "pcbnew.InteractiveRouter"; evt = COMMON_ACTIONS::zoomInCenter.MakeEvent();
activateTool = true; break;
case ID_ZOOM_OUT: // toolbar button "Zoom In"
evt = COMMON_ACTIONS::zoomOutCenter.MakeEvent();
break;
case ID_ZOOM_PAGE: // toolbar button "Fit on Screen"
evt = COMMON_ACTIONS::zoomFitScreen.MakeEvent();
break;
default:
aEvent.Skip();
break; break;
} }
// do nothing if the legacy view is active if( evt )
if( activateTool && m_editFrame->IsGalCanvasActive() ) m_toolMgr->ProcessEvent( *evt );
m_toolMgr->InvokeTool( toolName );
} }
...@@ -81,8 +81,7 @@ const std::string TOOL_EVENT::Format() const ...@@ -81,8 +81,7 @@ const std::string TOOL_EVENT::Format() const
{ TA_MOUSE_DRAG, "drag" }, { TA_MOUSE_DRAG, "drag" },
{ TA_MOUSE_MOTION, "motion" }, { TA_MOUSE_MOTION, "motion" },
{ TA_MOUSE_WHEEL, "wheel" }, { TA_MOUSE_WHEEL, "wheel" },
{ TA_KEY_UP, "key-up" }, { TA_KEY_PRESSED, "key-pressed" },
{ TA_KEY_DOWN, "key-down" },
{ TA_VIEW_REFRESH, "view-refresh" }, { TA_VIEW_REFRESH, "view-refresh" },
{ TA_VIEW_ZOOM, "view-zoom" }, { TA_VIEW_ZOOM, "view-zoom" },
{ TA_VIEW_PAN, "view-pan" }, { TA_VIEW_PAN, "view-pan" },
......
...@@ -46,6 +46,12 @@ TOOL_INTERACTIVE::~TOOL_INTERACTIVE() ...@@ -46,6 +46,12 @@ TOOL_INTERACTIVE::~TOOL_INTERACTIVE()
} }
void TOOL_INTERACTIVE::Activate()
{
m_toolMgr->InvokeTool( m_toolId );
}
OPT_TOOL_EVENT TOOL_INTERACTIVE::Wait( const TOOL_EVENT_LIST& aEventList ) OPT_TOOL_EVENT TOOL_INTERACTIVE::Wait( const TOOL_EVENT_LIST& aEventList )
{ {
return m_toolMgr->ScheduleWait( this, aEventList ); return m_toolMgr->ScheduleWait( this, aEventList );
......
...@@ -44,7 +44,7 @@ ...@@ -44,7 +44,7 @@
#include <wxPcbStruct.h> #include <wxPcbStruct.h>
#include <confirm.h> #include <confirm.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
using boost::optional; using boost::optional;
...@@ -103,6 +103,14 @@ TOOL_MANAGER::TOOL_MANAGER() : ...@@ -103,6 +103,14 @@ TOOL_MANAGER::TOOL_MANAGER() :
TOOL_MANAGER::~TOOL_MANAGER() TOOL_MANAGER::~TOOL_MANAGER()
{
DeleteAll();
delete m_actionMgr;
}
void TOOL_MANAGER::DeleteAll()
{ {
std::map<TOOL_BASE*, TOOL_STATE*>::iterator it, it_end; std::map<TOOL_BASE*, TOOL_STATE*>::iterator it, it_end;
...@@ -113,7 +121,7 @@ TOOL_MANAGER::~TOOL_MANAGER() ...@@ -113,7 +121,7 @@ TOOL_MANAGER::~TOOL_MANAGER()
delete it->first; // delete the tool itself delete it->first; // delete the tool itself
} }
delete m_actionMgr; m_toolState.clear();
} }
...@@ -196,6 +204,12 @@ bool TOOL_MANAGER::RunAction( const std::string& aActionName ) ...@@ -196,6 +204,12 @@ bool TOOL_MANAGER::RunAction( const std::string& aActionName )
} }
void TOOL_MANAGER::RunAction( const TOOL_ACTION& aAction )
{
m_actionMgr->RunAction( &aAction );
}
bool TOOL_MANAGER::invokeTool( TOOL_BASE* aTool ) bool TOOL_MANAGER::invokeTool( TOOL_BASE* aTool )
{ {
wxASSERT( aTool != NULL ); wxASSERT( aTool != NULL );
...@@ -239,9 +253,15 @@ bool TOOL_MANAGER::runTool( TOOL_BASE* aTool ) ...@@ -239,9 +253,15 @@ bool TOOL_MANAGER::runTool( TOOL_BASE* aTool )
return false; return false;
} }
// If the tool is already active, do not invoke it again // If the tool is already active, bring it to the top of the active tools stack
if( isActive( aTool ) ) if( isActive( aTool ) )
{
m_activeTools.erase( std::find( m_activeTools.begin(), m_activeTools.end(),
aTool->GetId() ) );
m_activeTools.push_front( aTool->GetId() );
return false; return false;
}
aTool->Reset( TOOL_INTERACTIVE::RUN ); aTool->Reset( TOOL_INTERACTIVE::RUN );
...@@ -281,6 +301,25 @@ void TOOL_MANAGER::ResetTools( TOOL_BASE::RESET_REASON aReason ) ...@@ -281,6 +301,25 @@ void TOOL_MANAGER::ResetTools( TOOL_BASE::RESET_REASON aReason )
} }
int TOOL_MANAGER::GetPriority( int aToolId ) const
{
int priority = 0;
for( std::deque<int>::const_iterator it = m_activeTools.begin(),
itEnd = m_activeTools.end(); it != itEnd; ++it )
{
std::cout << FindTool( *it )->GetName() << std::endl;
if( *it == aToolId )
return priority;
++priority;
}
return -1;
}
void TOOL_MANAGER::ScheduleNextState( TOOL_BASE* aTool, TOOL_STATE_FUNC& aHandler, void TOOL_MANAGER::ScheduleNextState( TOOL_BASE* aTool, TOOL_STATE_FUNC& aHandler,
const TOOL_EVENT_LIST& aConditions ) const TOOL_EVENT_LIST& aConditions )
{ {
...@@ -378,7 +417,7 @@ void TOOL_MANAGER::dispatchInternal( TOOL_EVENT& aEvent ) ...@@ -378,7 +417,7 @@ void TOOL_MANAGER::dispatchInternal( TOOL_EVENT& aEvent )
bool TOOL_MANAGER::dispatchStandardEvents( TOOL_EVENT& aEvent ) bool TOOL_MANAGER::dispatchStandardEvents( TOOL_EVENT& aEvent )
{ {
if( aEvent.Action() == TA_KEY_UP ) if( aEvent.Action() == TA_KEY_PRESSED )
{ {
// Check if there is a hotkey associated // Check if there is a hotkey associated
if( m_actionMgr->RunHotKey( aEvent.Modifier() | aEvent.KeyCode() ) ) if( m_actionMgr->RunHotKey( aEvent.Modifier() | aEvent.KeyCode() ) )
......
This diff is collapsed.
...@@ -31,25 +31,12 @@ using namespace KIGFX; ...@@ -31,25 +31,12 @@ using namespace KIGFX;
void VIEW_ITEM::ViewSetVisible( bool aIsVisible ) void VIEW_ITEM::ViewSetVisible( bool aIsVisible )
{ {
bool update = false;
if( m_visible != aIsVisible )
update = true;
m_visible = aIsVisible;
// update only if the visibility has really changed // update only if the visibility has really changed
if( update ) if( m_visible != aIsVisible )
{
m_visible = aIsVisible;
ViewUpdate( APPEARANCE ); ViewUpdate( APPEARANCE );
} }
void VIEW_ITEM::ViewUpdate( int aUpdateFlags )
{
if( !m_view )
return;
m_view->InvalidateItem( this, aUpdateFlags );
} }
......
...@@ -35,9 +35,7 @@ using namespace KIGFX; ...@@ -35,9 +35,7 @@ using namespace KIGFX;
const wxEventType WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE = wxNewEventType(); const wxEventType WX_VIEW_CONTROLS::EVT_REFRESH_MOUSE = wxNewEventType();
WX_VIEW_CONTROLS::WX_VIEW_CONTROLS( VIEW* aView, wxWindow* aParentPanel ) : WX_VIEW_CONTROLS::WX_VIEW_CONTROLS( VIEW* aView, wxWindow* aParentPanel ) :
VIEW_CONTROLS( aView ), VIEW_CONTROLS( aView ), m_state( IDLE ), m_parentPanel( aParentPanel )
m_state( IDLE ),
m_parentPanel( aParentPanel )
{ {
m_parentPanel->Connect( wxEVT_MOTION, m_parentPanel->Connect( wxEVT_MOTION,
wxMouseEventHandler( WX_VIEW_CONTROLS::onMotion ), NULL, this ); wxMouseEventHandler( WX_VIEW_CONTROLS::onMotion ), NULL, this );
...@@ -68,13 +66,44 @@ void VIEW_CONTROLS::ShowCursor( bool aEnabled ) ...@@ -68,13 +66,44 @@ void VIEW_CONTROLS::ShowCursor( bool aEnabled )
} }
void WX_VIEW_CONTROLS::onMotion( wxMouseEvent& aEvent ) void VIEW_CONTROLS::setCenter( const VECTOR2D& aCenter )
{ {
m_mousePosition.x = aEvent.GetX(); if( !m_panBoundary.Contains( aCenter ) )
m_mousePosition.y = aEvent.GetY(); {
VECTOR2D newCenter( aCenter );
if( aCenter.x < m_panBoundary.GetLeft() )
newCenter.x = m_panBoundary.GetLeft();
else if( aCenter.x > m_panBoundary.GetRight() )
newCenter.x = m_panBoundary.GetRight();
if( aCenter.y < m_panBoundary.GetTop() )
newCenter.y = m_panBoundary.GetTop();
else if( aCenter.y > m_panBoundary.GetBottom() )
newCenter.y = m_panBoundary.GetBottom();
m_view->SetCenter( newCenter );
}
else
{
m_view->SetCenter( aCenter );
}
}
updateCursor();
void VIEW_CONTROLS::setScale( double aScale, const VECTOR2D& aAnchor )
{
if( aScale < m_minScale )
aScale = m_minScale;
else if( aScale > m_maxScale )
aScale = m_maxScale;
m_view->SetScale( aScale, aAnchor );
}
void WX_VIEW_CONTROLS::onMotion( wxMouseEvent& aEvent )
{
bool isAutoPanning = false; bool isAutoPanning = false;
if( m_autoPanEnabled ) if( m_autoPanEnabled )
...@@ -84,10 +113,10 @@ void WX_VIEW_CONTROLS::onMotion( wxMouseEvent& aEvent ) ...@@ -84,10 +113,10 @@ void WX_VIEW_CONTROLS::onMotion( wxMouseEvent& aEvent )
{ {
if( m_state == DRAG_PANNING ) if( m_state == DRAG_PANNING )
{ {
VECTOR2D d = m_dragStartPoint - m_mousePosition; VECTOR2D d = m_dragStartPoint - VECTOR2D( aEvent.GetX(), aEvent.GetY() );
VECTOR2D delta = m_view->ToWorld( d, false ); VECTOR2D delta = m_view->ToWorld( d, false );
m_view->SetCenter( m_lookStartPoint + delta ); setCenter( m_lookStartPoint + delta );
aEvent.StopPropagation(); aEvent.StopPropagation();
} }
else else
...@@ -117,7 +146,7 @@ void WX_VIEW_CONTROLS::onWheel( wxMouseEvent& aEvent ) ...@@ -117,7 +146,7 @@ void WX_VIEW_CONTROLS::onWheel( wxMouseEvent& aEvent )
VECTOR2D delta( aEvent.ControlDown() ? -scrollSpeed : 0.0, VECTOR2D delta( aEvent.ControlDown() ? -scrollSpeed : 0.0,
aEvent.ShiftDown() ? -scrollSpeed : 0.0 ); aEvent.ShiftDown() ? -scrollSpeed : 0.0 );
m_view->SetCenter( m_view->GetCenter() + delta ); setCenter( m_view->GetCenter() + delta );
} }
else else
{ {
...@@ -140,7 +169,7 @@ void WX_VIEW_CONTROLS::onWheel( wxMouseEvent& aEvent ) ...@@ -140,7 +169,7 @@ void WX_VIEW_CONTROLS::onWheel( wxMouseEvent& aEvent )
} }
VECTOR2D anchor = m_view->ToWorld( VECTOR2D( aEvent.GetX(), aEvent.GetY() ) ); VECTOR2D anchor = m_view->ToWorld( VECTOR2D( aEvent.GetX(), aEvent.GetY() ) );
m_view->SetScale( m_view->GetScale() * zoomScale, anchor ); setScale( m_view->GetScale() * zoomScale, anchor );
} }
aEvent.Skip(); aEvent.Skip();
...@@ -197,9 +226,7 @@ void WX_VIEW_CONTROLS::onTimer( wxTimerEvent& aEvent ) ...@@ -197,9 +226,7 @@ void WX_VIEW_CONTROLS::onTimer( wxTimerEvent& aEvent )
dir = dir.Resize( borderSize ); dir = dir.Resize( borderSize );
dir = m_view->ToWorld( dir, false ); dir = m_view->ToWorld( dir, false );
m_view->SetCenter( m_view->GetCenter() + dir * m_autoPanSpeed ); setCenter( m_view->GetCenter() + dir * m_autoPanSpeed );
updateCursor();
// Notify tools that the cursor position has changed in the world coordinates // Notify tools that the cursor position has changed in the world coordinates
wxMouseEvent moveEvent( EVT_REFRESH_MOUSE ); wxMouseEvent moveEvent( EVT_REFRESH_MOUSE );
...@@ -238,7 +265,7 @@ void WX_VIEW_CONTROLS::SetGrabMouse( bool aEnabled ) ...@@ -238,7 +265,7 @@ void WX_VIEW_CONTROLS::SetGrabMouse( bool aEnabled )
} }
const VECTOR2D WX_VIEW_CONTROLS::GetMousePosition() const VECTOR2D WX_VIEW_CONTROLS::GetMousePosition() const
{ {
wxPoint msp = wxGetMousePosition(); wxPoint msp = wxGetMousePosition();
wxPoint winp = m_parentPanel->GetScreenPosition(); wxPoint winp = m_parentPanel->GetScreenPosition();
...@@ -247,6 +274,22 @@ const VECTOR2D WX_VIEW_CONTROLS::GetMousePosition() const ...@@ -247,6 +274,22 @@ const VECTOR2D WX_VIEW_CONTROLS::GetMousePosition() const
} }
VECTOR2D WX_VIEW_CONTROLS::GetCursorPosition() const
{
if( m_forceCursorPosition )
return m_forcedPosition;
else
{
VECTOR2D mousePosition = GetMousePosition();
if( m_snappingEnabled )
return m_view->GetGAL()->GetGridPoint( m_view->ToWorld( mousePosition ) );
else
return m_view->ToWorld( mousePosition );
}
}
bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent ) bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent )
{ {
VECTOR2D p( aEvent.GetX(), aEvent.GetY() ); VECTOR2D p( aEvent.GetX(), aEvent.GetY() );
...@@ -257,17 +300,19 @@ bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent ) ...@@ -257,17 +300,19 @@ bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent )
double borderEndX = m_view->GetScreenPixelSize().x - borderStart; double borderEndX = m_view->GetScreenPixelSize().x - borderStart;
double borderEndY = m_view->GetScreenPixelSize().y - borderStart; double borderEndY = m_view->GetScreenPixelSize().y - borderStart;
m_panDirection = VECTOR2D();
if( p.x < borderStart ) if( p.x < borderStart )
m_panDirection.x = -( borderStart - p.x ); m_panDirection.x = -( borderStart - p.x );
else if( p.x > borderEndX ) else if( p.x > borderEndX )
m_panDirection.x = ( p.x - borderEndX ); m_panDirection.x = ( p.x - borderEndX );
else
m_panDirection.x = 0;
if( p.y < borderStart ) if( p.y < borderStart )
m_panDirection.y = -( borderStart - p.y ); m_panDirection.y = -( borderStart - p.y );
else if( p.y > borderEndY ) else if( p.y > borderEndY )
m_panDirection.y = ( p.y - borderEndY ); m_panDirection.y = ( p.y - borderEndY );
else
m_panDirection.y = 0;
bool borderHit = ( m_panDirection.x != 0 || m_panDirection.y != 0 ); bool borderHit = ( m_panDirection.x != 0 || m_panDirection.y != 0 );
...@@ -304,14 +349,3 @@ bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent ) ...@@ -304,14 +349,3 @@ bool WX_VIEW_CONTROLS::handleAutoPanning( const wxMouseEvent& aEvent )
wxASSERT_MSG( false, wxT( "This line should never be reached" ) ); wxASSERT_MSG( false, wxT( "This line should never be reached" ) );
return false; // Should not be reached, just avoid the compiler warnings.. return false; // Should not be reached, just avoid the compiler warnings..
} }
void WX_VIEW_CONTROLS::updateCursor()
{
if( m_forceCursorPosition )
m_cursorPosition = m_view->ToScreen( m_forcedPosition );
else if( m_snappingEnabled )
m_cursorPosition = m_view->GetGAL()->GetGridPoint( m_mousePosition );
else
m_cursorPosition = m_mousePosition;
}
...@@ -189,7 +189,7 @@ void WORKSHEET_VIEWITEM::draw( const WS_DRAW_ITEM_TEXT* aItem, GAL* aGal ) const ...@@ -189,7 +189,7 @@ void WORKSHEET_VIEWITEM::draw( const WS_DRAW_ITEM_TEXT* aItem, GAL* aGal ) const
aGal->SetStrokeColor( COLOR4D( aItem->GetColor() ) ); aGal->SetStrokeColor( COLOR4D( aItem->GetColor() ) );
aGal->SetLineWidth( aItem->GetThickness() ); aGal->SetLineWidth( aItem->GetThickness() );
aGal->SetTextAttributes( aItem ); aGal->SetTextAttributes( aItem );
aGal->StrokeText( std::wstring( aItem->GetText().wc_str() ), position, 0.0 ); aGal->StrokeText( aItem->GetText(), position, 0.0 );
} }
......
...@@ -33,7 +33,7 @@ ...@@ -33,7 +33,7 @@
#include <fctsys.h> #include <fctsys.h>
#include <id.h> #include <id.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <gal/graphics_abstraction_layer.h> #include <gal/graphics_abstraction_layer.h>
#include <view/view.h> #include <view/view.h>
#include <class_base_screen.h> #include <class_base_screen.h>
...@@ -194,21 +194,19 @@ void EDA_DRAW_FRAME::OnZoom( wxCommandEvent& event ) ...@@ -194,21 +194,19 @@ void EDA_DRAW_FRAME::OnZoom( wxCommandEvent& event )
RedrawScreen( center, true ); RedrawScreen( center, true );
} }
if( IsGalCanvasActive() ) UpdateStatusBar();
{ }
// Apply computed view settings to GAL
KIGFX::VIEW* view = GetGalCanvas()->GetView();
KIGFX::GAL* gal = GetGalCanvas()->GetGAL();
double zoomFactor = gal->GetWorldScale() / gal->GetZoomFactor();
double zoom = 1.0 / ( zoomFactor * GetZoom() );
view->SetScale( zoom ); void EDA_DRAW_FRAME::SetNextZoom()
view->SetCenter( VECTOR2D( center ) ); {
GetGalCanvas()->Refresh(); GetScreen()->SetNextZoom();
} }
UpdateStatusBar();
void EDA_DRAW_FRAME::SetPrevZoom()
{
GetScreen()->SetPreviousZoom();
} }
......
...@@ -31,7 +31,7 @@ ...@@ -31,7 +31,7 @@
#include <pgm_base.h> #include <pgm_base.h>
#include <common.h> #include <common.h>
#include <class_drawpanel.h> #include <class_drawpanel.h>
#include <class_drawpanel_gal.h> #include <class_draw_panel_gal.h>
#include <confirm.h> #include <confirm.h>
#include <macros.h> #include <macros.h>
#include <bitmaps.h> #include <bitmaps.h>
......
...@@ -271,9 +271,7 @@ void SCH_EDIT_FRAME::Process_Config( wxCommandEvent& event ) ...@@ -271,9 +271,7 @@ void SCH_EDIT_FRAME::Process_Config( wxCommandEvent& event )
void SCH_EDIT_FRAME::OnSetOptions( wxCommandEvent& event ) void SCH_EDIT_FRAME::OnSetOptions( wxCommandEvent& event )
{ {
wxArrayString units; wxArrayString units;
GRIDS grid_list; GRIDS grid_list = GetScreen()->GetGrids();
GetScreen()->GetGrids( grid_list );
DIALOG_EESCHEMA_OPTIONS dlg( this ); DIALOG_EESCHEMA_OPTIONS dlg( this );
......
...@@ -65,7 +65,7 @@ public: ...@@ -65,7 +65,7 @@ public:
}; };
typedef std::vector< GRID_TYPE > GRIDS; typedef std::vector<GRID_TYPE> GRIDS;
/** /**
...@@ -445,11 +445,12 @@ public: ...@@ -445,11 +445,12 @@ public:
/** /**
* Function GetGrids(). * Function GetGrids().
* Copy the grid list to \a aList. * Returns the current list of grids.
*
* @param aList - List to copy to.
*/ */
void GetGrids( GRIDS& aList ); const GRIDS& GetGrids() const
{
return m_grids;
}
/** /**
* Function GetClass * Function GetClass
......
...@@ -33,8 +33,6 @@ ...@@ -33,8 +33,6 @@
#include <base_struct.h> #include <base_struct.h>
#include <gr_basic.h> #include <gr_basic.h>
#include <boost/ptr_container/ptr_vector.hpp>
#include <gr_basic.h>
#include <layers_id_colors_and_visibility.h> #include <layers_id_colors_and_visibility.h>
/// Abbrevation for fomatting internal units to a string. /// Abbrevation for fomatting internal units to a string.
......
...@@ -23,7 +23,7 @@ ...@@ -23,7 +23,7 @@
*/ */
/** /**
* @file class_drawpanel_gal.h: * @file class_draw_panel_gal.h:
* @brief EDA_DRAW_PANEL_GAL class definition. * @brief EDA_DRAW_PANEL_GAL class definition.
*/ */
......
...@@ -13,7 +13,6 @@ class MARKER_BASE ...@@ -13,7 +13,6 @@ class MARKER_BASE
public: public:
wxPoint m_Pos; ///< position of the marker wxPoint m_Pos; ///< position of the marker
protected: protected:
std::vector <wxPoint> m_Corners; ///< Corner list for shape definition (a polygon)
int m_MarkerType; ///< Can be used as a flag int m_MarkerType; ///< Can be used as a flag
EDA_COLOR_T m_Color; ///< color EDA_COLOR_T m_Color; ///< color
EDA_RECT m_ShapeBoundingBox; ///< Bounding box of the graphic symbol, relative EDA_RECT m_ShapeBoundingBox; ///< Bounding box of the graphic symbol, relative
......
...@@ -353,6 +353,18 @@ public: ...@@ -353,6 +353,18 @@ public:
*/ */
wxPoint GetGridPosition( const wxPoint& aPosition ) const; wxPoint GetGridPosition( const wxPoint& aPosition ) const;
/**
* Function SetNextGrid()
* changes the grid size settings to the next one available.
*/
virtual void SetNextGrid();
/**
* Function SetPrevGrid()
* changes the grid size settings to the previous one available.
*/
virtual void SetPrevGrid();
/** /**
* Command event handler for selecting grid sizes. * Command event handler for selecting grid sizes.
* *
...@@ -410,6 +422,18 @@ public: ...@@ -410,6 +422,18 @@ public:
virtual void OnZoom( wxCommandEvent& event ); virtual void OnZoom( wxCommandEvent& event );
/**
* Function SetNextZoom()
* changes the zoom to the next one available.
*/
void SetNextZoom();
/**
* Function SetPrevZoom()
* changes the zoom to the previous one available.
*/
void SetPrevZoom();
/** /**
* Function RedrawScreen * Function RedrawScreen
* redraws the entire screen area by updating the scroll bars and mouse pointer in * redraws the entire screen area by updating the scroll bars and mouse pointer in
......
...@@ -164,7 +164,7 @@ public: ...@@ -164,7 +164,7 @@ public:
// -------------- // --------------
/// @copydoc GAL::Transform() /// @copydoc GAL::Transform()
virtual void Transform( MATRIX3x3D aTransformation ); virtual void Transform( const MATRIX3x3D& aTransformation );
/// @copydoc GAL::Rotate() /// @copydoc GAL::Rotate()
virtual void Rotate( double aAngle ); virtual void Rotate( double aAngle );
...@@ -283,8 +283,6 @@ private: ...@@ -283,8 +283,6 @@ private:
wxPoint savedCursorPosition; ///< The last cursor position wxPoint savedCursorPosition; ///< The last cursor position
wxBitmap* cursorPixels; ///< Cursor pixels wxBitmap* cursorPixels; ///< Cursor pixels
wxBitmap* cursorPixelsSaved; ///< Saved cursor pixels wxBitmap* cursorPixelsSaved; ///< Saved cursor pixels
int cursorSize; ///< Cursor size
VECTOR2D cursorPosition; ///< Current cursor position
/// Maximum number of arguments for one command /// Maximum number of arguments for one command
static const int MAX_CAIRO_ARGUMENTS = 6; static const int MAX_CAIRO_ARGUMENTS = 6;
...@@ -354,8 +352,10 @@ private: ...@@ -354,8 +352,10 @@ private:
*/ */
void skipMouseEvent( wxMouseEvent& aEvent ); void skipMouseEvent( wxMouseEvent& aEvent );
/// @copydoc GAL::initCursor() /**
virtual void initCursor( int aCursorSize ); * @brief Prepares cursor bitmap.
*/
virtual void initCursor();
/** /**
* @brief Blits cursor into the current screen. * @brief Blits cursor into the current screen.
...@@ -386,6 +386,9 @@ private: ...@@ -386,6 +386,9 @@ private:
/// Format used to store pixels /// Format used to store pixels
static const cairo_format_t GAL_FORMAT = CAIRO_FORMAT_RGB24; static const cairo_format_t GAL_FORMAT = CAIRO_FORMAT_RGB24;
///> Opacity of a single layer
static const float LAYER_ALPHA = 0.8;
}; };
} // namespace KIGFX } // namespace KIGFX
......
...@@ -31,8 +31,6 @@ ...@@ -31,8 +31,6 @@
#include <stack> #include <stack>
#include <limits> #include <limits>
#include <wx/event.h>
#include <math/matrix3x3.h> #include <math/matrix3x3.h>
#include <gal/color4d.h> #include <gal/color4d.h>
...@@ -162,7 +160,7 @@ public: ...@@ -162,7 +160,7 @@ public:
virtual bool Show( bool aShow ) = 0; virtual bool Show( bool aShow ) = 0;
/// @brief Returns GAL canvas size in pixels /// @brief Returns GAL canvas size in pixels
VECTOR2D GetScreenPixelSize() const const VECTOR2I& GetScreenPixelSize() const
{ {
return screenSize; return screenSize;
} }
...@@ -222,7 +220,7 @@ public: ...@@ -222,7 +220,7 @@ public:
* *
* @return the color for stroking the outline. * @return the color for stroking the outline.
*/ */
inline COLOR4D GetStrokeColor() inline const COLOR4D& GetStrokeColor() const
{ {
return strokeColor; return strokeColor;
} }
...@@ -252,7 +250,7 @@ public: ...@@ -252,7 +250,7 @@ public:
* *
* @return the actual line width. * @return the actual line width.
*/ */
inline double GetLineWidth() inline double GetLineWidth() const
{ {
return lineWidth; return lineWidth;
} }
...@@ -335,7 +333,7 @@ public: ...@@ -335,7 +333,7 @@ public:
* *
* @param aTransformation is the ransformation matrix. * @param aTransformation is the ransformation matrix.
*/ */
virtual void Transform( MATRIX3x3D aTransformation ) = 0; virtual void Transform( const MATRIX3x3D& aTransformation ) = 0;
/** /**
* @brief Rotate the context. * @brief Rotate the context.
...@@ -428,11 +426,21 @@ public: ...@@ -428,11 +426,21 @@ public:
* *
* @return the transformation matrix. * @return the transformation matrix.
*/ */
MATRIX3x3D GetWorldScreenMatrix() const MATRIX3x3D& GetWorldScreenMatrix() const
{ {
return worldScreenMatrix; return worldScreenMatrix;
} }
/**
* @brief Get the screen <-> world transformation matrix.
*
* @return the transformation matrix.
*/
const MATRIX3x3D& GetScreenWorldMatrix() const
{
return screenWorldMatrix;
}
/** /**
* @brief Set the world <-> screen transformation matrix. * @brief Set the world <-> screen transformation matrix.
* *
...@@ -487,7 +495,7 @@ public: ...@@ -487,7 +495,7 @@ public:
* *
* @return the look at point. * @return the look at point.
*/ */
inline VECTOR2D GetLookAtPoint() inline const VECTOR2D& GetLookAtPoint() const
{ {
return lookAtPoint; return lookAtPoint;
} }
...@@ -507,7 +515,7 @@ public: ...@@ -507,7 +515,7 @@ public:
* *
* @return the zoom factor. * @return the zoom factor.
*/ */
inline double GetZoomFactor() inline double GetZoomFactor() const
{ {
return zoomFactor; return zoomFactor;
} }
...@@ -528,7 +536,7 @@ public: ...@@ -528,7 +536,7 @@ public:
/** /**
* @brief Returns the minimum depth in the currently used range (the top). * @brief Returns the minimum depth in the currently used range (the top).
*/ */
inline double GetMinDepth() inline double GetMinDepth() const
{ {
return depthRange.x; return depthRange.x;
} }
...@@ -536,7 +544,7 @@ public: ...@@ -536,7 +544,7 @@ public:
/** /**
* @brief Returns the maximum depth in the currently used range (the bottom). * @brief Returns the maximum depth in the currently used range (the bottom).
*/ */
inline double GetMaxDepth() inline double GetMaxDepth() const
{ {
return depthRange.y; return depthRange.y;
} }
...@@ -546,7 +554,7 @@ public: ...@@ -546,7 +554,7 @@ public:
* *
* @return the actual world scale factor. * @return the actual world scale factor.
*/ */
inline double GetWorldScale() inline double GetWorldScale() const
{ {
return worldScale; return worldScale;
} }
...@@ -694,7 +702,7 @@ public: ...@@ -694,7 +702,7 @@ public:
* *
* @return the grid line width * @return the grid line width
*/ */
inline double GetGridLineWidth() inline double GetGridLineWidth() const
{ {
return gridLineWidth; return gridLineWidth;
} }
...@@ -709,19 +717,17 @@ public: ...@@ -709,19 +717,17 @@ public:
gridLineWidth = aGridLineWidth; gridLineWidth = aGridLineWidth;
} }
/// @brief Draw the grid ///> @brief Draw the grid
void DrawGrid(); void DrawGrid();
/** /**
* Function GetGridPoint() * Function GetGridPoint()
* For a given point it returns the nearest point belonging to the grid. * For a given point it returns the nearest point belonging to the grid in world coordinates.
* *
* @param aPoint is the point for which the grid point is searched. * @param aPoint is the point for which the grid point is searched.
* @return The nearest grid point. * @return The nearest grid point in world coordinates.
*/ */
VECTOR2D GetGridPoint( VECTOR2D aPoint ) const; VECTOR2D GetGridPoint( const VECTOR2D& aPoint ) const;
/** /**
* @brief Change the grid display style. * @brief Change the grid display style.
...@@ -739,7 +745,7 @@ public: ...@@ -739,7 +745,7 @@ public:
* @param aPoint the pointposition in screen coordinates. * @param aPoint the pointposition in screen coordinates.
* @return the point position in world coordinates. * @return the point position in world coordinates.
*/ */
inline virtual VECTOR2D ToWorld( const VECTOR2D& aPoint ) const inline VECTOR2D ToWorld( const VECTOR2D& aPoint ) const
{ {
return VECTOR2D( screenWorldMatrix * aPoint ); return VECTOR2D( screenWorldMatrix * aPoint );
} }
...@@ -750,15 +756,15 @@ public: ...@@ -750,15 +756,15 @@ public:
* @param aPoint the pointposition in world coordinates. * @param aPoint the pointposition in world coordinates.
* @return the point position in screen coordinates. * @return the point position in screen coordinates.
*/ */
inline virtual VECTOR2D ToScreen( const VECTOR2D& aPoint ) const inline VECTOR2D ToScreen( const VECTOR2D& aPoint ) const
{ {
return VECTOR2D( worldScreenMatrix * aPoint ); return VECTOR2D( worldScreenMatrix * aPoint );
} }
/** /**
* @brief Enable/Disable cursor. * @brief Enable/disable cursor.
* *
* @param aIsCursorEnabled is true if the cursor should be enabled, else false. * @param aCursorEnabled is true if the cursor should be drawn, else false.
*/ */
inline void SetCursorEnabled( bool aCursorEnabled ) inline void SetCursorEnabled( bool aCursorEnabled )
{ {
...@@ -778,7 +784,7 @@ public: ...@@ -778,7 +784,7 @@ public:
/** /**
* @brief Set the cursor size. * @brief Set the cursor size.
* *
* @param aCursorSize is the size of the cursor. * @param aCursorSize is the size of the cursor expressed in pixels.
*/ */
inline void SetCursorSize( unsigned int aCursorSize ) inline void SetCursorSize( unsigned int aCursorSize )
{ {
...@@ -821,9 +827,11 @@ public: ...@@ -821,9 +827,11 @@ public:
/// Depth level on which the grid is drawn /// Depth level on which the grid is drawn
static const int GRID_DEPTH = 1024; static const int GRID_DEPTH = 1024;
static const double METRIC_UNIT_LENGTH = 1e9;
protected: protected:
std::stack<double> depthStack; ///< Stored depth values std::stack<double> depthStack; ///< Stored depth values
VECTOR2D screenSize; ///< Screen size in screen coordinates VECTOR2I screenSize; ///< Screen size in screen coordinates
double worldUnitLength; ///< The unit length of the world coordinates [inch] double worldUnitLength; ///< The unit length of the world coordinates [inch]
double screenDPI; ///< The dots per inch of the screen double screenDPI; ///< The dots per inch of the screen
...@@ -862,7 +870,8 @@ protected: ...@@ -862,7 +870,8 @@ protected:
bool isCursorEnabled; ///< Is the cursor enabled? bool isCursorEnabled; ///< Is the cursor enabled?
COLOR4D cursorColor; ///< Cursor color COLOR4D cursorColor; ///< Cursor color
int cursorSize; ///< Size of the cursor in pixels unsigned int cursorSize; ///< Size of the cursor in pixels
VECTOR2D cursorPosition; ///< Current cursor position (world coordinates)
/// Instance of object that stores information about how to draw texts /// Instance of object that stores information about how to draw texts
STROKE_FONT strokeFont; STROKE_FONT strokeFont;
...@@ -881,13 +890,6 @@ protected: ...@@ -881,13 +890,6 @@ protected:
*/ */
virtual void drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint ) = 0; virtual void drawGridLine( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint ) = 0;
/**
* @brief Initialize the cursor.
*
* @param aCursorSize is the size of the cursor.
*/
virtual void initCursor( int aCursorSize ) = 0;
static const int MIN_DEPTH = -2048; static const int MIN_DEPTH = -2048;
static const int MAX_DEPTH = 2047; static const int MAX_DEPTH = 2047;
}; };
......
...@@ -145,19 +145,12 @@ public: ...@@ -145,19 +145,12 @@ public:
/// @copydoc GAL::ClearScreen() /// @copydoc GAL::ClearScreen()
virtual void ClearScreen(); virtual void ClearScreen();
// -----------------
// Attribute setting
// -----------------
/// @copydoc GAL::SetStrokeColor()
virtual void SetStrokeColor( const COLOR4D& aColor );
// -------------- // --------------
// Transformation // Transformation
// -------------- // --------------
/// @copydoc GAL::Transform() /// @copydoc GAL::Transform()
virtual void Transform( MATRIX3x3D aTransformation ); virtual void Transform( const MATRIX3x3D& aTransformation );
/// @copydoc GAL::Rotate() /// @copydoc GAL::Rotate()
virtual void Rotate( double aAngle ); virtual void Rotate( double aAngle );
...@@ -299,8 +292,6 @@ private: ...@@ -299,8 +292,6 @@ private:
bool isShaderInitialized; ///< Was the shader initialized? bool isShaderInitialized; ///< Was the shader initialized?
bool isGrouping; ///< Was a group started? bool isGrouping; ///< Was a group started?
VECTOR2D cursorPosition; ///< Current cursor position
// Polygon tesselation // Polygon tesselation
/// The tessellator /// The tessellator
GLUtesselator* tesselator; GLUtesselator* tesselator;
...@@ -313,7 +304,7 @@ private: ...@@ -313,7 +304,7 @@ private:
* @param aStartPoint is the start point of the line. * @param aStartPoint is the start point of the line.
* @param aEndPoint is the end point of the line. * @param aEndPoint is the end point of the line.
*/ */
inline void drawLineQuad( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint ); void drawLineQuad( const VECTOR2D& aStartPoint, const VECTOR2D& aEndPoint );
/** /**
* @brief Draw a semicircle. Depending on settings (isStrokeEnabled & isFilledEnabled) it runs * @brief Draw a semicircle. Depending on settings (isStrokeEnabled & isFilledEnabled) it runs
...@@ -364,9 +355,6 @@ private: ...@@ -364,9 +355,6 @@ private:
/// Initialize GLEW /// Initialize GLEW
void initGlew(); void initGlew();
/// @copydoc GAL::initCursor()
virtual void initCursor( int aCursorSize );
/** /**
* @brief Blits cursor into the current screen. * @brief Blits cursor into the current screen.
*/ */
......
...@@ -46,7 +46,8 @@ public: ...@@ -46,7 +46,8 @@ public:
* to an object the segment belongs to (e.g. a line chain) or references to locally stored * to an object the segment belongs to (e.g. a line chain) or references to locally stored
* points (m_a, m_b). * points (m_a, m_b).
*/ */
VECTOR2I& A, B; VECTOR2I& A;
VECTOR2I& B;
/** Default constructor /** Default constructor
* Creates an empty (0, 0) segment, locally-referenced * Creates an empty (0, 0) segment, locally-referenced
...@@ -203,6 +204,8 @@ public: ...@@ -203,6 +204,8 @@ public:
bool Collide( const SEG& aSeg, int aClearance ) const; bool Collide( const SEG& aSeg, int aClearance ) const;
ecoord SquaredDistance( const SEG& aSeg ) const;
/** /**
* Function Distance() * Function Distance()
* *
...@@ -210,14 +213,16 @@ public: ...@@ -210,14 +213,16 @@ public:
* @param aSeg other segment * @param aSeg other segment
* @return minimum distance * @return minimum distance
*/ */
ecoord SquaredDistance( const SEG& aSeg ) const;
int Distance( const SEG& aSeg ) const int Distance( const SEG& aSeg ) const
{ {
return sqrt( SquaredDistance( aSeg ) ); return sqrt( SquaredDistance( aSeg ) );
} }
ecoord SquaredDistance( const VECTOR2I& aP ) const
{
return ( NearestPoint( aP ) - aP ).SquaredEuclideanNorm();
}
/** /**
* Function Distance() * Function Distance()
* *
...@@ -225,11 +230,6 @@ public: ...@@ -225,11 +230,6 @@ public:
* @param aP the point * @param aP the point
* @return minimum distance * @return minimum distance
*/ */
ecoord SquaredDistance( const VECTOR2I& aP ) const
{
return ( NearestPoint( aP ) - aP ).SquaredEuclideanNorm();
}
int Distance( const VECTOR2I& aP ) const int Distance( const VECTOR2I& aP ) const
{ {
return sqrt( SquaredDistance( aP ) ); return sqrt( SquaredDistance( aP ) );
...@@ -244,14 +244,14 @@ public: ...@@ -244,14 +244,14 @@ public:
*/ */
bool Collinear( const SEG& aSeg ) const bool Collinear( const SEG& aSeg ) const
{ {
ecoord qa1 = A.y - B.y; ecoord qa = A.y - B.y;
ecoord qb1 = B.x - A.x; ecoord qb = B.x - A.x;
ecoord qc1 = -qa1 * A.x - qb1 * A.y; ecoord qc = -qa * A.x - qb * A.y;
ecoord qa2 = aSeg.A.y - aSeg.B.y;
ecoord qb2 = aSeg.B.x - aSeg.A.x; ecoord d1 = std::abs( aSeg.A.x * qa + aSeg.A.y * qb + qc );
ecoord qc2 = -qa2 * aSeg.A.x - qb2 * aSeg.A.y; ecoord d2 = std::abs( aSeg.B.x * qa + aSeg.B.y * qb + qc );
return ( qa1 == qa2 ) && ( qb1 == qb2 ) && ( qc1 == qc2 ); return ( d1 <= 1 && d2 <= 1 );
} }
/** /**
......
...@@ -415,7 +415,7 @@ public: ...@@ -415,7 +415,7 @@ public:
* @param aP the point to be looked for * @param aP the point to be looked for
* @return index of the correspoinding point in the line chain or negative when not found. * @return index of the correspoinding point in the line chain or negative when not found.
*/ */
int Find ( const VECTOR2I& aP ) const; int Find( const VECTOR2I& aP ) const;
/** /**
* Function Slice() * Function Slice()
......
...@@ -246,6 +246,7 @@ enum PCB_VISIBLE ...@@ -246,6 +246,7 @@ enum PCB_VISIBLE
PADS_HOLES_VISIBLE, PADS_HOLES_VISIBLE,
VIAS_HOLES_VISIBLE, VIAS_HOLES_VISIBLE,
DRC_VISIBLE, ///< drc markers
WORKSHEET, ///< worksheet frame WORKSHEET, ///< worksheet frame
GP_OVERLAY, ///< general purpose overlay GP_OVERLAY, ///< general purpose overlay
......
...@@ -28,24 +28,9 @@ ...@@ -28,24 +28,9 @@
#define __BOX2_H #define __BOX2_H
#include <math/vector2d.h> #include <math/vector2d.h>
#include <limits>
template <class Vec>
class BOX2_TRAITS
{
};
template <>
class BOX2_TRAITS<VECTOR2I>
{
public:
enum
{
c_max_size = INT_MAX - 1,
c_min_coord_value = INT_MIN / 2 + 1
};
};
/** /**
* Class BOX2 * Class BOX2
* handles a 2-D bounding box, built on top of an origin point * handles a 2-D bounding box, built on top of an origin point
...@@ -59,8 +44,9 @@ private: ...@@ -59,8 +44,9 @@ private:
Vec m_Size; // Rectangle Size Vec m_Size; // Rectangle Size
public: public:
typedef typename Vec::coord_type coord_type; typedef typename Vec::coord_type coord_type;
typedef typename Vec::extended_type ecoord_type; typedef typename Vec::extended_type ecoord_type;
typedef typename std::numeric_limits<coord_type> coord_limits;
BOX2() {}; BOX2() {};
...@@ -73,8 +59,8 @@ public: ...@@ -73,8 +59,8 @@ public:
void SetMaximum() void SetMaximum()
{ {
m_Pos.x = m_Pos.y = BOX2_TRAITS<Vec>().c_min_coord_value; m_Pos.x = m_Pos.y = coord_limits::min() / 2 + coord_limits::epsilon();
m_Size.x = m_Size.y = BOX2_TRAITS<Vec>().c_max_size; m_Size.x = m_Size.y = coord_limits::max() - coord_limits::epsilon();
} }
Vec Centre() const Vec Centre() const
......
...@@ -109,6 +109,26 @@ public: ...@@ -109,6 +109,26 @@ public:
return ( m_activeLayers.count( aLayerId ) > 0 ); return ( m_activeLayers.count( aLayerId ) > 0 );
} }
/**
* Function GetHighlight
* Returns current highlight setting.
* @return True if highlight is enabled, false otherwise.
*/
bool GetHighlight() const
{
return m_highlightEnabled;
}
/**
* Function GetHighlightNetCode
* Returns netcode of currently highlighted net.
* @return Netcode of currently highlighted net.
*/
int GetHighlightNetCode() const
{
return m_highlightNetcode;
}
/** /**
* Function SetHighlight * Function SetHighlight
* Turns on/off highlighting - it may be done for the active layer or the specified net. * Turns on/off highlighting - it may be done for the active layer or the specified net.
...@@ -119,9 +139,7 @@ public: ...@@ -119,9 +139,7 @@ public:
inline void SetHighlight( bool aEnabled, int aNetcode = -1 ) inline void SetHighlight( bool aEnabled, int aNetcode = -1 )
{ {
m_highlightEnabled = aEnabled; m_highlightEnabled = aEnabled;
m_highlightNetcode = aNetcode;
if( aNetcode > 0 )
m_highlightNetcode = aNetcode;
} }
/** /**
......
...@@ -25,6 +25,7 @@ ...@@ -25,6 +25,7 @@
#ifndef ACTION_MANAGER_H_ #ifndef ACTION_MANAGER_H_
#define ACTION_MANAGER_H_ #define ACTION_MANAGER_H_
#include <list>
#include <map> #include <map>
#include <string> #include <string>
...@@ -81,6 +82,14 @@ public: ...@@ -81,6 +82,14 @@ public:
*/ */
bool RunAction( const std::string& aActionName ) const; bool RunAction( const std::string& aActionName ) const;
/**
* Function RunAction()
* Prepares an appropriate event and sends it to the destination specified in a TOOL_ACTION
* object.
* @param aAction is the action to be run.
*/
void RunAction( const TOOL_ACTION* aAction ) const;
/** /**
* Function RunHotKey() * Function RunHotKey()
* Runs an action associated with a hotkey (if there is one available). * Runs an action associated with a hotkey (if there is one available).
...@@ -89,13 +98,6 @@ public: ...@@ -89,13 +98,6 @@ public:
*/ */
bool RunHotKey( int aHotKey ) const; bool RunHotKey( int aHotKey ) const;
/**
* Function ClearHotKey()
* Removes an action associated with a hotkey.
* @param aHotKey is the hotkey to be cleared.
*/
void ClearHotKey( int aHotKey );
private: private:
///> Tool manager needed to run actions ///> Tool manager needed to run actions
TOOL_MANAGER* m_toolMgr; TOOL_MANAGER* m_toolMgr;
...@@ -107,15 +109,8 @@ private: ...@@ -107,15 +109,8 @@ private:
std::map<std::string, TOOL_ACTION*> m_actionNameIndex; std::map<std::string, TOOL_ACTION*> m_actionNameIndex;
///> Map for indexing actions by their hotkeys ///> Map for indexing actions by their hotkeys
std::map<int, TOOL_ACTION*> m_actionHotKeys; typedef std::map<int, std::list<TOOL_ACTION*> > HOTKEY_LIST;
HOTKEY_LIST m_actionHotKeys;
/**
* Function runAction()
* Prepares an appropriate event and sends it to the destination specified in a TOOL_ACTION
* object.
* @param aAction is the action to be run.
*/
void runAction( const TOOL_ACTION* aAction ) const;
}; };
#endif /* ACTION_MANAGER_H_ */ #endif /* ACTION_MANAGER_H_ */
...@@ -30,7 +30,7 @@ ...@@ -30,7 +30,7 @@
#include <cassert> #include <cassert>
#include <tool/tool_base.h> #include <tool/tool_base.h>
#include <tool/action_manager.h> #include <tool/tool_manager.h>
/** /**
* Class TOOL_ACTION * Class TOOL_ACTION
...@@ -50,14 +50,14 @@ public: ...@@ -50,14 +50,14 @@ public:
const std::string& aMenuDesc = std::string( "" ) ) : const std::string& aMenuDesc = std::string( "" ) ) :
m_name( aName ), m_scope( aScope ), m_defaultHotKey( aDefaultHotKey ), m_name( aName ), m_scope( aScope ), m_defaultHotKey( aDefaultHotKey ),
m_currentHotKey( aDefaultHotKey ), m_menuItem( aMenuItem ), m_currentHotKey( aDefaultHotKey ), m_menuItem( aMenuItem ),
m_menuDescription( aMenuDesc ), m_id( -1 ), m_actionMgr( NULL ) m_menuDescription( aMenuDesc ), m_id( -1 )
{ {
TOOL_MANAGER::Instance().RegisterAction( this );
} }
~TOOL_ACTION() ~TOOL_ACTION()
{ {
if( m_actionMgr ) TOOL_MANAGER::Instance().UnregisterAction( this );
m_actionMgr->UnregisterAction( this );
} }
bool operator==( const TOOL_ACTION& aRhs ) const bool operator==( const TOOL_ACTION& aRhs ) const
...@@ -171,6 +171,21 @@ public: ...@@ -171,6 +171,21 @@ public:
m_menuDescription = aDescription; m_menuDescription = aDescription;
} }
TOOL_ACTION_SCOPE GetScope() const
{
return m_scope;
}
/**
* Returns name of the tool associated with the action. It is basically the action name
* stripped of the last part (e.g. for "pcbnew.InteractiveDrawing.drawCircle" it is
* "pcbnew.InteractiveDrawing").
*/
std::string GetToolName() const
{
return m_name.substr( 0, m_name.rfind( '.' ) );
}
private: private:
friend class ACTION_MANAGER; friend class ACTION_MANAGER;
...@@ -180,12 +195,6 @@ private: ...@@ -180,12 +195,6 @@ private:
m_id = aId; m_id = aId;
} }
/// Assigns ACTION_MANAGER object that handles the TOOL_ACTION.
void setActionMgr( ACTION_MANAGER* aManager )
{
m_actionMgr = aManager;
}
/// Name of the action (convention is: app.[tool.]action.name) /// Name of the action (convention is: app.[tool.]action.name)
std::string m_name; std::string m_name;
...@@ -210,9 +219,6 @@ private: ...@@ -210,9 +219,6 @@ private:
/// Unique ID for fast matching. Assigned by ACTION_MANAGER. /// Unique ID for fast matching. Assigned by ACTION_MANAGER.
int m_id; int m_id;
/// Action manager that handles this TOOL_ACTION.
ACTION_MANAGER* m_actionMgr;
/// Origin of the action /// Origin of the action
// const TOOL_BASE* m_origin; // const TOOL_BASE* m_origin;
......
...@@ -79,7 +79,7 @@ public: ...@@ -79,7 +79,7 @@ public:
* specified tool). * specified tool).
* @param aEvent is the wxCommandEvent to be processed. * @param aEvent is the wxCommandEvent to be processed.
*/ */
virtual void DispatchWxCommand( const wxCommandEvent& aEvent ); virtual void DispatchWxCommand( wxCommandEvent& aEvent );
private: private:
///> Number of mouse buttons that is handled in events. ///> Number of mouse buttons that is handled in events.
......
...@@ -64,36 +64,35 @@ enum TOOL_ACTIONS ...@@ -64,36 +64,35 @@ enum TOOL_ACTIONS
TA_MOUSE_WHEEL = 0x0040, TA_MOUSE_WHEEL = 0x0040,
TA_MOUSE = 0x007f, TA_MOUSE = 0x007f,
TA_KEY_UP = 0x0080, TA_KEY_PRESSED = 0x0080,
TA_KEY_DOWN = 0x0100, TA_KEYBOARD = TA_KEY_PRESSED,
TA_KEYBOARD = TA_KEY_UP | TA_KEY_DOWN,
// View related events // View related events
TA_VIEW_REFRESH = 0x0200, TA_VIEW_REFRESH = 0x0100,
TA_VIEW_ZOOM = 0x0400, TA_VIEW_ZOOM = 0x0200,
TA_VIEW_PAN = 0x0800, TA_VIEW_PAN = 0x0400,
TA_VIEW_DIRTY = 0x1000, TA_VIEW_DIRTY = 0x0800,
TA_VIEW = 0x1e00, TA_VIEW = 0x0f00,
TA_CHANGE_LAYER = 0x2000, TA_CHANGE_LAYER = 0x1000,
// Tool cancel event. Issued automagically when the user hits escape or selects End Tool from // Tool cancel event. Issued automagically when the user hits escape or selects End Tool from
// the context menu. // the context menu.
TA_CANCEL_TOOL = 0x4000, TA_CANCEL_TOOL = 0x2000,
// Context menu update. Issued whenever context menu is open and the user hovers the mouse // Context menu update. Issued whenever context menu is open and the user hovers the mouse
// over one of choices. Used in dynamic highligting in disambiguation menu // over one of choices. Used in dynamic highligting in disambiguation menu
TA_CONTEXT_MENU_UPDATE = 0x8000, TA_CONTEXT_MENU_UPDATE = 0x4000,
// Context menu choice. Sent if the user picked something from the context menu or // Context menu choice. Sent if the user picked something from the context menu or
// closed it without selecting anything. // closed it without selecting anything.
TA_CONTEXT_MENU_CHOICE = 0x10000, TA_CONTEXT_MENU_CHOICE = 0x8000,
// This event is sent *before* undo/redo command is performed. // This event is sent *before* undo/redo command is performed.
TA_UNDO_REDO = 0x20000, TA_UNDO_REDO = 0x10000,
// Tool action (allows to control tools) // Tool action (allows to control tools)
TA_ACTION = 0x40000, TA_ACTION = 0x20000,
TA_ANY = 0xffffffff TA_ANY = 0xffffffff
}; };
...@@ -189,7 +188,7 @@ public: ...@@ -189,7 +188,7 @@ public:
m_scope( aScope ), m_scope( aScope ),
m_mouseButtons( 0 ) m_mouseButtons( 0 )
{ {
if( aCategory == TC_COMMAND ) if( aCategory == TC_COMMAND || aCategory == TC_MESSAGE )
m_commandStr = aExtraParam; m_commandStr = aExtraParam;
} }
...@@ -207,7 +206,7 @@ public: ...@@ -207,7 +206,7 @@ public:
///> Returns information about difference between current mouse cursor position and the place ///> Returns information about difference between current mouse cursor position and the place
///> where dragging has started. ///> where dragging has started.
const VECTOR2D Delta() const const VECTOR2D& Delta() const
{ {
assert( m_category == TC_MOUSE ); // this should be used only with mouse events assert( m_category == TC_MOUSE ); // this should be used only with mouse events
return m_mouseDelta; return m_mouseDelta;
...@@ -277,14 +276,9 @@ public: ...@@ -277,14 +276,9 @@ public:
return m_keyCode; return m_keyCode;
} }
bool IsKeyUp() const bool IsKeyPressed() const
{ {
return m_actions == TA_KEY_UP; return m_actions == TA_KEY_PRESSED;
}
bool IsKeyDown() const
{
return m_actions == TA_KEY_DOWN;
} }
void SetMouseDragOrigin( const VECTOR2D& aP ) void SetMouseDragOrigin( const VECTOR2D& aP )
...@@ -317,7 +311,7 @@ public: ...@@ -317,7 +311,7 @@ public:
if( !( m_actions & aEvent.m_actions ) ) if( !( m_actions & aEvent.m_actions ) )
return false; return false;
if( m_category == TC_COMMAND ) if( m_category == TC_COMMAND || m_category == TC_MESSAGE )
{ {
if( m_commandStr && aEvent.m_commandStr ) if( m_commandStr && aEvent.m_commandStr )
return *m_commandStr == *aEvent.m_commandStr; return *m_commandStr == *aEvent.m_commandStr;
......
...@@ -48,6 +48,12 @@ public: ...@@ -48,6 +48,12 @@ public:
TOOL_INTERACTIVE( const std::string& aName ); TOOL_INTERACTIVE( const std::string& aName );
virtual ~TOOL_INTERACTIVE(); virtual ~TOOL_INTERACTIVE();
/**
* Function Activate()
* Runs the tool. After activation, the tool starts receiving events until it is finished.
*/
void Activate();
/** /**
* Function SetContextMenu() * Function SetContextMenu()
* *
......
...@@ -48,9 +48,20 @@ class wxWindow; ...@@ -48,9 +48,20 @@ class wxWindow;
class TOOL_MANAGER class TOOL_MANAGER
{ {
public: public:
TOOL_MANAGER(); static TOOL_MANAGER& Instance()
{
static TOOL_MANAGER manager;
return manager;
}
~TOOL_MANAGER(); ~TOOL_MANAGER();
/**
* Deletes all the tools that were registered in the TOOL_MANAGER.
*/
void DeleteAll();
/** /**
* Generates an unique ID from for a tool with given name. * Generates an unique ID from for a tool with given name.
*/ */
...@@ -101,13 +112,21 @@ public: ...@@ -101,13 +112,21 @@ public:
/** /**
* Function RunAction() * Function RunAction()
* Runs the specified action. The common format is "application.ToolName.Action". * Runs the specified action. The common format for action names is "application.ToolName.Action".
* *
* @param aActionName is the name of action to be invoked. * @param aActionName is the name of action to be invoked.
* @return True if the action finished successfully, false otherwise. * @return True if the action finished successfully, false otherwise.
*/ */
bool RunAction( const std::string& aActionName ); bool RunAction( const std::string& aActionName );
/**
* Function RunAction()
* Runs the specified action.
*
* @param aAction is the action to be invoked.
*/
void RunAction( const TOOL_ACTION& aAction );
/** /**
* Function FindTool() * Function FindTool()
* Searches for a tool with given ID. * Searches for a tool with given ID.
...@@ -167,6 +186,36 @@ public: ...@@ -167,6 +186,36 @@ public:
return m_editFrame; return m_editFrame;
} }
/**
* Returns id of the tool that is on the top of the active tools stack
* (was invoked the most recently).
* @return Id of the currently used tool.
*/
int GetCurrentToolId() const
{
return m_activeTools.front();
}
/**
* Returns the tool that is on the top of the active tools stack
* (was invoked the most recently).
* @return Pointer to the currently used tool.
*/
TOOL_BASE* GetCurrentTool() const
{
return FindTool( GetCurrentToolId() );
}
/**
* Returns priority of a given tool. Higher number means that the tool is closer to the
* beginning of the active tools queue (i.e. receives events earlier, tools with lower
* priority receive events later).
* @param aToolId is the id of queried tool.
* @return The priority of a given tool. If returned number is negative, then it means that
* the tool id is invalid or the tool is not active.
*/
int GetPriority( int aToolId ) const;
/** /**
* Defines a state transition - the events that cause a given handler method in the tool * Defines a state transition - the events that cause a given handler method in the tool
* to be called. Called by TOOL_INTERACTIVE::Go(). May be called from a coroutine context. * to be called. Called by TOOL_INTERACTIVE::Go(). May be called from a coroutine context.
...@@ -203,6 +252,8 @@ public: ...@@ -203,6 +252,8 @@ public:
} }
private: private:
TOOL_MANAGER();
struct TOOL_STATE; struct TOOL_STATE;
typedef std::pair<TOOL_EVENT_LIST, TOOL_STATE_FUNC> TRANSITION; typedef std::pair<TOOL_EVENT_LIST, TOOL_STATE_FUNC> TRANSITION;
......
...@@ -40,111 +40,152 @@ ...@@ -40,111 +40,152 @@
#ifndef _HALF_EDGE_DART_ #ifndef _HALF_EDGE_DART_
#define _HALF_EDGE_DART_ #define _HALF_EDGE_DART_
#include <ttl/halfedge/hetriang.h> #include <ttl/halfedge/hetriang.h>
namespace hed
{
/**
* \class Dart
* \brief \b %Dart class for the half-edge data structure.
*
* See \ref api for a detailed description of how the member functions
* should be implemented.
*/
class DART
{
EDGE_PTR m_edge;
namespace hed { /// Dart direction: true if dart is counterclockwise in face
bool m_dir;
//------------------------------------------------------------------------------------------------
// Dart class for the half-edge data structure
//------------------------------------------------------------------------------------------------
/** \class Dart
* \brief \b %Dart class for the half-edge data structure.
*
* See \ref api for a detailed description of how the member functions
* should be implemented.
*/
class Dart {
EdgePtr edge_;
bool dir_; // true if dart is counterclockwise in face
public: public:
/// Default constructor /// Default constructor
Dart() { dir_ = true; } DART()
{
m_dir = true;
}
/// Constructor /// Constructor
Dart(const EdgePtr& edge, bool dir = true) { edge_ = edge; dir_ = dir; } DART( const EDGE_PTR& aEdge, bool aDir = true )
{
m_edge = aEdge;
m_dir = aDir;
}
/// Copy constructor /// Copy constructor
Dart(const Dart& dart) { edge_ = dart.edge_; dir_ = dart.dir_; } DART( const DART& aDart )
{
m_edge = aDart.m_edge;
m_dir = aDart.m_dir;
}
/// Destructor /// Destructor
~Dart() {} ~DART()
{
}
/// Assignment operator /// Assignment operator
Dart& operator = (const Dart& dart) { DART& operator=( const DART& aDart )
if (this == &dart) {
if( this == &aDart )
return *this;
m_edge = aDart.m_edge;
m_dir = aDart.m_dir;
return *this; return *this;
edge_ = dart.edge_;
dir_ = dart.dir_;
return *this;
} }
/// Comparing dart objects /// Comparing dart objects
bool operator==(const Dart& dart) const { bool operator==( const DART& aDart ) const
if (dart.edge_ == edge_ && dart.dir_ == dir_) {
return true; return ( aDart.m_edge == m_edge && aDart.m_dir == m_dir );
return false;
} }
/// Comparing dart objects /// Comparing dart objects
bool operator!=(const Dart& dart) const { bool operator!=( const DART& aDart ) const
return !(dart==*this); {
return !( aDart == *this );
} }
/// Maps the dart to a different node /// Maps the dart to a different node
Dart& alpha0() { dir_ = !dir_; return *this; } DART& Alpha0()
{
m_dir = !m_dir;
return *this;
}
/// Maps the dart to a different edge /// Maps the dart to a different edge
Dart& alpha1() { DART& Alpha1()
if (dir_) { {
edge_ = edge_->getNextEdgeInFace()->getNextEdgeInFace(); if( m_dir )
dir_ = false; {
} m_edge = m_edge->GetNextEdgeInFace()->GetNextEdgeInFace();
else { m_dir = false;
edge_ = edge_->getNextEdgeInFace(); }
dir_ = true; else
} {
return *this; m_edge = m_edge->GetNextEdgeInFace();
m_dir = true;
}
return *this;
} }
/// Maps the dart to a different triangle. \b Note: the dart is not changed if it is at the boundary! /// Maps the dart to a different triangle. \b Note: the dart is not changed if it is at the boundary!
Dart& alpha2() { DART& Alpha2()
if (edge_->getTwinEdge()) { {
edge_ = edge_->getTwinEdge(); if( m_edge->GetTwinEdge() )
dir_ = !dir_; {
} m_edge = m_edge->GetTwinEdge();
// else, the dart is at the boundary and should not be changed m_dir = !m_dir;
return *this; }
// else, the dart is at the boundary and should not be changed
return *this;
} }
// Utilities not required by TTL
// -----------------------------
/** @name Utilities not required by TTL */ /** @name Utilities not required by TTL */
//@{ //@{
void Init( const EDGE_PTR& aEdge, bool aDir = true )
{
m_edge = aEdge;
m_dir = aDir;
}
void init(const EdgePtr& edge, bool dir = true) { edge_ = edge; dir_ = dir; } double X() const
{
return GetNode()->GetX();
}
double x() const { return getNode()->GetX(); } // x-coordinate of source node double Y() const
double y() const { return getNode()->GetY(); } // y-coordinate of source node {
return GetNode()->GetY();
}
bool isCounterClockWise() const { return dir_; } bool IsCCW() const
{
return m_dir;
}
const NodePtr& getNode() const { return dir_ ? edge_->getSourceNode() : edge_->getTargetNode(); } const NODE_PTR& GetNode() const
const NodePtr& getOppositeNode() const { return dir_ ? edge_->getTargetNode() : edge_->getSourceNode(); } {
EdgePtr& getEdge() { return edge_; } return m_dir ? m_edge->GetSourceNode() : m_edge->GetTargetNode();
}
//@} // End of Utilities not required by TTL const NODE_PTR& GetOppositeNode() const
{
return m_dir ? m_edge->GetTargetNode() : m_edge->GetSourceNode();
}
}; EDGE_PTR& GetEdge()
{
return m_edge;
}
//@} // End of Utilities not required by TTL
};
}; // End of hed namespace } // End of hed namespace
#endif #endif
...@@ -40,136 +40,149 @@ ...@@ -40,136 +40,149 @@
#ifndef _HALF_EDGE_TRAITS_ #ifndef _HALF_EDGE_TRAITS_
#define _HALF_EDGE_TRAITS_ #define _HALF_EDGE_TRAITS_
#include <ttl/halfedge/hetriang.h> #include <ttl/halfedge/hetriang.h>
#include <ttl/halfedge/hedart.h> #include <ttl/halfedge/hedart.h>
namespace hed
namespace hed { {
/**
* \struct TTLtraits
//------------------------------------------------------------------------------------------------ * \brief \b Traits class (static struct) for the half-edge data structure.
// Traits class for the half-edge data structure *
//------------------------------------------------------------------------------------------------ * The member functions are those required by different function templates
* in the TTL. Documentation is given here to explain what actions
/** \struct TTLtraits * should be carried out on the actual data structure as required by the functions
* \brief \b Traits class (static struct) for the half-edge data structure. * in the \ref ttl namespace.
* *
* The member functions are those required by different function templates * The source code of \c %HeTraits.h shows how the traits class is implemented for the
* in the TTL. Documentation is given here to explain what actions * half-edge data structure.
* should be carried out on the actual data structure as required by the functions *
* in the \ref ttl namespace. * \see \ref api
* */
* The source code of \c %HeTraits.h shows how the traits class is implemented for the struct TTLtraits
* half-edge data structure. {
* /**
* \see \ref api * The floating point type used in calculations involving scalar products and cross products.
* */
*/ typedef double REAL_TYPE;
struct TTLtraits {
/** The floating point type used in calculations
* involving scalar products and cross products.
*/
typedef double real_type;
//----------------------------------------------------------------------------------------------
// ------------------------------- Geometric Predicates Group ---------------------------------
//----------------------------------------------------------------------------------------------
/** @name Geometric Predicates */ /** @name Geometric Predicates */
//@{ //@{
/**
//---------------------------------------------------------------------------------------------- * Scalar product between two 2D vectors represented as darts.\n
/** Scalar product between two 2D vectors represented as darts.\n *
* * ttl_util::scalarProduct2d can be used.
* ttl_util::scalarProduct2d can be used. */
*/ static REAL_TYPE ScalarProduct2D( const DART& aV1, const DART& aV2 )
static real_type scalarProduct2d(const Dart& v1, const Dart& v2) { {
Dart v10 = v1; v10.alpha0(); DART v10 = aV1;
Dart v20 = v2; v20.alpha0(); v10.Alpha0();
return ttl_util::scalarProduct2d(v10.x()-v1.x(), v10.y()-v1.y(),
v20.x()-v2.x(), v20.y()-v2.y()); DART v20 = aV2;
v20.Alpha0();
return ttl_util::ScalarProduct2D( v10.X() - aV1.X(), v10.Y() - aV1.Y(),
v20.X() - aV2.X(), v20.Y() - aV2.Y() );
} }
/**
//---------------------------------------------------------------------------------------------- * Scalar product between two 2D vectors.
/** Scalar product between two 2D vectors. * The first vector is represented by a dart \e v, and the second
* The first vector is represented by a dart \e v, and the second * vector has direction from the source node of \e v to the point \e p.\n
* vector has direction from the source node of \e v to the point \e p.\n *
* * ttl_util::ScalarProduct2D can be used.
* ttl_util::scalarProduct2d can be used. */
*/ static REAL_TYPE ScalarProduct2D( const DART& aV, const NODE_PTR& aP )
static real_type scalarProduct2d(const Dart& v, const NodePtr& p) { {
Dart d0 = v; d0.alpha0(); DART d0 = aV;
return ttl_util::scalarProduct2d(d0.x() - v.x(), d0.y() - v.y(), d0.Alpha0();
p->GetX() - v.x(), p->GetY() - v.y());
return ttl_util::ScalarProduct2D( d0.X() - aV.X(), d0.Y() - aV.Y(),
aP->GetX() - aV.X(), aP->GetY() - aV.Y() );
} }
/**
//---------------------------------------------------------------------------------------------- * Cross product between two vectors in the plane represented as darts.
/** Cross product between two vectors in the plane represented as darts. * The z-component of the cross product is returned.\n
* The z-component of the cross product is returned.\n *
* * ttl_util::CrossProduct2D can be used.
* ttl_util::crossProduct2d can be used. */
*/ static REAL_TYPE CrossProduct2D( const DART& aV1, const DART& aV2 )
static real_type crossProduct2d(const Dart& v1, const Dart& v2) { {
Dart v10 = v1; v10.alpha0(); DART v10 = aV1;
Dart v20 = v2; v20.alpha0(); v10.Alpha0();
return ttl_util::crossProduct2d(v10.x()-v1.x(), v10.y()-v1.y(),
v20.x()-v2.x(), v20.y()-v2.y()); DART v20 = aV2;
v20.Alpha0();
return ttl_util::CrossProduct2D( v10.X() - aV1.X(), v10.Y() - aV1.Y(),
v20.X() - aV2.X(), v20.Y() - aV2.Y() );
} }
/**
//---------------------------------------------------------------------------------------------- * Cross product between two vectors in the plane.
/** Cross product between two vectors in the plane. * The first vector is represented by a dart \e v, and the second
* The first vector is represented by a dart \e v, and the second * vector has direction from the source node of \e v to the point \e p.
* vector has direction from the source node of \e v to the point \e p. * The z-component of the cross product is returned.\n
* The z-component of the cross product is returned.\n *
* * ttl_util::CrossProduct2d can be used.
* ttl_util::crossProduct2d can be used. */
*/ static REAL_TYPE CrossProduct2D( const DART& aV, const NODE_PTR& aP )
static real_type crossProduct2d(const Dart& v, const NodePtr& p) { {
Dart d0 = v; d0.alpha0(); DART d0 = aV;
return ttl_util::crossProduct2d(d0.x() - v.x(), d0.y() - v.y(), d0.Alpha0();
p->GetX() - v.x(), p->GetY() - v.y());
return ttl_util::CrossProduct2D( d0.X() - aV.X(), d0.Y() - aV.Y(),
aP->GetX() - aV.X(), aP->GetY() - aV.Y() );
} }
/**
//---------------------------------------------------------------------------------------------- * Let \e n1 and \e n2 be the nodes associated with two darts, and let \e p
/** Let \e n1 and \e n2 be the nodes associated with two darts, and let \e p * be a point in the plane. Return a positive value if \e n1, \e n2,
* be a point in the plane. Return a positive value if \e n1, \e n2, * and \e p occur in counterclockwise order; a negative value if they occur
* and \e p occur in counterclockwise order; a negative value if they occur * in clockwise order; and zero if they are collinear.
* in clockwise order; and zero if they are collinear. */
*/ static REAL_TYPE Orient2D( const DART& aN1, const DART& aN2, const NODE_PTR& aP )
static real_type orient2d(const Dart& n1, const Dart& n2, const NodePtr& p) { {
real_type pa[2]; real_type pb[2]; real_type pc[2]; REAL_TYPE pa[2];
pa[0] = n1.x(); pa[1] = n1.y(); REAL_TYPE pb[2];
pb[0] = n2.x(); pb[1] = n2.y(); REAL_TYPE pc[2];
pc[0] = p->GetX(); pc[1] = p->GetY();
return ttl_util::orient2dfast(pa, pb, pc); pa[0] = aN1.X();
pa[1] = aN1.Y();
pb[0] = aN2.X();
pb[1] = aN2.Y();
pc[0] = aP->GetX();
pc[1] = aP->GetY();
return ttl_util::Orient2DFast( pa, pb, pc );
} }
/**
//---------------------------------------------------------------------------------------------- * This is the same predicate as represented with the function above,
/** This is the same predicate as represented with the function above, * but with a slighty different interface:
* but with a slighty different interface: * The last parameter is given as a dart where the source node of the dart
* The last parameter is given as a dart where the source node of the dart * represents a point in the plane.
* represents a point in the plane. * This function is required for constrained triangulation.
* This function is required for constrained triangulation. */
*/ static REAL_TYPE Orient2D( const DART& aN1, const DART& aN2, const DART& aP )
static real_type orient2d(const Dart& n1, const Dart& n2, const Dart& p) { {
real_type pa[2]; real_type pb[2]; real_type pc[2]; REAL_TYPE pa[2];
pa[0] = n1.x(); pa[1] = n1.y(); REAL_TYPE pb[2];
pb[0] = n2.x(); pb[1] = n2.y(); REAL_TYPE pc[2];
pc[0] = p.x(); pc[1] = p.y();
return ttl_util::orient2dfast(pa, pb, pc); pa[0] = aN1.X();
pa[1] = aN1.Y();
pb[0] = aN2.X();
pb[1] = aN2.Y();
pc[0] = aP.X();
pc[1] = aP.Y();
return ttl_util::Orient2DFast( pa, pb, pc );
} }
//@} // End of Geometric Predicates Group //@} // End of Geometric Predicates Group
}; };
}; // End of hed namespace }; // End of hed namespace
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
...@@ -34,6 +34,7 @@ ...@@ -34,6 +34,7 @@
#include <PolyLine.h> #include <PolyLine.h>
#include <math_for_graphics.h> #include <math_for_graphics.h>
#include <trigo.h> #include <trigo.h>
#include <common.h>
class LINE_READER; class LINE_READER;
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment