SAGA API  v9.7
api_file.cpp
Go to the documentation of this file.
1 
3 // //
4 // SAGA //
5 // //
6 // System for Automated Geoscientific Analyses //
7 // //
8 // Application Programming Interface //
9 // //
10 // Library: SAGA_API //
11 // //
12 //-------------------------------------------------------//
13 // //
14 // api_file.cpp //
15 // //
16 // Copyright (C) 2005 by Olaf Conrad //
17 // //
18 //-------------------------------------------------------//
19 // //
20 // This file is part of 'SAGA - System for Automated //
21 // Geoscientific Analyses'. //
22 // //
23 // This library is free software; you can redistribute //
24 // it and/or modify it under the terms of the GNU Lesser //
25 // General Public License as published by the Free //
26 // Software Foundation, either version 2.1 of the //
27 // License, or (at your option) any later version. //
28 // //
29 // This library is distributed in the hope that it will //
30 // be useful, but WITHOUT ANY WARRANTY; without even the //
31 // implied warranty of MERCHANTABILITY or FITNESS FOR A //
32 // PARTICULAR PURPOSE. See the GNU Lesser General Public //
33 // License for more details. //
34 // //
35 // You should have received a copy of the GNU Lesser //
36 // General Public License along with this program; if //
37 // not, see <http://www.gnu.org/licenses/>. //
38 // //
39 //-------------------------------------------------------//
40 // //
41 // contact: Olaf Conrad //
42 // Institute of Geography //
43 // University of Goettingen //
44 // Goldschmidtstr. 5 //
45 // 37077 Goettingen //
46 // Germany //
47 // //
48 // e-mail: oconrad@saga-gis.org //
49 // //
51 
52 //---------------------------------------------------------
53 #include <wx/utils.h>
54 #include <wx/filename.h>
55 #include <wx/dir.h>
56 #include <wx/wxcrtvararg.h>
57 #include <wx/wfstream.h>
58 #include <wx/zipstrm.h>
59 #include <wx/tarstrm.h>
60 #include <wx/txtstrm.h>
61 #include <wx/log.h>
62 #include <wx/version.h>
63 
64 #include "api_core.h"
65 
66 
68 // //
69 // //
70 // //
72 
73 //---------------------------------------------------------
74 #define m_pStream_Base ((wxStreamBase *)m_pStream)
75 #define m_pStream_I ((wxFFileInputStream *)m_pStream)
76 #define m_pStream_O ((wxFFileOutputStream *)m_pStream)
77 #define m_pStream_IO ((wxFFileStream *)m_pStream)
78 
79 
81 // //
82 // //
83 // //
85 
86 //---------------------------------------------------------
88 {
90 }
91 
92 //---------------------------------------------------------
93 CSG_File::CSG_File(const SG_Char *FileName, int Mode, bool bBinary, int Encoding)
94 {
96 
97  Open(FileName, Mode, bBinary, Encoding);
98 }
99 
100 //---------------------------------------------------------
102 {
103  Close();
104 }
105 
106 
108 // //
110 
111 //---------------------------------------------------------
112 bool CSG_File::Open(const SG_Char *_FileName, int Mode, bool bBinary, int Encoding)
113 {
114  Close();
115 
116  if( !_FileName ) { return( false ); } CSG_String FileName(_FileName);
117 
118  CSG_String Path(SG_File_Get_Path(FileName));
119 
120  if( !Path.is_Empty() && !SG_Dir_Exists(Path) )
121  {
122  return( false );
123  }
124 
125  if( Mode == SG_FILE_R && !SG_File_Exists(FileName) )
126  {
127  return( false );
128  }
129 
130  m_FileName = FileName; m_Mode = Mode;
131 
132  Set_Encoding(Encoding);
133 
134  switch( m_Mode )
135  {
136  case SG_FILE_W:
137  m_pStream = new wxFFileOutputStream(FileName.c_str(), bBinary ? "wb" : "w");
138  break;
139 
140  case SG_FILE_R:
141  m_pStream = new wxFFileInputStream (FileName.c_str(), bBinary ? "rb" : "r");
142  break;
143 
144  default: // SG_FILE_RW
145  m_pStream = new wxFFileStream (FileName.c_str(), SG_File_Exists(FileName)
146  ? (bBinary ? "r+b" : "r+")
147  : (bBinary ? "w+b" : "w+")
148  );
149  break;
150  }
151 
152  if( !m_pStream || !m_pStream_Base->IsOk() )
153  {
154  Close();
155 
156  return( false );
157  }
158 
159  return( true );
160 }
161 
162 //---------------------------------------------------------
163 bool CSG_File::Close(void)
164 {
165  if( m_pStream )
166  {
167  delete(m_pStream_Base);
168 
169  m_pStream = NULL;
170  }
171 
173 
174  return( true );
175 }
176 
177 
179 // //
181 
182 //---------------------------------------------------------
184 {
185  m_pStream = NULL;
186  m_pConvert = NULL;
188 }
189 
190 //---------------------------------------------------------
191 bool CSG_File::Set_Encoding(int Encoding)
192 {
193  if( m_pConvert )
194  {
195  if( m_pConvert != &wxConvLocal
196  && m_pConvert != &wxConvLibc
197  && m_pConvert != &wxConvUTF7
198  && m_pConvert != &wxConvUTF8 )
199  {
200  delete((wxMBConv *)m_pConvert);
201  }
202 
203  m_pConvert = NULL;
204  }
205 
206  m_Encoding = Encoding;
207 
208  switch( Encoding )
209  {
210  case SG_FILE_ENCODING_ANSI : break;
211  case SG_FILE_ENCODING_UTF7 : m_pConvert = &wxConvUTF7 ; break;
212  case SG_FILE_ENCODING_UTF8 : m_pConvert = &wxConvUTF8 ; break;
213  case SG_FILE_ENCODING_UTF16LE: m_pConvert = new wxMBConvUTF16LE(); break;
214  case SG_FILE_ENCODING_UTF16BE: m_pConvert = new wxMBConvUTF16BE(); break;
215  case SG_FILE_ENCODING_UTF32LE: m_pConvert = new wxMBConvUTF32LE(); break;
216  case SG_FILE_ENCODING_UTF32BE: m_pConvert = new wxMBConvUTF32BE(); break;
217  default : break;
218  }
219 
220  return( true );
221 }
222 
223 
225 // //
227 
228 //---------------------------------------------------------
230 {
231  return( m_pStream ? m_pStream_Base->GetLength() : -1 );
232 }
233 
234 //---------------------------------------------------------
235 bool CSG_File::is_EOF(void) const
236 {
237  return( is_Reading() && (m_Mode == SG_FILE_R ? m_pStream_I->Eof() : m_pStream_IO->Eof()) );
238 }
239 
240 //---------------------------------------------------------
241 bool CSG_File::Seek(sLong Offset, int Origin) const
242 {
243  if( m_pStream )
244  {
245  wxSeekMode Seek = Origin == SG_FILE_CURRENT ? wxFromCurrent : Origin == SG_FILE_END ? wxFromEnd : wxFromStart;
246 
247  switch( m_Mode )
248  {
249  case SG_FILE_R : return( m_pStream_I ->SeekI(Offset, Seek) != wxInvalidOffset );
250  case SG_FILE_W : return( m_pStream_O ->SeekO(Offset, Seek) != wxInvalidOffset );
251  default : return( m_pStream_IO->SeekI(Offset, Seek) != wxInvalidOffset
252  && m_pStream_IO->SeekO(Offset, Seek) != wxInvalidOffset );
253  }
254  }
255 
256  return( false );
257 }
258 
259 //---------------------------------------------------------
260 bool CSG_File::Seek_Start(void) const { return( Seek(0, SEEK_SET) ); }
261 bool CSG_File::Seek_End (void) const { return( Seek(0, SEEK_END) ); }
262 
263 //---------------------------------------------------------
265 {
266  if( m_pStream )
267  {
268  switch( m_Mode )
269  {
270  case SG_FILE_R : return( m_pStream_I ->TellI() );
271  case SG_FILE_W : return( m_pStream_O ->TellO() );
272  default : return( m_pStream_IO->TellI() );
273  }
274  }
275 
276  return( -1 );
277 }
278 
279 //---------------------------------------------------------
280 bool CSG_File::Flush(void)
281 {
282  return( m_pStream_O && m_pStream_O->GetFile()->Flush() );
283 }
284 
285 //---------------------------------------------------------
286 int CSG_File::Printf(const char *Format, ...)
287 {
288  if( !is_Writing() )
289  {
290  return( 0 );
291  }
292 
293  wxString String;
294 
295 #ifdef _SAGA_LINUX
296  wxString _Format(Format); _Format.Replace("%s", "%ls"); // workaround as we only use wide characters since wx 2.9.4 so interpret strings as multibyte
297  va_list argptr; va_start(argptr, _Format);
298  int Result = String.PrintfV(_Format, argptr);
299 #else
300  va_list argptr; va_start(argptr, Format);
301  int Result = String.PrintfV(Format, argptr);
302 #endif
303  va_end(argptr);
304 
305  Write(&String);
306 
307  return( Result );
308 }
309 
310 //---------------------------------------------------------
311 int CSG_File::Printf(const wchar_t *Format, ...)
312 {
313  if( !is_Writing() )
314  {
315  return( 0 );
316  }
317 
318  wxString String;
319 
320 #ifdef _SAGA_LINUX
321  wxString _Format(Format); _Format.Replace("%s", "%ls"); // workaround as we only use wide characters since wx 2.9.4 so interpret strings as multibyte
322  va_list argptr; va_start(argptr, _Format);
323  int Result = String.PrintfV(_Format, argptr);
324 #else
325  va_list argptr; va_start(argptr, Format);
326  int Result = String.PrintfV(Format, argptr);
327 #endif
328 
329  va_end(argptr);
330 
331  Write(&String);
332 
333  return( Result );
334 }
335 
336 //---------------------------------------------------------
337 size_t CSG_File::Read(void *Buffer, size_t Size, size_t Count) const
338 {
339  return( !is_Reading() || Size == 0 || Count == 0 ? 0 : m_Mode == SG_FILE_R
340  ? m_pStream_I ->Read(Buffer, Size * Count).LastRead() / Size
341  : m_pStream_IO->Read(Buffer, Size * Count).LastRead() / Size
342  );
343 }
344 
345 size_t CSG_File::Read(CSG_String &Buffer, size_t Size) const
346 {
347  if( is_Reading() && Size > 0 )
348  {
349  CSG_Buffer s(Size + 1);
350 
351  size_t i = Read(s.Get_Data(), sizeof(char), Size);
352 
353  if( i > 0 )
354  {
355  s[Size] = '\0';
356 
357  Buffer = s.Get_Data();
358 
359  return( i );
360  }
361  }
362 
363  Buffer.Clear();
364 
365  return( 0 );
366 }
367 
368 //---------------------------------------------------------
369 size_t CSG_File::Write(void *Buffer, size_t Size, size_t Count) const
370 {
371  return( !is_Writing() || Size == 0 || Count == 0 ? 0 : m_Mode == SG_FILE_W
372  ? m_pStream_O ->Write(Buffer, Size * Count).LastWrite()
373  : m_pStream_IO->Write(Buffer, Size * Count).LastWrite()
374  );
375 }
376 
377 size_t CSG_File::Write(const CSG_String &Buffer) const
378 {
379  if( m_pConvert )
380  {
381  wxString _Buffer(Buffer.w_str());
382 
383  const wxScopedCharBuffer s(_Buffer.mb_str(*((wxMBConv *)m_pConvert)));
384 
385  return( Write((void *)s.data(), sizeof(char), s.length()) );
386  }
387 
388  CSG_Buffer s(Buffer.to_ASCII()); // returns NULL terminated char sequence, Get_Size() count includes terminating NULL!!!
389 
390  return( s.Get_Size() > 1 ? Write((void *)s.Get_Data(), sizeof(char), s.Get_Size() - 1) : 0 );
391 }
392 
393 //---------------------------------------------------------
394 bool CSG_File::Read_Line(CSG_String &sLine) const
395 {
396  if( !is_Reading() || is_EOF() )
397  {
398  return( false );
399  }
400 
401  wxString s;
402 
403  if( m_pConvert )
404  {
405  if( m_Mode == SG_FILE_R )
406  {
407  wxTextInputStream Stream(*m_pStream_I , " \t", *((wxMBConv *)m_pConvert)); s = Stream.ReadLine();
408  }
409  else
410  {
411  wxTextInputStream Stream(*m_pStream_IO, " \t", *((wxMBConv *)m_pConvert)); s = Stream.ReadLine();
412  }
413  }
414  else
415  {
416  if( m_Mode == SG_FILE_R )
417  {
418  wxTextInputStream Stream(*m_pStream_I , " \t" ); s = Stream.ReadLine();
419  }
420  else
421  {
422  wxTextInputStream Stream(*m_pStream_IO, " \t" ); s = Stream.ReadLine();
423  }
424  }
425 
426  sLine = CSG_String(&s);
427 
428  return( !sLine.is_Empty() || !is_EOF() );
429 }
430 
431 //---------------------------------------------------------
432 int CSG_File::Read_Char(void) const
433 {
434  return( !is_Reading() ? 0 : m_Mode == SG_FILE_R ? m_pStream_I->GetC() : m_pStream_IO->GetC() );
435 }
436 
437 //---------------------------------------------------------
438 int CSG_File::Read_Int(bool bByteOrderBig) const
439 {
440  int Value = 0;
441 
442  if( Read(&Value, sizeof(Value)) == 1 )
443  {
444  if( bByteOrderBig )
445  {
446  SG_Swap_Bytes(&Value, sizeof(Value));
447  }
448  }
449 
450  return( Value );
451 }
452 
453 bool CSG_File::Write_Int(int Value, bool bByteOrderBig)
454 {
455  if( bByteOrderBig )
456  {
457  SG_Swap_Bytes(&Value, sizeof(Value));
458  }
459 
460  return( Write(&Value, sizeof(Value)) == sizeof(Value) );
461 }
462 
463 //---------------------------------------------------------
464 double CSG_File::Read_Double(bool bByteOrderBig) const
465 {
466  double Value = 0;
467 
468  if( Read(&Value, sizeof(Value)) == 1 )
469  {
470  if( bByteOrderBig )
471  {
472  SG_Swap_Bytes(&Value, sizeof(Value));
473  }
474  }
475 
476  return( Value );
477 }
478 
479 bool CSG_File::Write_Double(double Value, bool bByteOrderBig)
480 {
481  if( bByteOrderBig )
482  {
483  SG_Swap_Bytes(&Value, sizeof(Value));
484  }
485 
486  return( Write(&Value, sizeof(Value)) == sizeof(Value) );
487 }
488 
489 //---------------------------------------------------------
490 bool CSG_File::Scan(int &Value) const
491 {
492  if( is_Reading() )
493  {
494  int c; while( !is_EOF() && isspace(c = Read_Char()) ); // remove leading white space
495 
496  if( isdigit(c) || strchr("-+", c) )
497  {
498  CSG_String s = (char)c;
499 
500  while( !is_EOF() && isdigit(c = Read_Char()) )
501  {
502  s += (char)c;
503  }
504 
505  return( s.asInt(Value) );
506  }
507  }
508 
509  return( false );
510 }
511 
512 bool CSG_File::Scan(double &Value) const
513 {
514  if( is_Reading() )
515  {
516  int c; while( !is_EOF() && isspace(c = Read_Char()) ); // remove leading white space
517 
518  if( isdigit(c) || strchr("-+.,eE", c) )
519  {
520  CSG_String s = (char)c;
521 
522  while( !is_EOF() && (isdigit(c = Read_Char()) || strchr(".,eE", c) || strchr("", c)) )
523  {
524  s += (char)c;
525  }
526 
527  return( s.asDouble(Value) );
528  }
529  }
530 
531  return( false );
532 }
533 
534 bool CSG_File::Scan(CSG_String &Value, SG_Char Separator) const
535 {
536  if( is_Reading() && !is_EOF() )
537  {
538  Value.Clear();
539 
540  int c; while( !is_EOF() && (c = Read_Char()) != Separator && c != EOF )
541  {
542  Value += (char)c;
543  }
544 
545  return( true );
546  }
547 
548  return( false );
549 }
550 
551 //---------------------------------------------------------
552 int CSG_File::Scan_Int(void) const
553 {
554  int Value; return( Scan(Value) ? Value : 0 );
555 }
556 
557 double CSG_File::Scan_Double(void) const
558 {
559  double Value; return( Scan(Value) ? Value : 0.0 );
560 }
561 
563 {
564  CSG_String Value; Scan(Value, Separator); return( Value );
565 }
566 
567 
569 // //
570 // //
571 // //
573 
574 //---------------------------------------------------------
576 {
577  On_Construction();
578 }
579 
580 //---------------------------------------------------------
581 CSG_Archive::CSG_Archive(const SG_Char *FileName, int Mode, int Encoding)
582 {
583  On_Construction();
584 
585  Open(FileName, Mode, Encoding);
586 }
587 
588 //---------------------------------------------------------
590 {
591  Close();
592 }
593 
594 //---------------------------------------------------------
595 bool CSG_Archive::Open(const SG_Char *_FileName, int Mode, int Encoding)
596 {
597  Close();
598 
599  if( !_FileName ) { return( false ); } CSG_String FileName(_FileName);
600 
601  if( SG_File_Cmp_Extension(FileName, "tar") )
602  {
604  }
605  else // if( SG_File_Cmp_Extension(FileName, "zip") )
606  {
608  }
609 
610  m_Archive = FileName;
611 
613 
614  if( !Path.is_Empty() && !SG_Dir_Exists(Path) )
615  {
616  return( false );
617  }
618 
619  if( Mode == SG_FILE_R && !SG_File_Exists(m_Archive) )
620  {
621  return( false );
622  }
623 
624  wxLogNull logNo; // suppress user notification dialog for invalid zip files
625 
626  m_Mode = Mode; Set_Encoding(Encoding);
627 
628  if( Mode == SG_FILE_W )
629  {
630  if( is_Zip() )
631  {
632  m_pStream = new wxZipOutputStream(new wxFileOutputStream(m_Archive.c_str()));
633  }
634  else
635  {
636  m_pStream = new wxTarOutputStream(new wxFileOutputStream(m_Archive.c_str()));
637  }
638  }
639  else if( Mode == SG_FILE_R && SG_File_Exists(m_Archive) )
640  {
641  if( is_Zip() )
642  {
643  m_pStream = new wxZipInputStream (new wxFileInputStream (m_Archive.c_str()));
644  }
645  else
646  {
647  m_pStream = new wxTarInputStream (new wxFileInputStream (m_Archive.c_str()));
648  }
649  }
650 
651  if( !m_pStream || !m_pStream_Base->IsOk() )
652  {
653  Close();
654 
655  return( false );
656  }
657 
658  if( is_Reading() )
659  {
660  wxArchiveEntry *pEntry;
661 
662  while( (pEntry = ((wxArchiveInputStream *)m_pStream)->GetNextEntry()) != NULL )
663  {
664  m_Files += pEntry;
665  }
666  }
667 
668  return( true );
669 }
670 
671 //---------------------------------------------------------
673 {
674  for(sLong i=0; i<m_Files.Get_Size(); i++)
675  {
676  if( is_Zip() )
677  {
678  delete((wxZipEntry *)m_Files[i]);
679  }
680  else
681  {
682  delete((wxTarEntry *)m_Files[i]);
683  }
684  }
685 
686  m_Files.Set_Array(0);
687 
688  m_Archive.Clear();
689 
690  return( CSG_File::Close() );
691 }
692 
693 //---------------------------------------------------------
695 {
696  return( is_Writing() && Name && ((wxArchiveOutputStream *)m_pStream)->PutNextDirEntry(Name) );
697 }
698 
699 //---------------------------------------------------------
700 bool CSG_Archive::Add_File(const SG_Char *Name, bool bBinary)
701 {
702  if( is_Writing() && Name )
703  {
704  wxArchiveEntry *pEntry = NULL;
705 
706  if( is_Zip() )
707  {
708  pEntry = new wxZipEntry(Name);
709 
710  ((wxZipEntry *)pEntry)->SetIsText(bBinary == false);
711 
712  #if wxCHECK_VERSION(3, 1, 1)
713  ((wxZipOutputStream *)m_pStream)->SetFormat(wxZIP_FORMAT_ZIP64);
714  #endif
715  }
716  else
717  {
718  pEntry = new wxTarEntry(Name);
719  }
720 
721  if( ((wxArchiveOutputStream *)m_pStream)->PutNextEntry(pEntry) )
722  {
723  m_FileName = Name;
724 
725  return( true );
726  }
727  }
728 
729  return( false );
730 }
731 
732 //---------------------------------------------------------
733 bool CSG_Archive::is_Directory(size_t Index)
734 {
735  if( is_Reading() && m_Files[Index] )
736  {
737  return( ((wxArchiveEntry *)m_Files[Index])->IsDir() );
738  }
739 
740  return( false );
741 }
742 
743 //---------------------------------------------------------
744 bool CSG_Archive::Get_File(size_t Index)
745 {
746  if( is_Reading() && m_Files[Index] )
747  {
748  if( ((wxArchiveInputStream *)m_pStream)->OpenEntry(*(wxArchiveEntry *)m_Files[Index]) )
749  {
750  m_FileName = Get_File_Name(Index);
751 
752  return( true );
753  }
754  }
755 
756  return( false );
757 }
758 
759 //---------------------------------------------------------
761 {
762  if( is_Reading() && Name )
763  {
764  for(sLong i=0; i<m_Files.Get_Size(); i++)
765  {
766  if( !((wxArchiveEntry *)m_Files[i])->GetName().Cmp(Name) )
767  {
768  return( Get_File(i) );
769  }
770  }
771  }
772 
773  return( false );
774 }
775 
776 //---------------------------------------------------------
778 {
779  CSG_String s;
780 
781  if( is_Reading() && m_Files[Index] )
782  {
783  wxString Name(((wxArchiveEntry *)m_Files[Index])->GetName()); s = &Name;
784  }
785 
786  return( s );
787 }
788 
789 
791 // //
793 
794 //---------------------------------------------------------
795 bool CSG_Archive::Extract_All(const SG_Char *_Directory)
796 {
797  if( !is_Reading() )
798  {
799  return( false );
800  }
801 
802  #ifdef _SAGA_MSW
803  const char Separator = '\\';
804  #else
805  const char Separator = '/';
806  #endif
807 
808  CSG_String Directory(_Directory ? _Directory : SG_T(""));
809 
810  if( Directory.is_Empty() )
811  {
812  Directory = SG_File_Get_Path(m_Archive);
813  }
814  else if( !SG_Dir_Exists(Directory) )
815  {
816  SG_Dir_Create(Directory, true);
817  }
818 
819  Directory += Separator;
820 
821  //-----------------------------------------------------
822  for(size_t i=0; i<Get_File_Count() && SG_UI_Process_Set_Progress((int)i, (int)Get_File_Count()); i++)
823  {
824  if( is_Directory(i) )
825  {
826  SG_Dir_Create(Directory + Get_File_Name(i));
827  }
828  else
829  {
830  Extract(Get_File_Name(i), Directory + Get_File_Name(i));
831  }
832  }
833 
834  return( true );
835 }
836 
837 //---------------------------------------------------------
838 bool CSG_Archive::Extract(const SG_Char *File, const SG_Char *_toFile)
839 {
840  if( !is_Reading() || !Get_File(File) )
841  {
842  return( false );
843  }
844 
845  CSG_String toFile(_toFile ? _toFile : SG_T(""));
846 
847  if( toFile.is_Empty() )
848  {
850  }
851 
852  CSG_File Stream(toFile, SG_FILE_W, true, m_Encoding);
853 
854  if( !Stream.is_Open() )
855  {
856  return( false );
857  }
858 
859  //-----------------------------------------------------
860  #define UNZIP_BUFFER 4096
861 
862  char *Buffer[UNZIP_BUFFER];
863 
864  while( !is_EOF() )
865  {
866  size_t nBytes = Read(Buffer, sizeof(char), UNZIP_BUFFER);
867 
868  Stream.Write(Buffer, 1, nBytes); Stream.Flush();
869  }
870 
871  return( true );
872 }
873 
874 
876 // //
877 // //
878 // //
880 
881 //---------------------------------------------------------
882 bool SG_Dir_Exists(const CSG_String &Directory)
883 {
884  return( wxFileName::DirExists(Directory.c_str()) );
885 }
886 
887 //---------------------------------------------------------
888 bool SG_Dir_Create(const CSG_String &Directory, bool bFullPath)
889 {
890  if( SG_Dir_Exists(Directory) )
891  {
892  return( true );
893  }
894 
895  return( wxFileName::Mkdir(Directory.c_str(), wxS_DIR_DEFAULT, bFullPath ? wxPATH_MKDIR_FULL : 0) );
896 }
897 
898 //---------------------------------------------------------
899 bool SG_Dir_Delete(const CSG_String &Directory, bool bRecursive)
900 {
901  if( !SG_Dir_Exists(Directory) )
902  {
903  return( true );
904  }
905 
906  return( wxDir::Remove(Directory.c_str(), bRecursive ? wxPATH_RMDIR_RECURSIVE : 0) );
907 }
908 
909 //---------------------------------------------------------
911 {
912  wxString cwd = wxFileName::GetCwd();
913 
914  return( CSG_String(&cwd) );
915 }
916 
917 //---------------------------------------------------------
919 {
920  wxString fname = wxFileName::GetTempDir();
921 
922  return( CSG_String(&fname) );
923 }
924 
925 //---------------------------------------------------------
926 bool SG_Dir_List_Subdirectories (CSG_Strings &List, const CSG_String &Directory)
927 {
928  List.Clear();
929 
930  wxDir Dir;
931 
932  if( Dir.Open(Directory.c_str()) )
933  {
934  wxString FileName;
935 
936  if( Dir.GetFirst(&FileName, wxEmptyString, wxDIR_DIRS) )
937  {
938  do
939  {
940  List += SG_File_Make_Path(Directory, &FileName);
941  }
942  while( Dir.GetNext(&FileName) );
943  }
944  }
945 
946  return( List.Get_Count() > 0 );
947 }
948 
949 //---------------------------------------------------------
950 bool SG_Dir_List_Files (CSG_Strings &List, const CSG_String &Directory)
951 {
952  return( SG_Dir_List_Files(List, Directory, "") );
953 }
954 
955 bool SG_Dir_List_Files (CSG_Strings &List, const CSG_String &Directory, const CSG_String &Extension)
956 {
957  List.Clear();
958 
959  wxDir Dir;
960 
961  if( Dir.Open(Directory.c_str()) )
962  {
963  wxString FileName;
964 
965  if( Dir.GetFirst(&FileName, wxEmptyString, wxDIR_FILES) )
966  {
967  do
968  {
969  if( Extension.is_Empty() || SG_File_Cmp_Extension(&FileName, Extension) )
970  {
971  List += SG_File_Make_Path(Directory, &FileName);
972  }
973  }
974  while( Dir.GetNext(&FileName) );
975  }
976  }
977 
978  return( List.Get_Count() > 0 );
979 }
980 
981 
983 // //
984 // //
985 // //
987 
988 //---------------------------------------------------------
989 bool SG_File_Exists(const CSG_String &FileName)
990 {
991  return( wxFileExists(FileName.c_str()) );
992 }
993 
994 //---------------------------------------------------------
995 bool SG_File_Delete(const CSG_String &FileName)
996 {
997  return( SG_File_Exists(FileName) && wxRemoveFile(FileName.c_str()) );
998 }
999 
1000 //---------------------------------------------------------
1002 {
1003  return( SG_File_Get_Name_Temp(Prefix, "") );
1004 }
1005 
1006 CSG_String SG_File_Get_Name_Temp(const CSG_String &Prefix, const CSG_String &Directory)
1007 {
1008  if( !SG_Dir_Exists(Directory) )
1009  {
1010  return( CSG_String(wxFileName::CreateTempFileName(Prefix.c_str()).wc_str()) );
1011  }
1012 
1013  return( CSG_String(wxFileName::CreateTempFileName(SG_File_Make_Path(Directory, Prefix).w_str()).wc_str()) );
1014 }
1015 
1016 //---------------------------------------------------------
1017 CSG_String SG_File_Get_Name(const CSG_String &full_Path, bool bExtension)
1018 {
1019  wxFileName fn(full_Path.c_str());
1020 
1021  if( bExtension )
1022  {
1023  wxString s(fn.GetFullName()); return( CSG_String(&s) );
1024  }
1025 
1026  wxString s(fn.GetName()); return( &s );
1027 }
1028 
1029 //---------------------------------------------------------
1031 {
1032  wxString s(wxFileName(full_Path.c_str()).GetPath(wxPATH_GET_VOLUME|wxPATH_GET_SEPARATOR));
1033 
1034  return( CSG_String(&s) );
1035 }
1036 
1037 //---------------------------------------------------------
1039 {
1040  wxFileName fn(full_Path.c_str());
1041 
1042  fn.MakeAbsolute();
1043 
1044  wxString s(fn.GetFullPath()); return( &s );
1045 }
1046 
1047 //---------------------------------------------------------
1048 CSG_String SG_File_Get_Path_Relative(const CSG_String &Directory, const CSG_String &full_Path)
1049 {
1050  wxFileName fn(full_Path.c_str());
1051 
1052  fn.MakeRelativeTo(Directory.c_str());
1053 
1054  wxString s(fn.GetFullPath()); return( &s );
1055 }
1056 
1057 //---------------------------------------------------------
1058 CSG_String SG_File_Make_Path(const CSG_String &Directory, const CSG_String &Name)
1059 {
1060  return( SG_File_Make_Path(Directory, Name, "") );
1061 }
1062 
1063 CSG_String SG_File_Make_Path(const CSG_String &Directory, const CSG_String &Name, const CSG_String &Extension)
1064 {
1065  wxFileName fn;
1066 
1067  fn.AssignDir(!Directory.is_Empty() ? Directory.c_str() : SG_File_Get_Path(Name).c_str());
1068 
1069  if( !Extension.is_Empty() )
1070  {
1071  fn.SetName (SG_File_Get_Name(Name, false).c_str());
1072  fn.SetExt (Extension.c_str());
1073  }
1074  else
1075  {
1076  fn.SetFullName (SG_File_Get_Name(Name, true).c_str());
1077  }
1078 
1079  wxString s(fn.GetFullPath()); return( &s );
1080 }
1081 
1082 //---------------------------------------------------------
1083 bool SG_File_Cmp_Path(const CSG_String &Path1, const CSG_String &Path2)
1084 {
1085  wxFileName a(wxString(Path1.c_str())), b(wxString(Path2.c_str()));
1086 
1087  return( a.SameAs(b) );
1088 }
1089 
1090 //---------------------------------------------------------
1091 bool SG_File_Cmp_Extension(const CSG_String &FileName, const CSG_String &Extension)
1092 {
1093  return( SG_File_Get_Extension(FileName).CmpNoCase(Extension) == 0 );
1094 }
1095 
1096 //---------------------------------------------------------
1097 bool SG_File_Set_Extension(CSG_String &FileName, const CSG_String &Extension)
1098 {
1099  if( FileName.Length() > 0 )
1100  {
1101  wxFileName fn(FileName.c_str());
1102 
1103  fn.SetExt(Extension.c_str());
1104 
1105  wxString s(fn.GetFullPath());
1106 
1107  FileName = &s;
1108 
1109  return( true );
1110  }
1111 
1112  return( false );
1113 }
1114 
1115 //---------------------------------------------------------
1117 {
1118  wxFileName fn(FileName.c_str());
1119 
1120  wxString s(fn.GetExt()); return( &s );
1121 }
1122 
1123 
1125 // //
1126 // //
1127 // //
1129 
1130 //---------------------------------------------------------
1131 bool SG_Get_Environment(const CSG_String &Variable, CSG_String *Value)
1132 {
1133  if( Value == NULL )
1134  {
1135  return( wxGetEnv(Variable.w_str(), NULL) );
1136  }
1137 
1138  wxString s;
1139 
1140  if( wxGetEnv(Variable.w_str(), &s) )
1141  {
1142  *Value = s.wc_str();
1143 
1144  return( true );
1145  }
1146 
1147  return( false );
1148 }
1149 
1150 //---------------------------------------------------------
1151 bool SG_Set_Environment(const CSG_String &Variable, const CSG_String &Value)
1152 {
1153  return( wxSetEnv(Variable.w_str(), Value.w_str()) );
1154 }
1155 
1156 
1158 // //
1159 // //
1160 // //
1162 
1163 //---------------------------------------------------------
CSG_Archive::CSG_Archive
CSG_Archive(void)
Definition: api_file.cpp:575
m_pStream_O
#define m_pStream_O
Definition: api_file.cpp:76
CSG_File::Set_Encoding
bool Set_Encoding(int Encoding)
Definition: api_file.cpp:191
SG_T
#define SG_T(s)
Definition: api_core.h:537
CSG_File::Seek_Start
bool Seek_Start(void) const
Definition: api_file.cpp:260
CSG_Archive::Extract_All
bool Extract_All(const SG_Char *toDirectory=NULL)
Definition: api_file.cpp:795
CSG_String::to_ASCII
bool to_ASCII(char **pString, char Replace='_') const
Definition: api_string.cpp:933
SG_Swap_Bytes
SAGA_API_DLL_EXPORT void SG_Swap_Bytes(void *Buffer, int nBytes)
Definition: api_memory.cpp:154
CSG_String::w_str
const wchar_t * w_str(void) const
Definition: api_string.cpp:248
CSG_String::Length
size_t Length(void) const
Definition: api_string.cpp:172
CSG_File::m_FileName
CSG_String m_FileName
Definition: api_core.h:1189
SG_File_Get_Extension
CSG_String SG_File_Get_Extension(const CSG_String &FileName)
Definition: api_file.cpp:1116
CSG_Archive::m_Archive
CSG_String m_Archive
Definition: api_core.h:1234
CSG_Array_Pointer::Get_Size
sLong Get_Size(void) const
Definition: api_core.h:381
UNZIP_BUFFER
#define UNZIP_BUFFER
CSG_File::Seek
bool Seek(sLong Offset, int Origin=SG_FILE_START) const
Definition: api_file.cpp:241
CSG_String::asInt
int asInt(void) const
Definition: api_string.cpp:746
SG_File_Exists
bool SG_File_Exists(const CSG_String &FileName)
Definition: api_file.cpp:989
CSG_File::Scan
bool Scan(int &Value) const
Definition: api_file.cpp:490
CSG_File::Flush
bool Flush(void)
Definition: api_file.cpp:280
SG_FILE_ENCODING_UTF32BE
@ SG_FILE_ENCODING_UTF32BE
Definition: api_core.h:556
SG_File_Make_Path
CSG_String SG_File_Make_Path(const CSG_String &Directory, const CSG_String &Name)
Definition: api_file.cpp:1058
api_core.h
CSG_File::Scan_Int
int Scan_Int(void) const
Definition: api_file.cpp:552
SG_Dir_List_Subdirectories
bool SG_Dir_List_Subdirectories(CSG_Strings &List, const CSG_String &Directory)
Definition: api_file.cpp:926
SG_FILE_R
@ SG_FILE_R
Definition: api_core.h:1111
CSG_File::m_Mode
int m_Mode
Definition: api_core.h:1187
SG_FILE_END
@ SG_FILE_END
Definition: api_core.h:1121
CSG_File::Read
size_t Read(void *Buffer, size_t Size, size_t Count=1) const
Definition: api_file.cpp:337
CSG_File
Definition: api_core.h:1126
SG_FILE_ENCODING_UTF7
@ SG_FILE_ENCODING_UTF7
Definition: api_core.h:551
CSG_Strings::Clear
void Clear(void)
Definition: api_core.h:735
CSG_Buffer
Definition: api_core.h:224
SG_Dir_Create
bool SG_Dir_Create(const CSG_String &Directory, bool bFullPath)
Definition: api_file.cpp:888
CSG_File::Scan_String
CSG_String Scan_String(SG_Char Separator) const
Definition: api_file.cpp:562
SG_Dir_Get_Current
CSG_String SG_Dir_Get_Current(void)
Definition: api_file.cpp:910
CSG_Archive::~CSG_Archive
virtual ~CSG_Archive(void)
Definition: api_file.cpp:589
SG_FILE_ENCODING_UNDEFINED
@ SG_FILE_ENCODING_UNDEFINED
Definition: api_core.h:557
SG_File_Cmp_Extension
bool SG_File_Cmp_Extension(const CSG_String &FileName, const CSG_String &Extension)
Definition: api_file.cpp:1091
CSG_File::On_Construction
void On_Construction(void)
Definition: api_file.cpp:183
CSG_File::is_Writing
bool is_Writing(void) const
Definition: api_core.h:1147
CSG_File::Scan_Double
double Scan_Double(void) const
Definition: api_file.cpp:557
SG_FILE_TYPE_TAR
@ SG_FILE_TYPE_TAR
Definition: api_core.h:1104
sLong
signed long long sLong
Definition: api_core.h:158
CSG_File::Read_Int
int Read_Int(bool bBigEndian=false) const
Definition: api_file.cpp:438
SG_File_Get_Name
CSG_String SG_File_Get_Name(const CSG_String &full_Path, bool bExtension)
Definition: api_file.cpp:1017
CSG_File::Open
virtual bool Open(const SG_Char *FileName, int Mode=SG_FILE_R, bool bBinary=true, int Encoding=SG_FILE_ENCODING_ANSI)
Definition: api_file.cpp:112
SG_FILE_ENCODING_UTF32LE
@ SG_FILE_ENCODING_UTF32LE
Definition: api_core.h:555
CSG_Buffer::Get_Size
size_t Get_Size(void) const
Definition: api_core.h:241
SG_Get_Environment
bool SG_Get_Environment(const CSG_String &Variable, CSG_String *Value)
Definition: api_file.cpp:1131
CSG_Archive::m_Type
TSG_File_Type m_Type
Definition: api_core.h:1232
CSG_File::m_Encoding
int m_Encoding
Definition: api_core.h:1187
SG_FILE_CURRENT
@ SG_FILE_CURRENT
Definition: api_core.h:1120
CSG_Archive::Get_File
bool Get_File(const SG_Char *Name)
Definition: api_file.cpp:760
CSG_Archive::Add_Directory
bool Add_Directory(const SG_Char *Name)
Definition: api_file.cpp:694
CSG_File::Close
virtual bool Close(void)
Definition: api_file.cpp:163
CSG_File::Read_Char
int Read_Char(void) const
Definition: api_file.cpp:432
SG_FILE_W
@ SG_FILE_W
Definition: api_core.h:1112
CSG_Strings
Definition: api_core.h:700
SG_File_Delete
bool SG_File_Delete(const CSG_String &FileName)
Definition: api_file.cpp:995
CSG_File::is_Open
bool is_Open(void) const
Definition: api_core.h:1145
SG_File_Cmp_Path
bool SG_File_Cmp_Path(const CSG_String &Path1, const CSG_String &Path2)
Definition: api_file.cpp:1083
CSG_Buffer::Get_Data
char * Get_Data(int Offset=0) const
Definition: api_core.h:244
SG_File_Get_Path_Relative
CSG_String SG_File_Get_Path_Relative(const CSG_String &Directory, const CSG_String &full_Path)
Definition: api_file.cpp:1048
CSG_Archive::Get_File_Count
size_t Get_File_Count(void)
Definition: api_core.h:1220
CSG_Archive::Close
virtual bool Close(void)
Definition: api_file.cpp:672
SG_FILE_ENCODING_UTF16LE
@ SG_FILE_ENCODING_UTF16LE
Definition: api_core.h:553
CSG_File::Write_Double
bool Write_Double(double Value, bool bBigEndian=false)
Definition: api_file.cpp:479
m_pStream_I
#define m_pStream_I
Definition: api_file.cpp:75
CSG_File::m_pConvert
void * m_pConvert
Definition: api_core.h:1191
CSG_File::Length
sLong Length(void) const
Definition: api_file.cpp:229
SG_File_Get_Name_Temp
CSG_String SG_File_Get_Name_Temp(const CSG_String &Prefix)
Definition: api_file.cpp:1001
CSG_Archive::Add_File
bool Add_File(const SG_Char *Name, bool bBinary=true)
Definition: api_file.cpp:700
CSG_String::Clear
void Clear(void)
Definition: api_string.cpp:259
CSG_Archive::Open
virtual bool Open(const SG_Char *FileName, int Mode=SG_FILE_R, int Encoding=SG_FILE_ENCODING_ANSI)
Definition: api_file.cpp:595
SG_Char
#define SG_Char
Definition: api_core.h:536
m_pStream_IO
#define m_pStream_IO
Definition: api_file.cpp:77
CSG_String
Definition: api_core.h:563
SG_Dir_List_Files
bool SG_Dir_List_Files(CSG_Strings &List, const CSG_String &Directory)
Definition: api_file.cpp:950
CSG_File::m_pStream
void * m_pStream
Definition: api_core.h:1191
CSG_File::Printf
int Printf(const char *Format,...)
Definition: api_file.cpp:286
CSG_String::is_Empty
bool is_Empty(void) const
Definition: api_string.cpp:178
SG_Set_Environment
bool SG_Set_Environment(const CSG_String &Variable, const CSG_String &Value)
Definition: api_file.cpp:1151
CSG_Archive::Extract
bool Extract(const SG_Char *File, const SG_Char *toFile=NULL)
Definition: api_file.cpp:838
SG_UI_Process_Set_Progress
bool SG_UI_Process_Set_Progress(int Position, int Range)
Definition: api_callback.cpp:255
SG_FILE_ENCODING_UTF16BE
@ SG_FILE_ENCODING_UTF16BE
Definition: api_core.h:554
CSG_File::Write_Int
bool Write_Int(int Value, bool bBigEndian=false)
Definition: api_file.cpp:453
CSG_Array_Pointer::Set_Array
bool Set_Array(sLong nValues, bool bShrink=true)
Definition: api_core.h:387
CSG_File::Read_Line
bool Read_Line(CSG_String &Line) const
Definition: api_file.cpp:394
SG_File_Get_Path
CSG_String SG_File_Get_Path(const CSG_String &full_Path)
Definition: api_file.cpp:1030
CSG_File::Read_Double
double Read_Double(bool bBigEndian=false) const
Definition: api_file.cpp:464
SG_Dir_Delete
bool SG_Dir_Delete(const CSG_String &Directory, bool bRecursive)
Definition: api_file.cpp:899
SG_File_Set_Extension
bool SG_File_Set_Extension(CSG_String &FileName, const CSG_String &Extension)
Definition: api_file.cpp:1097
CSG_String::asDouble
double asDouble(void) const
Definition: api_string.cpp:784
CSG_String::c_str
const SG_Char * c_str(void) const
Definition: api_string.cpp:236
CSG_File::Write
size_t Write(void *Buffer, size_t Size, size_t Count=1) const
Definition: api_file.cpp:369
CSG_Strings::Get_Count
int Get_Count(void) const
Definition: api_core.h:713
CSG_File::CSG_File
CSG_File(void)
Definition: api_file.cpp:87
SG_Dir_Get_Temp
CSG_String SG_Dir_Get_Temp(void)
Definition: api_file.cpp:918
SG_FILE_TYPE_ZIP
@ SG_FILE_TYPE_ZIP
Definition: api_core.h:1103
CSG_Archive::is_Directory
bool is_Directory(size_t Index)
Definition: api_file.cpp:733
SG_FILE_ENCODING_ANSI
@ SG_FILE_ENCODING_ANSI
Definition: api_core.h:550
CSG_File::is_EOF
bool is_EOF(void) const
Definition: api_file.cpp:235
SG_FILE_ENCODING_UTF8
@ SG_FILE_ENCODING_UTF8
Definition: api_core.h:552
m_pStream_Base
#define m_pStream_Base
Definition: api_file.cpp:74
CSG_File::is_Reading
bool is_Reading(void) const
Definition: api_core.h:1146
SG_Dir_Exists
bool SG_Dir_Exists(const CSG_String &Directory)
Definition: api_file.cpp:882
CSG_File::Get_File_Name
virtual const CSG_String & Get_File_Name(void) const
Definition: api_core.h:1137
CSG_Archive::m_Files
CSG_Array_Pointer m_Files
Definition: api_core.h:1236
CSG_File::Seek_End
bool Seek_End(void) const
Definition: api_file.cpp:261
CSG_File::Tell
sLong Tell(void) const
Definition: api_file.cpp:264
CSG_Archive::is_Zip
bool is_Zip(void) const
Definition: api_core.h:1214
SG_File_Get_Path_Absolute
CSG_String SG_File_Get_Path_Absolute(const CSG_String &full_Path)
Definition: api_file.cpp:1038
CSG_File::~CSG_File
virtual ~CSG_File(void)
Definition: api_file.cpp:101