]> git.saurik.com Git - wxWidgets.git/commitdiff
initial implementation of wxAboutBox()
authorVadim Zeitlin <vadim@wxwidgets.org>
Sun, 8 Oct 2006 01:02:04 +0000 (01:02 +0000)
committerVadim Zeitlin <vadim@wxwidgets.org>
Sun, 8 Oct 2006 01:02:04 +0000 (01:02 +0000)
git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@41683 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775

include/wx/aboutdlg.h [new file with mode: 0644]
include/wx/generic/aboutdlgg.h [new file with mode: 0644]
samples/dialogs/dialogs.cpp
samples/dialogs/dialogs.h
src/generic/aboutdlgg.cpp [new file with mode: 0644]
src/msw/aboutdlg.cpp [new file with mode: 0644]

diff --git a/include/wx/aboutdlg.h b/include/wx/aboutdlg.h
new file mode 100644 (file)
index 0000000..2f7419e
--- /dev/null
@@ -0,0 +1,141 @@
+///////////////////////////////////////////////////////////////////////////////
+// Name:        wx/aboutdlg.h
+// Purpose:     declaration of wxAboutDialog class
+// Author:      Vadim Zeitlin
+// Created:     2006-10-07
+// RCS-ID:      $Id$
+// Copyright:   (c) 2006 Vadim Zeitlin <vadim@wxwindows.org>
+// Licence:     wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+#ifndef _WX_ABOUTDLG_H_
+#define _WX_ABOUTDLG_H_
+
+#include "wx/defs.h"
+
+#if wxUSE_ABOUTDLG
+
+#include "wx/app.h"
+#include "wx/icon.h"
+
+// ----------------------------------------------------------------------------
+// wxAboutDialogInfo: information shown by the standard "About" dialog
+// ----------------------------------------------------------------------------
+
+class WXDLLIMPEXP_CORE wxAboutDialogInfo
+{
+public:
+    // all fields are initially uninitialized
+    wxAboutDialogInfo() { }
+
+    // accessors for various simply fields
+    // -----------------------------------
+
+    // name of the program, if not used defaults wxApp::GetAppName()
+    void SetName(const wxString& name) { m_name = name; }
+    wxString GetName() const
+        { return m_name.empty() ? wxTheApp->GetAppName() : m_name; }
+
+    // version of the program, in free format (but without "version" word)
+    void SetVersion(const wxString& version) { m_version = version; }
+    bool HasVersion() const { return !m_version.empty(); }
+    wxString GetVersion() const { return m_version; }
+
+    // brief, but possibly multiline, description of the program
+    void SetDescription(const wxString& desc) { m_description = desc; }
+    bool HasDescription() const { return !m_description.empty(); }
+    wxString GetDescription() const { return m_description; }
+
+    // short string containing the program copyright information
+    void SetCopyright(const wxString& copyright) { m_copyright = copyright; }
+    bool HasCopyright() const { return !m_copyright.empty(); }
+    wxString GetCopyright() const { return m_copyright; }
+
+    // long, multiline string containing the text of the program licence
+    void SetLicence(const wxString& licence) { m_licence = licence; }
+    void SetLicense(const wxString& licence) { m_licence = licence; }
+    bool HasLicence() const { return !m_licence.empty(); }
+    wxString GetLicence() const { return m_licence; }
+
+    // icon to be shown in the dialog, defaults to the main frame icon
+    void SetIcon(const wxIcon& icon) { m_icon = icon; }
+    bool HasIcon() const { return m_icon.Ok(); }
+    wxIcon GetIcon() const { return m_icon; }
+
+    // web site for the program and its description (defaults to URL itself if
+    // empty)
+    void SetWebSite(const wxString& url, const wxString& desc = wxEmptyString)
+    {
+        m_url = url;
+        m_urlDesc = desc.empty() ? url : desc;
+    }
+
+    bool HasWebSite() const { return !m_url.empty(); }
+
+    wxString GetWebSiteURL() const { return m_url; }
+    wxString GetWebSiteDescription() const { return m_urlDesc; }
+
+    // accessors for the arrays
+    // ------------------------
+
+    // the list of developers of the program
+    void SetDevelopers(const wxArrayString& developers)
+        { m_developers = developers; }
+    void AddDeveloper(const wxString& developer)
+        { m_developers.push_back(developer); }
+
+    bool HasDevelopers() const { return !m_developers.empty(); }
+    const wxArrayString& GetDevelopers() const { return m_developers; }
+
+    // the list of documentation writers
+    void SetDocWriters(const wxArrayString& docwriters)
+        { m_docwriters = docwriters; }
+    void AddDocWriter(const wxString& docwriter)
+        { m_docwriters.push_back(docwriter); }
+
+    bool HasDocWriters() const { return !m_docwriters.empty(); }
+    const wxArrayString& GetDocWriters() const { return m_docwriters; }
+
+    // the list of artists for the program art
+    void SetArtists(const wxArrayString& artists)
+        { m_artists = artists; }
+    void AddArtist(const wxString& artist)
+        { m_artists.push_back(artist); }
+
+    bool HasArtists() const { return !m_artists.empty(); }
+    const wxArrayString& GetArtists() const { return m_artists; }
+
+    // the list of translators
+    void SetTranslators(const wxArrayString& translators)
+        { m_translators = translators; }
+    void AddTranslator(const wxString& translator)
+        { m_translators.push_back(translator); }
+
+    bool HasTranslators() const { return !m_translators.empty(); }
+    const wxArrayString& GetTranslators() const { return m_translators; }
+
+private:
+    wxString m_name,
+             m_version,
+             m_description,
+             m_copyright,
+             m_licence;
+
+    wxIcon m_icon;
+
+    wxString m_url,
+             m_urlDesc;
+
+    wxArrayString m_developers,
+                  m_docwriters,
+                  m_artists,
+                  m_translators;
+};
+
+// functions to show the about dialog box
+WXDLLIMPEXP_CORE void wxAboutBox(const wxAboutDialogInfo& info);
+
+#endif // wxUSE_ABOUTDLG
+
+#endif // _WX_ABOUTDLG_H_
+
diff --git a/include/wx/generic/aboutdlgg.h b/include/wx/generic/aboutdlgg.h
new file mode 100644 (file)
index 0000000..d5bf6f8
--- /dev/null
@@ -0,0 +1,68 @@
+///////////////////////////////////////////////////////////////////////////////
+// Name:        wx/generic/aboutdlgg.h
+// Purpose:     generic wxAboutDialog implementation
+// Author:      Vadim Zeitlin
+// Created:     2006-10-07
+// RCS-ID:      $Id$
+// Copyright:   (c) 2006 Vadim Zeitlin <vadim@wxwindows.org>
+// Licence:     wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+#ifndef _WX_GENERIC_ABOUTDLGG_H_
+#define _WX_GENERIC_ABOUTDLGG_H_
+
+#include "wx/defs.h"
+
+#if wxUSE_ABOUTDLG
+
+#include "wx/dialog.h"
+
+class WXDLLIMPEXP_CORE wxAboutDialogInfo;
+class WXDLLIMPEXP_CORE wxSizer;
+
+// ----------------------------------------------------------------------------
+// wxAboutDialog: generic "About" dialog implementation
+// ----------------------------------------------------------------------------
+
+class WXDLLIMPEXP_CORE wxAboutDialog : public wxDialog
+{
+public:
+    // constructors and Create() method
+    // --------------------------------
+
+    // default ctor, you must use Create() to really initialize the dialog
+    wxAboutDialog() { Init(); }
+
+    // ctor which fully initializes the object
+    wxAboutDialog(const wxAboutDialogInfo& info)
+    {
+        Init();
+
+        (void)Create(info);
+    }
+
+    // this method must be called if and only if the default ctor was used
+    bool Create(const wxAboutDialogInfo& info);
+
+protected:
+    // common part of all ctors
+    void Init() { m_sizerText = NULL; }
+
+    // add arbitrary control to the text sizer contents
+    void AddControl(wxWindow *win);
+
+    // add the text, if it's not empty, to the text sizer contents
+    void AddText(const wxString& text);
+
+
+    wxSizer *m_sizerText;
+};
+
+// unlike wxAboutBox which can show either the native or generic about dialog,
+// this function always shows the generic one
+WXDLLIMPEXP_CORE void wxGenericAboutBox(const wxAboutDialogInfo& info);
+
+#endif // wxUSE_ABOUTDLG
+
+#endif // _WX_GENERIC_ABOUTDLGG_H_
+
index 7296bfa0b8e936d00aa8026444c6e3932dab0ccc..196636832df47f3c947a9e244653e0637fc404cd 100644 (file)
     #include "wx/progdlg.h"
 #endif // wxUSE_PROGRESSDLG
 
