Files
wxWidgets/utils/configtool/src/utils.cpp
Mattia Barbon d21f1d8f15 wxGTK compilation fixes.
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@31837 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
2005-02-07 21:00:47 +00:00

549 lines
15 KiB
C++

/////////////////////////////////////////////////////////////////////////////
// Name: utils.cpp
// Purpose: Utility functions and classes
// Author: Julian Smart
// Modified by:
// Created: 2002-09-04
// RCS-ID: $Id$
// Copyright: (c) Julian Smart
// Licence:
/////////////////////////////////////////////////////////////////////////////
#ifdef __GNUG__
// #pragma implementation
#endif
// For compilers that support precompilation, includes "wx/wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
#pragma hdrstop
#endif
#include <math.h>
#ifndef WX_PRECOMP
#include "wx/splitter.h"
#include "wx/datstrm.h"
#include "wx/file.h"
#include "wx/listctrl.h"
#include "wx/process.h"
#include "wx/variant.h"
#include "wx/cmdline.h"
#include "wx/msgdlg.h"
#include "wx/log.h"
#include "wx/sizer.h"
#include "wx/icon.h"
#endif
#include "wx/wfstream.h"
#include "wx/cshelp.h"
#include "wx/image.h"
#include "wx/imaglist.h"
#include "wx/tokenzr.h"
#include "wx/notebook.h"
#include "wx/mimetype.h"
#include "utils.h"
// Returns the image type, or -1, determined from the extension.
int apDetermineImageType(const wxString& filename)
{
wxString path, name, ext;
wxSplitPath(filename, & path, & name, & ext);
ext.MakeLower();
if (ext == _T("jpg") || ext == _T("jpeg"))
return wxBITMAP_TYPE_JPEG;
else if (ext == _T("gif"))
return wxBITMAP_TYPE_GIF;
else if (ext == _T("bmp"))
return wxBITMAP_TYPE_BMP;
else if (ext == _T("png"))
return wxBITMAP_TYPE_PNG;
else if (ext == _T("pcx"))
return wxBITMAP_TYPE_PCX;
else if (ext == _T("tif") || ext == _T("tiff"))
return wxBITMAP_TYPE_TIF;
else
return -1;
}
// Convert a colour to a 6-digit hex string
wxString apColourToHexString(const wxColour& col)
{
wxString hex;
hex += wxDecToHex(col.Red());
hex += wxDecToHex(col.Green());
hex += wxDecToHex(col.Blue());
return hex;
}
// Convert 6-digit hex string to a colour
wxColour apHexStringToColour(const wxString& hex)
{
unsigned char r = (unsigned char)wxHexToDec(hex.Mid(0, 2));
unsigned char g = (unsigned char)wxHexToDec(hex.Mid(2, 2));
unsigned char b = (unsigned char)wxHexToDec(hex.Mid(4, 2));
return wxColour(r, g, b);
}
// Convert a wxFont to a string
wxString apFontToString(const wxFont& font)
{
wxString str;
str.Printf(wxT("%d,%d,%d,%d,%d,%s"), (int) font.GetPointSize(),
(int) font.GetFamily(), (int) font.GetStyle(), (int) font.GetWeight(),
(int) font.GetUnderlined(), font.GetFaceName().c_str());
return str;
}
static inline int StringToInt(const wxString& s)
{
long tmp;
s.ToLong(&tmp);
return int(tmp);
}
// Convert a string to a wxFont
wxFont apStringToFont(const wxString& str)
{
int pointSize = 12;
int family = wxSWISS;
int style = wxNORMAL;
int weight = wxNORMAL;
int underlined = 0;
wxString facename(wxT(""));
wxStringTokenizer tkz(str, wxT(","));
int i = 0;
while (tkz.HasMoreTokens())
{
wxString token = tkz.GetNextToken();
if (i == 0)
{
pointSize = StringToInt(token);
#if defined(__WXGTK__) || defined(__WXMAC__)
if (pointSize < 8)
pointSize = 8;
if (pointSize == 9)
pointSize = 10;
#endif
}
else if (i == 1)
family = StringToInt(token);
else if (i == 2)
style = StringToInt(token);
else if (i == 3)
weight = StringToInt(token);
else if (i == 4)
underlined = StringToInt(token);
else if (i == 5)
{
facename = token;
#if defined(__WXGTK__)
if (facename == wxT("Arial"))
facename = wxT("helvetica");
#endif
}
i ++;
}
return wxFont(pointSize, family, style, weight, (underlined != 0), facename);
}
// Get the index of the given named wxNotebook page
int apFindNotebookPage(wxNotebook* notebook, const wxString& name)
{
int i;
for (i = 0; i < (int)notebook->GetPageCount(); i++)
if (name == notebook->GetPageText(i))
return i;
return -1;
}
/*
* View an HTML file
*/
void apViewHTMLFile(const wxString& url)
{
#ifdef __WXMSW__
HKEY hKey;
TCHAR szCmdName[1024];
DWORD dwType, dw = sizeof(szCmdName);
LONG lRes;
lRes = RegOpenKey(HKEY_CLASSES_ROOT, _T("htmlfile\\shell\\open\\command"), &hKey);
if(lRes == ERROR_SUCCESS && RegQueryValueEx(hKey,(LPTSTR)NULL, NULL,
&dwType, (LPBYTE)szCmdName, &dw) == ERROR_SUCCESS)
{
wxStrcat(szCmdName, (const wxChar*) url);
PROCESS_INFORMATION piProcInfo;
STARTUPINFO siStartInfo;
memset(&siStartInfo, 0, sizeof(STARTUPINFO));
siStartInfo.cb = sizeof(STARTUPINFO);
CreateProcess(NULL, szCmdName, NULL, NULL, false, 0, NULL,
NULL, &siStartInfo, &piProcInfo );
}
if(lRes == ERROR_SUCCESS)
RegCloseKey(hKey);
#else
wxFileType *ft = wxTheMimeTypesManager->GetFileTypeFromExtension(wxT("html"));
if ( !ft )
{
wxLogError(_T("Impossible to determine the file type for extension html. Please edit your MIME types."));
return ;
}
wxString cmd;
bool ok = ft->GetOpenCommand(&cmd,
wxFileType::MessageParameters(url, _T("")));
delete ft;
if (!ok)
{
// TODO: some kind of configuration dialog here.
wxMessageBox(_("Could not determine the command for running the browser."),
wxT("Browsing problem"), wxOK|wxICON_EXCLAMATION);
return ;
}
ok = (wxExecute(cmd, false) != 0);
#endif
}
wxString wxGetTempDir()
{
wxString dir;
#if defined(__WXMAC__) && !defined(__DARWIN__)
dir = wxMacFindFolder( (short) kOnSystemDisk, kTemporaryFolderType, kCreateFolder ) ;
#else // !Mac
wxString dirEnv(wxGetenv(_T("TMP")));
dir = dirEnv;
if ( dir.empty() )
{
wxString envVar(wxGetenv(_T("TEMP")));
dir = envVar;
}
if ( dir.empty() )
{
// default
#ifdef __DOS__
dir = _T(".");
#else
dir = _T("/tmp");
#endif
}
#endif // Mac/!Mac
return dir;
}
// Invoke app for file type
// Eventually we should allow the user to select an app.
bool apInvokeAppForFile(const wxString& filename)
{
wxString path, file, ext;
wxSplitPath(filename, & path, & file, & ext);
wxFileType *ft = wxTheMimeTypesManager->GetFileTypeFromExtension(ext);
if ( !ft )
{
wxString msg;
msg.Printf(wxT("Sorry, could not determine what application to invoke for extension %s\nYou may need to edit your MIME types."),
ext.c_str());
wxMessageBox(msg, wxT("Application Invocation"), wxICON_EXCLAMATION|wxOK);
return false;
}
wxString cmd;
ft->GetOpenCommand(&cmd, wxFileType::MessageParameters(filename, _T("")));
delete ft;
return (wxExecute(cmd, false) != 0);
}
// Find the absolute path where this application has been run from.
// argv0 is wxTheApp->argv[0]
// cwd is the current working directory (at startup)
// appVariableName is the name of a variable containing the directory for this app, e.g.
// MYAPPDIR. This is checked first.
wxString apFindAppPath(const wxString& argv0, const wxString& cwd, const wxString& appVariableName)
{
// Try appVariableName
if (!appVariableName.IsEmpty())
{
wxString strVar(wxGetenv(appVariableName.c_str()));
if (!strVar.IsEmpty())
return strVar;
}
if (wxIsAbsolutePath(argv0))
return wxPathOnly(argv0);
else
{
// Is it a relative path?
wxString currentDir(cwd);
if (currentDir.Last() != wxFILE_SEP_PATH)
currentDir += wxFILE_SEP_PATH;
currentDir += argv0;
if (wxFileExists(currentDir))
return wxPathOnly(currentDir);
}
// OK, it's neither an absolute path nor a relative path.
// Search PATH.
wxPathList pathList;
pathList.AddEnvList(wxT("PATH"));
wxString strPath = pathList.FindAbsoluteValidPath(argv0);
if (!strPath.IsEmpty())
return wxPathOnly(strPath);
// Failed
return wxEmptyString;
}
// Adds a context-sensitive help button, for non-Windows platforms
void apAddContextHelpButton(wxWindow*
#if defined(__WXGTK__) || defined(__WXMAC__)
parent
#else
WXUNUSED(parent)
#endif
, wxSizer*
#if defined(__WXGTK__) || defined(__WXMAC__)
sizer
#else
WXUNUSED(sizer)
#endif
, int
#if defined(__WXGTK__) || defined(__WXMAC__)
sizerFlags
#else
WXUNUSED(sizerFlags)
#endif
, int
#if defined(__WXGTK__) || defined(__WXMAC__)
sizerBorder
#else
WXUNUSED(sizerBorder)
#endif
)
{
#if defined(__WXGTK__) || defined(__WXMAC__)
#ifdef __WXMAC__
wxSize buttonSize(20, 20);
#else
wxSize buttonSize = wxDefaultSize;
#endif
wxButton *contextButton = new wxContextHelpButton( parent, wxID_CONTEXT_HELP,
wxDefaultPosition, buttonSize);
sizer->Add( contextButton, 0, sizerFlags, sizerBorder );
// Add a bit of space on the right, to allow for the dialog resizing
// handle
#ifdef __WXMAC__
sizer->Add(0, 0, 0, wxRIGHT, 10);
#endif
contextButton->SetHelpText(_("Invokes context-sensitive help for the clicked-on window."));
#if 0
if (wxGetApp().UsingTooltips())
{
contextButton->SetToolTip(_("Invokes context-sensitive help for the clicked-on window."));
}
#endif
#endif
}
// Get selected wxNotebook page
wxWindow* apNotebookGetSelectedPage(wxNotebook* notebook)
{
int sel = notebook->GetSelection();
if (sel > -1)
{
return notebook->GetPage(sel);
}
return NULL;
}
/*
* wxIconInfo
*/
wxIconInfo::wxIconInfo(const wxString& name)
{
m_maxStates = 0;
m_name = name;
int i;
for (i = 0; i < wxMAX_ICON_STATES; i++)
m_states[i] = 0;
}
int wxIconInfo::GetIconId(int state, bool enabled) const
{
wxASSERT ( state < (wxMAX_ICON_STATES * 2) );
wxASSERT ( state < m_maxStates );
return m_states[state * 2 + (enabled ? 0 : 1)];
}
void wxIconInfo::SetIconId(int state, bool enabled, int iconId)
{
wxASSERT ( state < (wxMAX_ICON_STATES * 2) );
if (state+1 > m_maxStates)
m_maxStates = state+1;
m_states[state * 2 + (enabled ? 0 : 1)] = iconId;
}
/*
* wxIconTable
* Contains a list of wxIconInfos
*/
wxIconTable::wxIconTable(wxImageList* imageList)
{
m_imageList = imageList;
WX_CLEAR_LIST(wxIconTable,*this);
}
void wxIconTable::AppendInfo(wxIconInfo* info)
{
Append(info);
}
// Easy way of initialising both the image list and the
// table. It will generate image ids itself while appending the icon.
bool wxIconTable::AddInfo(const wxString& name, const wxIcon& icon, int state, bool enabled)
{
wxASSERT (m_imageList != NULL);
wxIconInfo* info = FindInfo(name);
if (!info)
{
info = new wxIconInfo(name);
Append(info);
}
info->SetIconId(state, enabled, m_imageList->Add(icon));
return true;
}
wxIconInfo* wxIconTable::FindInfo(const wxString& name) const
{
wxObjectList::compatibility_iterator node = GetFirst();
while (node)
{
wxIconInfo* info = (wxIconInfo*) node->GetData();
if (info->GetName() == name)
return info;
node = node->GetNext();
}
return NULL;
}
int wxIconTable::GetIconId(const wxString& name, int state, bool enabled) const
{
wxIconInfo* info = FindInfo(name);
if (!info)
return -1;
return info->GetIconId(state, enabled);
}
bool wxIconTable::SetIconId(const wxString& name, int state, bool enabled, int iconId)
{
wxIconInfo* info = FindInfo(name);
if (!info)
return false;
info->SetIconId(state, enabled, iconId);
return true;
}
// Output stream operators
wxOutputStream& operator <<(wxOutputStream& stream, const wxString& s)
{
stream.Write(s, s.Length());
return stream;
}
wxOutputStream& operator <<(wxOutputStream& stream, long l)
{
wxString str;
str.Printf(_T("%ld"), l);
return stream << str;
}
wxOutputStream& operator <<(wxOutputStream& stream, const wxChar c)
{
wxString str;
str.Printf(_T("%c"), c);
return stream << str;
}
// Convert characters to HTML equivalents
wxString ctEscapeHTMLCharacters(const wxString& str)
{
wxString s;
size_t len = str.Length();
size_t i;
for (i = 0; i < len; i++)
{
wxChar c = str.GetChar(i);
if (c == _T('<'))
s += _T("&lt;");
else if (c == _T('>'))
s += _T("&gt;");
else if (c == _T('&'))
s += _T("&amp;");
else
s += c;
}
return s;
}
// Match 'matchText' against 'matchAgainst', optionally constraining to
// whole-word only.
bool ctMatchString(const wxString& matchAgainst, const wxString& matchText, bool wholeWordOnly)
{
// Fast operation if not matching against whole words only
if (!wholeWordOnly)
return (matchAgainst.Find(matchText) != wxNOT_FOUND);
wxString left(matchAgainst);
bool success = false;
int matchTextLen = (int) matchText.Length();
while (!success && !matchAgainst.IsEmpty())
{
int pos = left.Find(matchText);
if (pos == wxNOT_FOUND)
return false;
bool firstCharOK = false;
bool lastCharOK = false;
if (pos == 0 || !wxIsalnum(left[(size_t) (pos-1)]))
firstCharOK = true;
if (((pos + matchTextLen) == (int) left.Length()) || !wxIsalnum(left[(size_t) (pos + matchTextLen)]))
lastCharOK = true;
if (firstCharOK && lastCharOK)
success = true;
left = left.Mid(pos+1);
}
return success;
}