1. changed wxIconBundle to use m_refData and COW to make copying icon bundles

fast (which was needed for 2)
2. make it possible to return wxIconBundles from wxArtProvider
3. implement Mac-specific wxArtProvider doing (2)

(modified patch 1581960)


git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@45309 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Vadim Zeitlin
2007-04-07 19:59:51 +00:00
parent 0597e7f977
commit 527343602e
21 changed files with 629 additions and 160 deletions

View File

@@ -4391,6 +4391,7 @@ COND_TOOLKIT_MAC___GUI_SRC_OBJECTS = \
monodll_accel.o \ monodll_accel.o \
monodll_aga.o \ monodll_aga.o \
monodll_app.o \ monodll_app.o \
monodll_artmac.o \
monodll_bitmap.o \ monodll_bitmap.o \
monodll_bmpbuttn.o \ monodll_bmpbuttn.o \
monodll_brush.o \ monodll_brush.o \
@@ -6193,6 +6194,7 @@ COND_TOOLKIT_MAC___GUI_SRC_OBJECTS_1 = \
monolib_accel.o \ monolib_accel.o \
monolib_aga.o \ monolib_aga.o \
monolib_app.o \ monolib_app.o \
monolib_artmac.o \
monolib_bitmap.o \ monolib_bitmap.o \
monolib_bmpbuttn.o \ monolib_bmpbuttn.o \
monolib_brush.o \ monolib_brush.o \
@@ -8224,6 +8226,7 @@ COND_TOOLKIT_MAC___GUI_SRC_OBJECTS_2 = \
coredll_accel.o \ coredll_accel.o \
coredll_aga.o \ coredll_aga.o \
coredll_app.o \ coredll_app.o \
coredll_artmac.o \
coredll_bitmap.o \ coredll_bitmap.o \
coredll_bmpbuttn.o \ coredll_bmpbuttn.o \
coredll_brush.o \ coredll_brush.o \
@@ -9693,6 +9696,7 @@ COND_TOOLKIT_MAC___GUI_SRC_OBJECTS_3 = \
corelib_accel.o \ corelib_accel.o \
corelib_aga.o \ corelib_aga.o \
corelib_app.o \ corelib_app.o \
corelib_artmac.o \
corelib_bitmap.o \ corelib_bitmap.o \
corelib_bmpbuttn.o \ corelib_bmpbuttn.o \
corelib_brush.o \ corelib_brush.o \
@@ -13558,6 +13562,9 @@ monodll_textctrlce.o: $(srcdir)/src/msw/wince/textctrlce.cpp $(MONODLL_ODEP)
monodll_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(MONODLL_ODEP) monodll_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(MONODLL_ODEP)
$(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp
monodll_artmac.o: $(srcdir)/src/mac/carbon/artmac.cpp $(MONODLL_ODEP)
$(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/mac/carbon/artmac.cpp
monodll_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(MONODLL_ODEP) monodll_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(MONODLL_ODEP)
$(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp
@@ -17731,6 +17738,9 @@ monolib_textctrlce.o: $(srcdir)/src/msw/wince/textctrlce.cpp $(MONOLIB_ODEP)
monolib_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(MONOLIB_ODEP) monolib_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(MONOLIB_ODEP)
$(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp
monolib_artmac.o: $(srcdir)/src/mac/carbon/artmac.cpp $(MONOLIB_ODEP)
$(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/mac/carbon/artmac.cpp
monolib_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(MONOLIB_ODEP) monolib_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(MONOLIB_ODEP)
$(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp
@@ -22915,6 +22925,9 @@ coredll_textctrlce.o: $(srcdir)/src/msw/wince/textctrlce.cpp $(COREDLL_ODEP)
coredll_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(COREDLL_ODEP) coredll_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(COREDLL_ODEP)
$(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp $(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp
coredll_artmac.o: $(srcdir)/src/mac/carbon/artmac.cpp $(COREDLL_ODEP)
$(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/mac/carbon/artmac.cpp
coredll_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(COREDLL_ODEP) coredll_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(COREDLL_ODEP)
$(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp $(CXXC) -c -o $@ $(COREDLL_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp
@@ -25891,6 +25904,9 @@ corelib_textctrlce.o: $(srcdir)/src/msw/wince/textctrlce.cpp $(CORELIB_ODEP)
corelib_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(CORELIB_ODEP) corelib_aga.o: $(srcdir)/src/mac/carbon/aga.cpp $(CORELIB_ODEP)
$(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp $(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/mac/carbon/aga.cpp
corelib_artmac.o: $(srcdir)/src/mac/carbon/artmac.cpp $(CORELIB_ODEP)
$(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/mac/carbon/artmac.cpp
corelib_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(CORELIB_ODEP) corelib_dccg.o: $(srcdir)/src/mac/carbon/dccg.cpp $(CORELIB_ODEP)
$(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp $(CXXC) -c -o $@ $(CORELIB_CXXFLAGS) $(srcdir)/src/mac/carbon/dccg.cpp

View File

@@ -2100,6 +2100,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file!
src/mac/carbon/accel.cpp src/mac/carbon/accel.cpp
src/mac/carbon/aga.cpp src/mac/carbon/aga.cpp
src/mac/carbon/app.cpp src/mac/carbon/app.cpp
src/mac/carbon/artmac.cpp
src/mac/carbon/bitmap.cpp src/mac/carbon/bitmap.cpp
src/mac/carbon/bmpbuttn.cpp src/mac/carbon/bmpbuttn.cpp
src/mac/carbon/brush.cpp src/mac/carbon/brush.cpp

View File

@@ -4486,7 +4486,7 @@ clean:
-if exist $(LIBDIRNAME)\wx$(PORTNAME)$(WXUNIVNAME)$(WX_RELEASE_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_gl.lib del $(LIBDIRNAME)\wx$(PORTNAME)$(WXUNIVNAME)$(WX_RELEASE_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_gl.lib -if exist $(LIBDIRNAME)\wx$(PORTNAME)$(WXUNIVNAME)$(WX_RELEASE_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_gl.lib del $(LIBDIRNAME)\wx$(PORTNAME)$(WXUNIVNAME)$(WX_RELEASE_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_gl.lib
cd ..\..\samples cd ..\..\samples
$(MAKE) -f makefile.vc $(MAKEARGS) clean $(MAKE) -f makefile.vc $(MAKEARGS) clean
cd $(MAKEDIR) cd "$(MAKEDIR)"
setup_h: $(SETUPHDIR)\wx ..\..\include\wx\$(__SETUP_H_SUBDIR_FILENAMES)\setup.h $(SETUPHDIR)\wx\setup.h $(SETUPHDIR)\wx\msw\rcdefs.h setup_h: $(SETUPHDIR)\wx ..\..\include\wx\$(__SETUP_H_SUBDIR_FILENAMES)\setup.h $(SETUPHDIR)\wx\setup.h $(SETUPHDIR)\wx\msw\rcdefs.h
@@ -4833,7 +4833,7 @@ $(LIBDIRNAME)\wx$(PORTNAME)$(WXUNIVNAME)$(WX_RELEASE_NODOT)$(WXUNICODEFLAG)$(WXD
sub_samples: sub_samples:
cd ..\..\samples cd ..\..\samples
$(MAKE) -f makefile.vc $(MAKEARGS) all $(MAKE) -f makefile.vc $(MAKEARGS) all
cd $(MAKEDIR) cd "$(MAKEDIR)"
$(LIBDIRNAME): $(LIBDIRNAME):
if not exist $(LIBDIRNAME) mkdir $(LIBDIRNAME) if not exist $(LIBDIRNAME) mkdir $(LIBDIRNAME)

View File

@@ -115,6 +115,7 @@ wxGTK:
wxMac: wxMac:
- Better IconRef support (Alan Shouls)
- Fix duplicate (empty) help menu in non-English programs (Andreas Jacobs) - Fix duplicate (empty) help menu in non-English programs (Andreas Jacobs)
- Allow accelerators to be used with buttons too (Ryan Wilcox) - Allow accelerators to be used with buttons too (Ryan Wilcox)
- Support resource forks in wxCopyFile() (Hank Schultz) - Support resource forks in wxCopyFile() (Hank Schultz)

View File

@@ -10,9 +10,10 @@ When wxWidgets needs to display an icon or a bitmap (e.g. in the standard file
dialog), it does not use a hard-coded resource but asks wxArtProvider for it dialog), it does not use a hard-coded resource but asks wxArtProvider for it
instead. This way users can plug in their own wxArtProvider class and easily instead. This way users can plug in their own wxArtProvider class and easily
replace standard art with their own version. All replace standard art with their own version. All
that is needed is to derive a class from wxArtProvider, override its that is needed is to derive a class from wxArtProvider, override either its
\helpref{CreateBitmap}{wxartprovidercreatebitmap} method and register the \helpref{CreateBitmap}{wxartprovidercreatebitmap} and/or its
provider with \helpref{CreateIconBundle}{wxartprovidercreateiconbundle} methods
and register the provider with
\helpref{wxArtProvider::Push}{wxartproviderpush}: \helpref{wxArtProvider::Push}{wxartproviderpush}:
\begin{verbatim} \begin{verbatim}
@@ -22,12 +23,20 @@ provider with
wxBitmap CreateBitmap(const wxArtID& id, wxBitmap CreateBitmap(const wxArtID& id,
const wxArtClient& client, const wxArtClient& client,
const wxSize size) const wxSize size)
// optionally override this one as well
wxIconBundle CreateIconBundle(const wxArtID& id,
const wxArtClient& client)
{ ... } { ... }
}; };
... ...
wxArtProvider::Push(new MyProvider); wxArtProvider::Push(new MyProvider);
\end{verbatim} \end{verbatim}
If you need bitmap images (of the same artwork) that should be displayed at different sizes
you should probably consider overriding \helpref{CreateIconBundle()}{wxartprovidercreateiconbundle}
and supplying icon bundles that contain different bitmap sizes.
There's another way of taking advantage of this class: you can use it in your code and use There's another way of taking advantage of this class: you can use it in your code and use
platform native icons as provided by \helpref{wxArtProvider::GetBitmap}{wxartprovidergetbitmap} or platform native icons as provided by \helpref{wxArtProvider::GetBitmap}{wxartprovidergetbitmap} or
\helpref{wxArtProvider::GetIcon}{wxartprovidergeticon} (NB: this is not yet really \helpref{wxArtProvider::GetIcon}{wxartprovidergeticon} (NB: this is not yet really
@@ -37,7 +46,7 @@ small).
\membersection{Identifying art resources}\label{artprovideridentifying} \membersection{Identifying art resources}\label{artprovideridentifying}
Every bitmap is known to wxArtProvider under an unique ID that is used by when Every bitmap and icon bundle are known to wxArtProvider under an unique ID that is used when
requesting a resource from it. The ID is represented by wxArtID type and can requesting a resource from it. The ID is represented by wxArtID type and can
have one of these predefined values (you can see bitmaps represented by these have one of these predefined values (you can see bitmaps represented by these
constants in the \helpref{artprov}{sampleartprovider} sample): constants in the \helpref{artprov}{sampleartprovider} sample):
@@ -159,10 +168,10 @@ by \helpref{GetBitmap}{wxartprovidergetbitmap}.
\func{wxBitmap}{CreateBitmap}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client}, \param{const wxSize\& }{size}} \func{wxBitmap}{CreateBitmap}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client}, \param{const wxSize\& }{size}}
Derived art provider classes must override this method to create requested Derived art provider classes must override this method or the CreateIconBundle() method
art resource. Note that returned bitmaps are cached by wxArtProvider and it is therefore to create requested art resource. Note that returned bitmaps are cached by wxArtProvider
not necessary to optimize CreateBitmap for speed (e.g. you may create wxBitmap objects and it is therefore not necessary to optimize CreateBitmap() for speed (e.g. you may create
from XPMs here). wxBitmap objects from XPMs here).
\wxheading{Parameters} \wxheading{Parameters}
@@ -178,10 +187,33 @@ dimensions, it will be automatically rescaled to meet client's request.}
This is {\bf not} part of wxArtProvider's public API, use This is {\bf not} part of wxArtProvider's public API, use
\helpref{wxArtProvider::GetBitmap}{wxartprovidergetbitmap} or \helpref{wxArtProvider::GetBitmap}{wxartprovidergetbitmap} or
\helpref{wxArtProvider::GetIconBundle}{wxartprovidergeticonbundle} or
\helpref{wxArtProvider::GetIcon}{wxartprovidergeticon} \helpref{wxArtProvider::GetIcon}{wxartprovidergeticon}
to query wxArtProvider for a resource. to query wxArtProvider for a resource.
\func{wxIconBundle}{CreateIconBundle}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client}}
Derived art provider classes must override this method or the CreateIconBundle method
to create requested art resource. Note that returned icon bundles are cached by wxArtProvider
and it is therefore not necessary to optimize CreateIconBundle for speed (e.g. you may create icon bundles
from artwork resources here).
\wxheading{Parameters}
\docparam{id}{wxArtID unique identifier of the icon bundle.}
\docparam{client}{wxArtClient identifier of the client (i.e. who is asking for the icon bundle).
This only servers as a hint.}
\wxheading{Note}
This is {\bf not} part of wxArtProvider's public API, use
\helpref{wxArtProvider::GetBitmap}{wxartprovidergetbitmap} or
\helpref{wxArtProvider::GetIconBundle}{wxartprovidergeticonbundle} or
\helpref{wxArtProvider::GetIcon}{wxartprovidergeticon}
to query wxArtProvider for a resource.
\membersection{wxArtProvider::Delete}\label{wxartproviderdelete} \membersection{wxArtProvider::Delete}\label{wxartproviderdelete}
\func{static bool}{Delete}{\param{wxArtProvider* }{provider}} \func{static bool}{Delete}{\param{wxArtProvider* }{provider}}
@@ -208,6 +240,23 @@ Query registered providers for bitmap with given ID.
The bitmap if one of registered providers recognizes the ID or wxNullBitmap otherwise. The bitmap if one of registered providers recognizes the ID or wxNullBitmap otherwise.
\membersection{wxArtProvider::GetIconBundle}\label{wxartprovidergeticonbundle}
\func{static wxIconBundle}{GetIconBundle}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client = wxART\_OTHER}}
Query registered providers for icon bundle with given ID.
\wxheading{Parameters}
\docparam{id}{wxArtID unique identifier of the icon bundle.}
\docparam{client}{wxArtClient identifier of the client (i.e. who is asking for the icon bundle).}
\wxheading{Return value}
The icon bundle if one of registered providers recognizes the ID or wxNullIconBundle otherwise.
\membersection{wxArtProvider::GetIcon}\label{wxartprovidergeticon} \membersection{wxArtProvider::GetIcon}\label{wxartprovidergeticon}
\func{static wxIcon}{GetIcon}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client = wxART\_OTHER}, \param{const wxSize\& }{size = wxDefaultSize}} \func{static wxIcon}{GetIcon}{\param{const wxArtID\& }{id}, \param{const wxArtClient\& }{client = wxART\_OTHER}, \param{const wxSize\& }{size = wxDefaultSize}}

View File

@@ -6,7 +6,12 @@ see also \helpref{wxDialog::SetIcons}{wxdialogseticons} and
\wxheading{Derived from} \wxheading{Derived from}
No base class \helpref{wxGDIObject}{wxgdiobject}\\
\helpref{wxObject}{wxobject}
\wxheading{Predefined objects}
{\bf wxNullIconBundle}
\latexignore{\rtfignore{\wxheading{Members}}} \latexignore{\rtfignore{\wxheading{Members}}}
@@ -50,7 +55,7 @@ replaced by the new one.
\membersection{wxIconBundle::GetIcon}\label{wxiconbundlegeticon} \membersection{wxIconBundle::GetIcon}\label{wxiconbundlegeticon}
\constfunc{const wxIcon\&}{GetIcon}{\param{const wxSize\& }{size}} \constfunc{wxIcon}{GetIcon}{\param{const wxSize\& }{size}}
Returns the icon with the given size; if no such icon exists, Returns the icon with the given size; if no such icon exists,
returns the icon with size wxSYS\_ICON\_X/wxSYS\_ICON\_Y; returns the icon with size wxSYS\_ICON\_X/wxSYS\_ICON\_Y;
@@ -58,13 +63,24 @@ if no such icon exists,
returns the first icon in the bundle. If size = wxSize( -1, -1 ), returns the first icon in the bundle. If size = wxSize( -1, -1 ),
returns the icon with size wxSYS\_ICON\_X/wxSYS\_ICON\_Y. returns the icon with size wxSYS\_ICON\_X/wxSYS\_ICON\_Y.
\constfunc{const wxIcon\&}{GetIcon}{\param{wxCoord }{size = -1}} \constfunc{wxIcon}{GetIcon}{\param{wxCoord }{size = -1}}
Same as GetIcon( wxSize( size, size ) ). Same as GetIcon( wxSize( size, size ) ).
\membersection{wxIconBundle::operator=}\label{wxiconbundleoperatorassign} \membersection{wxIconBundle::operator $=$}\label{wxiconbundleoperatorassign}
\func{const wxIconBundle\&}{operator=}{\param{const wxIconBundle\& }{ic}} \func{wxIconBundle\&}{operator $=$}{\param{const wxIconBundle\& }{ic}}
Assignment operator. Assignment operator, using \helpref{reference counting}{trefcount}.
\membersection{wxIconBundle::operator $==$}\label{wxiconbundleoperatorequals}
\func{bool}{operator $==$}{\param{const wxIconBundle\& }{ic}}
Equality operator. This returns \true if two icon bundles are equal.
\membersection{wxIconBundle::operator $!=$}\label{wxiconbundleoperatornotequals}
\func{bool}{operator $!=$}{\param{const wxIconBundle\& }{ic}}
Inequality operator. This returns \true if two icon bundles are not equal.

View File

@@ -15,6 +15,7 @@
#include "wx/string.h" #include "wx/string.h"
#include "wx/bitmap.h" #include "wx/bitmap.h"
#include "wx/icon.h" #include "wx/icon.h"
#include "wx/iconbndl.h"
class WXDLLEXPORT wxArtProvidersList; class WXDLLEXPORT wxArtProvidersList;
class WXDLLEXPORT wxArtProviderCache; class WXDLLEXPORT wxArtProviderCache;
@@ -44,6 +45,7 @@ typedef wxString wxArtID;
#define wxART_HELP_BROWSER wxART_MAKE_CLIENT_ID(wxART_HELP_BROWSER) #define wxART_HELP_BROWSER wxART_MAKE_CLIENT_ID(wxART_HELP_BROWSER)
#define wxART_MESSAGE_BOX wxART_MAKE_CLIENT_ID(wxART_MESSAGE_BOX) #define wxART_MESSAGE_BOX wxART_MAKE_CLIENT_ID(wxART_MESSAGE_BOX)
#define wxART_BUTTON wxART_MAKE_CLIENT_ID(wxART_BUTTON) #define wxART_BUTTON wxART_MAKE_CLIENT_ID(wxART_BUTTON)
#define wxART_LIST wxART_MAKE_CLIENT_ID(wxART_LIST)
#define wxART_OTHER wxART_MAKE_CLIENT_ID(wxART_OTHER) #define wxART_OTHER wxART_MAKE_CLIENT_ID(wxART_OTHER)
@@ -146,6 +148,11 @@ public:
const wxArtClient& client = wxART_OTHER, const wxArtClient& client = wxART_OTHER,
const wxSize& size = wxDefaultSize); const wxSize& size = wxDefaultSize);
// Query the providers for iconbundle with given ID and return it. Return
// wxNullIconBundle if no provider provides it.
static wxIconBundle GetIconBundle(const wxArtID& id,
const wxArtClient& client = wxART_OTHER);
// Get the size hint of an icon from a specific wxArtClient, queries // Get the size hint of an icon from a specific wxArtClient, queries
// the topmost provider if platform_dependent = false // the topmost provider if platform_dependent = false
static wxSize GetSizeHint(const wxArtClient& client, bool platform_dependent = false); static wxSize GetSizeHint(const wxArtClient& client, bool platform_dependent = false);
@@ -177,12 +184,18 @@ protected:
return GetSizeHint(client, true); return GetSizeHint(client, true);
} }
// Derived classes must override this method to create requested // Derived classes must override CreateBitmap or CreateIconBundle
// art resource. This method is called only once per instance's // (or both) to create requested art resource. This method is called
// lifetime for each requested wxArtID. // only once per instance's lifetime for each requested wxArtID.
virtual wxBitmap CreateBitmap(const wxArtID& WXUNUSED(id), virtual wxBitmap CreateBitmap(const wxArtID& WXUNUSED(id),
const wxArtClient& WXUNUSED(client), const wxArtClient& WXUNUSED(client),
const wxSize& WXUNUSED(size)) = 0; const wxSize& WXUNUSED(size)) { return wxNullBitmap; }
virtual wxIconBundle CreateIconBundle(const wxArtID& WXUNUSED(id),
const wxArtClient& WXUNUSED(client))
{
return wxNullIconBundle;
}
private: private:
static void CommonAddingProvider(); static void CommonAddingProvider();

View File

@@ -37,6 +37,7 @@ class WXDLLIMPEXP_CORE wxPalette;
class WXDLLIMPEXP_CORE wxPen; class WXDLLIMPEXP_CORE wxPen;
class WXDLLIMPEXP_CORE wxRegion; class WXDLLIMPEXP_CORE wxRegion;
class WXDLLIMPEXP_BASE wxString; class WXDLLIMPEXP_BASE wxString;
class WXDLLIMPEXP_CORE wxIconBundle;
// --------------------------------------------------------------------------- // ---------------------------------------------------------------------------
// constants // constants
@@ -712,9 +713,10 @@ extern WXDLLEXPORT_DATA(wxIcon) wxNullIcon;
extern WXDLLEXPORT_DATA(wxCursor) wxNullCursor; extern WXDLLEXPORT_DATA(wxCursor) wxNullCursor;
extern WXDLLEXPORT_DATA(wxPen) wxNullPen; extern WXDLLEXPORT_DATA(wxPen) wxNullPen;
extern WXDLLEXPORT_DATA(wxBrush) wxNullBrush; extern WXDLLEXPORT_DATA(wxBrush) wxNullBrush;
extern WXDLLEXPORT_DATA(wxPalette) wxNullPalette; extern WXDLLEXPORT_DATA(wxPalette) wxNullPalette;
extern WXDLLEXPORT_DATA(wxFont) wxNullFont; extern WXDLLEXPORT_DATA(wxFont) wxNullFont;
extern WXDLLEXPORT_DATA(wxColour) wxNullColour; extern WXDLLEXPORT_DATA(wxColour) wxNullColour;
extern WXDLLEXPORT_DATA(wxIconBundle) wxNullIconBundle;
extern WXDLLEXPORT_DATA(wxColourDatabase*) wxTheColourDatabase; extern WXDLLEXPORT_DATA(wxColourDatabase*) wxTheColourDatabase;

View File

@@ -13,57 +13,80 @@
#define _WX_ICONBNDL_H_ #define _WX_ICONBNDL_H_
#include "wx/dynarray.h" #include "wx/dynarray.h"
#include "wx/gdiobj.h"
// for wxSize // for wxSize
#include "wx/gdicmn.h" #include "wx/gdicmn.h"
#include "wx/icon.h"
class WXDLLIMPEXP_CORE wxIcon; class WXDLLIMPEXP_CORE wxIcon;
class WXDLLIMPEXP_BASE wxString; class WXDLLIMPEXP_BASE wxString;
WX_DECLARE_EXPORTED_OBJARRAY( wxIcon, wxIconArray ); class WXDLLEXPORT wxIconBundle;
WX_DECLARE_EXPORTED_OBJARRAY(wxIcon, wxIconArray);
// this class can't load bitmaps of type wxBITMAP_TYPE_ICO_RESOURCE, // this class can't load bitmaps of type wxBITMAP_TYPE_ICO_RESOURCE,
// if you need them, you have to load them manually and call // if you need them, you have to load them manually and call
// wxIconCollection::AddIcon // wxIconCollection::AddIcon
class WXDLLEXPORT wxIconBundle class WXDLLEXPORT wxIconBundle : public wxGDIObject
{ {
public: public:
// default constructor // default constructor
wxIconBundle() : m_icons() {} wxIconBundle();
// initializes the bundle with the icon(s) found in the file // initializes the bundle with the icon(s) found in the file
wxIconBundle( const wxString& file, long type ) : m_icons() wxIconBundle(const wxString& file, long type);
{ AddIcon( file, type ); }
// initializes the bundle with a single icon // initializes the bundle with a single icon
wxIconBundle( const wxIcon& icon ) : m_icons() wxIconBundle(const wxIcon& icon);
{ AddIcon( icon ); }
const wxIconBundle& operator =( const wxIconBundle& ic ); // initializes the bundle from another icon bundle
wxIconBundle( const wxIconBundle& ic ) : m_icons() wxIconBundle(const wxIconBundle& icon);
{ *this = ic; }
wxIconBundle& operator=(const wxIconBundle& ic)
{ if ( this != &ic) Ref(ic); return *this; }
virtual bool IsOk() const;
~wxIconBundle() { DeleteIcons(); }
// adds all the icons contained in the file to the collection, // adds all the icons contained in the file to the collection,
// if the collection already contains icons with the same // if the collection already contains icons with the same
// width and height, they are replaced // width and height, they are replaced
void AddIcon( const wxString& file, long type ); void AddIcon(const wxString& file, long type);
// adds the icon to the collection, if the collection already // adds the icon to the collection, if the collection already
// contains an icon with the same width and height, it is // contains an icon with the same width and height, it is
// replaced // replaced
void AddIcon( const wxIcon& icon ); void AddIcon(const wxIcon& icon);
// returns the icon with the given size; if no such icon exists, // returns the icon with the given size; if no such icon exists,
// returns the icon with size wxSYS_ICON_[XY]; if no such icon exists, // returns the icon with size wxSYS_ICON_[XY]; if no such icon exists,
// returns the first icon in the bundle // returns the first icon in the bundle
const wxIcon& GetIcon( const wxSize& size ) const; wxIcon GetIcon(const wxSize& size) const;
// equivalent to GetIcon( wxSize( size, size ) ) // equivalent to GetIcon( wxSize( size, size ) )
const wxIcon& GetIcon( wxCoord size = wxDefaultCoord ) const wxIcon GetIcon(wxCoord size = wxDefaultCoord) const
{ return GetIcon( wxSize( size, size ) ); } { return GetIcon( wxSize( size, size ) ); }
// enumerate all icons in the bundle: don't use these functions if ti can
// be avoided, using GetIcon() directly is better
// return the number of available icons
size_t GetIconCount() const;
// return the icon at index (must be < GetIconCount())
wxIcon GetIconByIndex(size_t n) const;
protected:
virtual wxObjectRefData *CreateRefData() const;
virtual wxObjectRefData *CloneRefData(const wxObjectRefData *data) const;
private: private:
// delete all icons // delete all icons
void DeleteIcons(); void DeleteIcons();
public:
wxIconArray m_icons; DECLARE_DYNAMIC_CLASS(wxIconBundle)
}; };
#endif #endif // _WX_ICONBNDL_H_
// _WX_ICONBNDL_H_

View File

@@ -29,6 +29,9 @@ public:
{ {
LoadFile(loc.GetFileName(), wxBITMAP_TYPE_ICON); LoadFile(loc.GetFileName(), wxBITMAP_TYPE_ICON);
} }
wxIcon(WXHICON icon, const wxSize& size);
virtual ~wxIcon(); virtual ~wxIcon();
bool LoadFile(const wxString& name, wxBitmapType flags /* = wxBITMAP_TYPE_ICON_RESOURCE */ , bool LoadFile(const wxString& name, wxBitmapType flags /* = wxBITMAP_TYPE_ICON_RESOURCE */ ,

View File

@@ -145,7 +145,7 @@ public:
virtual bool IsIconized() const = 0; virtual bool IsIconized() const = 0;
// get the frame icon // get the frame icon
const wxIcon& GetIcon() const { return m_icons.GetIcon( -1 ); } wxIcon GetIcon() const { return m_icons.GetIcon( -1 ); }
// get the frame icons // get the frame icons
const wxIconBundle& GetIcons() const { return m_icons; } const wxIconBundle& GetIcons() const { return m_icons; }

View File

@@ -24,6 +24,7 @@
#include "wx/colordlg.h" #include "wx/colordlg.h"
#include "wx/numdlg.h" #include "wx/numdlg.h"
#include "wx/artprov.h"
#include "wx/image.h" #include "wx/image.h"
#include "wx/imaglist.h" #include "wx/imaglist.h"
#include "wx/treectrl.h" #include "wx/treectrl.h"
@@ -96,6 +97,7 @@ BEGIN_EVENT_TABLE(MyFrame, wxFrame)
MENU_LINK(DeleteAll) MENU_LINK(DeleteAll)
MENU_LINK(Recreate) MENU_LINK(Recreate)
MENU_LINK(ToggleImages) MENU_LINK(ToggleImages)
MENU_LINK(ToggleAlternateImages)
MENU_LINK(ToggleButtons) MENU_LINK(ToggleButtons)
MENU_LINK(SetImageSize) MENU_LINK(SetImageSize)
MENU_LINK(CollapseAndReset) MENU_LINK(CollapseAndReset)
@@ -209,6 +211,7 @@ MyFrame::MyFrame(const wxString& title, int x, int y, int w, int h)
style_menu->AppendCheckItem(TreeTest_ToggleSel, wxT("Toggle &selection mode")); style_menu->AppendCheckItem(TreeTest_ToggleSel, wxT("Toggle &selection mode"));
#endif // NO_MULTIPLE_SELECTION #endif // NO_MULTIPLE_SELECTION
style_menu->AppendCheckItem(TreeTest_ToggleImages, wxT("Toggle show ima&ges")); style_menu->AppendCheckItem(TreeTest_ToggleImages, wxT("Toggle show ima&ges"));
style_menu->AppendCheckItem(TreeTest_ToggleAlternateImages, wxT("Toggle alternate images"));
style_menu->Append(TreeTest_SetImageSize, wxT("Set image si&ze...")); style_menu->Append(TreeTest_SetImageSize, wxT("Set image si&ze..."));
style_menu->AppendSeparator(); style_menu->AppendSeparator();
style_menu->Append(TreeTest_SetFgColour, wxT("Set &foreground colour...")); style_menu->Append(TreeTest_SetFgColour, wxT("Set &foreground colour..."));
@@ -276,6 +279,7 @@ MyFrame::MyFrame(const wxString& title, int x, int y, int w, int h)
CreateTreeWithDefStyle(); CreateTreeWithDefStyle();
menu_bar->Check(TreeTest_ToggleImages, true); menu_bar->Check(TreeTest_ToggleImages, true);
menu_bar->Check(TreeTest_ToggleAlternateImages, false);
#if wxUSE_STATUSBAR #if wxUSE_STATUSBAR
// create a status bar // create a status bar
@@ -601,6 +605,14 @@ void MyFrame::OnToggleImages(wxCommandEvent& WXUNUSED(event))
} }
} }
void MyFrame::OnToggleAlternateImages(wxCommandEvent& WXUNUSED(event))
{
bool alternateImages = m_treeCtrl->AlternateImages();
m_treeCtrl->SetAlternateImages(!alternateImages);
m_treeCtrl->CreateImageList(0);
}
void MyFrame::OnToggleButtons(wxCommandEvent& WXUNUSED(event)) void MyFrame::OnToggleButtons(wxCommandEvent& WXUNUSED(event))
{ {
#if USE_GENERIC_TREECTRL || !defined(__WXMSW__) #if USE_GENERIC_TREECTRL || !defined(__WXMSW__)
@@ -706,7 +718,8 @@ IMPLEMENT_DYNAMIC_CLASS(MyTreeCtrl, wxTreeCtrl)
MyTreeCtrl::MyTreeCtrl(wxWindow *parent, const wxWindowID id, MyTreeCtrl::MyTreeCtrl(wxWindow *parent, const wxWindowID id,
const wxPoint& pos, const wxSize& size, const wxPoint& pos, const wxSize& size,
long style) long style)
: wxTreeCtrl(parent, id, pos, size, style) : wxTreeCtrl(parent, id, pos, size, style),
m_alternateImages(false)
{ {
m_reverseSort = false; m_reverseSort = false;
@@ -734,15 +747,29 @@ void MyTreeCtrl::CreateImageList(int size)
// should correspond to TreeCtrlIcon_xxx enum // should correspond to TreeCtrlIcon_xxx enum
wxBusyCursor wait; wxBusyCursor wait;
wxIcon icons[5]; wxIcon icons[5];
icons[0] = wxIcon(icon1_xpm);
icons[1] = wxIcon(icon2_xpm);
icons[2] = wxIcon(icon3_xpm);
icons[3] = wxIcon(icon4_xpm);
icons[4] = wxIcon(icon5_xpm);
int sizeOrig = icons[0].GetWidth(); if (m_alternateImages)
{
icons[TreeCtrlIcon_File] = wxIcon(icon1_xpm);
icons[TreeCtrlIcon_FileSelected] = wxIcon(icon2_xpm);
icons[TreeCtrlIcon_Folder] = wxIcon(icon3_xpm);
icons[TreeCtrlIcon_FolderSelected] = wxIcon(icon4_xpm);
icons[TreeCtrlIcon_FolderOpened] = wxIcon(icon5_xpm);
}
else
{
wxSize iconSize(size, size);
icons[TreeCtrlIcon_File] =
icons[TreeCtrlIcon_FileSelected] = wxArtProvider::GetIcon(wxART_NORMAL_FILE, wxART_LIST, iconSize);
icons[TreeCtrlIcon_Folder] =
icons[TreeCtrlIcon_FolderSelected] =
icons[TreeCtrlIcon_FolderOpened] = wxArtProvider::GetIcon(wxART_FOLDER, wxART_LIST, iconSize);
}
for ( size_t i = 0; i < WXSIZEOF(icons); i++ ) for ( size_t i = 0; i < WXSIZEOF(icons); i++ )
{ {
int sizeOrig = icons[0].GetWidth();
if ( size == sizeOrig ) if ( size == sizeOrig )
{ {
images->Add(icons[i]); images->Add(icons[i]);
@@ -771,12 +798,25 @@ void MyTreeCtrl::CreateButtonsImageList(int size)
// should correspond to TreeCtrlIcon_xxx enum // should correspond to TreeCtrlIcon_xxx enum
wxBusyCursor wait; wxBusyCursor wait;
wxIcon icons[4]; wxIcon icons[4];
icons[0] = wxIcon(icon3_xpm); // closed
icons[1] = wxIcon(icon3_xpm); // closed, selected
icons[2] = wxIcon(icon5_xpm); // open
icons[3] = wxIcon(icon5_xpm); // open, selected
for ( size_t i = 0; i < WXSIZEOF(icons); i++ ) if (m_alternateImages)
{
icons[0] = wxIcon(icon3_xpm); // closed
icons[1] = wxIcon(icon3_xpm); // closed, selected
icons[2] = wxIcon(icon5_xpm); // open
icons[3] = wxIcon(icon5_xpm); // open, selected
}
else
{
wxSize iconSize(size, size);
icons[0] = // closed
icons[1] = wxArtProvider::GetIcon(wxART_FOLDER, wxART_LIST, iconSize); // closed, selected
icons[2] = // open
icons[3] = wxArtProvider::GetIcon(wxART_FOLDER_OPEN, wxART_LIST, iconSize);// open, selected
}
for ( size_t i = 0; i < WXSIZEOF(icons); i++ )
{ {
int sizeOrig = icons[i].GetWidth(); int sizeOrig = icons[i].GetWidth();
if ( size == sizeOrig ) if ( size == sizeOrig )

View File

@@ -61,7 +61,7 @@ public:
TreeCtrlIcon_FolderOpened TreeCtrlIcon_FolderOpened
}; };
MyTreeCtrl() { } MyTreeCtrl() { m_alternateImages = false; }
MyTreeCtrl(wxWindow *parent, const wxWindowID id, MyTreeCtrl(wxWindow *parent, const wxWindowID id,
const wxPoint& pos, const wxSize& size, const wxPoint& pos, const wxSize& size,
long style); long style);
@@ -111,6 +111,9 @@ public:
void SetLastItem(wxTreeItemId id) { m_lastItem = id; } void SetLastItem(wxTreeItemId id) { m_lastItem = id; }
void SetAlternateImages(bool show) { m_alternateImages = show; }
bool AlternateImages() const { return m_alternateImages; }
protected: protected:
virtual int OnCompareItems(const wxTreeItemId& i1, const wxTreeItemId& i2); virtual int OnCompareItems(const wxTreeItemId& i1, const wxTreeItemId& i2);
@@ -133,6 +136,7 @@ private:
bool m_reverseSort; // flag for OnCompareItems bool m_reverseSort; // flag for OnCompareItems
wxTreeItemId m_lastItem, // for OnEnsureVisible() wxTreeItemId m_lastItem, // for OnEnsureVisible()
m_draggedItem; // item being dragged right now m_draggedItem; // item being dragged right now
bool m_alternateImages;
// NB: due to an ugly wxMSW hack you _must_ use DECLARE_DYNAMIC_CLASS() // NB: due to an ugly wxMSW hack you _must_ use DECLARE_DYNAMIC_CLASS()
// if you want your overloaded OnCompareItems() to be called. // if you want your overloaded OnCompareItems() to be called.
@@ -193,6 +197,7 @@ public:
void OnRecreate(wxCommandEvent& event); void OnRecreate(wxCommandEvent& event);
void OnToggleButtons(wxCommandEvent& event); void OnToggleButtons(wxCommandEvent& event);
void OnToggleImages(wxCommandEvent& event); void OnToggleImages(wxCommandEvent& event);
void OnToggleAlternateImages(wxCommandEvent& event);
void OnSetImageSize(wxCommandEvent& event); void OnSetImageSize(wxCommandEvent& event);
void OnCollapseAndReset(wxCommandEvent& event); void OnCollapseAndReset(wxCommandEvent& event);
@@ -274,6 +279,7 @@ enum
TreeTest_DeleteAll, TreeTest_DeleteAll,
TreeTest_Recreate, TreeTest_Recreate,
TreeTest_ToggleImages, TreeTest_ToggleImages,
TreeTest_ToggleAlternateImages,
TreeTest_ToggleButtons, TreeTest_ToggleButtons,
TreeTest_SetImageSize, TreeTest_SetImageSize,
TreeTest_ToggleSel, TreeTest_ToggleSel,

View File

@@ -43,6 +43,7 @@ WX_DEFINE_LIST(wxArtProvidersList)
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
WX_DECLARE_EXPORTED_STRING_HASH_MAP(wxBitmap, wxArtProviderBitmapsHash); WX_DECLARE_EXPORTED_STRING_HASH_MAP(wxBitmap, wxArtProviderBitmapsHash);
WX_DECLARE_EXPORTED_STRING_HASH_MAP(wxIconBundle, wxArtProviderIconBundlesHash);
class WXDLLEXPORT wxArtProviderCache class WXDLLEXPORT wxArtProviderCache
{ {
@@ -51,14 +52,22 @@ public:
void PutBitmap(const wxString& full_id, const wxBitmap& bmp) void PutBitmap(const wxString& full_id, const wxBitmap& bmp)
{ m_bitmapsHash[full_id] = bmp; } { m_bitmapsHash[full_id] = bmp; }
bool GetIconBundle(const wxString& full_id, wxIconBundle* bmp);
void PutIconBundle(const wxString& full_id, const wxIconBundle& iconbundle)
{ m_iconBundlesHash[full_id] = iconbundle; }
void Clear(); void Clear();
static wxString ConstructHashID(const wxArtID& id, static wxString ConstructHashID(const wxArtID& id,
const wxArtClient& client, const wxArtClient& client,
const wxSize& size); const wxSize& size);
static wxString ConstructHashID(const wxArtID& id,
const wxArtClient& client);
private: private:
wxArtProviderBitmapsHash m_bitmapsHash; wxArtProviderBitmapsHash m_bitmapsHash; // cache of wxBitmaps
wxArtProviderIconBundlesHash m_iconBundlesHash; // cache of wxIconBundles
}; };
bool wxArtProviderCache::GetBitmap(const wxString& full_id, wxBitmap* bmp) bool wxArtProviderCache::GetBitmap(const wxString& full_id, wxBitmap* bmp)
@@ -75,21 +84,43 @@ bool wxArtProviderCache::GetBitmap(const wxString& full_id, wxBitmap* bmp)
} }
} }
bool wxArtProviderCache::GetIconBundle(const wxString& full_id, wxIconBundle* bmp)
{
wxArtProviderIconBundlesHash::iterator entry = m_iconBundlesHash.find(full_id);
if ( entry == m_iconBundlesHash.end() )
{
return false;
}
else
{
*bmp = entry->second;
return true;
}
}
void wxArtProviderCache::Clear() void wxArtProviderCache::Clear()
{ {
m_bitmapsHash.clear(); m_bitmapsHash.clear();
m_iconBundlesHash.clear();
} }
/*static*/ wxString wxArtProviderCache::ConstructHashID( /* static */ wxString
const wxArtID& id, const wxArtClient& client, wxArtProviderCache::ConstructHashID(const wxArtID& id,
const wxSize& size) const wxArtClient& client)
{ {
wxString str; return id + _T('-') + client;
str.Printf(wxT("%s-%s-%i-%i"), id.c_str(), client.c_str(), size.x, size.y);
return str;
} }
/* static */ wxString
wxArtProviderCache::ConstructHashID(const wxArtID& id,
const wxArtClient& client,
const wxSize& size)
{
return ConstructHashID(id, client) + _T('-') +
wxString::Format(_T("%d-%d"), size.x, size.y);
}
// ============================================================================ // ============================================================================
// wxArtProvider class // wxArtProvider class
// ============================================================================ // ============================================================================
@@ -216,12 +247,39 @@ wxArtProvider::~wxArtProvider()
#endif #endif
break; break;
} }
// We could try the IconBundles here and convert what we find
// to a bitmap.
}
sm_cache->PutBitmap(hashId, bmp);
} }
sm_cache->PutBitmap(hashId, bmp); return bmp;
}
/*static*/ wxIconBundle wxArtProvider::GetIconBundle(const wxArtID& id, const wxArtClient& client)
{
// safety-check against writing client,id,size instead of id,client,size:
wxASSERT_MSG( client.Last() == _T('C'), _T("invalid 'client' parameter") );
wxCHECK_MSG( sm_providers, wxNullIconBundle, _T("no wxArtProvider exists") );
wxString hashId = wxArtProviderCache::ConstructHashID(id, client);
wxIconBundle iconbundle;
if ( !sm_cache->GetIconBundle(hashId, &iconbundle) )
{
for (wxArtProvidersList::compatibility_iterator node = sm_providers->GetFirst();
node; node = node->GetNext())
{
iconbundle = node->GetData()->CreateIconBundle(id, client);
if ( iconbundle.IsOk() )
break;
}
sm_cache->PutIconBundle(hashId, iconbundle);
} }
return bmp; return iconbundle;
} }
/*static*/ wxIcon wxArtProvider::GetIcon(const wxArtID& id, /*static*/ wxIcon wxArtProvider::GetIcon(const wxArtID& id,
@@ -230,6 +288,12 @@ wxArtProvider::~wxArtProvider()
{ {
wxCHECK_MSG( sm_providers, wxNullIcon, _T("no wxArtProvider exists") ); wxCHECK_MSG( sm_providers, wxNullIcon, _T("no wxArtProvider exists") );
// First look for an appropriate icon bundle - this will give us the best icon
wxIconBundle iconBundle = GetIconBundle(id, client);
if ( iconBundle.IsOk() )
return iconBundle.GetIcon(size);
// If there is no icon bundle then look for a bitmap
wxBitmap bmp = GetBitmap(id, client, size); wxBitmap bmp = GetBitmap(id, client, size);
if ( !bmp.Ok() ) if ( !bmp.Ok() )
return wxNullIcon; return wxNullIcon;

View File

@@ -77,7 +77,7 @@ protected:
wxArtProvider::Push(new wxDefaultArtProvider); wxArtProvider::Push(new wxDefaultArtProvider);
} }
#if !defined(__WXGTK20__) || defined(__WXUNIVERSAL__) #if !(defined(__WXGTK20__) || defined(__WXMAC__)) || defined(__WXUNIVERSAL__)
/*static*/ void wxArtProvider::InitNativeProvider() /*static*/ void wxArtProvider::InitNativeProvider()
{ {
} }

View File

@@ -25,6 +25,7 @@
#include "wx/brush.h" #include "wx/brush.h"
#include "wx/palette.h" #include "wx/palette.h"
#include "wx/icon.h" #include "wx/icon.h"
#include "wx/iconbndl.h"
#include "wx/cursor.h" #include "wx/cursor.h"
#include "wx/settings.h" #include "wx/settings.h"
#include "wx/bitmap.h" #include "wx/bitmap.h"
@@ -52,6 +53,7 @@ WXDLLIMPEXP_DATA_CORE(wxPen) wxNullPen;
#if wxUSE_PALETTE #if wxUSE_PALETTE
WXDLLIMPEXP_DATA_CORE(wxPalette) wxNullPalette; WXDLLIMPEXP_DATA_CORE(wxPalette) wxNullPalette;
#endif #endif
WXDLLIMPEXP_DATA_CORE(wxIconBundle) wxNullIconBundle;
const wxSize wxDefaultSize(wxDefaultCoord, wxDefaultCoord); const wxSize wxDefaultSize(wxDefaultCoord, wxDefaultCoord);
const wxPoint wxDefaultPosition(wxDefaultCoord, wxDefaultCoord); const wxPoint wxDefaultPosition(wxDefaultCoord, wxDefaultCoord);

View File

@@ -1,13 +1,21 @@
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
// Name: src/common/iconbndl.cpp // Name: src/common/iconbndl.cpp
// Purpose: wxIconBundle // Purpose: wxIconBundle
// Author: Mattia Barbon // Author: Mattia Barbon, Vadim Zeitlin
// Created: 23.03.2002 // Created: 23.03.2002
// RCS-ID: $Id$ // RCS-ID: $Id$
// Copyright: (c) Mattia barbon // Copyright: (c) Mattia barbon
// Licence: wxWindows licence // Licence: wxWindows licence
///////////////////////////////////////////////////////////////////////////// /////////////////////////////////////////////////////////////////////////////
// ============================================================================
// declarations
// ============================================================================
// ----------------------------------------------------------------------------
// headers
// ----------------------------------------------------------------------------
// For compilers that support precompilation, includes "wx.h". // For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h" #include "wx/wxprec.h"
@@ -30,113 +38,200 @@
WX_DEFINE_OBJARRAY(wxIconArray) WX_DEFINE_OBJARRAY(wxIconArray)
const wxIconBundle& wxIconBundle::operator =( const wxIconBundle& ic ) IMPLEMENT_DYNAMIC_CLASS(wxIconBundle, wxGDIObject)
#define M_ICONBUNDLEDATA ((wxIconBundleRefData *)m_refData)
// ----------------------------------------------------------------------------
// wxIconBundleRefData
// ----------------------------------------------------------------------------
class WXDLLEXPORT wxIconBundleRefData : public wxGDIRefData
{ {
if( this == &ic ) return *this; public:
// default and copy ctors and assignment operators are ok
size_t i, max = ic.m_icons.GetCount(); protected:
wxIconArray m_icons;
DeleteIcons(); friend class WXDLLEXPORT wxIconBundle;
for( i = 0; i < max; ++i ) };
m_icons.Add( ic.m_icons[i] );
return *this; // ============================================================================
// wxIconBundle implementation
// ============================================================================
wxIconBundle::wxIconBundle()
: wxGDIObject()
{
m_refData = new wxIconBundleRefData;
}
wxIconBundle::wxIconBundle(const wxString& file, long type)
: wxGDIObject()
{
m_refData = new wxIconBundleRefData;
AddIcon(file, type);
}
wxIconBundle::wxIconBundle(const wxIconBundle& icon)
: wxGDIObject()
{
Ref(icon);
}
wxIconBundle::wxIconBundle(const wxIcon& icon)
: wxGDIObject()
{
m_refData = new wxIconBundleRefData;
AddIcon(icon);
}
wxObjectRefData *wxIconBundle::CreateRefData() const
{
return new wxIconBundleRefData;
}
wxObjectRefData *wxIconBundle::CloneRefData(const wxObjectRefData *data) const
{
return new wxIconBundleRefData(*wx_static_cast(const wxIconBundleRefData *, data));
} }
void wxIconBundle::DeleteIcons() void wxIconBundle::DeleteIcons()
{ {
m_icons.Empty(); wxIconBundleRefData* ref = new wxIconBundleRefData();
UnRef();
m_refData = ref;
} }
#if wxUSE_IMAGE bool wxIconBundle::IsOk() const
void wxIconBundle::AddIcon( const wxString& file, long type )
#else
void wxIconBundle::AddIcon( const wxString& WXUNUSED(file), long WXUNUSED(type) )
#endif
{ {
return M_ICONBUNDLEDATA && !M_ICONBUNDLEDATA->m_icons.IsEmpty();
}
void wxIconBundle::AddIcon(const wxString& file, long type)
{
#ifdef __WXMAC__
// Deal with standard icons
if ( type == wxBITMAP_TYPE_ICON_RESOURCE )
{
wxIcon tmp(file, type);
if (tmp.Ok())
{
AddIcon(tmp);
return;
}
}
#endif // __WXMAC__
#if wxUSE_IMAGE && (!defined(__WXMSW__) || wxUSE_WXDIB) #if wxUSE_IMAGE && (!defined(__WXMSW__) || wxUSE_WXDIB)
size_t count = wxImage::GetImageCount( file, type );
size_t i;
wxImage image; wxImage image;
for( i = 0; i < count; ++i ) const size_t count = wxImage::GetImageCount( file, type );
for ( size_t i = 0; i < count; ++i )
{ {
if( !image.LoadFile( file, type, i ) ) if ( !image.LoadFile( file, type, i ) )
{ {
wxLogError( _("Failed to load image %d from file '%s'."), wxLogError( _("Failed to load image %d from file '%s'."),
i, file.c_str() ); i, file.c_str() );
continue; continue;
} }
wxIcon* tmp = new wxIcon(); wxIcon tmp;
tmp->CopyFromBitmap( wxBitmap( image ) ); tmp.CopyFromBitmap(wxBitmap(image));
AddIcon( *tmp ); AddIcon(tmp);
delete tmp;
} }
#else // !wxUSE_IMAGE
wxUnusedVar(file);
wxUnusedVar(type);
#endif // wxUSE_IMAGE/!wxUSE_IMAGE
}
wxIcon wxIconBundle::GetIcon(const wxSize& size) const
{
wxCHECK_MSG( IsOk(), wxNullIcon, _T("invalid icon bundle") );
const wxIconArray& iconArray = M_ICONBUNDLEDATA->m_icons;
const size_t count = iconArray.size();
// optimize for the common case of icon bundles containing one icon only
wxIcon iconBest;
switch ( count )
{
case 0:
// nothing to do, iconBest is already invalid
break;
case 1:
iconBest = iconArray[0];
break;
default:
// there is more than one icon, find the best match:
wxCoord sysX = wxSystemSettings::GetMetric( wxSYS_ICON_X ),
sysY = wxSystemSettings::GetMetric( wxSYS_ICON_Y );
for ( size_t i = 0; i < count; i++ )
{
const wxIcon& icon = iconArray[i];
wxCoord sx = icon.GetWidth(),
sy = icon.GetHeight();
// if we got an icon of exactly the requested size, we're done
if ( sx == size.x && sy == size.y )
{
iconBest = icon;
break;
}
// the best icon is by default (arbitrarily) the first one but
// if we find a system-sized icon, take it instead
if ( sx == sysX && sy == sysY || !iconBest.IsOk() )
iconBest = icon;
}
}
#ifdef __WXMAC__
return wxIcon(iconBest.GetHICON(), size);
#else
return iconBest;
#endif #endif
} }
const wxIcon& wxIconBundle::GetIcon( const wxSize& size ) const void wxIconBundle::AddIcon(const wxIcon& icon)
{ {
// temp. variable needed to fix Borland C++ 5.5.1 problem wxCHECK_RET( icon.IsOk(), _T("invalid icon") );
// with passing a return value through two functions
wxIcon *tmp;
size_t max = m_icons.GetCount(); AllocExclusive();
// if we have one or no icon, we can return now without doing more work: wxIconArray& iconArray = M_ICONBUNDLEDATA->m_icons;
if ( max <= 1 )
// replace existing icon with the same size if we already have it
const size_t count = iconArray.size();
for ( size_t i = 0; i < count; ++i )
{ {
if ( max == 1 ) // fix for broken BCC wxIcon& tmp = iconArray[i];
tmp = &m_icons[0]; if ( tmp.Ok() &&
else // max == 0 tmp.GetWidth() == icon.GetWidth() &&
tmp = &wxNullIcon; tmp.GetHeight() == icon.GetHeight() )
return *tmp;
}
// there are more icons, find the best match:
wxCoord sysX = wxSystemSettings::GetMetric( wxSYS_ICON_X ),
sysY = wxSystemSettings::GetMetric( wxSYS_ICON_Y );
wxIcon *sysIcon = 0;
for( size_t i = 0; i < max; i++ )
{
if( !m_icons[i].Ok() )
continue;
wxCoord sx = m_icons[i].GetWidth(), sy = m_icons[i].GetHeight();
// requested size
if( sx == size.x && sy == size.y )
{
tmp = &m_icons[i]; // fix for broken BCC
return *tmp;
}
// keep track if there is a system-size icon
if( sx == sysX && sy == sysY )
sysIcon = &m_icons[i];
}
// return the system-sized icon if we've got one
if( sysIcon ) return *sysIcon;
// we certainly have at least one icon thanks to the <=1 check above
tmp = &m_icons[0];
return *tmp;
}
void wxIconBundle::AddIcon( const wxIcon& icon )
{
size_t i, max = m_icons.GetCount();
for( i = 0; i < max; ++i )
{
wxIcon& tmp = m_icons[i];
if( tmp.Ok() && tmp.GetWidth() == icon.GetWidth() &&
tmp.GetHeight() == icon.GetHeight() )
{ {
tmp = icon; tmp = icon;
return; return;
} }
} }
m_icons.Add( icon ); // if we don't, add an icon with new size
iconArray.Add(icon);
} }
size_t wxIconBundle::GetIconCount() const
{
return M_ICONBUNDLEDATA->m_icons.size();
}
wxIcon wxIconBundle::GetIconByIndex(size_t n) const
{
return M_ICONBUNDLEDATA->m_icons[n];
}

View File

@@ -1175,7 +1175,13 @@ void wxTopLevelWindowGTK::SetTitle( const wxString &title )
void wxTopLevelWindowGTK::SetIcon( const wxIcon &icon ) void wxTopLevelWindowGTK::SetIcon( const wxIcon &icon )
{ {
SetIcons( wxIconBundle( icon ) ); // passing wxNullIcon to SetIcon() is possible (it means that we shouldn't
// have any icon), but adding an invalid icon to wxIconBundle is not
wxIconBundle icons;
if ( icon.Ok() )
icons.AddIcon(icon);
SetIcons(icons);
} }
void wxTopLevelWindowGTK::SetIcons( const wxIconBundle &icons ) void wxTopLevelWindowGTK::SetIcons( const wxIconBundle &icons )
@@ -1185,15 +1191,13 @@ void wxTopLevelWindowGTK::SetIcons( const wxIconBundle &icons )
wxTopLevelWindowBase::SetIcons( icons ); wxTopLevelWindowBase::SetIcons( icons );
GList *list = NULL; GList *list = NULL;
size_t max = icons.m_icons.GetCount();
for (size_t i = 0; i < max; i++) const size_t numIcons = icons.GetIconCount();
for ( size_t i = 0; i < numIcons; i++ )
{ {
if (icons.m_icons[i].Ok()) list = g_list_prepend(list, icons.GetIconByIndex(i).GetPixbuf());
{
list = g_list_prepend(list, icons.m_icons[i].GetPixbuf());
}
} }
gtk_window_set_icon_list(GTK_WINDOW(m_widget), list); gtk_window_set_icon_list(GTK_WINDOW(m_widget), list);
g_list_free(list); g_list_free(list);
} }