+#if wxUSE_ABOUTDLG
+    #include "wx/aboutdlg.h"
+#endif // wxUSE_ABOUTDLG
+
 #if wxUSE_BUSYINFO
     #include "wx/busyinfo.h"
 #endif // wxUSE_BUSYINFO
@@ -179,6 +183,11 @@ BEGIN_EVENT_TABLE(MyFrame, wxFrame)
     EVT_MENU(DIALOGS_PROGRESS,                      MyFrame::ShowProgress)
 #endif // wxUSE_PROGRESSDLG
 
+#if wxUSE_ABOUTDLG
+    EVT_MENU(DIALOGS_ABOUTDLG_SIMPLE,               MyFrame::ShowSimpleAboutDialog)
+    EVT_MENU(DIALOGS_ABOUTDLG_FANCY,                MyFrame::ShowFancyAboutDialog)
+#endif // wxUSE_ABOUTDLG
+
 #if wxUSE_BUSYINFO
     EVT_MENU(DIALOGS_BUSYINFO,                      MyFrame::ShowBusyInfo)
 #endif // wxUSE_BUSYINFO
@@ -234,9 +243,9 @@ bool MyApp::OnInit()
     MyFrame *frame = new MyFrame((wxFrame *) NULL, _T("wxWidgets dialogs example"));
 
     // Make a menubar
