KiCad PCB EDA Suite
common.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) 2014-2015 Jean-Pierre Charras, jp.charras at wanadoo.fr
5  * Copyright (C) 2008 Wayne Stambaugh <stambaughw@gmail.com>
6  * Copyright (C) 1992-2018 KiCad Developers, see AUTHORS.txt for contributors.
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, you may find one here:
20  * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
21  * or you may search the http://www.gnu.org website for the version 2 license,
22  * or you may write to the Free Software Foundation, Inc.,
23  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
24  */
25 
30 #include <fctsys.h>
31 #include <eda_base_frame.h>
32 #include <base_struct.h>
33 #include <common.h>
34 #include <macros.h>
35 #include <base_units.h>
36 #include <reporter.h>
37 
38 #include <wx/process.h>
39 #include <wx/config.h>
40 #include <wx/utils.h>
41 #include <wx/stdpaths.h>
42 #include <wx/url.h>
43 
44 #include <pgm_base.h>
45 
46 using KIGFX::COLOR4D;
47 
48 
58 
59 
60 std::atomic<unsigned int> LOCALE_IO::m_c_count(0);
61 
63 {
64  // use thread safe, atomic operation
65  if( m_c_count++ == 0 )
66  {
67  // Store the user locale name, to restore this locale later, in dtor
68  m_user_locale = setlocale( LC_NUMERIC, nullptr );
69  // Switch the locale to C locale, to read/write files with fp numbers
70  setlocale( LC_NUMERIC, "C" );
71  }
72 }
73 
74 
76 {
77  // use thread safe, atomic operation
78  if( --m_c_count == 0 )
79  {
80  // revert to the user locale
81  setlocale( LC_NUMERIC, m_user_locale.c_str() );
82  }
83 }
84 
85 
86 wxSize GetTextSize( const wxString& aSingleLine, wxWindow* aWindow )
87 {
88  wxCoord width;
89  wxCoord height;
90 
91  {
92  wxClientDC dc( aWindow );
93  dc.SetFont( aWindow->GetFont() );
94  dc.GetTextExtent( aSingleLine, &width, &height );
95  }
96 
97  return wxSize( width, height );
98 }
99 
100 
101 bool EnsureTextCtrlWidth( wxTextCtrl* aCtrl, const wxString* aString )
102 {
103  wxWindow* window = aCtrl->GetParent();
104 
105  if( !window )
106  window = aCtrl;
107 
108  wxString ctrlText;
109 
110  if( !aString )
111  {
112  ctrlText = aCtrl->GetValue();
113  aString = &ctrlText;
114  }
115 
116  wxSize textz = GetTextSize( *aString, window );
117  wxSize ctrlz = aCtrl->GetSize();
118 
119  if( ctrlz.GetWidth() < textz.GetWidth() + 10 )
120  {
121  ctrlz.SetWidth( textz.GetWidth() + 10 );
122  aCtrl->SetSizeHints( ctrlz );
123  return true;
124  }
125 
126  return false;
127 }
128 
129 
130 void SelectReferenceNumber( wxTextEntry* aTextEntry )
131 {
132  wxString ref = aTextEntry->GetValue();
133 
134  if( ref.find_first_of( '?' ) != ref.npos )
135  {
136  aTextEntry->SetSelection( ref.find_first_of( '?' ), ref.find_last_of( '?' ) + 1 );
137  }
138  else
139  {
140  wxString num = ref;
141 
142  while( !num.IsEmpty() && ( !isdigit( num.Last() ) || !isdigit( num.GetChar( 0 ) ) ) )
143  {
144  if( !isdigit( num.Last() ) )
145  num.RemoveLast();
146  if( !isdigit( num.GetChar ( 0 ) ) )
147  num = num.Right( num.Length() - 1);
148  }
149 
150  aTextEntry->SetSelection( ref.Find( num ), ref.Find( num ) + num.Length() );
151 
152  if( num.IsEmpty() )
153  aTextEntry->SetSelection( -1, -1 );
154  }
155 }
156 
157 
158 void wxStringSplit( const wxString& aText, wxArrayString& aStrings, wxChar aSplitter )
159 {
160  wxString tmp;
161 
162  for( unsigned ii = 0; ii < aText.Length(); ii++ )
163  {
164  if( aText[ii] == aSplitter )
165  {
166  aStrings.Add( tmp );
167  tmp.Clear();
168  }
169 
170  else
171  tmp << aText[ii];
172  }
173 
174  if( !tmp.IsEmpty() )
175  {
176  aStrings.Add( tmp );
177  }
178 }
179 
180 
181 int ProcessExecute( const wxString& aCommandLine, int aFlags, wxProcess *callback )
182 {
183  return wxExecute( aCommandLine, aFlags, callback );
184 }
185 
186 
188 {
189  static timestamp_t oldTimeStamp;
190  timestamp_t newTimeStamp;
191 
192  newTimeStamp = time( NULL );
193 
194  if( newTimeStamp <= oldTimeStamp )
195  newTimeStamp = oldTimeStamp + 1;
196 
197  oldTimeStamp = newTimeStamp;
198 
199  return newTimeStamp;
200 }
201 
202 
203 double RoundTo0( double x, double precision )
204 {
205  assert( precision != 0 );
206 
207  long long ix = KiROUND( x * precision );
208 
209  if ( x < 0.0 )
210  ix = -ix;
211 
212  int remainder = ix % 10; // remainder is in precision mm
213 
214  if( remainder <= 2 )
215  ix -= remainder; // truncate to the near number
216  else if( remainder >= 8 )
217  ix += 10 - remainder; // round to near number
218 
219  if ( x < 0 )
220  ix = -ix;
221 
222  return (double) ix / precision;
223 }
224 
225 
226 wxConfigBase* GetNewConfig( const wxString& aProgName )
227 {
228  wxConfigBase* cfg = 0;
229  wxFileName configname;
230  configname.AssignDir( GetKicadConfigPath() );
231  configname.SetFullName( aProgName );
232 
233  cfg = new wxFileConfig( wxT( "" ), wxT( "" ), configname.GetFullPath() );
234  return cfg;
235 }
236 
237 
239 {
240  wxFileName cfgpath;
241 
242  // http://docs.wxwidgets.org/3.0/classwx_standard_paths.html#a7c7cf595d94d29147360d031647476b0
243  cfgpath.AssignDir( wxStandardPaths::Get().GetUserConfigDir() );
244 
245  // GetUserConfigDir() does not default to ~/.config which is the current standard
246  // configuration file location on Linux. This has been fixed in later versions of wxWidgets.
247 #if !defined( __WXMSW__ ) && !defined( __WXMAC__ )
248  wxArrayString dirs = cfgpath.GetDirs();
249 
250  if( dirs.Last() != ".config" )
251  cfgpath.AppendDir( ".config" );
252 #endif
253 
254  wxString envstr;
255 
256  // This shouldn't cause any issues on Windows or MacOS.
257  if( wxGetEnv( wxT( "XDG_CONFIG_HOME" ), &envstr ) && !envstr.IsEmpty() )
258  {
259  // Override the assignment above with XDG_CONFIG_HOME
260  cfgpath.AssignDir( envstr );
261  }
262 
263  cfgpath.AppendDir( wxT( "kicad" ) );
264 
265  // Use KICAD_CONFIG_HOME to allow the user to force a specific configuration path.
266  if( wxGetEnv( wxT( "KICAD_CONFIG_HOME" ), &envstr ) && !envstr.IsEmpty() )
267  {
268  // Override the assignment above with KICAD_CONFIG_HOME
269  cfgpath.AssignDir( envstr );
270  }
271 
272  if( !cfgpath.DirExists() )
273  {
274  cfgpath.Mkdir( wxS_DIR_DEFAULT, wxPATH_MKDIR_FULL );
275  }
276 
277  return cfgpath.GetPath();
278 }
279 
280 
282 {
286 #ifdef __WINDOWS__
287  Bracket_Windows = '%', // yeah, Windows people are a bit strange ;-)
288 #endif
290 };
291 
292 
293 //
294 // Stolen from wxExpandEnvVars and then heavily optimized
295 //
296 wxString KIwxExpandEnvVars(const wxString& str)
297 {
298  size_t strlen = str.length();
299 
300  wxString strResult;
301  strResult.Alloc(strlen);
302 
303  for ( size_t n = 0; n < strlen; n++ ) {
304  wxUniChar str_n = str[n];
305 
306  switch ( str_n.GetValue() ) {
307 #ifdef __WINDOWS__
308  case wxT('%'):
309 #endif // __WINDOWS__
310  case wxT('$'):
311  {
312  Bracket bracket;
313 #ifdef __WINDOWS__
314  if ( str_n == wxT('%') )
315  bracket = Bracket_Windows;
316  else
317 #endif // __WINDOWS__
318  if ( n == strlen - 1 ) {
319  bracket = Bracket_None;
320  }
321  else {
322  switch ( str[n + 1].GetValue() ) {
323  case wxT('('):
324  bracket = Bracket_Normal;
325  str_n = str[++n]; // skip the bracket
326  break;
327 
328  case wxT('{'):
329  bracket = Bracket_Curly;
330  str_n = str[++n]; // skip the bracket
331  break;
332 
333  default:
334  bracket = Bracket_None;
335  }
336  }
337 
338  size_t m = n + 1;
339  wxUniChar str_m = str[m];
340 
341  while ( m < strlen && (wxIsalnum(str_m) || str_m == wxT('_')) )
342  str_m = str[++m];
343 
344  wxString strVarName(str.c_str() + n + 1, m - n - 1);
345 
346 #ifdef __WXWINCE__
347  const bool expanded = false;
348 #else
349  // NB: use wxGetEnv instead of wxGetenv as otherwise variables
350  // set through wxSetEnv may not be read correctly!
351  bool expanded = false;
352  wxString tmp;
353  if (wxGetEnv(strVarName, &tmp))
354  {
355  strResult += tmp;
356  expanded = true;
357  }
358  else
359 #endif
360  {
361  // variable doesn't exist => don't change anything
362 #ifdef __WINDOWS__
363  if ( bracket != Bracket_Windows )
364 #endif
365  if ( bracket != Bracket_None )
366  strResult << str[n - 1];
367  strResult << str_n << strVarName;
368  }
369 
370  // check the closing bracket
371  if ( bracket != Bracket_None ) {
372  if ( m == strlen || str_m != (wxChar)bracket ) {
373  // under MSW it's common to have '%' characters in the registry
374  // and it's annoying to have warnings about them each time, so
375  // ignroe them silently if they are not used for env vars
376  //
377  // under Unix, OTOH, this warning could be useful for the user to
378  // understand why isn't the variable expanded as intended
379 #ifndef __WINDOWS__
380  wxLogWarning(_("Environment variables expansion failed: missing '%c' at position %u in '%s'."),
381  (char)bracket, (unsigned int) (m + 1), str.c_str());
382 #endif // __WINDOWS__
383  }
384  else {
385  // skip closing bracket unless the variables wasn't expanded
386  if ( !expanded )
387  strResult << (wxChar)bracket;
388  str_m = str[++m];
389  }
390  }
391 
392  n = m - 1; // skip variable name
393  str_n = str[n];
394  }
395  break;
396 
397  case wxT('\\'):
398  // backslash can be used to suppress special meaning of % and $
399  if ( n != strlen - 1 && (str[n + 1] == wxT('%') || str[n + 1] == wxT('$')) ) {
400  str_n = str[++n];
401  strResult += str_n;
402 
403  break;
404  }
405  //else: fall through
406 
407  default:
408  strResult += str_n;
409  }
410  }
411 
412  return strResult;
413 }
414 
415 
416 #include <ki_mutex.h>
417 const wxString ExpandEnvVarSubstitutions( const wxString& aString )
418 {
419  // wxGetenv( wchar_t* ) is not re-entrant on linux.
420  // Put a lock on multithreaded use of wxGetenv( wchar_t* ), called from wxEpandEnvVars(),
421  static MUTEX getenv_mutex;
422 
423  MUTLOCK lock( getenv_mutex );
424 
425  // We reserve the right to do this another way, by providing our own member
426  // function.
427  return KIwxExpandEnvVars( aString );
428 }
429 
430 
431 const wxString ResolveUriByEnvVars( const wxString& aUri )
432 {
433  // URL-like URI: return as is.
434  wxURL url( aUri );
435  if( url.GetError() == wxURL_NOERR )
436  return aUri;
437 
438  // Otherwise, the path points to a local file. Resolve environment
439  // variables if any.
440  return ExpandEnvVarSubstitutions( aUri );
441 }
442 
443 
444 bool EnsureFileDirectoryExists( wxFileName* aTargetFullFileName,
445  const wxString& aBaseFilename,
446  REPORTER* aReporter )
447 {
448  wxString msg;
449  wxString baseFilePath = wxFileName( aBaseFilename ).GetPath();
450 
451  // make aTargetFullFileName path, which is relative to aBaseFilename path (if it is not
452  // already an absolute path) absolute:
453  if( !aTargetFullFileName->MakeAbsolute( baseFilePath ) )
454  {
455  if( aReporter )
456  {
457  msg.Printf( _( "Cannot make path \"%s\" absolute with respect to \"%s\"." ),
458  GetChars( aTargetFullFileName->GetPath() ),
459  GetChars( baseFilePath ) );
460  aReporter->Report( msg, REPORTER::RPT_ERROR );
461  }
462 
463  return false;
464  }
465 
466  // Ensure the path of aTargetFullFileName exists, and create it if needed:
467  wxString outputPath( aTargetFullFileName->GetPath() );
468 
469  if( !wxFileName::DirExists( outputPath ) )
470  {
471  if( wxMkdir( outputPath ) )
472  {
473  if( aReporter )
474  {
475  msg.Printf( _( "Output directory \"%s\" created.\n" ), GetChars( outputPath ) );
476  aReporter->Report( msg, REPORTER::RPT_INFO );
477  return true;
478  }
479  }
480  else
481  {
482  if( aReporter )
483  {
484  msg.Printf( _( "Cannot create output directory \"%s\".\n" ),
485  GetChars( outputPath ) );
486  aReporter->Report( msg, REPORTER::RPT_ERROR );
487  }
488 
489  return false;
490  }
491  }
492 
493  return true;
494 }
495 
496 
497 #ifdef __WXMAC__
498 wxString GetOSXKicadUserDataDir()
499 {
500  // According to wxWidgets documentation for GetUserDataDir:
501  // Mac: ~/Library/Application Support/appname
502  wxFileName udir( wxStandardPaths::Get().GetUserDataDir(), wxEmptyString );
503 
504  // Since appname is different if started via launcher or standalone binary
505  // map all to "kicad" here
506  udir.RemoveLastDir();
507  udir.AppendDir( wxT( "kicad" ) );
508 
509  return udir.GetPath();
510 }
511 
512 
513 wxString GetOSXKicadMachineDataDir()
514 {
515  return wxT( "/Library/Application Support/kicad" );
516 }
517 
518 
519 wxString GetOSXKicadDataDir()
520 {
521  // According to wxWidgets documentation for GetDataDir:
522  // Mac: appname.app/Contents/SharedSupport bundle subdirectory
523  wxFileName ddir( wxStandardPaths::Get().GetDataDir(), wxEmptyString );
524 
525  // This must be mapped to main bundle for everything but kicad.app
526  const wxArrayString dirs = ddir.GetDirs();
527  if( dirs[dirs.GetCount() - 3] != wxT( "kicad.app" ) )
528  {
529  // Bundle structure resp. current path is
530  // kicad.app/Contents/Applications/<standalone>.app/Contents/SharedSupport
531  // and will be mapped to
532  // kicad.app/Contents/SharedSupprt
533  ddir.RemoveLastDir();
534  ddir.RemoveLastDir();
535  ddir.RemoveLastDir();
536  ddir.RemoveLastDir();
537  ddir.AppendDir( wxT( "SharedSupport" ) );
538  }
539 
540  return ddir.GetPath();
541 }
542 #endif
543 
544 // add this only if it is not in wxWidgets (for instance before 3.1.0)
545 #ifdef USE_KICAD_WXSTRING_HASH
546 size_t std::hash<wxString>::operator()( const wxString& s ) const
547 {
548  return std::hash<std::wstring>{}( s.ToStdWstring() );
549 }
550 #endif
551 
552 
553 #ifdef USE_KICAD_WXPOINT_LESS
554 bool std::less<wxPoint>::operator()( const wxPoint& aA, const wxPoint& aB ) const
555 {
556  if( aA.x == aB.x )
557  return aA.y < aB.y;
558 
559  return aA.x < aB.x;
560 }
561 #endif
562 
563 
579 WX_FILENAME::WX_FILENAME( const wxString& aPath, const wxString& aFilename ) :
580  m_fn( aPath, aFilename ),
581  m_path( aPath ),
582  m_fullName( aFilename )
583 { }
584 
585 
586 void WX_FILENAME::SetFullName( const wxString& aFileNameAndExtension )
587 {
588  m_fullName = aFileNameAndExtension;
589 }
590 
591 
592 wxString WX_FILENAME::GetName() const
593 {
594  size_t dot = m_fullName.find_last_of( wxT( '.' ) );
595  return m_fullName.substr( 0, dot );
596 }
597 
598 
599 wxString WX_FILENAME::GetFullName() const
600 {
601  return m_fullName;
602 }
603 
604 
605 wxString WX_FILENAME::GetPath() const
606 {
607  return m_path;
608 }
609 
610 
611 wxString WX_FILENAME::GetFullPath() const
612 {
613  return m_path + wxT( '/' ) + m_fullName;
614 }
615 
616 
617 // Write locally-cached values to the wxFileName. MUST be called before using m_fn.
619 {
620  size_t dot = m_fullName.find_last_of( wxT( '.' ) );
621  m_fn.SetName( m_fullName.substr( 0, dot ) );
622  m_fn.SetExt( m_fullName.substr( dot + 1 ) );
623 }
624 
625 
627 {
628  resolve();
629 
630  if( m_fn.FileExists() )
631  return m_fn.GetModificationTime().GetValue().GetValue();
632 
633  return 0;
634 }
635 
636 
643 bool matchWild( const char* pat, const char* text, bool dot_special )
644 {
645  if ( !*text )
646  {
647  /* Match if both are empty. */
648  return !*pat;
649  }
650 
651  const char *m = pat,
652  *n = text,
653  *ma = NULL,
654  *na = NULL;
655  int just = 0,
656  acount = 0,
657  count = 0;
658 
659  if (dot_special && (*n == '.'))
660  {
661  /* Never match so that hidden Unix files
662  * are never found. */
663  return false;
664  }
665 
666  for (;;)
667  {
668  if (*m == '*')
669  {
670  ma = ++m;
671  na = n;
672  just = 1;
673  acount = count;
674  }
675  else if (*m == '?')
676  {
677  m++;
678  if (!*n++)
679  return false;
680  }
681  else
682  {
683  if (*m == '\\')
684  {
685  m++;
686  /* Quoting "nothing" is a bad thing */
687  if (!*m)
688  return false;
689  }
690  if (!*m)
691  {
692  /*
693  * If we are out of both strings or we just
694  * saw a wildcard, then we can say we have a
695  * match
696  */
697  if (!*n)
698  return true;
699  if (just)
700  return true;
701  just = 0;
702  goto not_matched;
703  }
704  /*
705  * We could check for *n == NULL at this point, but
706  * since it's more common to have a character there,
707  * check to see if they match first (m and n) and
708  * then if they don't match, THEN we can check for
709  * the NULL of n
710  */
711  just = 0;
712  if (*m == *n)
713  {
714  m++;
715  count++;
716  n++;
717  }
718  else
719  {
720 
721  not_matched:
722 
723  /*
724  * If there are no more characters in the
725  * string, but we still need to find another
726  * character (*m != NULL), then it will be
727  * impossible to match it
728  */
729  if (!*n)
730  return false;
731 
732  if (ma)
733  {
734  m = ma;
735  n = ++na;
736  count = acount;
737  }
738  else
739  return false;
740  }
741  }
742  }
743 }
744 
745 
750 #if wxUSE_DATETIME && defined(__WIN32__) && !defined(__WXMICROWIN__)
751 
752 // Convert between wxDateTime and FILETIME which is a 64-bit value representing
753 // the number of 100-nanosecond intervals since January 1, 1601 UTC.
754 //
755 // This is the offset between FILETIME epoch and the Unix/wxDateTime Epoch.
756 static wxInt64 EPOCH_OFFSET_IN_MSEC = wxLL(11644473600000);
757 
758 static void ConvertFileTimeToWx(wxDateTime *dt, const FILETIME &ft)
759 {
760  wxLongLong t(ft.dwHighDateTime, ft.dwLowDateTime);
761  t /= 10000; // Convert hundreds of nanoseconds to milliseconds.
762  t -= EPOCH_OFFSET_IN_MSEC;
763 
764  *dt = wxDateTime(t);
765 }
766 
767 #endif // wxUSE_DATETIME && __WIN32__
768 
769 
779 long long TimestampDir( const wxString& aDirPath, const wxString& aFilespec )
780 {
781  long long timestamp = 0;
782 
783 #if defined(__WIN32__)
784  // Win32 version.
785  // Save time by not searching for each path twice: once in wxDir.GetNext() and once in
786  // wxFileName.GetModificationTime(). Also cuts out wxWidgets' string-matching and case
787  // conversion by staying on the MSW side of things.
788  std::wstring filespec( aDirPath.t_str() );
789  filespec += '\\';
790  filespec += aFilespec.t_str();
791 
792  WIN32_FIND_DATA findData;
793  wxDateTime lastModDate;
794 
795  HANDLE fileHandle = ::FindFirstFile( filespec.data(), &findData );
796 
797  if( fileHandle != INVALID_HANDLE_VALUE )
798  {
799  do
800  {
801  ConvertFileTimeToWx( &lastModDate, findData.ftLastWriteTime );
802  timestamp += lastModDate.GetValue().GetValue();
803  }
804  while ( FindNextFile( fileHandle, &findData ) != 0);
805  }
806 
807  FindClose( fileHandle );
808 #else
809  // POSIX version.
810  // Save time by not converting between encodings -- do everything on the file-system side.
811  std::string filespec( aFilespec.fn_str() );
812  std::string dir_path( aDirPath.fn_str() );
813 
814  DIR* dir = opendir( dir_path.c_str() );
815 
816  if( dir )
817  {
818  for( dirent* dir_entry = readdir( dir ); dir_entry; dir_entry = readdir( dir ) )
819  {
820  if( !matchWild( filespec.c_str(), dir_entry->d_name, true ) )
821  continue;
822 
823  std::string entry_path = dir_path + '/' + dir_entry->d_name;
824  struct stat entry_stat;
825 
826  wxCRT_Lstat( entry_path.c_str(), &entry_stat );
827 
828  // Timestamp the source file, not the symlink
829  if( S_ISLNK( entry_stat.st_mode ) ) // wxFILE_EXISTS_SYMLINK
830  {
831  char buffer[ PATH_MAX + 1 ];
832  ssize_t pathLen = readlink( entry_path.c_str(), buffer, PATH_MAX );
833 
834  if( pathLen > 0 )
835  {
836  buffer[ pathLen ] = '\0';
837  entry_path = dir_path + buffer;
838 
839  wxCRT_Lstat( entry_path.c_str(), &entry_stat );
840  }
841  }
842 
843  if( S_ISREG( entry_stat.st_mode ) ) // wxFileExists()
844  timestamp += entry_stat.st_mtime * 1000;
845  }
846 
847  closedir( dir );
848  }
849 #endif
850 
851  return timestamp;
852 }
853 
854 
void wxStringSplit(const wxString &aText, wxArrayString &aStrings, wxChar aSplitter)
Split aString to a string list separated at aSplitter.
Definition: common.cpp:158
WX_FILENAME(const wxString &aPath, const wxString &aFilename)
Performance enhancements to file and directory operations.
Definition: common.cpp:579
wxString GetFullName() const
Definition: common.cpp:599
int ProcessExecute(const wxString &aCommandLine, int aFlags, wxProcess *callback)
Run a command in a child process.
Definition: common.cpp:181
~LOCALE_IO()
Definition: common.cpp:75
long timestamp_t
timestamp_t is our type to represent unique IDs for all kinds of elements; historically simply the ti...
Definition: common.h:52
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 wxString ResolveUriByEnvVars(const wxString &aUri)
Replace any environment variables in file-path uris (leaving network-path URIs alone).
Definition: common.cpp:431
Implementation of conversion functions that require both schematic and board internal units...
double RoundTo0(double x, double precision)
Round to the nearest precision.
Definition: common.cpp:203
wxString KIwxExpandEnvVars(const wxString &str)
Definition: common.cpp:296
wxConfigBase * GetNewConfig(const wxString &aProgName)
Create a new wxConfig so we can put configuration files in a more proper place for each platform...
Definition: common.cpp:226
boost::interprocess::interprocess_mutex MUTEX
Establish KiCad MUTEX choices here in this file: typedef MUTEX and typedef MUTLOCK.
Definition: ki_mutex.h:42
wxString m_path
Definition: common.h:411
Class REPORTER is a pure virtual class used to derive REPORTER objects from.
Definition: reporter.h:61
void SetFullName(const wxString &aFileNameAndExtension)
Definition: common.cpp:586
const string & str
Definition: json11.cpp:596
This file contains miscellaneous commonly used macros and functions.
wxSize GetTextSize(const wxString &aSingleLine, wxWindow *aWindow)
Return the size of aSingleLine of text when it is rendered in aWindow using whatever font is currentl...
Definition: common.cpp:86
wxFileName m_fn
Definition: common.h:410
wxString GetPath() const
Definition: common.cpp:605
static std::atomic< unsigned int > m_c_count
Definition: common.h:187
void SelectReferenceNumber(wxTextEntry *aTextEntry)
Select the number (or "?") in a reference for ease of editing.
Definition: common.cpp:130
long long GetTimestamp()
Definition: common.cpp:626
timestamp_t GetNewTimeStamp()
Definition: common.cpp:187
void resolve()
Definition: common.cpp:618
bool EnsureTextCtrlWidth(wxTextCtrl *aCtrl, const wxString *aString)
Set the minimum pixel width on a text control in order to make a text string be fully visible within ...
Definition: common.cpp:101
const wxString ExpandEnvVarSubstitutions(const wxString &aString)
Replace any environment variable references with their values.
Definition: common.cpp:417
bool EnsureFileDirectoryExists(wxFileName *aTargetFullFileName, const wxString &aBaseFilename, REPORTER *aReporter)
Make aTargetFullFileName absolute and create the path of this file if it doesn&#39;t yet exist...
Definition: common.cpp:444
Bracket
Definition: common.cpp:281
Base window classes and related definitions.
long long TimestampDir(const wxString &aDirPath, const wxString &aFilespec)
A copy of ConvertFileTimeToWx() because wxWidgets left it as a static function private to src/common/...
Definition: common.cpp:779
LOCALE_IO()
Definition: common.cpp:62
wxString GetName() const
Definition: common.cpp:592
wxString GetKicadConfigPath()
Return the user configuration path used to store KiCad&#39;s configuration files.
Definition: common.cpp:238
bool matchWild(const char *pat, const char *text, bool dot_special)
A copy of wxMatchWild(), which wxWidgets attributes to Douglas A.
Definition: common.cpp:643
bool operator()(const wxPoint &aA, const wxPoint &aB) const
Definition: common.cpp:554
boost::interprocess::scoped_lock< MUTEX > MUTLOCK
Definition: ki_mutex.h:43
static const wxChar * GetChars(const wxString &s)
Function GetChars returns a wxChar* to the actual wxChar* data within a wxString, and is helpful for ...
Definition: macros.h:92
see class PGM_BASE
wxString GetFullPath() const
Definition: common.cpp:611
The common library.
virtual REPORTER & Report(const wxString &aText, SEVERITY aSeverity=RPT_UNDEFINED)=0
Function Report is a pure virtual function to override in the derived object.
size_t operator()(const wxString &s) const
Definition: common.cpp:546
Basic classes for most KiCad items.
wxString m_fullName
Definition: common.h:412
COLOR4D g_GhostColor
Global variables definitions.
Definition: common.cpp:57
std::string m_user_locale
Definition: common.h:191
Class COLOR4D is the color representation with 4 components: red, green, blue, alpha.
Definition: color4d.h:39