108
src/mac/carbon/artmac.cpp Normal file
View File

@@ -0,0 +1,108 @@
/////////////////////////////////////////////////////////////////////////////
// Name: src/mac/carbon/artmac.cpp
// Purpose: wxArtProvider instance with native Mac stock icons
// Author: Alan Shouls
// Created: 2006-10-30
// RCS-ID: $Id$
// Copyright: (c) wxWindows team
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
// ---------------------------------------------------------------------------
// headers
// ---------------------------------------------------------------------------
// For compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"
#if defined(__BORLANDC__)
#pragma hdrstop
#endif
#ifndef WX_PRECOMP
#include "wx/image.h"
#endif
#include "wx/artprov.h"
#include "wx/image.h"
// ----------------------------------------------------------------------------
// wxMacArtProvider
// ----------------------------------------------------------------------------
class wxMacArtProvider : public wxArtProvider
{
protected:
virtual wxBitmap CreateBitmap(const wxArtID& id, const wxArtClient& client,
const wxSize& size);
virtual wxIconBundle CreateIconBundle(const wxArtID& id,
const wxArtClient& client);
};
/* static */ void wxArtProvider::InitNativeProvider()
{
wxArtProvider::Push(new wxMacArtProvider);
}
// ----------------------------------------------------------------------------
// helper macros
// ----------------------------------------------------------------------------
#define CREATE_STD_ICON(iconId, xpmRc) \
{ \
wxIconBundle icon(_T(iconId), wxBITMAP_TYPE_ICON_RESOURCE); \
return icon; \
}
// Macro used in CreateBitmap to get wxICON_FOO icons:
#define ART_MSGBOX(artId, iconId, xpmRc) \
if ( id == artId ) \
{ \
CREATE_STD_ICON(#iconId, xpmRc) \
}
static wxIconBundle wxMacArtProvider_CreateIconBundle(const wxArtID& id)
{
ART_MSGBOX(wxART_ERROR, wxICON_ERROR, error)
ART_MSGBOX(wxART_INFORMATION, wxICON_INFORMATION, info)
ART_MSGBOX(wxART_WARNING, wxICON_WARNING, warning)
ART_MSGBOX(wxART_QUESTION, wxICON_QUESTION, question)
ART_MSGBOX(wxART_FOLDER, wxICON_FOLDER, folder)
ART_MSGBOX(wxART_FOLDER_OPEN, wxICON_FOLDER_OPEN, folder_open)
ART_MSGBOX(wxART_NORMAL_FILE, wxICON_NORMAL_FILE, deffile)
return wxNullIconBundle;
}
// ----------------------------------------------------------------------------
// CreateIconBundle
// ----------------------------------------------------------------------------
wxIconBundle wxMacArtProvider::CreateIconBundle(const wxArtID& id, const wxArtClient& client)
{
// On the Mac folders in lists are always drawn closed, so if an open
// folder icon is asked for we will ask for a closed one in its place
if ( client == wxART_LIST && id == wxART_FOLDER_OPEN )
return wxMacArtProvider_CreateIconBundle(wxART_FOLDER);
return wxMacArtProvider_CreateIconBundle(id);
}
// ----------------------------------------------------------------------------
// CreateBitmap
// ----------------------------------------------------------------------------
wxBitmap wxMacArtProvider::CreateBitmap(const wxArtID& id,
const wxArtClient& client,
const wxSize& reqSize)
{
wxIconBundle ic(CreateIconBundle(id, client));
if (ic.IsOk())
{
wxIcon theIcon(ic.GetIcon(reqSize));
return wxBitmap(theIcon);
}
return wxNullBitmap;
}

View File

@@ -53,6 +53,18 @@ wxIcon::wxIcon(
LoadFile( icon_file, (wxBitmapType) flags, desiredWidth, desiredHeight ); LoadFile( icon_file, (wxBitmapType) flags, desiredWidth, desiredHeight );
} }
wxIcon::wxIcon(WXHICON icon, const wxSize& size)
: wxGDIObject()
{
// as the icon owns that ref, we have to acquire it as well
if (icon)
AcquireIconRef( (IconRef) icon ) ;
m_refData = new wxIconRefData( icon ) ;
M_ICONDATA->SetWidth( size.x ) ;
M_ICONDATA->SetHeight( size.y ) ;
}
wxIcon::~wxIcon() wxIcon::~wxIcon()
{ {
} }
@@ -126,6 +138,18 @@ bool wxIcon::LoadFile(
{ {
theId = kAlertStopIcon ; theId = kAlertStopIcon ;
} }
else if ( filename == wxT("wxICON_FOLDER") )
{
theId = kGenericFolderIcon ;
}
else if ( filename == wxT("wxICON_FOLDER_OPEN") )
{
theId = kOpenFolderIcon ;
}
else if ( filename == wxT("wxICON_NORMAL_FILE") )
{
theId = kGenericDocumentIcon ;
}
else else
{ {
#if 0 #if 0

View File

@@ -106,31 +106,32 @@ private:
// Setting icons for window manager: // Setting icons for window manager:
// ---------------------------------------------------------------------------- // ----------------------------------------------------------------------------
void wxSetIconsX11( WXDisplay* display, WXWindow window, void
const wxIconBundle& ib ) wxSetIconsX11(WXDisplay* display, WXWindow window, const wxIconBundle& ib)
{ {
#if !wxUSE_NANOX #if !wxUSE_NANOX
size_t size = 0; size_t size = 0;
size_t i, max = ib.m_icons.GetCount();
for( i = 0; i < max; ++i ) const size_t numIcons = ib.GetIconCount();
if( ib.m_icons[i].Ok() ) for ( size_t i = 0; i < numIcons; ++i )
size += 2 + ib.m_icons[i].GetWidth() * ib.m_icons[i].GetHeight(); {
const wxIcon icon = ib.GetIconByIndex(i);
size += 2 + icon.GetWidth() * icon.GetHeight();
}
wxMAKE_ATOM(_NET_WM_ICON, (Display*)display); wxMAKE_ATOM(_NET_WM_ICON, (Display*)display);
if( size > 0 ) if ( size > 0 )
{ {
// The code below is correct for 64-bit machines also.
// wxUint32* data = new wxUint32[size];
// wxUint32* ptr = data;
unsigned long* data = new unsigned long[size]; unsigned long* data = new unsigned long[size];
unsigned long* ptr = data; unsigned long* ptr = data;
for( i = 0; i < max; ++i ) for ( size_t i = 0; i < numIcons; ++i )
{ {
const wxImage image = ib.m_icons[i].ConvertToImage(); const wxImage image = ib.GetIconByIndex(i).ConvertToImage();
int width = image.GetWidth(), height = image.GetHeight(); int width = image.GetWidth(),
height = image.GetHeight();
unsigned char* imageData = image.GetData(); unsigned char* imageData = image.GetData();
unsigned char* imageDataEnd = imageData + ( width * height * 3 ); unsigned char* imageDataEnd = imageData + ( width * height * 3 );
bool hasMask = image.HasMask(); bool hasMask = image.HasMask();
@@ -153,7 +154,8 @@ void wxSetIconsX11( WXDisplay* display, WXWindow window,
*ptr++ = width; *ptr++ = width;
*ptr++ = height; *ptr++ = height;
while( imageData < imageDataEnd ) { while ( imageData < imageDataEnd )
{
r = imageData[0]; r = imageData[0];
g = imageData[1]; g = imageData[1];
b = imageData[2]; b = imageData[2];