-    wxMenu *file_menu = new wxMenu;
+    wxMenu *menuDlg = new wxMenu;
 
-    file_menu->Append(DIALOGS_MESSAGE_BOX, _T("&Message box\tCtrl-M"));
+    menuDlg->Append(DIALOGS_MESSAGE_BOX, _T("&Message box\tCtrl-M"));
 
 
 #if wxUSE_COLOURDLG || wxUSE_FONTDLG || wxUSE_CHOICEDLG
@@ -268,7 +277,7 @@ bool MyApp::OnInit()
         choices_menu->Append(DIALOGS_CHOOSE_FONT_GENERIC, _T("Choose &font (generic)"));
     #endif // USE_FONTDLG_GENERIC
 
-    file_menu->Append(wxID_ANY,_T("&Choices and selectors"),choices_menu);
+    menuDlg->Append(wxID_ANY,_T("&Choices and selectors"),choices_menu);
 #endif // wxUSE_COLOURDLG || wxUSE_FONTDLG || wxUSE_CHOICEDLG
 
 
@@ -285,7 +294,7 @@ bool MyApp::OnInit()
         entry_menu->Append(DIALOGS_NUM_ENTRY, _T("&Numeric entry\tCtrl-N"));
     #endif // wxUSE_NUMBERDLG
 
-    file_menu->Append(wxID_ANY,_T("&Entry dialogs"),entry_menu);
+    menuDlg->Append(wxID_ANY,_T("&Entry dialogs"),entry_menu);
 
 #endif // wxUSE_TEXTDLG || wxUSE_NUMBERDLG
 
@@ -305,7 +314,7 @@ bool MyApp::OnInit()
         filedlg_menu->Append(DIALOGS_FILE_SAVE_GENERIC,  _T("Sa&ve file (generic)"));
     #endif // USE_FILEDLG_GENERIC
 
