]> git.saurik.com Git - wxWidgets.git/blame - utils/configtool/src/utils.cpp
Miscellaneous compilation and warning fixes.
[wxWidgets.git] / utils / configtool / src / utils.cpp
CommitLineData
d7463f75
JS
1/////////////////////////////////////////////////////////////////////////////
2// Name: utils.cpp
3// Purpose: Utility functions and classes
4// Author: Julian Smart
5// Modified by:
6// Created: 2002-09-04
7// RCS-ID: $Id$
8// Copyright: (c) Julian Smart
4fe30bce 9// Licence:
d7463f75
JS
10/////////////////////////////////////////////////////////////////////////////
11
12#ifdef __GNUG__
13// #pragma implementation
14#endif
15
d9ab621e
WS
16// For compilers that support precompilation, includes "wx/wx.h".
17#include "wx/wxprec.h"
18
19#ifdef __BORLANDC__
20#pragma hdrstop
21#endif
22
23#include <math.h>
24
25#ifndef WX_PRECOMP
26
d7463f75 27#include "wx/splitter.h"
d7463f75
JS
28#include "wx/datstrm.h"
29#include "wx/file.h"
30#include "wx/listctrl.h"
d7463f75 31#include "wx/process.h"
d7463f75 32#include "wx/variant.h"
d7463f75 33#include "wx/cmdline.h"
60c474a0
MB
34#include "wx/msgdlg.h"
35#include "wx/log.h"
d7463f75 36
d7463f75
JS
37#endif
38
d9ab621e
WS
39#include "wx/wfstream.h"
40#include "wx/cshelp.h"
41#include "wx/image.h"
42#include "wx/imaglist.h"
43#include "wx/tokenzr.h"
44#include "wx/notebook.h"
45#include "wx/mimetype.h"
d7463f75
JS
46#include "utils.h"
47
48// Returns the image type, or -1, determined from the extension.
49int apDetermineImageType(const wxString& filename)
50{
51 wxString path, name, ext;
52
53 wxSplitPath(filename, & path, & name, & ext);
54
55 ext.MakeLower();
69da0d99 56 if (ext == _T("jpg") || ext == _T("jpeg"))
d7463f75 57 return wxBITMAP_TYPE_JPEG;
69da0d99 58 else if (ext == _T("gif"))
d7463f75 59 return wxBITMAP_TYPE_GIF;
69da0d99 60 else if (ext == _T("bmp"))
d7463f75 61 return wxBITMAP_TYPE_BMP;
69da0d99 62 else if (ext == _T("png"))
d7463f75 63 return wxBITMAP_TYPE_PNG;
69da0d99 64 else if (ext == _T("pcx"))
d7463f75 65 return wxBITMAP_TYPE_PCX;
69da0d99 66 else if (ext == _T("tif") || ext == _T("tiff"))
d7463f75
JS
67 return wxBITMAP_TYPE_TIF;
68 else
69 return -1;
70}
71
72// Convert a colour to a 6-digit hex string
73wxString apColourToHexString(const wxColour& col)
74{
75 wxString hex;
76
77 hex += wxDecToHex(col.Red());
78 hex += wxDecToHex(col.Green());
79 hex += wxDecToHex(col.Blue());
80
81 return hex;
82}
83
84// Convert 6-digit hex string to a colour
85wxColour apHexStringToColour(const wxString& hex)
86{
254a2129
WS
87 unsigned char r = (unsigned char)wxHexToDec(hex.Mid(0, 2));
88 unsigned char g = (unsigned char)wxHexToDec(hex.Mid(2, 2));
89 unsigned char b = (unsigned char)wxHexToDec(hex.Mid(4, 2));
d7463f75
JS
90
91 return wxColour(r, g, b);
92}
93
94// Convert a wxFont to a string
95wxString apFontToString(const wxFont& font)
96{
97 wxString str;
98 str.Printf(wxT("%d,%d,%d,%d,%d,%s"), (int) font.GetPointSize(),
99 (int) font.GetFamily(), (int) font.GetStyle(), (int) font.GetWeight(),
100 (int) font.GetUnderlined(), font.GetFaceName().c_str());
101
102 return str;
103}
104
3ac35b57
MB
105static inline int StringToInt(const wxString& s)
106{
107 long tmp;
108 s.ToLong(&tmp);
109
110 return int(tmp);
111}
112
d7463f75
JS
113// Convert a string to a wxFont
114wxFont apStringToFont(const wxString& str)
115{
116 int pointSize = 12;
117 int family = wxSWISS;
118 int style = wxNORMAL;
119 int weight = wxNORMAL;
120 int underlined = 0;
121 wxString facename(wxT(""));
122
123 wxStringTokenizer tkz(str, wxT(","));
124 int i = 0;
125 while (tkz.HasMoreTokens())
126 {
127 wxString token = tkz.GetNextToken();
128
129 if (i == 0)
130 {
3ac35b57 131 pointSize = StringToInt(token);
d7463f75
JS
132#if defined(__WXGTK__) || defined(__WXMAC__)
133 if (pointSize < 8)
134 pointSize = 8;
135 if (pointSize == 9)
136 pointSize = 10;
254a2129 137#endif
d7463f75
JS
138 }
139 else if (i == 1)
3ac35b57 140 family = StringToInt(token);
d7463f75 141 else if (i == 2)
3ac35b57 142 style = StringToInt(token);
d7463f75 143 else if (i == 3)
3ac35b57 144 weight = StringToInt(token);
d7463f75 145 else if (i == 4)
3ac35b57 146 underlined = StringToInt(token);
d7463f75
JS
147 else if (i == 5)
148 {
149 facename = token;
150#if defined(__WXGTK__)
151 if (facename == wxT("Arial"))
152 facename = wxT("helvetica");
153#endif
154 }
155 i ++;
156
157 }
158 return wxFont(pointSize, family, style, weight, (underlined != 0), facename);
159}
160
161
162// Get the index of the given named wxNotebook page
163int apFindNotebookPage(wxNotebook* notebook, const wxString& name)
164{
165 int i;
69da0d99 166 for (i = 0; i < (int)notebook->GetPageCount(); i++)
d7463f75
JS
167 if (name == notebook->GetPageText(i))
168 return i;
169 return -1;
170}
171
172/*
173 * View an HTML file
174 */
175
176void apViewHTMLFile(const wxString& url)
177{
178#ifdef __WXMSW__
179 HKEY hKey;
180 TCHAR szCmdName[1024];
181 DWORD dwType, dw = sizeof(szCmdName);
182 LONG lRes;
69da0d99 183 lRes = RegOpenKey(HKEY_CLASSES_ROOT, _T("htmlfile\\shell\\open\\command"), &hKey);
d7463f75
JS
184 if(lRes == ERROR_SUCCESS && RegQueryValueEx(hKey,(LPTSTR)NULL, NULL,
185 &dwType, (LPBYTE)szCmdName, &dw) == ERROR_SUCCESS)
186 {
69da0d99 187 wxStrcat(szCmdName, (const wxChar*) url);
d7463f75
JS
188 PROCESS_INFORMATION piProcInfo;
189 STARTUPINFO siStartInfo;
190 memset(&siStartInfo, 0, sizeof(STARTUPINFO));
191 siStartInfo.cb = sizeof(STARTUPINFO);
4fe30bce 192 CreateProcess(NULL, szCmdName, NULL, NULL, false, 0, NULL,
d7463f75
JS
193 NULL, &siStartInfo, &piProcInfo );
194 }
195 if(lRes == ERROR_SUCCESS)
196 RegCloseKey(hKey);
197#else
198 wxFileType *ft = wxTheMimeTypesManager->GetFileTypeFromExtension(wxT("html"));
199 if ( !ft )
200 {
201 wxLogError(_T("Impossible to determine the file type for extension html. Please edit your MIME types."));
202 return ;
203 }
204
205 wxString cmd;
206 bool ok = ft->GetOpenCommand(&cmd,
207 wxFileType::MessageParameters(url, _T("")));
208 delete ft;
209
210 if (!ok)
211 {
212 // TODO: some kind of configuration dialog here.
213 wxMessageBox(_("Could not determine the command for running the browser."),
4fe30bce 214 wxT("Browsing problem"), wxOK|wxICON_EXCLAMATION);
d7463f75
JS
215 return ;
216 }
217
4fe30bce 218 ok = (wxExecute(cmd, false) != 0);
d7463f75
JS
219#endif
220}
221
222wxString wxGetTempDir()
223{
224 wxString dir;
225#if defined(__WXMAC__) && !defined(__DARWIN__)
226 dir = wxMacFindFolder( (short) kOnSystemDisk, kTemporaryFolderType, kCreateFolder ) ;
227#else // !Mac
d9ab621e
WS
228 wxString dirEnv(wxGetenv(_T("TMP")));
229 dir = dirEnv;
d7463f75
JS
230 if ( dir.empty() )
231 {
d9ab621e
WS
232 wxString envVar(wxGetenv(_T("TEMP")));
233 dir = envVar;
d7463f75 234 }
254a2129 235
d7463f75
JS
236 if ( dir.empty() )
237 {
238 // default
239#ifdef __DOS__
240 dir = _T(".");
241#else
242 dir = _T("/tmp");
243#endif
244 }
245#endif // Mac/!Mac
246 return dir;
247}
248
249// Invoke app for file type
250// Eventually we should allow the user to select an app.
251bool apInvokeAppForFile(const wxString& filename)
252{
253 wxString path, file, ext;
254 wxSplitPath(filename, & path, & file, & ext);
255
256 wxFileType *ft = wxTheMimeTypesManager->GetFileTypeFromExtension(ext);
257 if ( !ft )
258 {
259 wxString msg;
260 msg.Printf(wxT("Sorry, could not determine what application to invoke for extension %s\nYou may need to edit your MIME types."),
261 ext.c_str());
262 wxMessageBox(msg, wxT("Application Invocation"), wxICON_EXCLAMATION|wxOK);
4fe30bce 263 return false;
d7463f75
JS
264 }
265
266 wxString cmd;
79830320 267 ft->GetOpenCommand(&cmd, wxFileType::MessageParameters(filename, _T("")));
d7463f75
JS
268 delete ft;
269
4fe30bce 270 return (wxExecute(cmd, false) != 0);
d7463f75
JS
271}
272
273// Find the absolute path where this application has been run from.
274// argv0 is wxTheApp->argv[0]
275// cwd is the current working directory (at startup)
276// appVariableName is the name of a variable containing the directory for this app, e.g.
277// MYAPPDIR. This is checked first.
278
279wxString apFindAppPath(const wxString& argv0, const wxString& cwd, const wxString& appVariableName)
280{
d7463f75
JS
281 // Try appVariableName
282 if (!appVariableName.IsEmpty())
283 {
d9ab621e
WS
284 wxString strVar(wxGetenv(appVariableName.c_str()));
285 if (!strVar.IsEmpty())
286 return strVar;
d7463f75
JS
287 }
288
289 if (wxIsAbsolutePath(argv0))
290 return wxPathOnly(argv0);
291 else
292 {
293 // Is it a relative path?
294 wxString currentDir(cwd);
295 if (currentDir.Last() != wxFILE_SEP_PATH)
296 currentDir += wxFILE_SEP_PATH;
297
d9ab621e
WS
298 currentDir += argv0;
299 if (wxFileExists(currentDir))
300 return wxPathOnly(currentDir);
d7463f75
JS
301 }
302
303 // OK, it's neither an absolute path nor a relative path.
304 // Search PATH.
305
306 wxPathList pathList;
307 pathList.AddEnvList(wxT("PATH"));
d9ab621e
WS
308 wxString strPath = pathList.FindAbsoluteValidPath(argv0);
309 if (!strPath.IsEmpty())
310 return wxPathOnly(strPath);
d7463f75
JS
311
312 // Failed
313 return wxEmptyString;
314}
315
316// Adds a context-sensitive help button, for non-Windows platforms
254a2129 317void apAddContextHelpButton(wxWindow*
69da0d99
JS
318 #if defined(__WXGTK__) || defined(__WXMAC__)
319 parent
320 #else
321 WXUNUSED(parent)
322 #endif
254a2129 323 , wxSizer*
69da0d99
JS
324 #if defined(__WXGTK__) || defined(__WXMAC__)
325 sizer
326 #else
327 WXUNUSED(sizer)
328 #endif
254a2129 329 , int
69da0d99
JS
330 #if defined(__WXGTK__) || defined(__WXMAC__)
331 sizerFlags
332 #else
333 WXUNUSED(sizerFlags)
334 #endif
254a2129 335 , int
69da0d99
JS
336 #if defined(__WXGTK__) || defined(__WXMAC__)
337 sizerBorder
338 #else
339 WXUNUSED(sizerBorder)
340 #endif
341 )
d7463f75
JS
342{
343#if defined(__WXGTK__) || defined(__WXMAC__)
344#ifdef __WXMAC__
345 wxSize buttonSize(20, 20);
346#else
4fe30bce 347 wxSize buttonSize = wxDefaultSize;
d7463f75
JS
348#endif
349 wxButton *contextButton = new wxContextHelpButton( parent, wxID_CONTEXT_HELP,
350 wxDefaultPosition, buttonSize);
351 sizer->Add( contextButton, 0, sizerFlags, sizerBorder );
352
353 // Add a bit of space on the right, to allow for the dialog resizing
354 // handle
355#ifdef __WXMAC__
356 sizer->Add(0, 0, 0, wxRIGHT, 10);
357#endif
358
359 contextButton->SetHelpText(_("Invokes context-sensitive help for the clicked-on window."));
02ae000a 360#if 0
d7463f75
JS
361 if (wxGetApp().UsingTooltips())
362 {
363 contextButton->SetToolTip(_("Invokes context-sensitive help for the clicked-on window."));
364 }
365#endif
02ae000a 366#endif
d7463f75
JS
367}
368
369// Get selected wxNotebook page
370wxWindow* apNotebookGetSelectedPage(wxNotebook* notebook)
371{
372 int sel = notebook->GetSelection();
373 if (sel > -1)
374 {
375 return notebook->GetPage(sel);
376 }
377 return NULL;
378}
379
380/*
381* wxIconInfo
382*/
383
384wxIconInfo::wxIconInfo(const wxString& name)
385{
386 m_maxStates = 0;
387 m_name = name;
388 int i;
389 for (i = 0; i < wxMAX_ICON_STATES; i++)
390 m_states[i] = 0;
391}
392
393int wxIconInfo::GetIconId(int state, bool enabled) const
394{
395 wxASSERT ( state < (wxMAX_ICON_STATES * 2) );
396 wxASSERT ( state < m_maxStates );
254a2129 397
d7463f75
JS
398 return m_states[state * 2 + (enabled ? 0 : 1)];
399}
400
401void wxIconInfo::SetIconId(int state, bool enabled, int iconId)
402{
403 wxASSERT ( state < (wxMAX_ICON_STATES * 2) );
404 if (state+1 > m_maxStates)
405 m_maxStates = state+1;
254a2129 406
d7463f75
JS
407 m_states[state * 2 + (enabled ? 0 : 1)] = iconId;
408}
409
410/*
411* wxIconTable
412* Contains a list of wxIconInfos
413*/
414
415wxIconTable::wxIconTable(wxImageList* imageList)
416{
417 m_imageList = imageList;
d9ab621e 418 WX_CLEAR_LIST(wxIconTable,*this);
d7463f75
JS
419}
420
421void wxIconTable::AppendInfo(wxIconInfo* info)
422{
423 Append(info);
424}
425
426// Easy way of initialising both the image list and the
427// table. It will generate image ids itself while appending the icon.
428bool wxIconTable::AddInfo(const wxString& name, const wxIcon& icon, int state, bool enabled)
429{
430 wxASSERT (m_imageList != NULL);
254a2129 431
d7463f75
JS
432 wxIconInfo* info = FindInfo(name);
433 if (!info)
434 {
435 info = new wxIconInfo(name);
436 Append(info);
437 }
438 info->SetIconId(state, enabled, m_imageList->Add(icon));
4fe30bce 439 return true;
d7463f75
JS
440}
441
442wxIconInfo* wxIconTable::FindInfo(const wxString& name) const
443{
d9ab621e 444 wxObjectList::compatibility_iterator node = GetFirst();
d7463f75
JS
445 while (node)
446 {
f8105809 447 wxIconInfo* info = (wxIconInfo*) node->GetData();
d7463f75
JS
448 if (info->GetName() == name)
449 return info;
f8105809 450 node = node->GetNext();
d7463f75
JS
451 }
452 return NULL;
453}
454
455int wxIconTable::GetIconId(const wxString& name, int state, bool enabled) const
456{
457 wxIconInfo* info = FindInfo(name);
458 if (!info)
459 return -1;
460 return info->GetIconId(state, enabled);
461}
462
463bool wxIconTable::SetIconId(const wxString& name, int state, bool enabled, int iconId)
464{
465 wxIconInfo* info = FindInfo(name);
466 if (!info)
4fe30bce 467 return false;
d7463f75 468 info->SetIconId(state, enabled, iconId);
4fe30bce 469 return true;
d7463f75
JS
470}
471
472// Output stream operators
473
474wxOutputStream& operator <<(wxOutputStream& stream, const wxString& s)
475{
476 stream.Write(s, s.Length());
477 return stream;
478}
479
480wxOutputStream& operator <<(wxOutputStream& stream, long l)
481{
482 wxString str;
483 str.Printf(_T("%ld"), l);
484 return stream << str;
485}
486
69da0d99 487wxOutputStream& operator <<(wxOutputStream& stream, const wxChar c)
d7463f75
JS
488{
489 wxString str;
490 str.Printf(_T("%c"), c);
491 return stream << str;
492}
493
494// Convert characters to HTML equivalents
495wxString ctEscapeHTMLCharacters(const wxString& str)
496{
497 wxString s;
498 size_t len = str.Length();
499 size_t i;
500 for (i = 0; i < len; i++)
501 {
502 wxChar c = str.GetChar(i);
503 if (c == _T('<'))
504 s += _T("&lt;");
505 else if (c == _T('>'))
506 s += _T("&gt;");
507 else if (c == _T('&'))
508 s += _T("&amp;");
509 else
510 s += c;
511 }
512 return s;
f8105809 513}
e7767867
JS
514
515// Match 'matchText' against 'matchAgainst', optionally constraining to
516// whole-word only.
517bool ctMatchString(const wxString& matchAgainst, const wxString& matchText, bool wholeWordOnly)
518{
519 // Fast operation if not matching against whole words only
520 if (!wholeWordOnly)
4fe30bce 521 return (matchAgainst.Find(matchText) != wxNOT_FOUND);
e7767867
JS
522
523 wxString left(matchAgainst);
4fe30bce 524 bool success = false;
e7767867
JS
525 int matchTextLen = (int) matchText.Length();
526 while (!success && !matchAgainst.IsEmpty())
527 {
79830320 528 int pos = left.Find(matchText);
4fe30bce
WS
529 if (pos == wxNOT_FOUND)
530 return false;
e7767867 531
4fe30bce
WS
532 bool firstCharOK = false;
533 bool lastCharOK = false;
e7767867 534 if (pos == 0 || !wxIsalnum(left[(size_t) (pos-1)]))
4fe30bce 535 firstCharOK = true;
e7767867
JS
536
537 if (((pos + matchTextLen) == (int) left.Length()) || !wxIsalnum(left[(size_t) (pos + matchTextLen)]))
4fe30bce 538 lastCharOK = true;
e7767867
JS
539
540 if (firstCharOK && lastCharOK)
4fe30bce 541 success = true;
e7767867
JS
542
543 left = left.Mid(pos+1);
544 }
545 return success;
546}