KiCad PCB EDA Suite
dialog_position_relative.cpp
Go to the documentation of this file.
1 /*
2  * This program source code file is part of KiCad, a free EDA CAD application.
3  *
4  * Copyright (C) 2017-2018 KiCad Developers, see AUTHORS.txt for contributors.
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version 2
9  * of the License, or (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, you may find one here:
18  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
19  * or you may search the http://www.gnu.org website for the version 2 license,
20  * or you may write to the Free Software Foundation, Inc.,
21  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
22  */
23 
24 #include <pcb_edit_frame.h>
25 #include "tools/pcb_actions.h"
26 
28 
29 // initialise statics
31 
32 
34  wxPoint& anchor ) :
36  m_toolMgr( aParent->GetToolManager() ),
37  m_translation( translation ),
38  m_anchor_position( anchor ),
39  m_xOffset( aParent, m_xLabel, m_xEntry, m_xUnit ),
40  m_yOffset( aParent, m_yLabel, m_yEntry, m_yUnit )
41 {
42  // tabbing goes through the entries in sequence
43  m_yEntry->MoveAfterInTabOrder( m_xEntry );
44 
45  // and set up the entries according to the saved options
46  m_polarCoords->SetValue( m_options.polarCoords );
47  updateDialogControls( m_polarCoords->IsChecked() );
48 
51 
52  m_stdButtonsOK->SetDefault();
53 
55 }
56 
57 
58 void DIALOG_POSITION_RELATIVE::ToPolarDeg( double x, double y, double& r, double& q )
59 {
60  // convert to polar coordinates
61  r = hypot( x, y );
62 
63  q = ( r != 0) ? RAD2DEG( atan2( y, x ) ) : 0;
64 }
65 
66 
68 {
69  if( polar )
70  {
71  const int r = m_xOffset.GetValue();
72  const double q = m_yOffset.GetValue();
73 
74  val.x = r * cos( DEG2RAD( q / 10.0 ) );
75  val.y = r * sin( DEG2RAD( q / 10.0 ) );
76  }
77  else
78  {
79  // direct read
80  val.x = m_xOffset.GetValue();
81  val.y = m_yOffset.GetValue();
82  }
83 
84  // no validation to do here, but in future, you could return false here
85  return true;
86 }
87 
88 
89 void DIALOG_POSITION_RELATIVE::OnPolarChanged( wxCommandEvent& event )
90 {
91  bool newPolar = m_polarCoords->IsChecked();
92  wxPoint val;
93 
94  // get the value as previously stored
95  GetTranslationInIU( val, !newPolar );
96 
97  // now switch the controls to the new representations
98  updateDialogControls( newPolar );
99 
100  if( newPolar )
101  {
102  // convert to polar coordinates
103  double r, q;
104  ToPolarDeg( val.x, val.y, r, q );
105 
106  m_xOffset.SetValue( KiROUND( r / 10.0) * 10 );
107  m_yOffset.SetValue( q * 10 );
108  }
109  else
110  {
111  // vector is already in Cartesian, so just render out
112  // note - round off the last decimal place (10nm) to prevent
113  // (some) rounding causing errors when round-tripping
114  // you can never eliminate entirely, however
115  m_xOffset.SetValue( KiROUND( val.x / 10.0 ) * 10 );
116  m_yOffset.SetValue( KiROUND( val.y / 10.0 ) * 10 );
117  }
118 }
119 
120 
122 {
123  if( aPolar )
124  {
125  m_xOffset.SetLabel( _( "Distance:" ) ); // Polar radius
126  m_yOffset.SetLabel( _( "Angle:" ) ); // Polar theta or angle
128  }
129  else
130  {
131  m_xOffset.SetLabel( _( "Offset X:" ) );
132  m_yOffset.SetLabel( _( "Offset Y:" ) );
134  }
135 }
136 
137 
138 void DIALOG_POSITION_RELATIVE::OnClear( wxCommandEvent& event )
139 {
140  wxObject* obj = event.GetEventObject();
141 
142  if( obj == m_clearX )
143  {
144  m_xOffset.SetValue( 0 );
145  }
146  else if( obj == m_clearY )
147  {
148  m_yOffset.SetValue( 0 );
149  }
150 }
151 
152 
153 void DIALOG_POSITION_RELATIVE::OnSelectItemClick( wxCommandEvent& event )
154 {
155  event.Skip();
156 
158  wxASSERT( posrelTool );
160 
161  Hide();
162 }
163 
164 
166 {
167  BOARD* board = (BOARD*) m_toolMgr->GetModel();
168 
169  m_anchor_position = board->GetGridOrigin();
170  m_referenceInfo->SetLabel( _( "Reference location: grid origin" ) );
171 }
172 
173 
175 {
177 
179  m_referenceInfo->SetLabel( _( "Reference location: local coordinates origin" ) );
180 }
181 
182 
184 {
185  wxString reference = _( "<none selected>" );
186 
187  if( aItem )
188  {
189  m_anchor_position = dynamic_cast<BOARD_ITEM*>( aItem )->GetPosition();
190  reference = aItem->GetSelectMenuText( GetUserUnits() );
191  }
192 
193  m_referenceInfo->SetLabel( wxString::Format( "Reference item: %s", reference ) );
194 
195  Show( true );
196 }
197 
198 
199 void DIALOG_POSITION_RELATIVE::OnOkClick( wxCommandEvent& event )
200 {
201  // for the output, we only deliver a Cartesian vector
202  bool ok = GetTranslationInIU( m_translation, m_polarCoords->IsChecked() );
203 
204  if( ok )
205  {
206  // save the settings
207  m_options.polarCoords = m_polarCoords->GetValue();
211  wxASSERT( posrelTool );
212 
214 
215  event.Skip();
216  }
217 }
218 
219 
220 void DIALOG_POSITION_RELATIVE::OnTextFocusLost( wxFocusEvent& event )
221 {
222  wxTextCtrl* obj = static_cast<wxTextCtrl*>( event.GetEventObject() );
223 
224  if( obj->GetValue().IsEmpty() )
225  obj->SetValue( "0" );
226 
227  event.Skip();
228 }
Class POSITION_RELATIVE_TOOL.
void OnUseGridOriginClick(wxCommandEvent &event) override
static int KiROUND(double v)
Round a floating point number to an integer using "round halfway cases away from zero".
Definition: common.h:120
const wxPoint & GetGridOrigin() const
Definition: class_board.h:356
Class BOARD_ITEM is a base class for any item which can be embedded within the BOARD container class...
wxWindow * GetEditFrame() const
Definition: tool_manager.h:267
void OnOkClick(wxCommandEvent &event) override
double RAD2DEG(double rad)
Definition: trigo.h:200
void FinishDialogSettings()
In all dialogs, we must call the same functions to fix minimal dlg size, the default position and per...
DIALOG_POSITION_RELATIVE(PCB_BASE_FRAME *aParent, wxPoint &translation, wxPoint &anchor)
bool RunAction(const std::string &aActionName, bool aNow=false, T aParam=NULL)
Function RunAction() Runs the specified action.
Definition: tool_manager.h:125
static TOOL_ACTION selectpositionRelativeItem
Selection of anchor item for position relative tool.
Definition: pcb_actions.h:257
virtual void SetUnits(EDA_UNITS_T aUnits, bool aUseMils=false)
Function SetUnits Normally not needed (as the UNIT_BINDER inherits from the parent frame)...
Definition: unit_binder.cpp:64
virtual wxString GetSelectMenuText(EDA_UNITS_T aUnits) const
Function GetSelectMenuText returns the text to display to be used in the selection clarification cont...
void OnTextFocusLost(wxFocusEvent &event) override
wxPoint m_O_Curseur
Relative Screen cursor coordinate (on grid) in user units.
Definition: base_screen.h:185
void OnClear(wxCommandEvent &event) override
virtual int GetValue()
Function GetValue Returns the current value in Internal Units.
void OnUseUserOriginClick(wxCommandEvent &event) override
void OnSelectItemClick(wxCommandEvent &event) override
bool Show(bool show) override
int RelativeItemSelectionMove(wxPoint anchor, wxPoint translation)
Function RelativeItemSelectionMove()
Class DIALOG_POSITION_RELATIVE_BASE.
void SetLabel(const wxString &aLabel)
void Format(OUTPUTFORMATTER *out, int aNestLevel, int aCtl, CPTREE &aTree)
Function Format outputs a PTREE into s-expression format via an OUTPUTFORMATTER derivative.
Definition: ptree.cpp:205
EDA_ITEM * GetModel() const
Definition: tool_manager.h:262
double DEG2RAD(double deg)
Definition: trigo.h:199
Class BOARD holds information pertinent to a Pcbnew printed circuit board.
Definition: class_board.h:170
void OnPolarChanged(wxCommandEvent &event) override
virtual void SetValue(int aValue)
Function SetValue Sets new value (in Internal Units) for the text field, taking care of units convers...
bool GetTranslationInIU(wxPoint &val, bool polar)
Get the (Cartesian) translation described by the text entries.
Class EDA_ITEM is a base class for most all the KiCad significant classes, used in schematics and boa...
Definition: base_struct.h:154
PCB_SCREEN * GetScreen() const override
Return a pointer to a BASE_SCREEN or one of its derivatives.
void ToPolarDeg(double x, double y, double &r, double &q)
Convert a given Cartesian point into a polar representation.
class PCB_BASE_FRAME basic PCB main window class for Pcbnew, Gerbview, and CvPcb footprint viewer...
EDA_UNITS_T GetUserUnits() const override
Definition: dialog_shim.h:132
static POSITION_RELATIVE_OPTIONS m_options