-    file_menu->Append(wxID_ANY,_T("&File operations"),filedlg_menu);
+    menuDlg->Append(wxID_ANY,_T("&File operations"),filedlg_menu);
 
 #endif // wxUSE_FILEDLG
 
@@ -314,7 +323,7 @@ bool MyApp::OnInit()
 
     dir_menu->Append(DIALOGS_DIR_CHOOSE,  _T("&Choose a directory\tCtrl-D"));
     dir_menu->Append(DIALOGS_DIRNEW_CHOOSE,  _T("Choose a directory (with \"Ne&w\" button)\tShift-Ctrl-D"));
-    file_menu->Append(wxID_ANY,_T("&Directory operations"),dir_menu);
+    menuDlg->Append(wxID_ANY,_T("&Directory operations"),dir_menu);
 
     #if USE_DIRDLG_GENERIC
         dir_menu->AppendSeparator();
@@ -344,7 +353,7 @@ bool MyApp::OnInit()
        info_menu->Append(DIALOGS_LOG_DIALOG, _T("&Log dialog\tCtrl-L"));
     #endif // wxUSE_LOG_DIALOG
 
-    file_menu->Append(wxID_ANY,_T("&Informative dialogs"),info_menu);
+    menuDlg->Append(wxID_ANY,_T("&Informative dialogs"),info_menu);
 
 #endif // wxUSE_STARTUP_TIPS || wxUSE_PROGRESSDLG || wxUSE_BUSYINFO || wxUSE_LOG_DIALOG
 
@@ -353,7 +362,7 @@ bool MyApp::OnInit()
     wxMenu *find_menu = new wxMenu;
     find_menu->AppendCheckItem(DIALOGS_FIND, _T("&Find dialog\tCtrl-F"));
     find_menu->AppendCheckItem(DIALOGS_REPLACE, _T("Find and &replace dialog\tShift-Ctrl-F"));
-    file_menu->Append(wxID_ANY,_T("&Searching"),find_menu);
+    menuDlg->Append(wxID_ANY,_T("&Searching"),find_menu);
 #endif // wxUSE_FINDREPLDLG
 
 #if USE_MODAL_PRESENTATION
@@ -362,7 +371,7 @@ bool MyApp::OnInit()
     dialogs_menu->AppendCheckItem(DIALOGS_MODELESS, _T("Mode&less dialog\tCtrl-Z"));
     dialogs_menu->Append(DIALOGS_CENTRE_SCREEN, _T("Centered on &screen\tShift-Ctrl-1"));
     dialogs_menu->Append(DIALOGS_CENTRE_PARENT, _T("Centered on &parent\tShift-Ctrl-2"));
-    file_menu->Append(wxID_ANY, _T("&Generic dialogs"), dialogs_menu);
+    menuDlg->Append(wxID_ANY, _T("&Generic dialogs"), dialogs_menu);
 #endif // USE_MODAL_PRESENTATION
 
 #if USE_SETTINGS_DIALOG
@@ -377,17 +386,27 @@ bool MyApp::OnInit()
     sheet_menu->Append(DIALOGS_PROPERTY_SHEET_BUTTONTOOLBOOK, _T("Button &Toolbook sheet\tShift-Ctrl-U"));
 #endif
 */
-    file_menu->Append(wxID_ANY, _T("&Property sheets"), sheet_menu);
+    menuDlg->Append(wxID_ANY, _T("&Property sheets"), sheet_menu);
 #endif // USE_SETTINGS_DIALOG
 
-    file_menu->Append(DIALOGS_REQUEST, _T("&Request user attention\tCtrl-R"));
+    menuDlg->Append(DIALOGS_REQUEST, _T("&Request user attention\tCtrl-R"));
+
+    menuDlg->AppendSeparator();
+    menuDlg->Append(wxID_EXIT, _T("E&xit\tAlt-X"));
 
-    file_menu->AppendSeparator();
-    file_menu->Append(wxID_EXIT, _T("E&xit\tAlt-X"));
+#if wxUSE_ABOUTDLG
+    wxMenu *menuHelp = new wxMenu;
+    menuHelp->Append(DIALOGS_ABOUTDLG_SIMPLE, _T("&About (simple)..."));
+    menuHelp->Append(DIALOGS_ABOUTDLG_FANCY, _T("About (&fancy)..."));
+#endif // wxUSE_ABOUTDLG
 
-    wxMenuBar *menu_bar = new wxMenuBar;
-    menu_bar->Append(file_menu, _T("&File"));
-    frame->SetMenuBar(menu_bar);
+    wxMenuBar *menubar = new wxMenuBar;
+    menubar->Append(menuDlg, _T("&Dialogs"));
+#if wxUSE_ABOUTDLG
+    menubar->Append(menuHelp, _T("&Help"));
+#endif // wxUSE_ABOUTDLG
+
+    frame->SetMenuBar(menubar);
 
     myCanvas = new MyCanvas(frame);
     myCanvas->SetBackgroundColour(*wxWHITE);
@@ -1153,6 +1172,35 @@ void MyFrame::ShowProgress( wxCommandEvent& WXUNUSED(event) )
 
 #endif // wxUSE_PROGRESSDLG
 
+#if wxUSE_ABOUTDLG
+
+static void CommonAboutInfoInit(wxAboutDialogInfo& info)
+{
+    info.SetName(_T("Dialogs Sample"));
+    info.SetVersion(wxVERSION_NUM_DOT_STRING);
+    info.SetDescription(_T("This sample shows different wxWidgets dialogs"));
+    info.SetCopyright(_T("© 1998-2006 wxWidgets dev team"));
+}
+
+void MyFrame::ShowSimpleAboutDialog(wxCommandEvent& WXUNUSED(event))
+{
+    wxAboutDialogInfo info;
+    CommonAboutInfoInit(info);
+
+    wxAboutBox(info);
+}
+
+void MyFrame::ShowFancyAboutDialog(wxCommandEvent& WXUNUSED(event))
+{
+    wxAboutDialogInfo info;
+    CommonAboutInfoInit(info);
+    info.SetWebSite(_T("http://www.wxwidgets.org/"), _T("wxWidgets web site"));
+
+    wxAboutBox(info);
+}
+
+#endif // wxUSE_ABOUTDLG
+
 #if wxUSE_BUSYINFO
 
 void MyFrame::ShowBusyInfo(wxCommandEvent& WXUNUSED(event))
index 45e8d92843148f9bea0c8533f5bc16289b9fc29d..23fa45fc0cf81b9f0b3f01a5309ea0683d5a545c 100644 (file)
@@ -244,6 +244,11 @@ public:
     void ShowProgress(wxCommandEvent& event);
 #endif // wxUSE_PROGRESSDLG
 
+#if wxUSE_ABOUTDLG
+    void ShowSimpleAboutDialog(wxCommandEvent& event);
+    void ShowFancyAboutDialog(wxCommandEvent& event);
+#endif // wxUSE_ABOUTDLG
+
 #if wxUSE_BUSYINFO
     void ShowBusyInfo(wxCommandEvent& event);
 #endif // wxUSE_BUSYINFO
@@ -330,6 +335,8 @@ enum
     DIALOGS_CENTRE_PARENT,
     DIALOGS_MODELESS_BTN,
     DIALOGS_PROGRESS,
+    DIALOGS_ABOUTDLG_SIMPLE,
+    DIALOGS_ABOUTDLG_FANCY,
     DIALOGS_BUSYINFO,
     DIALOGS_FIND,
     DIALOGS_REPLACE,
diff --git a/src/generic/aboutdlgg.cpp b/src/generic/aboutdlgg.cpp
new file mode 100644 (file)
index 0000000..c915bba
--- /dev/null
@@ -0,0 +1,135 @@
+///////////////////////////////////////////////////////////////////////////////
+// Name:        src/generic/aboutdlgg.cpp
+// Purpose:     implements wxGenericAboutBox() function
+// Author:      Vadim Zeitlin
+// Created:     2006-10-08
+// RCS-ID:      $Id$
+// Copyright:   (c) 2006 Vadim Zeitlin <vadim@wxwindows.org>
+// Licence:     wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+// ============================================================================
+// declarations
+// ============================================================================
+
+// ----------------------------------------------------------------------------
+// headers
+// ----------------------------------------------------------------------------
+
+// for compilers that support precompilation, includes "wx.h".
+#include "wx/wxprec.h"
+
+#ifdef __BORLANDC__
+    #pragma hdrstop
+#endif
+
+#if wxUSE_ABOUTDLG
+
+#ifndef WX_PRECOMP
+    #include "wx/sizer.h"
+
+    #include "wx/statbmp.h"
+    #include "wx/stattext.h"
+#endif //WX_PRECOMP
+
+#include "wx/aboutdlg.h"
+#include "wx/generic/aboutdlgg.h"
+
+#include "wx/hyperlink.h"
+
+// ============================================================================
+// wxAboutDialog implementation
+// ============================================================================
+
+bool wxAboutDialog::Create(const wxAboutDialogInfo& info)
+{
+    // TODO: should we use main frame as parent by default here?
+    if ( !wxDialog::Create(NULL, wxID_ANY, _("About ") + info.GetName()) )
+        return false;
+
+    m_sizerText = new wxBoxSizer(wxVERTICAL);
+    wxString nameAndVersion = info.GetName();
+    if ( info.HasVersion() )
+        nameAndVersion << _T(' ') << info.GetVersion();
+    wxStaticText *label = new wxStaticText(this, wxID_ANY, nameAndVersion);
+    wxFont fontBig(*wxNORMAL_FONT);
+    fontBig.SetPointSize(fontBig.GetPointSize() + 2);
+    fontBig.SetWeight(wxFONTWEIGHT_BOLD);
+    label->SetFont(fontBig);
+
+    m_sizerText->Add(label, wxSizerFlags().Centre().Border());
+    m_sizerText->AddSpacer(5);
+
+    AddText(info.GetCopyright());
+    AddText(info.GetDescription());
+
+    if ( info.HasWebSite() )
+    {
+#if wxUSE_HYPERLINKCTRL
+        AddControl(new wxHyperlinkCtrl(this, wxID_ANY,
+                                       info.GetWebSiteDescription(),
+                                       info.GetWebSiteURL()));
+#else
+        AddText(info.GetWebSiteURL());
+#endif // wxUSE_HYPERLINKCTRL/!wxUSE_HYPERLINKCTRL
+    }
+
+    // TODO: add licence
+
+    // TODO: add credits (developers, artists, doc writers, translators)
+
+
+    wxSizer *sizerIconAndText = new wxBoxSizer(wxHORIZONTAL);
+#if wxUSE_STATBMP
+    if ( info.HasIcon() )
+        sizerIconAndText->Add(new wxStaticBitmap(this, wxID_ANY, info.GetIcon()));
+#endif // wxUSE_STATBMP
+    sizerIconAndText->Add(m_sizerText, wxSizerFlags(1).Expand());
+
+    wxSizer *sizerTop = new wxBoxSizer(wxVERTICAL);
+    sizerTop->Add(sizerIconAndText, wxSizerFlags(1).Expand().Border());
+    sizerTop->Add(new wxButton(this, wxID_OK), wxSizerFlags().Right().Border());
+    SetSizerAndFit(sizerTop);
+
+    CentreOnScreen();
+    return true;
+}
+
+void wxAboutDialog::AddControl(wxWindow *win)
+{
+    wxCHECK_RET( m_sizerText, _T("can only be called after Create()") );
+    wxASSERT_MSG( win, _T("can't add NULL window to about dialog") );
+
+    m_sizerText->Add(win, wxSizerFlags().Border(wxDOWN).Centre());
+}
+
+void wxAboutDialog::AddText(const wxString& text)
+{
+    if ( !text.empty() )
+        AddControl(new wxStaticText(this, wxID_ANY, text));
+}
+
+// ----------------------------------------------------------------------------
+// public functions
+// ----------------------------------------------------------------------------
+
+void wxGenericAboutBox(const wxAboutDialogInfo& info)
+{
+    wxAboutDialog dlg(info);
+    dlg.ShowModal();
+}
+
+// currently wxAboutBox is implemented natively only under wxMSW, so we provide
+// it here for the other platforms (this is going to change when GTK+ and Mac
+// native versions are implemented)
+#ifndef __WXMSW__
+
+void wxAboutBox(const wxAboutDialogInfo& info)
+{
+    wxGenericAboutBox(info);
+}
+
+#endif // platforms without native about dialog
+
+
+#endif // wxUSE_ABOUTDLG
diff --git a/src/msw/aboutdlg.cpp b/src/msw/aboutdlg.cpp
new file mode 100644 (file)
index 0000000..9b6ee68
--- /dev/null
@@ -0,0 +1,94 @@
+///////////////////////////////////////////////////////////////////////////////
+// Name:        src/msw/aboutdlg.cpp
+// Purpose:     implementation of wxAboutBox() for wxMSW
+// Author:      Vadim Zeitlin
+// Created:     2006-10-07
+// RCS-ID:      $Id$
+// Copyright:   (c) 2006 Vadim Zeitlin <vadim@wxwindows.org>
+// Licence:     wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+// ============================================================================
+// declarations
+// ============================================================================
+
+// ----------------------------------------------------------------------------
+// headers
+// ----------------------------------------------------------------------------
+
+// for compilers that support precompilation, includes "wx.h".
+#include "wx/wxprec.h"
+
+#ifdef __BORLANDC__
+    #pragma hdrstop
+#endif
+
+#if wxUSE_ABOUTDLG
+
+#ifndef WX_PRECOMP
+#endif //WX_PRECOMP
+
+#include "wx/aboutdlg.h"
+#include "wx/generic/aboutdlgg.h"
+
+// ============================================================================
+// implementation
+// ============================================================================
+
+// helper function: returns all array elements in a single comma-separated and
+// newline-terminated string
+static wxString AllAsString(const wxArrayString& a)
+{
+    wxString s;
+    const size_t count = a.size();
+    for ( size_t n = 0; n < count; n++ )
+    {
+        s << a[n] << (n == count - 1 ? _T("\n") : _T(", "));
+    }
+
+    return s;
+}
+
+// our public entry point
+void wxAboutBox(const wxAboutDialogInfo& info)
+{
+    // we prefer to show a simple message box if we don't have any fields which
+    // can't be shown in it because as much as there is a standard about box
+    // under MSW at all, this is it
+    if ( info.HasWebSite() || info.HasIcon() || info.HasLicence() )
+    {
+        // we need to use the full-blown generic version
+        wxGenericAboutBox(info);
+    }
+    else // simple "native" version should do
+    {
+        // build the text to show in the box
+        const wxString name = info.GetName();
+        wxString msg;
+        msg << name;
+        if ( info.HasVersion() )
+            msg << _(" Version ") << info.GetVersion();
+        msg << _T('\n');
+
+        if ( info.HasCopyright() )
+            msg << info.GetCopyright() << _T('\n');
+
+        msg << info.GetDescription() << _T('\n');
+
+        if ( info.HasDevelopers() )
+            msg << _("Developed by ") << AllAsString(info.GetDevelopers());
+
+        if ( info.HasDocWriters() )
+            msg << _("Documentation by ") << AllAsString(info.GetDocWriters());
+
+        if ( info.HasArtists() )
+            msg << _("Graphics art by ") << AllAsString(info.GetArtists());
+
+        if ( info.HasTranslators() )
+            msg << _("Translations by ") << AllAsString(info.GetTranslators());
+
+        wxMessageBox(msg, _T("About ") + name);
+    }
+}
+
+#endif // wxUSE_ABOUTDLG