diff --git a/Makefile.in b/Makefile.in
index a15c0958dc..9c4dcdf98e 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -310,6 +310,7 @@ WXSCINTILLA_OBJECTS = \
PLUGINS_INST_DIR = $(libdir)/wx/$(PLUGIN_VERSION0)
ALL_BASE_HEADERS = \
wx/afterstd.h \
+ wx/any.h \
wx/anystr.h \
wx/app.h \
wx/apptrait.h \
@@ -470,6 +471,7 @@ ALL_HEADERS = \
$(ALL_GUI_HEADERS)
ALL_PORTS_BASE_HEADERS = \
wx/afterstd.h \
+ wx/any.h \
wx/anystr.h \
wx/app.h \
wx/apptrait.h \
@@ -665,6 +667,7 @@ ALL_PORTS_BASE_HEADERS = \
wx/xml/xml.h \
wx/xtixml.h
ALL_BASE_SOURCES = \
+ src/common/any.cpp \
src/common/appbase.cpp \
src/common/arcall.cpp \
src/common/arcfind.cpp \
@@ -855,6 +858,7 @@ MONODLL_OBJCXXFLAGS = $(__monodll_PCH_INC) -D__WX$(TOOLKIT)__ \
-I$(top_srcdir)/src/stc/scintilla/src -D__WX__ -DSCI_LEXER -DLINK_LEXERS \
$(PIC_FLAG) $(CPPFLAGS) $(OBJCXXFLAGS)
MONODLL_OBJECTS = \
+ monodll_any.o \
monodll_appbase.o \
monodll_arcall.o \
monodll_arcfind.o \
@@ -982,6 +986,7 @@ MONOLIB_OBJCXXFLAGS = $(__monolib_PCH_INC) -D__WX$(TOOLKIT)__ \
-I$(top_srcdir)/src/stc/scintilla/src -D__WX__ -DSCI_LEXER -DLINK_LEXERS \
$(CPPFLAGS) $(OBJCXXFLAGS)
MONOLIB_OBJECTS = \
+ monolib_any.o \
monolib_appbase.o \
monolib_arcall.o \
monolib_arcfind.o \
@@ -1104,6 +1109,7 @@ BASEDLL_OBJCXXFLAGS = $(__basedll_PCH_INC) -D__WX$(TOOLKIT)__ \
-DwxUSE_BASE=1 $(PIC_FLAG) $(CPPFLAGS) $(OBJCXXFLAGS)
BASEDLL_OBJECTS = \
$(__basedll___win32rc) \
+ basedll_any.o \
basedll_appbase.o \
basedll_arcall.o \
basedll_arcfind.o \
@@ -1209,6 +1215,7 @@ BASELIB_OBJCXXFLAGS = $(__baselib_PCH_INC) -D__WX$(TOOLKIT)__ \
$(__INC_REGEX_p) $(__INC_EXPAT_p) -DwxUSE_GUI=0 -DwxUSE_BASE=1 $(CPPFLAGS) \
$(OBJCXXFLAGS)
BASELIB_OBJECTS = \
+ baselib_any.o \
baselib_appbase.o \
baselib_arcall.o \
baselib_arcfind.o \
@@ -14203,6 +14210,9 @@ wxscintilla_WindowAccessor.o: $(srcdir)/src/stc/scintilla/src/WindowAccessor.cxx
wxscintilla_XPM.o: $(srcdir)/src/stc/scintilla/src/XPM.cxx
$(CXXC) -c -o $@ $(WXSCINTILLA_CXXFLAGS) $(srcdir)/src/stc/scintilla/src/XPM.cxx
+monodll_any.o: $(srcdir)/src/common/any.cpp $(MONODLL_ODEP)
+ $(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/common/any.cpp
+
monodll_appbase.o: $(srcdir)/src/common/appbase.cpp $(MONODLL_ODEP)
$(CXXC) -c -o $@ $(MONODLL_CXXFLAGS) $(srcdir)/src/common/appbase.cpp
@@ -18940,6 +18950,9 @@ monodll_sound_sdl.o: $(srcdir)/src/unix/sound_sdl.cpp $(MONODLL_ODEP)
monodll_version_rc.o: $(srcdir)/src/msw/version.rc $(MONODLL_ODEP)
$(WINDRES) -i$< -o$@ --define __WX$(TOOLKIT)__ $(__WXUNIV_DEFINE_p_62) $(__DEBUG_DEFINE_p_61) $(__EXCEPTIONS_DEFINE_p_61) $(__RTTI_DEFINE_p_61) $(__THREAD_DEFINE_p_61) --define WXBUILDING --define WXDLLNAME=$(WXDLLNAMEPREFIXGUI)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)$(WXCOMPILER)$(VENDORTAG)$(WXDLLVERSIONTAG) $(__RCDEFDIR_p) --include-dir $(top_srcdir)/include $(__INC_TIFF_BUILD_p_62) $(__INC_TIFF_p_62) $(__INC_JPEG_p_62) $(__INC_PNG_p_61) $(__INC_ZLIB_p_63) $(__INC_REGEX_p_61) $(__INC_EXPAT_p_61) --define wxUSE_BASE=1 --define WXMAKINGDLL --include-dir $(top_srcdir)/src/stc/scintilla/include --include-dir $(top_srcdir)/src/stc/scintilla/src --define __WX__ --define SCI_LEXER --define LINK_LEXERS
+monolib_any.o: $(srcdir)/src/common/any.cpp $(MONOLIB_ODEP)
+ $(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/common/any.cpp
+
monolib_appbase.o: $(srcdir)/src/common/appbase.cpp $(MONOLIB_ODEP)
$(CXXC) -c -o $@ $(MONOLIB_CXXFLAGS) $(srcdir)/src/common/appbase.cpp
@@ -23677,6 +23690,9 @@ monolib_sound_sdl.o: $(srcdir)/src/unix/sound_sdl.cpp $(MONOLIB_ODEP)
basedll_version_rc.o: $(srcdir)/src/msw/version.rc $(BASEDLL_ODEP)
$(WINDRES) -i$< -o$@ --define __WX$(TOOLKIT)__ $(__WXUNIV_DEFINE_p_62) $(__DEBUG_DEFINE_p_61) $(__EXCEPTIONS_DEFINE_p_61) $(__RTTI_DEFINE_p_61) $(__THREAD_DEFINE_p_61) --define WXBUILDING --define WXDLLNAME=$(WXDLLNAMEPREFIX)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)$(WXCOMPILER)$(VENDORTAG)$(WXDLLVERSIONTAG) $(__RCDEFDIR_p) --include-dir $(top_srcdir)/include $(__INC_TIFF_BUILD_p_62) $(__INC_TIFF_p_62) $(__INC_JPEG_p_62) $(__INC_PNG_p_61) $(__INC_ZLIB_p_63) $(__INC_REGEX_p_61) $(__INC_EXPAT_p_61) --define wxUSE_GUI=0 --define WXMAKINGDLL_BASE --define wxUSE_BASE=1
+basedll_any.o: $(srcdir)/src/common/any.cpp $(BASEDLL_ODEP)
+ $(CXXC) -c -o $@ $(BASEDLL_CXXFLAGS) $(srcdir)/src/common/any.cpp
+
basedll_appbase.o: $(srcdir)/src/common/appbase.cpp $(BASEDLL_ODEP)
$(CXXC) -c -o $@ $(BASEDLL_CXXFLAGS) $(srcdir)/src/common/appbase.cpp
@@ -24148,6 +24164,9 @@ basedll_cocoa_utils.o: $(srcdir)/src/osx/cocoa/utils.mm $(BASEDLL_ODEP)
@COND_PLATFORM_MACOSX_1@basedll_utilsunx.o: $(srcdir)/src/unix/utilsunx.cpp $(BASEDLL_ODEP)
@COND_PLATFORM_MACOSX_1@ $(CXXC) -c -o $@ $(BASEDLL_CXXFLAGS) $(srcdir)/src/unix/utilsunx.cpp
+baselib_any.o: $(srcdir)/src/common/any.cpp $(BASELIB_ODEP)
+ $(CXXC) -c -o $@ $(BASELIB_CXXFLAGS) $(srcdir)/src/common/any.cpp
+
baselib_appbase.o: $(srcdir)/src/common/appbase.cpp $(BASELIB_ODEP)
$(CXXC) -c -o $@ $(BASELIB_CXXFLAGS) $(srcdir)/src/common/appbase.cpp
diff --git a/build/bakefiles/files.bkl b/build/bakefiles/files.bkl
index 6849e3fee6..5b045f8b8d 100644
--- a/build/bakefiles/files.bkl
+++ b/build/bakefiles/files.bkl
@@ -304,6 +304,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file!
+ src/common/any.cpp
src/common/appbase.cpp
src/common/arcall.cpp
src/common/arcfind.cpp
@@ -392,6 +393,7 @@ IMPORTANT: please read docs/tech/tn0016.txt before modifying this file!
wx/afterstd.h
+ wx/any.h
wx/anystr.h
wx/app.h
wx/apptrait.h
diff --git a/build/msw/makefile.bcc b/build/msw/makefile.bcc
index a60282ccba..1a65bf39e5 100644
--- a/build/msw/makefile.bcc
+++ b/build/msw/makefile.bcc
@@ -308,6 +308,7 @@ MONODLL_CXXFLAGS = $(__RUNTIME_LIBS) -I$(BCCDIR)\include $(__DEBUGINFO) \
$(CXXFLAGS)
MONODLL_OBJECTS = \
$(OBJS)\monodll_dummy.obj \
+ $(OBJS)\monodll_any.obj \
$(OBJS)\monodll_appbase.obj \
$(OBJS)\monodll_arcall.obj \
$(OBJS)\monodll_arcfind.obj \
@@ -448,6 +449,7 @@ MONOLIB_CXXFLAGS = $(__RUNTIME_LIBS) -I$(BCCDIR)\include $(__DEBUGINFO) \
$(CXXFLAGS)
MONOLIB_OBJECTS = \
$(OBJS)\monolib_dummy.obj \
+ $(OBJS)\monolib_any.obj \
$(OBJS)\monolib_appbase.obj \
$(OBJS)\monolib_arcall.obj \
$(OBJS)\monolib_arcfind.obj \
@@ -585,6 +587,7 @@ BASEDLL_CXXFLAGS = $(__RUNTIME_LIBS) -I$(BCCDIR)\include $(__DEBUGINFO) \
-DwxUSE_BASE=1 -Hu -H=$(OBJS)\wxprec_basedll.csm $(CPPFLAGS) $(CXXFLAGS)
BASEDLL_OBJECTS = \
$(OBJS)\basedll_dummy.obj \
+ $(OBJS)\basedll_any.obj \
$(OBJS)\basedll_appbase.obj \
$(OBJS)\basedll_arcall.obj \
$(OBJS)\basedll_arcfind.obj \
@@ -707,6 +710,7 @@ BASELIB_CXXFLAGS = $(__RUNTIME_LIBS) -I$(BCCDIR)\include $(__DEBUGINFO) \
-H=$(OBJS)\wxprec_baselib.csm $(CPPFLAGS) $(CXXFLAGS)
BASELIB_OBJECTS = \
$(OBJS)\baselib_dummy.obj \
+ $(OBJS)\baselib_any.obj \
$(OBJS)\baselib_appbase.obj \
$(OBJS)\baselib_arcall.obj \
$(OBJS)\baselib_arcfind.obj \
@@ -5495,6 +5499,9 @@ $(OBJS)\wxscintilla_XPM.obj: ..\..\src\stc\scintilla\src\XPM.cxx
$(OBJS)\monodll_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) -q -c -P -o$@ $(MONODLL_CXXFLAGS) -H ..\..\src\common\dummy.cpp
+$(OBJS)\monodll_any.obj: ..\..\src\common\any.cpp
+ $(CXX) -q -c -P -o$@ $(MONODLL_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\monodll_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) -q -c -P -o$@ $(MONODLL_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -7732,6 +7739,9 @@ $(OBJS)\monodll_version.res: ..\..\src\msw\version.rc
$(OBJS)\monolib_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) -q -c -P -o$@ $(MONOLIB_CXXFLAGS) -H ..\..\src\common\dummy.cpp
+$(OBJS)\monolib_any.obj: ..\..\src\common\any.cpp
+ $(CXX) -q -c -P -o$@ $(MONOLIB_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\monolib_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) -q -c -P -o$@ $(MONOLIB_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -9969,6 +9979,9 @@ $(OBJS)\basedll_dummy.obj: ..\..\src\common\dummy.cpp
$(OBJS)\basedll_version.res: ..\..\src\msw\version.rc
brcc32 -32 -r -fo$@ -i$(BCCDIR)\include -d__WXMSW__ $(__WXUNIV_DEFINE_p_62) $(__DEBUG_DEFINE_p_61) $(__EXCEPTIONS_DEFINE_p_61) $(__RTTI_DEFINE_p_61) $(__THREAD_DEFINE_p_61) $(__UNICODE_DEFINE_p_62) $(__MSLU_DEFINE_p_61) $(__GFXCTX_DEFINE_p_61) -i$(SETUPHDIR) -i..\..\include -dWXBUILDING -dWXDLLNAME=wxbase$(WX_VERSION_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_bcc$(VENDORTAG) -i..\..\src\tiff\libtiff -i..\..\src\jpeg -i..\..\src\png -i..\..\src\zlib -i..\..\src\regex -i..\..\src\expat\lib -dwxUSE_GUI=0 -dWXMAKINGDLL_BASE -dwxUSE_BASE=1 ..\..\src\msw\version.rc
+$(OBJS)\basedll_any.obj: ..\..\src\common\any.cpp
+ $(CXX) -q -c -P -o$@ $(BASEDLL_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\basedll_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) -q -c -P -o$@ $(BASEDLL_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -10284,6 +10297,9 @@ $(OBJS)\basedll_volume.obj: ..\..\src\msw\volume.cpp
$(OBJS)\baselib_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) -q -c -P -o$@ $(BASELIB_CXXFLAGS) -H ..\..\src\common\dummy.cpp
+$(OBJS)\baselib_any.obj: ..\..\src\common\any.cpp
+ $(CXX) -q -c -P -o$@ $(BASELIB_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\baselib_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) -q -c -P -o$@ $(BASELIB_CXXFLAGS) ..\..\src\common\appbase.cpp
diff --git a/build/msw/makefile.gcc b/build/msw/makefile.gcc
index 0159901c1e..ae9165a644 100644
--- a/build/msw/makefile.gcc
+++ b/build/msw/makefile.gcc
@@ -295,6 +295,7 @@ MONODLL_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) \
-Wno-ctor-dtor-privacy $(CPPFLAGS) $(CXXFLAGS)
MONODLL_OBJECTS = \
$(OBJS)\monodll_dummy.o \
+ $(OBJS)\monodll_any.o \
$(OBJS)\monodll_appbase.o \
$(OBJS)\monodll_arcall.o \
$(OBJS)\monodll_arcfind.o \
@@ -436,6 +437,7 @@ MONOLIB_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) \
-Wno-ctor-dtor-privacy $(CPPFLAGS) $(CXXFLAGS)
MONOLIB_OBJECTS = \
$(OBJS)\monolib_dummy.o \
+ $(OBJS)\monolib_any.o \
$(OBJS)\monolib_appbase.o \
$(OBJS)\monolib_arcall.o \
$(OBJS)\monolib_arcfind.o \
@@ -575,6 +577,7 @@ BASEDLL_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) \
BASEDLL_OBJECTS = \
$(OBJS)\basedll_dummy.o \
$(OBJS)\basedll_version_rc.o \
+ $(OBJS)\basedll_any.o \
$(OBJS)\basedll_appbase.o \
$(OBJS)\basedll_arcall.o \
$(OBJS)\basedll_arcfind.o \
@@ -697,6 +700,7 @@ BASELIB_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) \
$(CXXFLAGS)
BASELIB_OBJECTS = \
$(OBJS)\baselib_dummy.o \
+ $(OBJS)\baselib_any.o \
$(OBJS)\baselib_appbase.o \
$(OBJS)\baselib_arcall.o \
$(OBJS)\baselib_arcfind.o \
@@ -5653,6 +5657,9 @@ $(OBJS)\wxscintilla_XPM.o: ../../src/stc/scintilla/src/XPM.cxx
$(OBJS)\monodll_dummy.o: ../../src/common/dummy.cpp
$(CXX) -c -o $@ $(MONODLL_CXXFLAGS) $(CPPDEPS) $<
+$(OBJS)\monodll_any.o: ../../src/common/any.cpp
+ $(CXX) -c -o $@ $(MONODLL_CXXFLAGS) $(CPPDEPS) $<
+
$(OBJS)\monodll_appbase.o: ../../src/common/appbase.cpp
$(CXX) -c -o $@ $(MONODLL_CXXFLAGS) $(CPPDEPS) $<
@@ -8002,6 +8009,9 @@ $(OBJS)\monodll_version_rc.o: ../../src/msw/version.rc
$(OBJS)\monolib_dummy.o: ../../src/common/dummy.cpp
$(CXX) -c -o $@ $(MONOLIB_CXXFLAGS) $(CPPDEPS) $<
+$(OBJS)\monolib_any.o: ../../src/common/any.cpp
+ $(CXX) -c -o $@ $(MONOLIB_CXXFLAGS) $(CPPDEPS) $<
+
$(OBJS)\monolib_appbase.o: ../../src/common/appbase.cpp
$(CXX) -c -o $@ $(MONOLIB_CXXFLAGS) $(CPPDEPS) $<
@@ -10351,6 +10361,9 @@ $(OBJS)\basedll_dummy.o: ../../src/common/dummy.cpp
$(OBJS)\basedll_version_rc.o: ../../src/msw/version.rc
windres --use-temp-file -i$< -o$@ --define __WXMSW__ $(__WXUNIV_DEFINE_p_62) $(__DEBUG_DEFINE_p_61) $(__EXCEPTIONS_DEFINE_p_61) $(__RTTI_DEFINE_p_61) $(__THREAD_DEFINE_p_61) $(__UNICODE_DEFINE_p_62) $(__MSLU_DEFINE_p_61) $(__GFXCTX_DEFINE_p_61) --include-dir $(SETUPHDIR) --include-dir ../../include --define WXBUILDING --define WXDLLNAME=wxbase$(WX_VERSION_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_gcc$(VENDORTAG) --include-dir ../../src/tiff/libtiff --include-dir ../../src/jpeg --include-dir ../../src/png --include-dir ../../src/zlib --include-dir ../../src/regex --include-dir ../../src/expat/lib --define wxUSE_GUI=0 --define WXMAKINGDLL_BASE --define wxUSE_BASE=1
+$(OBJS)\basedll_any.o: ../../src/common/any.cpp
+ $(CXX) -c -o $@ $(BASEDLL_CXXFLAGS) $(CPPDEPS) $<
+
$(OBJS)\basedll_appbase.o: ../../src/common/appbase.cpp
$(CXX) -c -o $@ $(BASEDLL_CXXFLAGS) $(CPPDEPS) $<
@@ -10666,6 +10679,9 @@ $(OBJS)\basedll_volume.o: ../../src/msw/volume.cpp
$(OBJS)\baselib_dummy.o: ../../src/common/dummy.cpp
$(CXX) -c -o $@ $(BASELIB_CXXFLAGS) $(CPPDEPS) $<
+$(OBJS)\baselib_any.o: ../../src/common/any.cpp
+ $(CXX) -c -o $@ $(BASELIB_CXXFLAGS) $(CPPDEPS) $<
+
$(OBJS)\baselib_appbase.o: ../../src/common/appbase.cpp
$(CXX) -c -o $@ $(BASELIB_CXXFLAGS) $(CPPDEPS) $<
diff --git a/build/msw/makefile.vc b/build/msw/makefile.vc
index 5d14da8cba..71f5912442 100644
--- a/build/msw/makefile.vc
+++ b/build/msw/makefile.vc
@@ -311,6 +311,7 @@ MONODLL_CXXFLAGS = /M$(__RUNTIME_LIBS_100)$(__DEBUGRUNTIME) /DWIN32 \
/Fp"$(OBJS)\wxprec_monodll.pch" $(CPPFLAGS) $(CXXFLAGS)
MONODLL_OBJECTS = \
$(OBJS)\monodll_dummy.obj \
+ $(OBJS)\monodll_any.obj \
$(OBJS)\monodll_appbase.obj \
$(OBJS)\monodll_arcall.obj \
$(OBJS)\monodll_arcfind.obj \
@@ -456,6 +457,7 @@ MONOLIB_CXXFLAGS = /M$(__RUNTIME_LIBS_113)$(__DEBUGRUNTIME) /DWIN32 \
/Fp"$(OBJS)\wxprec_monolib.pch" $(CPPFLAGS) $(CXXFLAGS)
MONOLIB_OBJECTS = \
$(OBJS)\monolib_dummy.obj \
+ $(OBJS)\monolib_any.obj \
$(OBJS)\monolib_appbase.obj \
$(OBJS)\monolib_arcall.obj \
$(OBJS)\monolib_arcfind.obj \
@@ -599,6 +601,7 @@ BASEDLL_CXXFLAGS = /M$(__RUNTIME_LIBS_127)$(__DEBUGRUNTIME) /DWIN32 \
BASEDLL_OBJECTS = \
$(OBJS)\basedll_dummy.obj \
$(OBJS)\basedll_version.res \
+ $(OBJS)\basedll_any.obj \
$(OBJS)\basedll_appbase.obj \
$(OBJS)\basedll_arcall.obj \
$(OBJS)\basedll_arcfind.obj \
@@ -726,6 +729,7 @@ BASELIB_CXXFLAGS = /M$(__RUNTIME_LIBS_140)$(__DEBUGRUNTIME) /DWIN32 \
/Fp"$(OBJS)\wxprec_baselib.pch" $(CPPFLAGS) $(CXXFLAGS)
BASELIB_OBJECTS = \
$(OBJS)\baselib_dummy.obj \
+ $(OBJS)\baselib_any.obj \
$(OBJS)\baselib_appbase.obj \
$(OBJS)\baselib_arcall.obj \
$(OBJS)\baselib_arcfind.obj \
@@ -5861,6 +5865,9 @@ $(OBJS)\wxscintilla_XPM.obj: ..\..\src\stc\scintilla\src\XPM.cxx
$(OBJS)\monodll_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) /c /nologo /TP /Fo$@ $(MONODLL_CXXFLAGS) /Ycwx/wxprec.h ..\..\src\common\dummy.cpp
+$(OBJS)\monodll_any.obj: ..\..\src\common\any.cpp
+ $(CXX) /c /nologo /TP /Fo$@ $(MONODLL_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\monodll_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) /c /nologo /TP /Fo$@ $(MONODLL_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -8098,6 +8105,9 @@ $(OBJS)\monodll_version.res: ..\..\src\msw\version.rc
$(OBJS)\monolib_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) /c /nologo /TP /Fo$@ $(MONOLIB_CXXFLAGS) /Ycwx/wxprec.h ..\..\src\common\dummy.cpp
+$(OBJS)\monolib_any.obj: ..\..\src\common\any.cpp
+ $(CXX) /c /nologo /TP /Fo$@ $(MONOLIB_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\monolib_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) /c /nologo /TP /Fo$@ $(MONOLIB_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -10335,6 +10345,9 @@ $(OBJS)\basedll_dummy.obj: ..\..\src\common\dummy.cpp
$(OBJS)\basedll_version.res: ..\..\src\msw\version.rc
rc /fo$@ /d WIN32 $(____DEBUGRUNTIME_4) $(__NO_VC_CRTDBG_p_68) /d __WXMSW__ $(__WXUNIV_DEFINE_p_62) $(__DEBUG_DEFINE_p_61) $(__EXCEPTIONS_DEFINE_p_61) $(__RTTI_DEFINE_p_61) $(__THREAD_DEFINE_p_61) $(__UNICODE_DEFINE_p_62) $(__MSLU_DEFINE_p_61) $(__GFXCTX_DEFINE_p_61) /i $(SETUPHDIR) /i ..\..\include /d WXBUILDING /d WXDLLNAME=wxbase$(WX_VERSION_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_vc$(VENDORTAG) /i ..\..\src\tiff\libtiff /i ..\..\src\jpeg /i ..\..\src\png /i ..\..\src\zlib /i ..\..\src\regex /i ..\..\src\expat\lib /d wxUSE_GUI=0 /d WXMAKINGDLL_BASE /d wxUSE_BASE=1 ..\..\src\msw\version.rc
+$(OBJS)\basedll_any.obj: ..\..\src\common\any.cpp
+ $(CXX) /c /nologo /TP /Fo$@ $(BASEDLL_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\basedll_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) /c /nologo /TP /Fo$@ $(BASEDLL_CXXFLAGS) ..\..\src\common\appbase.cpp
@@ -10650,6 +10663,9 @@ $(OBJS)\basedll_volume.obj: ..\..\src\msw\volume.cpp
$(OBJS)\baselib_dummy.obj: ..\..\src\common\dummy.cpp
$(CXX) /c /nologo /TP /Fo$@ $(BASELIB_CXXFLAGS) /Ycwx/wxprec.h ..\..\src\common\dummy.cpp
+$(OBJS)\baselib_any.obj: ..\..\src\common\any.cpp
+ $(CXX) /c /nologo /TP /Fo$@ $(BASELIB_CXXFLAGS) ..\..\src\common\any.cpp
+
$(OBJS)\baselib_appbase.obj: ..\..\src\common\appbase.cpp
$(CXX) /c /nologo /TP /Fo$@ $(BASELIB_CXXFLAGS) ..\..\src\common\appbase.cpp
diff --git a/build/msw/makefile.wat b/build/msw/makefile.wat
index 18cb56ed3e..d02c4c6208 100644
--- a/build/msw/makefile.wat
+++ b/build/msw/makefile.wat
@@ -3439,6 +3439,7 @@ MONODLL_CXXFLAGS = -bd $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) &
$(__EXCEPTIONSFLAG) $(CPPFLAGS) $(CXXFLAGS)
MONODLL_OBJECTS = &
$(OBJS)\monodll_dummy.obj &
+ $(OBJS)\monodll_any.obj &
$(OBJS)\monodll_appbase.obj &
$(OBJS)\monodll_arcall.obj &
$(OBJS)\monodll_arcfind.obj &
@@ -3579,6 +3580,7 @@ MONOLIB_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) &
$(CPPFLAGS) $(CXXFLAGS)
MONOLIB_OBJECTS = &
$(OBJS)\monolib_dummy.obj &
+ $(OBJS)\monolib_any.obj &
$(OBJS)\monolib_appbase.obj &
$(OBJS)\monolib_arcall.obj &
$(OBJS)\monolib_arcfind.obj &
@@ -3717,6 +3719,7 @@ BASEDLL_CXXFLAGS = -bd $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) &
$(CPPFLAGS) $(CXXFLAGS)
BASEDLL_OBJECTS = &
$(OBJS)\basedll_dummy.obj &
+ $(OBJS)\basedll_any.obj &
$(OBJS)\basedll_appbase.obj &
$(OBJS)\basedll_arcall.obj &
$(OBJS)\basedll_arcfind.obj &
@@ -3839,6 +3842,7 @@ BASELIB_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) &
$(CPPFLAGS) $(CXXFLAGS)
BASELIB_OBJECTS = &
$(OBJS)\baselib_dummy.obj &
+ $(OBJS)\baselib_any.obj &
$(OBJS)\baselib_appbase.obj &
$(OBJS)\baselib_arcall.obj &
$(OBJS)\baselib_arcfind.obj &
@@ -5920,6 +5924,9 @@ $(OBJS)\wxscintilla_XPM.obj : .AUTODEPEND ..\..\src\stc\scintilla\src\XPM.cxx
$(OBJS)\monodll_dummy.obj : .AUTODEPEND ..\..\src\common\dummy.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(MONODLL_CXXFLAGS) $<
+$(OBJS)\monodll_any.obj : .AUTODEPEND ..\..\src\common\any.cpp
+ $(CXX) -bt=nt -zq -fo=$^@ $(MONODLL_CXXFLAGS) $<
+
$(OBJS)\monodll_appbase.obj : .AUTODEPEND ..\..\src\common\appbase.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(MONODLL_CXXFLAGS) $<
@@ -8269,6 +8276,9 @@ $(OBJS)\monodll_version.res : .AUTODEPEND ..\..\src\msw\version.rc
$(OBJS)\monolib_dummy.obj : .AUTODEPEND ..\..\src\common\dummy.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(MONOLIB_CXXFLAGS) $<
+$(OBJS)\monolib_any.obj : .AUTODEPEND ..\..\src\common\any.cpp
+ $(CXX) -bt=nt -zq -fo=$^@ $(MONOLIB_CXXFLAGS) $<
+
$(OBJS)\monolib_appbase.obj : .AUTODEPEND ..\..\src\common\appbase.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(MONOLIB_CXXFLAGS) $<
@@ -10618,6 +10628,9 @@ $(OBJS)\basedll_dummy.obj : .AUTODEPEND ..\..\src\common\dummy.cpp
$(OBJS)\basedll_version.res : .AUTODEPEND ..\..\src\msw\version.rc
wrc -q -ad -bt=nt -r -fo=$^@ -d__WXMSW__ $(__WXUNIV_DEFINE_p) $(__DEBUG_DEFINE_p) $(__EXCEPTIONS_DEFINE_p) $(__RTTI_DEFINE_p) $(__THREAD_DEFINE_p) $(__UNICODE_DEFINE_p) $(__GFXCTX_DEFINE_p) -i=$(SETUPHDIR) -i=..\..\include -dWXBUILDING -dWXDLLNAME=wxbase$(WX_VERSION_NODOT)$(WXUNICODEFLAG)$(WXDEBUGFLAG)$(WX_LIB_FLAVOUR)_wat$(VENDORTAG) -i=..\..\src\tiff\libtiff -i=..\..\src\jpeg -i=..\..\src\png -i=..\..\src\zlib -i=..\..\src\regex -i=..\..\src\expat\lib -dwxUSE_GUI=0 -dWXMAKINGDLL_BASE -dwxUSE_BASE=1 $<
+$(OBJS)\basedll_any.obj : .AUTODEPEND ..\..\src\common\any.cpp
+ $(CXX) -bt=nt -zq -fo=$^@ $(BASEDLL_CXXFLAGS) $<
+
$(OBJS)\basedll_appbase.obj : .AUTODEPEND ..\..\src\common\appbase.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(BASEDLL_CXXFLAGS) $<
@@ -10933,6 +10946,9 @@ $(OBJS)\basedll_volume.obj : .AUTODEPEND ..\..\src\msw\volume.cpp
$(OBJS)\baselib_dummy.obj : .AUTODEPEND ..\..\src\common\dummy.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(BASELIB_CXXFLAGS) $<
+$(OBJS)\baselib_any.obj : .AUTODEPEND ..\..\src\common\any.cpp
+ $(CXX) -bt=nt -zq -fo=$^@ $(BASELIB_CXXFLAGS) $<
+
$(OBJS)\baselib_appbase.obj : .AUTODEPEND ..\..\src\common\appbase.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(BASELIB_CXXFLAGS) $<
diff --git a/build/msw/wx_base.dsp b/build/msw/wx_base.dsp
index 4bc1022d75..5230122619 100644
--- a/build/msw/wx_base.dsp
+++ b/build/msw/wx_base.dsp
@@ -244,6 +244,10 @@ LIB32=link.exe -lib
# PROP Default_Filter ""
# Begin Source File
+SOURCE=..\..\src\common\any.cpp
+# End Source File
+# Begin Source File
+
SOURCE=..\..\src\common\appbase.cpp
# End Source File
# Begin Source File
@@ -1039,6 +1043,10 @@ SOURCE=..\..\include\wx\afterstd.h
# End Source File
# Begin Source File
+SOURCE=..\..\include\wx\any.h
+# End Source File
+# Begin Source File
+
SOURCE=..\..\include\wx\anystr.h
# End Source File
# Begin Source File
diff --git a/build/msw/wx_vc7_base.vcproj b/build/msw/wx_vc7_base.vcproj
index a032ba90a4..3c2a33a32c 100644
--- a/build/msw/wx_vc7_base.vcproj
+++ b/build/msw/wx_vc7_base.vcproj
@@ -524,6 +524,9 @@
+
+
@@ -1205,6 +1208,9 @@
+
+
diff --git a/build/msw/wx_vc8_base.vcproj b/build/msw/wx_vc8_base.vcproj
index dcbfff119d..4aa08b9f1e 100644
--- a/build/msw/wx_vc8_base.vcproj
+++ b/build/msw/wx_vc8_base.vcproj
@@ -734,6 +734,10 @@
Name="Common Sources"
UniqueIdentifier="{A6A5C30D-BDB6-5050-906D-10A96065136C}"
>
+
+
@@ -1627,6 +1631,10 @@
RelativePath="..\..\include\wx\afterstd.h"
>
+
+
diff --git a/build/msw/wx_vc9_base.vcproj b/build/msw/wx_vc9_base.vcproj
index 89ca7503c2..c5af22ed92 100644
--- a/build/msw/wx_vc9_base.vcproj
+++ b/build/msw/wx_vc9_base.vcproj
@@ -730,6 +730,10 @@
Name="Common Sources"
UniqueIdentifier="{A6A5C30D-BDB6-5050-906D-10A96065136C}"
>
+
+
@@ -1623,6 +1627,10 @@
RelativePath="..\..\include\wx\afterstd.h"
>
+
+
diff --git a/configure b/configure
index 8273903a77..535c97c026 100755
--- a/configure
+++ b/configure
@@ -1,5 +1,5 @@
#! /bin/sh
-# From configure.in Id.
+# From configure.in Id: configure.in 61944 2009-09-16 12:06:02Z PJC .
# Guess values for system-dependent variables and create Makefiles.
# Generated by GNU Autoconf 2.61 for wxWidgets 2.9.1.
#
@@ -1711,6 +1711,7 @@ Optional Features:
--enable-baseevtloop use event loop in console programs too
--enable-epollloop use wxEpollDispatcher class (Linux only)
--enable-selectloop use wxSelectDispatcher class
+ --enable-any use wxAny class
--enable-apple_ieee use the Apple IEEE codec
--enable-arcstream use wxArchive streams
--enable-base64 use base64 encoding/decoding functions
@@ -6274,6 +6275,50 @@ echo "${ECHO_T}$result" >&6; }
+ enablestring=
+ defaultval=$wxUSE_ALL_FEATURES
+ if test -z "$defaultval"; then
+ if test x"$enablestring" = xdisable; then
+ defaultval=yes
+ else
+ defaultval=no
+ fi
+ fi
+
+ { echo "$as_me:$LINENO: checking for --${enablestring:-enable}-any" >&5
+echo $ECHO_N "checking for --${enablestring:-enable}-any... $ECHO_C" >&6; }
+ # Check whether --enable-any was given.
+if test "${enable_any+set}" = set; then
+ enableval=$enable_any;
+ if test "$enableval" = yes; then
+ wx_cv_use_any='wxUSE_ANY=yes'
+ else
+ wx_cv_use_any='wxUSE_ANY=no'
+ fi
+
+else
+
+ wx_cv_use_any='wxUSE_ANY=${'DEFAULT_wxUSE_ANY":-$defaultval}"
+
+fi
+
+
+ eval "$wx_cv_use_any"
+
+ if test x"$enablestring" = xdisable; then
+ if test $wxUSE_ANY = no; then
+ result=yes
+ else
+ result=no
+ fi
+ else
+ result=$wxUSE_ANY
+ fi
+
+ { echo "$as_me:$LINENO: result: $result" >&5
+echo "${ECHO_T}$result" >&6; }
+
+
enablestring=
defaultval=$wxUSE_ALL_FEATURES
if test -z "$defaultval"; then
@@ -42260,6 +42305,13 @@ _ACEOF
fi
+if test "$wxUSE_ANY" = "yes"; then
+ cat >>confdefs.h <<\_ACEOF
+#define wxUSE_ANY 1
+_ACEOF
+
+fi
+
if test "$wxUSE_APPLE_IEEE" = "yes"; then
cat >>confdefs.h <<\_ACEOF
#define wxUSE_APPLE_IEEE 1
diff --git a/configure.in b/configure.in
index f5e9343db1..aff441405d 100644
--- a/configure.in
+++ b/configure.in
@@ -728,6 +728,7 @@ WX_ARG_FEATURE(epollloop, [ --enable-epollloop use wxEpollDispatcher c
WX_ARG_FEATURE(selectloop, [ --enable-selectloop use wxSelectDispatcher class], wxUSE_SELECT_DISPATCHER)
dnl please keep the settings below in alphabetical order
+WX_ARG_FEATURE(any, [ --enable-any use wxAny class], wxUSE_ANY)
WX_ARG_FEATURE(apple_ieee, [ --enable-apple_ieee use the Apple IEEE codec], wxUSE_APPLE_IEEE)
WX_ARG_FEATURE(arcstream, [ --enable-arcstream use wxArchive streams], wxUSE_ARCHIVE_STREAMS)
WX_ARG_FEATURE(base64, [ --enable-base64 use base64 encoding/decoding functions], wxUSE_BASE64)
@@ -5473,6 +5474,10 @@ if test "$wxUSE_EXTENDED_RTTI" = "yes"; then
AC_DEFINE(wxUSE_EXTENDED_RTTI)
fi
+if test "$wxUSE_ANY" = "yes"; then
+ AC_DEFINE(wxUSE_ANY)
+fi
+
if test "$wxUSE_APPLE_IEEE" = "yes"; then
AC_DEFINE(wxUSE_APPLE_IEEE)
fi
diff --git a/docs/changes.txt b/docs/changes.txt
index 8bcebd9415..f9055f7267 100644
--- a/docs/changes.txt
+++ b/docs/changes.txt
@@ -1,4 +1,4 @@
--------------------------------------------------------------------------------
+-------------------------------------------------------------------------------
wxWidgets Change Log
-------------------------------------------------------------------------------
@@ -391,6 +391,8 @@ All:
- Fix bug with position argument in wxImage::Size() (Byron Sorgdrager).
- Fix bug with parsing concatenated switches in wxCmdLineParser (Mike Funduc).
- Added wxMBConv::cMB2WC(wxCharBuffer) and cWC2MB(wxWCharBuffer) overloads.
+- Added wxAny class; a modern, backwards-incompatible replacement for
+ wxVariant.
All (GUI):
diff --git a/docs/doxygen/mainpages/cat_classes.h b/docs/doxygen/mainpages/cat_classes.h
index b287c33871..97820dfb6a 100644
--- a/docs/doxygen/mainpages/cat_classes.h
+++ b/docs/doxygen/mainpages/cat_classes.h
@@ -624,6 +624,7 @@ Related overview: @ref overview_log
These are the data structure classes supported by wxWidgets.
+@li wxAny: A class for storing arbitrary types that may change at run-time
@li wxCmdLineParser: Command line parser class
@li wxDateSpan: A logical time interval.
@li wxDateTime: A class for date/time manipulations
diff --git a/docs/doxygen/mainpages/const_wxusedef.h b/docs/doxygen/mainpages/const_wxusedef.h
index 78fb4b3509..2f04505ab4 100644
--- a/docs/doxygen/mainpages/const_wxusedef.h
+++ b/docs/doxygen/mainpages/const_wxusedef.h
@@ -67,6 +67,7 @@ library:
@itemdef{wxUSE_ACCEL, Use wxAcceleratorTable/Entry classes and support for them in wxMenu, wxMenuBar.}
@itemdef{wxUSE_AFM_FOR_POSTSCRIPT, In wxPostScriptDC class use AFM (adobe font metrics) file for character widths.}
@itemdef{wxUSE_ANIMATIONCTRL, Use wxAnimationCtrl class.}
+@itemdef{wxUSE_ANY, Use wxAny class.}
@itemdef{wxUSE_APPLE_IEEE, IEEE Extended to/from double routines; see src/common/extended.c file.}
@itemdef{wxUSE_ARCHIVE_STREAMS, Enable streams for archive formats.}
@itemdef{wxUSE_AUI, Use AUI (dockable windows) library.}
diff --git a/docs/doxygen/scripts/common.py b/docs/doxygen/scripts/common.py
index 41e80d7201..5285e0e3c5 100644
--- a/docs/doxygen/scripts/common.py
+++ b/docs/doxygen/scripts/common.py
@@ -7,6 +7,8 @@ ignored_methods = {
# these classes are either replaced by different data types in bindings, or have equivalent / better
# functionality provided by the target language.
excluded_classes = [
+ "wxAny",
+ "wxAnyValueType",
"wxArchiveClassFactory",
"wxArchiveEntry",
"wxArchiveInputStream",
diff --git a/include/wx/any.h b/include/wx/any.h
new file mode 100644
index 0000000000..9acda4ef55
--- /dev/null
+++ b/include/wx/any.h
@@ -0,0 +1,794 @@
+/////////////////////////////////////////////////////////////////////////////
+// Name: wx/any.h
+// Purpose: wxAny class
+// Author: Jaakko Salli
+// Modified by:
+// Created: 07/05/2009
+// RCS-ID: $Id$
+// Copyright: (c) wxWidgets team
+// Licence: wxWindows licence
+/////////////////////////////////////////////////////////////////////////////
+
+#ifndef _WX_ANY_H_
+#define _WX_ANY_H_
+
+#include "wx/defs.h"
+
+#if wxUSE_ANY
+
+#include "wx/string.h"
+#include "wx/meta/movable.h"
+#include "wx/meta/if.h"
+
+
+// Size of the wxAny value buffer.
+enum
+{
+ WX_ANY_VALUE_BUFFER_SIZE = 16
+};
+
+union wxAnyValueBuffer
+{
+ void* m_ptr;
+ wxByte m_buffer[WX_ANY_VALUE_BUFFER_SIZE];
+};
+
+typedef void (*wxAnyClassInfo)();
+
+
+//
+// wxAnyValueType is base class for value type functionality for C++ data
+// types used with wxAny. Usually the default template (wxAnyValueTypeImpl<>)
+// will create a satisfactory wxAnyValueType implementation for a data type.
+//
+class WXDLLIMPEXP_BASE wxAnyValueType
+{
+public:
+ /**
+ Default constructor.
+ */
+ wxAnyValueType();
+
+ /**
+ Destructor.
+ */
+ virtual ~wxAnyValueType()
+ {
+ }
+
+ /**
+ This function is used for internal type matching.
+ */
+ virtual wxAnyClassInfo GetClassInfo() const = 0;
+
+ /**
+ This function is used for internal type matching.
+ */
+ virtual bool IsSameType(const wxAnyValueType* otherType) const = 0;
+
+ /**
+ This function is called every time the data in wxAny
+ buffer needs to be freed.
+ */
+ virtual void DeleteValue(wxAnyValueBuffer& buf) const = 0;
+
+ /**
+ Implement this for buffer-to-buffer copy. src.m_ptr can
+ be expected to be NULL if value type of previously stored
+ data was different.
+ */
+ virtual void CopyBuffer(const wxAnyValueBuffer& src,
+ wxAnyValueBuffer& dst) const = 0;
+
+ /**
+ Convert value into buffer of different type. Return false if
+ not possible.
+ */
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const = 0;
+
+ /**
+ Use this template function for checking if wxAnyValueType represents
+ a specific C++ data type.
+
+ @remarks This template function does not work on some older compilers
+ (such as Visual C++ 6.0). For full compiler ccompatibility
+ please use wxANY_VALUE_TYPE_CHECK_TYPE(valueTypePtr, T) macro
+ instead.
+
+ @see wxAny::CheckType()
+ */
+ // FIXME-VC6: remove this hack when VC6 is no longer supported
+ template
+ bool CheckType(T* reserved = NULL);
+private:
+};
+
+//
+// This method of checking the type is compatible with VC6
+#define wxANY_VALUE_TYPE_CHECK_TYPE(valueTypePtr, T) \
+ wxAnyValueTypeImpl::IsSameClass(valueTypePtr)
+
+ //valueTypePtr->CheckType(static_cast(NULL))
+
+
+/**
+ Helper macro for defining user value types.
+
+ NB: We really cannot compare sm_classInfo directly in IsSameClass(),
+ but instead call sm_instance->GetClassInfo(). The former technique
+ broke at least on GCC 4.2 (but worked on VC8 shared build).
+*/
+#define WX_DECLARE_ANY_VALUE_TYPE(CLS) \
+ friend class wxAny; \
+public: \
+ static void sm_classInfo() {} \
+ \
+ virtual wxAnyClassInfo GetClassInfo() const \
+ { \
+ return sm_classInfo; \
+ } \
+ static bool IsSameClass(const wxAnyValueType* otherType) \
+ { \
+ return sm_instance->GetClassInfo() == otherType->GetClassInfo(); \
+ } \
+ virtual bool IsSameType(const wxAnyValueType* otherType) const \
+ { \
+ return IsSameClass(otherType); \
+ } \
+private: \
+ static CLS* sm_instance; \
+public: \
+ static wxAnyValueType* GetInstance() \
+ { \
+ return sm_instance; \
+ }
+
+
+#define WX_IMPLEMENT_ANY_VALUE_TYPE(CLS) \
+ CLS* CLS::sm_instance = new CLS();
+
+
+#ifdef __VISUALC6__
+ // "non dll-interface class 'xxx' used as base interface
+ #pragma warning (push)
+ #pragma warning (disable:4275)
+#endif
+
+/**
+ Following are helper classes for the wxAnyValueTypeImplBase.
+*/
+namespace wxPrivate
+{
+
+template
+class wxAnyValueTypeOpsMovable
+{
+public:
+ static void DeleteValue(wxAnyValueBuffer& buf)
+ {
+ wxUnusedVar(buf);
+ }
+
+ static void SetValue(const T& value,
+ wxAnyValueBuffer& buf)
+ {
+ memcpy(buf.m_buffer, &value, sizeof(T));
+ }
+
+ static const T& GetValue(const wxAnyValueBuffer& buf)
+ {
+ return *(reinterpret_cast(&buf.m_buffer[0]));
+ }
+};
+
+
+template
+class wxAnyValueTypeOpsGeneric
+{
+public:
+ template
+ class DataHolder
+ {
+ public:
+ DataHolder(const T2& value)
+ {
+ m_value = value;
+ }
+ virtual ~DataHolder() { }
+
+ T2 m_value;
+ private:
+ wxDECLARE_NO_COPY_CLASS(DataHolder);
+ };
+
+ static void DeleteValue(wxAnyValueBuffer& buf)
+ {
+ DataHolder* holder = static_cast*>(buf.m_ptr);
+ delete holder;
+ }
+
+ static void SetValue(const T& value,
+ wxAnyValueBuffer& buf)
+ {
+ DataHolder* holder = new DataHolder(value);
+ buf.m_ptr = holder;
+ }
+
+ static const T& GetValue(const wxAnyValueBuffer& buf)
+ {
+ DataHolder* holder = static_cast*>(buf.m_ptr);
+ return holder->m_value;
+ }
+};
+
+} // namespace wxPrivate
+
+
+/**
+ Intermediate template for the generic value type implementation.
+ We can derive from this same value type for multiple actual types
+ (for instance, we can have wxAnyValueTypeImplInt for all signed
+ integer types), and also easily implement specialized templates
+ with specific dynamic type conversion.
+*/
+template
+class wxAnyValueTypeImplBase : public wxAnyValueType
+{
+ typedef typename wxIf< wxIsMovable::value &&
+ sizeof(T) <= WX_ANY_VALUE_BUFFER_SIZE,
+ wxPrivate::wxAnyValueTypeOpsMovable,
+ wxPrivate::wxAnyValueTypeOpsGeneric >::value
+ Ops;
+
+public:
+ wxAnyValueTypeImplBase() : wxAnyValueType() { }
+ virtual ~wxAnyValueTypeImplBase() { }
+
+ virtual void DeleteValue(wxAnyValueBuffer& buf) const
+ {
+ Ops::DeleteValue(buf);
+ buf.m_ptr = NULL; // This is important
+ }
+
+ virtual void CopyBuffer(const wxAnyValueBuffer& src,
+ wxAnyValueBuffer& dst) const
+ {
+ Ops::DeleteValue(dst);
+ Ops::SetValue(Ops::GetValue(src), dst);
+ }
+
+ /**
+ It is important to reimplement this in any specialized template
+ classes that inherit from wxAnyValueTypeImplBase.
+ */
+ static void SetValue(const T& value,
+ wxAnyValueBuffer& buf)
+ {
+ Ops::SetValue(value, buf);
+ }
+
+ /**
+ It is important to reimplement this in any specialized template
+ classes that inherit from wxAnyValueTypeImplBase.
+ */
+ static const T& GetValue(const wxAnyValueBuffer& buf)
+ {
+ return Ops::GetValue(buf);
+ }
+};
+
+
+/*
+ Generic value type template. Note that bulk of the implementation
+ resides in wxAnyValueTypeImplBase.
+*/
+template
+class wxAnyValueTypeImpl : public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+public:
+ wxAnyValueTypeImpl() : wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImpl() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+ {
+ wxUnusedVar(src);
+ wxUnusedVar(dstType);
+ wxUnusedVar(dst);
+ return false;
+ }
+};
+
+template
+wxAnyValueTypeImpl* wxAnyValueTypeImpl::sm_instance =
+ new wxAnyValueTypeImpl();
+
+
+//
+// Helper macro for using same base value type implementation for multiple
+// actual C++ data types.
+//
+#define WX_ANY_DEFINE_SUB_TYPE(T, CLSTYPE) \
+template<> \
+class wxAnyValueTypeImpl : public wxAnyValueTypeImpl##CLSTYPE \
+{ \
+ typedef wxAnyBase##CLSTYPE##Type UseDataType; \
+public: \
+ wxAnyValueTypeImpl() : wxAnyValueTypeImpl##CLSTYPE() { } \
+ virtual ~wxAnyValueTypeImpl() { } \
+ static void SetValue(const T& value, wxAnyValueBuffer& buf) \
+ { \
+ *(reinterpret_cast(&buf.m_buffer[0])) = \
+ static_cast(value); \
+ } \
+ static T GetValue(const wxAnyValueBuffer& buf) \
+ { \
+ return static_cast( \
+ *(reinterpret_cast(&buf.m_buffer[0]))); \
+ } \
+};
+
+
+//
+// Integer value types
+//
+
+#ifdef wxLongLong_t
+ typedef wxLongLong_t wxAnyBaseIntType;
+ typedef wxULongLong_t wxAnyBaseUintType;
+#else
+ typedef long wxAnyBaseIntType;
+ typedef unsigned long wxAnyBaseUintType;
+#endif
+
+
+class WXDLLIMPEXP_BASE wxAnyValueTypeImplInt :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImplInt)
+public:
+ wxAnyValueTypeImplInt() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImplInt() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const;
+};
+
+
+class WXDLLIMPEXP_BASE wxAnyValueTypeImplUint :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImplUint)
+public:
+ wxAnyValueTypeImplUint() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImplUint() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const;
+};
+
+
+WX_ANY_DEFINE_SUB_TYPE(signed long, Int)
+WX_ANY_DEFINE_SUB_TYPE(signed int, Int)
+WX_ANY_DEFINE_SUB_TYPE(signed short, Int)
+WX_ANY_DEFINE_SUB_TYPE(signed char, Int)
+#ifdef wxLongLong_t
+WX_ANY_DEFINE_SUB_TYPE(wxLongLong_t, Int)
+#endif
+
+WX_ANY_DEFINE_SUB_TYPE(unsigned long, Uint)
+WX_ANY_DEFINE_SUB_TYPE(unsigned int, Uint)
+WX_ANY_DEFINE_SUB_TYPE(unsigned short, Uint)
+WX_ANY_DEFINE_SUB_TYPE(unsigned char, Uint)
+#ifdef wxLongLong_t
+WX_ANY_DEFINE_SUB_TYPE(wxULongLong_t, Uint)
+#endif
+
+
+//
+// String value type
+//
+class WXDLLIMPEXP_BASE wxAnyValueTypeImplString :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImplString)
+public:
+ wxAnyValueTypeImplString() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImplString() { }
+
+ /**
+ Convert value into buffer of different type. Return false if
+ not possible.
+ */
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const;
+
+};
+
+template<>
+class wxAnyValueTypeImpl : public wxAnyValueTypeImplString
+{
+public:
+ wxAnyValueTypeImpl() : wxAnyValueTypeImplString() { }
+ virtual ~wxAnyValueTypeImpl() { }
+};
+
+
+//
+// Bool value type
+//
+template<>
+class WXDLLIMPEXP_BASE wxAnyValueTypeImpl :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+public:
+ wxAnyValueTypeImpl() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImpl() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const;
+};
+
+//
+// Floating point value type
+//
+class WXDLLIMPEXP_BASE wxAnyValueTypeImplDouble :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImplDouble)
+public:
+ wxAnyValueTypeImplDouble() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImplDouble() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const;
+};
+
+// WX_ANY_DEFINE_SUB_TYPE requires this
+typedef double wxAnyBaseDoubleType;
+
+WX_ANY_DEFINE_SUB_TYPE(float, Double)
+WX_ANY_DEFINE_SUB_TYPE(double, Double)
+
+
+#ifdef __VISUALC6__
+ // Re-enable useless VC6 warnings
+ #pragma warning (pop)
+#endif
+
+
+/*
+ Let's define a discrete Null value so we don't have to really
+ ever check if wxAny.m_type pointer is NULL or not. This is an
+ optimization, mostly. Implementation of this value type is
+ "hidden" in the source file.
+*/
+extern WXDLLIMPEXP_DATA_BASE(wxAnyValueType*) wxAnyNullValueType;
+
+
+//
+// We need to implement custom signed/unsigned int equals operators
+// for signed/unsigned (eg. wxAny(128UL) == 128L) comparisons to work.
+#define WXANY_IMPLEMENT_INT_EQ_OP(TS, TUS) \
+bool operator==(TS value) const \
+{ \
+ if ( wxAnyValueTypeImpl::IsSameClass(m_type) ) \
+ return (value == static_cast \
+ (wxAnyValueTypeImpl::GetValue(m_buffer))); \
+ if ( wxAnyValueTypeImpl::IsSameClass(m_type) ) \
+ return (value == static_cast \
+ (wxAnyValueTypeImpl::GetValue(m_buffer))); \
+ return false; \
+} \
+bool operator==(TUS value) const \
+{ \
+ if ( wxAnyValueTypeImpl::IsSameClass(m_type) ) \
+ return (value == static_cast \
+ (wxAnyValueTypeImpl::GetValue(m_buffer))); \
+ if ( wxAnyValueTypeImpl::IsSameClass(m_type) ) \
+ return (value == static_cast \
+ (wxAnyValueTypeImpl::GetValue(m_buffer))); \
+ return false; \
+}
+
+
+//
+// The wxAny class represents a container for any type. A variant's value
+// can be changed at run time, possibly to a different type of value.
+//
+// As standard, wxAny can store value of almost any type, in a fairly
+// optimal manner even.
+//
+class WXDLLIMPEXP_BASE wxAny
+{
+public:
+ /**
+ Default constructor.
+ */
+ wxAny()
+ {
+ m_type = wxAnyNullValueType;
+ }
+
+ /**
+ Destructor.
+ */
+ ~wxAny()
+ {
+ m_type->DeleteValue(m_buffer);
+ }
+
+ //@{
+ /**
+ Various constructors.
+ */
+ wxAny(const char* value)
+ {
+ m_type = wxAnyNullValueType;
+ Assign(wxString(value));
+ }
+ wxAny(const wchar_t* value)
+ {
+ m_type = wxAnyNullValueType;
+ Assign(wxString(value));
+ }
+
+ wxAny(const wxAny& any)
+ {
+ m_type = wxAnyNullValueType;
+ AssignAny(any);
+ }
+
+ template
+ wxAny(const T& value)
+ {
+ m_type = wxAnyValueTypeImpl::sm_instance;
+ wxAnyValueTypeImpl::SetValue(value, m_buffer);
+ }
+ //@}
+
+ /**
+ Use this template function for checking if this wxAny holds
+ a specific C++ data type.
+
+ @remarks This template function does not work on some older compilers
+ (such as Visual C++ 6.0). For full compiler ccompatibility
+ please use wxANY_CHECK_TYPE(any, T) macro instead.
+
+ @see wxAnyValueType::CheckType()
+ */
+ // FIXME-VC6: remove this hack when VC6 is no longer supported
+ template
+ bool CheckType(T* = NULL)
+ {
+ return m_type->CheckType();
+ }
+
+ /**
+ Returns the value type as wxAnyValueType instance.
+
+ @remarks You cannot reliably test whether two wxAnys are of
+ same value type by simply comparing return values
+ of wxAny::GetType(). Instead use
+ wxAnyValueType::CheckType() template function.
+ */
+ const wxAnyValueType* GetType() const
+ {
+ return m_type;
+ }
+
+ /**
+ Tests if wxAny is null (that is, whether there is data).
+ */
+ bool IsNull() const
+ {
+ return (m_type == wxAnyNullValueType);
+ }
+
+ /**
+ Makes wxAny null (that is, clears it).
+ */
+ void MakeNull()
+ {
+ m_type->DeleteValue(m_buffer);
+ m_type = wxAnyNullValueType;
+ }
+
+ //@{
+ /**
+ Assignment operators.
+ */
+ wxAny& operator=(const wxAny &any)
+ {
+ AssignAny(any);
+ return *this;
+ }
+
+ template
+ wxAny& operator=(const T &value)
+ {
+ m_type->DeleteValue(m_buffer);
+ m_type = wxAnyValueTypeImpl::sm_instance;
+ wxAnyValueTypeImpl::SetValue(value, m_buffer);
+ return *this;
+ }
+
+ wxAny& operator=(const char* value)
+ { Assign(wxString(value)); return *this; }
+ wxAny& operator=(const wchar_t* value)
+ { Assign(wxString(value)); return *this; }
+ //@}
+
+ //@{
+ /**
+ Equality operators.
+ */
+ bool operator==(const wxString& value) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ return false;
+
+ return value ==
+ static_cast
+ (wxAnyValueTypeImpl::GetValue(m_buffer));
+ }
+
+ bool operator==(const char* value) const
+ { return (*this) == wxString(value); }
+ bool operator==(const wchar_t* value) const
+ { return (*this) == wxString(value); }
+
+ //
+ // We need to implement custom signed/unsigned int equals operators
+ // for signed/unsigned (eg. wxAny(128UL) == 128L) comparisons to work.
+ WXANY_IMPLEMENT_INT_EQ_OP(signed char, unsigned char)
+ WXANY_IMPLEMENT_INT_EQ_OP(signed short, unsigned short)
+ WXANY_IMPLEMENT_INT_EQ_OP(signed int, unsigned int)
+ WXANY_IMPLEMENT_INT_EQ_OP(signed long, unsigned long)
+#ifdef wxLongLong_t
+ WXANY_IMPLEMENT_INT_EQ_OP(wxLongLong_t, wxULongLong_t)
+#endif
+
+ bool operator==(float value) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ return false;
+
+ return value ==
+ static_cast
+ (wxAnyValueTypeImpl::GetValue(m_buffer));
+ }
+
+ bool operator==(double value) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ return false;
+
+ return value ==
+ static_cast
+ (wxAnyValueTypeImpl::GetValue(m_buffer));
+ }
+
+ bool operator==(bool value) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ return false;
+
+ return value == (wxAnyValueTypeImpl::GetValue(m_buffer));
+ }
+
+ //@}
+
+ //@{
+ /**
+ Inequality operators (implement as template).
+ */
+ template
+ bool operator!=(const T& value) const
+ { return !((*this) == value); }
+ //@}
+
+ /**
+ This template function converts wxAny into given type. No dynamic
+ conversion is performed, so if the type is incorrect an assertion
+ failure will occur in debug builds, and a bogus value is returned
+ in release ones.
+
+ @remarks This template function does not work on some older compilers
+ (such as Visual C++ 6.0). For full compiler ccompatibility
+ please use wxANY_AS(any, T) macro instead.
+ */
+ // FIXME-VC6: remove this hack when VC6 is no longer supported
+ template
+ T As(T* = NULL) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ wxFAIL_MSG("Incorrect or non-convertible data type");
+ return static_cast(wxAnyValueTypeImpl::GetValue(m_buffer));
+ }
+
+ /**
+ Template function that etrieves and converts the value of this
+ variant to the type that T* value is.
+
+ @return Returns @true if conversion was succesfull.
+ */
+ template
+ bool GetAs(T* value) const
+ {
+ if ( !wxAnyValueTypeImpl::IsSameClass(m_type) )
+ {
+ wxAnyValueType* otherType =
+ wxAnyValueTypeImpl::sm_instance;
+ wxAnyValueBuffer temp_buf;
+
+ if ( !m_type->ConvertValue(m_buffer, otherType, temp_buf) )
+ return false;
+
+ *value =
+ static_cast(wxAnyValueTypeImpl::GetValue(temp_buf));
+ otherType->DeleteValue(temp_buf);
+
+ return true;
+ }
+ *value = static_cast(wxAnyValueTypeImpl::GetValue(m_buffer));
+ return true;
+ }
+
+private:
+ // Assignment functions
+ void AssignAny(const wxAny &any);
+
+ template
+ void Assign(const T &value)
+ {
+ m_type->DeleteValue(m_buffer);
+ m_type = wxAnyValueTypeImpl::sm_instance;
+ wxAnyValueTypeImpl::SetValue(value, m_buffer);
+ }
+
+ // Data
+ wxAnyValueType* m_type;
+ wxAnyValueBuffer m_buffer;
+};
+
+
+//
+// This method of checking the type is compatible with VC6
+#define wxANY_CHECK_TYPE(any, T) \
+ wxANY_VALUE_TYPE_CHECK_TYPE(any.GetType(), T)
+
+
+//
+// This method of getting the value is compatible with VC6
+#define wxANY_AS(any, T) \
+ any.As(static_cast(NULL))
+
+
+template
+inline bool wxAnyValueType::CheckType(T* reserved)
+{
+ wxUnusedVar(reserved);
+ return wxAnyValueTypeImpl::IsSameClass(this);
+}
+
+
+
+#endif // wxUSE_ANY
+
+#endif // _WX_ANY_H_
diff --git a/include/wx/chkconf.h b/include/wx/chkconf.h
index 95bba3811a..0d4f0b008c 100644
--- a/include/wx/chkconf.h
+++ b/include/wx/chkconf.h
@@ -68,6 +68,14 @@
please keep the options in alphabetical order!
*/
+#ifndef wxUSE_ANY
+# ifdef wxABORT_ON_CONFIG_ERROR
+# error "wxUSE_ANY must be defined."
+# else
+# define wxUSE_ANY 0
+# endif
+#endif /* wxUSE_ANY */
+
#ifndef wxUSE_CONSOLE_EVENTLOOP
# ifdef wxABORT_ON_CONFIG_ERROR
# error "wxUSE_CONSOLE_EVENTLOOP must be defined."
diff --git a/include/wx/msw/setup0.h b/include/wx/msw/setup0.h
index 60f67f7312..9deacf6e96 100644
--- a/include/wx/msw/setup0.h
+++ b/include/wx/msw/setup0.h
@@ -570,6 +570,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/msw/wince/setup.h b/include/wx/msw/wince/setup.h
index f13813b574..e9d70cee44 100644
--- a/include/wx/msw/wince/setup.h
+++ b/include/wx/msw/wince/setup.h
@@ -570,6 +570,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/os2/setup0.h b/include/wx/os2/setup0.h
index 48ccfd6c52..5403761a21 100644
--- a/include/wx/os2/setup0.h
+++ b/include/wx/os2/setup0.h
@@ -570,6 +570,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/osx/setup0.h b/include/wx/osx/setup0.h
index 1783604b04..2af5514a2f 100644
--- a/include/wx/osx/setup0.h
+++ b/include/wx/osx/setup0.h
@@ -571,6 +571,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/palmos/setup0.h b/include/wx/palmos/setup0.h
index 18ca37e61c..33b7c3fa88 100644
--- a/include/wx/palmos/setup0.h
+++ b/include/wx/palmos/setup0.h
@@ -570,6 +570,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/setup_inc.h b/include/wx/setup_inc.h
index cc24179174..b014a90b88 100644
--- a/include/wx/setup_inc.h
+++ b/include/wx/setup_inc.h
@@ -566,6 +566,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/include/wx/univ/setup0.h b/include/wx/univ/setup0.h
index 7a270163cb..7f9cb99638 100644
--- a/include/wx/univ/setup0.h
+++ b/include/wx/univ/setup0.h
@@ -569,6 +569,14 @@
// possible in which case setting this to 0 can gain up to 100KB.
#define wxUSE_VARIANT 1
+// Support for wxAny class, the successor for wxVariant.
+//
+// Default is 1.
+//
+// Recommended setting: 1 unless you want to reduce the library size by a small amount,
+// or your compiler cannot for some reason cope with complexity of templates used.
+#define wxUSE_ANY 1
+
// Support for regular expression matching via wxRegEx class: enable this to
// use POSIX regular expressions in your code. You need to compile regex
// library from src/regex to use it under Windows.
diff --git a/interface/wx/any.h b/interface/wx/any.h
new file mode 100644
index 0000000000..9dc3442018
--- /dev/null
+++ b/interface/wx/any.h
@@ -0,0 +1,425 @@
+/////////////////////////////////////////////////////////////////////////////
+// Name: any.h
+// Purpose: interface of wxAny
+// Author: wxWidgets team
+// RCS-ID: $Id$
+// Licence: wxWindows license
+/////////////////////////////////////////////////////////////////////////////
+
+
+/**
+ @class wxAny
+
+ The wxAny class represents a container for any type. Its value
+ can be changed at run time, possibly to a different type of value.
+
+ wxAny is successor class for wxVariant, essentially doing the same thing
+ in a more modern, template-based manner and with transparent support
+ for any user data type.
+
+ Some pseudo-code'ish example of use with arbitrary user data:
+
+ @code
+ void SomeFunction()
+ {
+ MyClass myObject;
+ wxAny any = myObject;
+
+ // Do something
+ // ...
+
+ // Let's do a sanity check to make sure that any still holds
+ // data of correct type.
+ if ( any.CheckType() )
+ {
+ // Thank goodness, still a correct type.
+ MyClass myObject2 = any.As();
+ }
+ else
+ {
+ // Something has gone horribly wrong!
+ wxFAIL();
+ }
+ }
+ @endcode
+
+ When compared to wxVariant, there are various internal implementation
+ differences as well. For instance, wxAny only allocates separate data
+ object in heap for large (ie. size in bytes more than
+ WX_ANY_VALUE_BUFFER_SIZE) or 'non-movable' data types. Pointers, integers,
+ bools etc. are fitted in the wxAny's own buffer without need for any extra
+ allocation. Use following code to declare your own data type as 'movable':
+
+ @code
+ #include "wx/meta/movable.h"
+ WX_DECLARE_TYPE_MOVABLE(MyClass)
+ @endcode
+
+ However, you must be aware that 'movable' means such data that can be
+ copied with memcpy() without corrupting program integrity. For instance,
+ movable objects usually cannot contain pointers or references to other
+ data. wxRect, wxPoint, and wxSize are good examples of movable classes.
+
+ Note that pointers to any and all classes are already automatically
+ declared as movable data.
+
+ @library{wxbase}
+ @category{data}
+
+ @see wxAnyValueType, wxVariant
+*/
+class wxAny
+{
+public:
+ /**
+ Default constructor. It seeds the object with a null value.
+ */
+ wxAny();
+
+ /**
+ Constructs wxAny from data.
+ */
+ template
+ wxAny(const T& value);
+
+ /**
+ Constructs wxAny from another wxAny.
+ */
+ wxAny(const wxAny& any);
+
+ /**
+ Destructor.
+ */
+ ~wxAny();
+
+ /**
+ This template function converts wxAny into given type. No dynamic
+ conversion is performed, so if the type is incorrect an assertion
+ failure will occur in debug builds, and a bogus value is returned
+ in release ones.
+
+ @remarks This template function may not work properly with Visual C++
+ 6. For full compiler compatibility, please use
+ wxANY_AS(any, T) macro instead.
+ */
+ template
+ T As() const;
+
+ /**
+ Use this template function for checking if this wxAny holds
+ a specific C++ data type.
+
+ @remarks This template function may not work properly with Visual C++
+ 6. For full compiler compatibility, please use
+ wxANY_CHECK_TYPE(any, T) macro instead.
+
+ @see wxAnyValueType::CheckType()
+ */
+ template
+ bool CheckType();
+
+ /**
+ Template function that retrieves and converts the value of this
+ wxAny to the type that T* value is.
+
+ @return Returns @true if conversion was succesfull.
+ */
+ template
+ bool GetAs(T* value) const;
+
+ /**
+ Returns the value type as wxAnyValueType instance.
+
+ @remarks You cannot reliably test whether two wxAnys are of
+ same value type by simply comparing return values
+ of wxAny::GetType(). Instead use
+ wxAnyValueType::CheckType() template function.
+ */
+ const wxAnyValueType* GetType() const;
+
+ /**
+ Tests if wxAny is null (that is, whether there is data).
+ */
+ bool IsNull() const;
+
+ /**
+ Makes wxAny null (that is, clears it).
+ */
+ void MakeNull();
+
+ //@{
+ /**
+ @name Assignment operators
+ */
+ template
+ wxAny& operator=(const T &value);
+ wxAny& operator=(const wxAny &any);
+ //@}
+
+ //@{
+ /**
+ @name Equality operators
+
+ @remarks Generic template-based comparison operators have not been
+ provided for various code consistency reasons, so for custom
+ data types you have do something like this:
+
+ @code
+ if ( any.CheckType() &&
+ any.As() == myObjectPtr )
+ {
+ // Do something if any stores myObjectPtr
+ }
+ @endcode
+ */
+ bool operator==(signed char value) const;
+ bool operator==(signed short value) const;
+ bool operator==(signed int value) const;
+ bool operator==(signed long value) const;
+ bool operator==(wxLongLong_t value) const;
+ bool operator==(unsigned char value) const;
+ bool operator==(unsigned short value) const;
+ bool operator==(unsigned int value) const;
+ bool operator==(unsigned long value) const;
+ bool operator==(wxULongLong_t value) const;
+ bool operator==(float value) const;
+ bool operator==(double value) const;
+ bool operator==(bool value) const;
+ bool operator==(const char* value) const;
+ bool operator==(const wchar_t* value) const;
+ bool operator==(const wxString& value) const;
+ //@}
+
+ //@{
+ /**
+ @name Inequality operators
+ */
+ bool operator!=(signed char value) const;
+ bool operator!=(signed short value) const;
+ bool operator!=(signed int value) const;
+ bool operator!=(signed long value) const;
+ bool operator!=(wxLongLong_t value) const;
+ bool operator!=(unsigned char value) const;
+ bool operator!=(unsigned short value) const;
+ bool operator!=(unsigned int value) const;
+ bool operator!=(unsigned long value) const;
+ bool operator!=(wxULongLong_t value) const;
+ bool operator!=(float value) const;
+ bool operator!=(double value) const;
+ bool operator!=(bool value) const;
+ bool operator!=(const char* value) const;
+ bool operator!=(const wchar_t* value) const;
+ bool operator!=(const wxString& value) const;
+ //@}
+};
+
+/**
+ This is value getter macro that is more compatible with older
+ compilers, such as Visual C++ 6.0.
+*/
+#define wxANY_AS(any, T)
+
+
+/**
+ This is type checking macro that is more compatible with older
+ compilers, such as Visual C++ 6.0.
+*/
+#define wxANY_CHECK_TYPE(any, T)
+
+
+/**
+ Size of the wxAny value buffer.
+*/
+enum
+{
+ WX_ANY_VALUE_BUFFER_SIZE = 16
+};
+
+/**
+ Type for buffer within wxAny for holding data.
+*/
+union wxAnyValueBuffer
+{
+ void* m_ptr;
+ wxByte m_buffer[WX_ANY_VALUE_BUFFER_SIZE];
+};
+
+
+/**
+ @class wxAnyValueType
+
+ wxAnyValueType is base class for value type functionality for C++ data
+ types used with wxAny. Usually the default template will create a
+ satisfactory wxAnyValueType implementation for a data type, but
+ sometimes you may need to add some customization. To do this you will need
+ to add specialized template of wxAnyValueTypeImpl<>. Often your only
+ need may be to add dynamic type conversion which would be done like
+ this:
+
+ @code
+ template<>
+ class wxAnyValueTypeImpl :
+ public wxAnyValueTypeImplBase
+ {
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+ public:
+ wxAnyValueTypeImpl() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImpl() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+ {
+ // GetValue() is a static member function implemented
+ // in wxAnyValueTypeImplBase<>.
+ MyClass value = GetValue(src);
+
+ // TODO: Convert value from src buffer to destination
+ // type and buffer. If cannot be done, return
+ // false. This is a simple sample.
+ if ( dstType->CheckType() )
+ {
+ wxString s = value.ToString();
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else
+ {
+ return false;
+ }
+ }
+ };
+
+ //
+ // Following must be placed somewhere in your source code
+ WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+ @endcode
+
+ wxAnyValueTypeImplBase<> template, from which we inherit in the above
+ example, contains the bulk of the default wxAnyValueTypeImpl<> template
+ implementation, and as such allows you to easily add some minor
+ customization.
+
+ If you need a have complete control over the type interpretation, you
+ will need to derive a class directly from wxAnyValueType, like this:
+
+ @code
+ template <>
+ class wxAnyValueTypeImpl : public wxAnyValueType
+ {
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+ public:
+ virtual void DeleteValue(wxAnyValueBuffer& buf) const
+ {
+ // TODO: Free the data in buffer
+ // It is important to clear the buffer like this
+ // at the end of DeleteValue().
+ buf.m_ptr = NULL;
+ }
+
+ virtual void CopyBuffer(const wxAnyValueBuffer& src,
+ wxAnyValueBuffer& dst) const
+ {
+ // TODO: Copy value from one buffer to another.
+ }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+ {
+ // TODO: Convert value from src buffer to destination
+ // type and buffer.
+ }
+
+ //
+ // Following static functions must be implemented
+ //
+
+ static void SetValue(const T& value,
+ wxAnyValueBuffer& buf)
+ {
+ // TODO: Store value into buf.
+ }
+
+ static const T& GetValue(const wxAnyValueBuffer& buf)
+ {
+ // TODO: Return reference to value stored in buffer.
+ }
+ };
+
+ //
+ // Following must be placed somewhere in your source code
+ WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+
+ @endcode
+
+ @library{wxbase}
+ @category{data}
+
+ @see wxAny
+*/
+class wxAnyValueType
+{
+public:
+ /**
+ Default constructor.
+ */
+ wxAnyValueType();
+
+ /**
+ Destructor.
+ */
+ virtual ~wxAnyValueType();
+
+ /**
+ Use this template function for checking if wxAnyValueType represents
+ a specific C++ data type.
+
+ @remarks This template function does not work on some older compilers
+ (such as Visual C++ 6.0). For full compiler ccompatibility
+ please use wxANY_VALUE_TYPE_CHECK_TYPE(valueTypePtr, T) macro
+ instead.
+
+ @see wxAny::CheckType()
+ */
+ template
+ bool CheckType();
+
+ /**
+ Convert value into buffer of different type. Return false if
+ not possible.
+ */
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const = 0;
+
+ /**
+ Implement this for buffer-to-buffer copy. src.m_ptr can
+ be expected to be NULL if value type of previously stored
+ data was different.
+ */
+ virtual void CopyBuffer(const wxAnyValueBuffer& src,
+ wxAnyValueBuffer& dst) const = 0;
+
+ /**
+ This function is called every time the data in wxAny
+ buffer needs to be freed.
+ */
+ virtual void DeleteValue(wxAnyValueBuffer& buf) const = 0;
+
+ /**
+ This function is used for internal type matching.
+ */
+ virtual wxAnyClassInfo GetClassInfo() const = 0;
+
+ /**
+ This function is used for internal type matching.
+ */
+ virtual bool IsSameType(const wxAnyValueType* otherType) const = 0;
+};
+
+/**
+ This is type checking macro that is more compatible with older
+ compilers, such as Visual C++ 6.0.
+*/
+#define wxANY_VALUE_TYPE_CHECK_TYPE(valueTypePtr, T)
diff --git a/setup.h.in b/setup.h.in
index 117d7b5542..2ec082aec9 100644
--- a/setup.h.in
+++ b/setup.h.in
@@ -294,6 +294,8 @@
#define wxUSE_VARIANT 0
+#define wxUSE_ANY 0
+
#define wxUSE_REGEX 0
#define wxUSE_SYSTEM_OPTIONS 0
diff --git a/setup.h_vms b/setup.h_vms
index 08f7070753..670bef3763 100644
--- a/setup.h_vms
+++ b/setup.h_vms
@@ -315,6 +315,8 @@ typedef pid_t GPid;
#define wxUSE_VARIANT 1
+#define wxUSE_ANY 1
+
#define wxUSE_REGEX 0
#define wxUSE_SYSTEM_OPTIONS 1
diff --git a/src/common/any.cpp b/src/common/any.cpp
new file mode 100644
index 0000000000..62f6b45d08
--- /dev/null
+++ b/src/common/any.cpp
@@ -0,0 +1,402 @@
+/////////////////////////////////////////////////////////////////////////////
+// Name: src/common/any.cpp
+// Purpose: wxAny class, container for any type
+// Author: Jaakko Salli
+// Modified by:
+// Created: 07/05/2009
+// RCS-ID: $Id$
+// Copyright: (c) wxWidgets team
+// Licence: wxWindows licence
+/////////////////////////////////////////////////////////////////////////////
+
+// For compilers that support precompilation, includes "wx/wx.h".
+#include "wx/wxprec.h"
+
+#ifdef __BORLANDC__
+ #pragma hdrstop
+#endif
+
+#include "wx/any.h"
+
+#if wxUSE_ANY
+
+#ifndef WX_PRECOMP
+ #include "wx/math.h"
+ #include "wx/crt.h"
+#endif
+
+#include "wx/vector.h"
+#include "wx/module.h"
+
+using namespace wxPrivate;
+
+//-------------------------------------------------------------------------
+// wxAnyValueTypeGlobals
+//-------------------------------------------------------------------------
+
+//
+// Helper class to manage wxAnyValueType instances and other
+// related global variables.
+//
+// NB: We really need to have wxAnyValueType instances allocated
+// in heap. They are stored as static template member variables,
+// and with them we just can't be too careful (eg. not allocating
+// them in heap broke the type identification in GCC).
+//
+class wxAnyValueTypeGlobals
+{
+public:
+ wxAnyValueTypeGlobals()
+ {
+ }
+ ~wxAnyValueTypeGlobals()
+ {
+ for ( size_t i=0; i m_valueTypes;
+};
+
+static wxAnyValueTypeGlobals* g_wxAnyValueTypeGlobals = NULL;
+
+//
+// This class is to make sure that wxAnyValueType instances
+// etc. get freed correctly. We must use a separate wxAnyValueTypeGlobals
+// because wxModule itself is instantiated too late.
+//
+class wxAnyValueTypeGlobalsManager : public wxModule
+{
+ DECLARE_DYNAMIC_CLASS(wxAnyValueTypeGlobalsManager)
+public:
+ wxAnyValueTypeGlobalsManager() : wxModule() { }
+ virtual ~wxAnyValueTypeGlobalsManager() { }
+
+ virtual bool OnInit()
+ {
+ return true;
+ }
+ virtual void OnExit()
+ {
+ delete g_wxAnyValueTypeGlobals;
+ g_wxAnyValueTypeGlobals = NULL;
+ }
+private:
+};
+
+IMPLEMENT_DYNAMIC_CLASS(wxAnyValueTypeGlobalsManager, wxModule)
+
+
+//-------------------------------------------------------------------------
+// wxAnyValueType
+//-------------------------------------------------------------------------
+
+wxAnyValueType::wxAnyValueType()
+{
+ if ( !g_wxAnyValueTypeGlobals )
+ g_wxAnyValueTypeGlobals = new wxAnyValueTypeGlobals();
+
+ g_wxAnyValueTypeGlobals->RegisterValueType(this);
+}
+
+//-------------------------------------------------------------------------
+// wxAny
+//-------------------------------------------------------------------------
+
+void wxAny::AssignAny(const wxAny &any)
+{
+ if ( !any.m_type->IsSameType(m_type) )
+ {
+ m_type->DeleteValue(m_buffer);
+ m_type = any.m_type;
+ }
+ m_type->CopyBuffer(any.m_buffer, m_buffer);
+}
+
+//-------------------------------------------------------------------------
+// Dynamic conversion member functions
+//-------------------------------------------------------------------------
+
+//
+// Define integer minimum and maximum as helpers
+#ifdef wxLongLong_t
+const wxAnyBaseIntType UseIntMin = wxINT64_MIN;
+const wxAnyBaseUintType UseIntMax = wxINT64_MAX;
+const wxAnyBaseUintType UseUintMax = wxUINT64_MAX;
+#else
+const wxAnyBaseIntType UseIntMin = LONG_MIN;
+const wxAnyBaseUintType UseUintMax = ULONG_MAX;
+const wxAnyBaseUintType UseIntMax = LONG_MAX;
+#endif
+
+const double UseIntMinF = static_cast(UseIntMin);
+#ifndef __VISUALC6__
+const double UseIntMaxF = static_cast(UseIntMax);
+const double UseUintMaxF = static_cast(UseUintMax);
+#else
+// VC6 doesn't implement conversion from unsigned __int64 to double
+const wxAnyBaseIntType UseIntMax0 = static_cast(UseIntMax);
+const wxAnyBaseIntType UseUintMax0 = static_cast(UseUintMax);
+const double UseIntMaxF = static_cast(UseIntMax0);
+const double UseUintMaxF = static_cast(UseUintMax0);
+#endif
+
+
+bool wxAnyValueTypeImplInt::ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+{
+ wxAnyBaseIntType value = GetValue(src);
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxString) )
+ {
+#ifdef wxLongLong_t
+ wxLongLong ll(value);
+ wxString s = ll.ToString();
+#else
+ wxString s = wxString::Format(wxS("%ld"), (long)value);
+#endif
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseUintType) )
+ {
+ if ( value < 0 )
+ return false;
+ wxAnyBaseUintType ul = (wxAnyBaseUintType) value;
+ wxAnyValueTypeImplUint::SetValue(ul, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, double) )
+ {
+ double value2 = static_cast(value);
+ wxAnyValueTypeImplDouble::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, bool) )
+ {
+ bool value2 = value ? true : false;
+ wxAnyValueTypeImpl::SetValue(value2, dst);
+ }
+ else
+ return false;
+
+ return true;
+}
+
+bool wxAnyValueTypeImplUint::ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+{
+ wxAnyBaseUintType value = GetValue(src);
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxString) )
+ {
+#ifdef wxLongLong_t
+ wxULongLong ull(value);
+ wxString s = ull.ToString();
+#else
+ wxString s = wxString::Format(wxS("%lu"), (long)value);
+#endif
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseIntType) )
+ {
+ if ( value > UseIntMax )
+ return false;
+ wxAnyBaseIntType l = (wxAnyBaseIntType) value;
+ wxAnyValueTypeImplInt::SetValue(l, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, double) )
+ {
+#ifndef __VISUALC6__
+ double value2 = static_cast(value);
+#else
+ // VC6 doesn't implement conversion from unsigned __int64 to double
+ wxAnyBaseIntType value0 = static_cast(value);
+ double value2 = static_cast(value0);
+#endif
+ wxAnyValueTypeImplDouble::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, bool) )
+ {
+ bool value2 = value ? true : false;
+ wxAnyValueTypeImpl::SetValue(value2, dst);
+ }
+ else
+ return false;
+
+ return true;
+}
+
+bool wxAnyValueTypeImplString::ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+{
+ wxString value = GetValue(src);
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseIntType) )
+ {
+ wxAnyBaseIntType value2;
+#ifdef wxLongLong_t
+ if ( !value.ToLongLong(&value2) )
+#else
+ if ( !value.ToLong(&value2) )
+#endif
+ return false;
+ wxAnyValueTypeImplInt::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseUintType) )
+ {
+ wxAnyBaseUintType value2;
+#ifdef wxLongLong_t
+ if ( !value.ToULongLong(&value2) )
+#else
+ if ( !value.ToULong(&value2) )
+#endif
+ return false;
+ wxAnyValueTypeImplUint::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, double) )
+ {
+ double value2;
+ if ( !value.ToDouble(&value2) )
+ return false;
+ wxAnyValueTypeImplDouble::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, bool) )
+ {
+ bool value2;
+ value.MakeLower();
+ if ( value == wxS("true") ||
+ value == wxS("yes") ||
+ value == wxS('1') )
+ value2 = true;
+ else if ( value == wxS("false") ||
+ value == wxS("no") ||
+ value == wxS('0') )
+ value2 = false;
+ else
+ return false;
+
+ wxAnyValueTypeImpl::SetValue(value2, dst);
+ }
+ else
+ return false;
+
+ return true;
+}
+
+bool wxAnyValueTypeImpl::ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+{
+ bool value = GetValue(src);
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseIntType) )
+ {
+ wxAnyBaseIntType value2 = static_cast(value);
+ wxAnyValueTypeImplInt::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseUintType) )
+ {
+ wxAnyBaseIntType value2 = static_cast(value);
+ wxAnyValueTypeImplUint::SetValue(value2, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxString) )
+ {
+ wxString s;
+ if ( value )
+ s = wxS("true");
+ else
+ s = wxS("false");
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else
+ return false;
+
+ return true;
+}
+
+bool wxAnyValueTypeImplDouble::ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+{
+ double value = GetValue(src);
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseIntType) )
+ {
+ if ( value < UseIntMinF || value > UseIntMaxF )
+ return false;
+ wxAnyBaseUintType ul = static_cast(value);
+ wxAnyValueTypeImplUint::SetValue(ul, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxAnyBaseUintType) )
+ {
+ if ( value < 0.0 || value > UseUintMaxF )
+ return false;
+ wxAnyBaseUintType ul = static_cast(value);
+ wxAnyValueTypeImplUint::SetValue(ul, dst);
+ }
+ else if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxString) )
+ {
+ wxString s = wxString::Format(wxS("%.14g"), value);
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else
+ return false;
+
+ return true;
+}
+
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImplInt)
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImplUint)
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImplString)
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImplDouble)
+
+//-------------------------------------------------------------------------
+// wxAnyNullValueType implementation
+//-------------------------------------------------------------------------
+
+class wxAnyNullValue
+{
+private:
+ void* m_dummy;
+};
+
+template <>
+class wxAnyValueTypeImpl : public wxAnyValueType
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+public:
+ virtual void DeleteValue(wxAnyValueBuffer& buf) const
+ {
+ buf.m_ptr = NULL; // This is important
+ }
+
+ // Dummy implementations
+ virtual void CopyBuffer(const wxAnyValueBuffer& src,
+ wxAnyValueBuffer& dst) const
+ {
+ wxUnusedVar(src);
+ wxUnusedVar(dst);
+ }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+ {
+ wxUnusedVar(src);
+ wxUnusedVar(dstType);
+ wxUnusedVar(dst);
+ return false;
+ }
+
+private:
+};
+
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+
+wxAnyValueType* wxAnyNullValueType =
+ wxAnyValueTypeImpl::GetInstance();
+
+#endif // wxUSE_ANY
diff --git a/src/common/descrip.mms b/src/common/descrip.mms
index 6e302a5319..c47371405d 100644
--- a/src/common/descrip.mms
+++ b/src/common/descrip.mms
@@ -212,7 +212,8 @@ OBJECTS2=tbarbase.obj,srchcmn.obj,\
listctrlcmn.obj,socketiohandler.obj,fdiodispatcher.obj,\
selectdispatcher.obj,overlaycmn.obj,windowid.obj,sstream.obj,\
wrapsizer.obj,headerctrlcmn.obj,headercolcmn.obj,\
- rearrangectrl.obj,spinctrlcmn.obj,datetimefmt.obj,xlocale.obj
+ rearrangectrl.obj,spinctrlcmn.obj,datetimefmt.obj,xlocale.obj,\
+ any.obj
OBJECTS_MOTIF=radiocmn.obj,combocmn.obj
@@ -229,6 +230,7 @@ SOURCES = \
accelcmn.cpp,\
anidecod.cpp,\
animatecmn.cpp,\
+ any.cpp,\
appbase.cpp,\
appcmn.cpp,\
arrstr.cpp,\
@@ -459,6 +461,7 @@ $(OBJECTS_MOTIF) : [--.include.wx]setup.h
accelcmn.obj : accelcmn.cpp
anidecod.obj : anidecod.cpp
animatecmn.obj : animatecmn.cpp
+any.obj : any.cpp
appbase.obj : appbase.cpp
appcmn.obj : appcmn.cpp
arrstr.obj : arrstr.cpp
diff --git a/tests/Makefile.in b/tests/Makefile.in
index fcc3680ff7..7291842378 100644
--- a/tests/Makefile.in
+++ b/tests/Makefile.in
@@ -54,6 +54,7 @@ TEST_CXXFLAGS = $(__test_PCH_INC) -D__WX$(TOOLKIT)__ $(__WXUNIV_DEFINE_p) \
$(CPPUNIT_CFLAGS) $(CXXWARNINGS) $(CPPFLAGS) $(CXXFLAGS)
TEST_OBJECTS = \
test_test.o \
+ test_anytest.o \
test_archivetest.o \
test_ziptest.o \
test_tartest.o \
@@ -346,6 +347,9 @@ fr:
test_test.o: $(srcdir)/test.cpp $(TEST_ODEP)
$(CXXC) -c -o $@ $(TEST_CXXFLAGS) $(srcdir)/test.cpp
+test_anytest.o: $(srcdir)/any/anytest.cpp $(TEST_ODEP)
+ $(CXXC) -c -o $@ $(TEST_CXXFLAGS) $(srcdir)/any/anytest.cpp
+
test_archivetest.o: $(srcdir)/archive/archivetest.cpp $(TEST_ODEP)
$(CXXC) -c -o $@ $(TEST_CXXFLAGS) $(srcdir)/archive/archivetest.cpp
diff --git a/tests/any/anytest.cpp b/tests/any/anytest.cpp
new file mode 100644
index 0000000000..4b05691644
--- /dev/null
+++ b/tests/any/anytest.cpp
@@ -0,0 +1,431 @@
+///////////////////////////////////////////////////////////////////////////////
+// Name: tests/any/anytest.cpp
+// Purpose: Test the wxAny classes
+// Author: Jaakko Salli
+// RCS-ID: $Id$
+// Copyright: (c) the wxWidgets team
+// Licence: wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+#include "testprec.h"
+
+#ifdef __BORLANDC__
+# pragma hdrstop
+#endif
+
+#if wxUSE_ANY
+
+#include "wx/any.h"
+#include "wx/datetime.h"
+
+#include
+
+// ----------------------------------------------------------------------------
+// test class
+// ----------------------------------------------------------------------------
+
+class wxAnyTestCase : public CppUnit::TestCase
+{
+public:
+ wxAnyTestCase();
+
+private:
+ CPPUNIT_TEST_SUITE( wxAnyTestCase );
+ CPPUNIT_TEST( Equality );
+ CPPUNIT_TEST( As );
+ CPPUNIT_TEST( GetAs );
+ CPPUNIT_TEST( Null );
+ CPPUNIT_TEST( CustomTemplateSpecialization );
+ CPPUNIT_TEST_SUITE_END();
+
+ void Equality();
+ void As();
+ void GetAs();
+ void Null();
+ void CustomTemplateSpecialization();
+
+ wxDateTime m_testDateTime;
+
+ wxAny m_anySignedChar1;
+ wxAny m_anySignedShort1;
+ wxAny m_anySignedInt1;
+ wxAny m_anySignedLong1;
+ wxAny m_anySignedLongLong1;
+ wxAny m_anyUnsignedChar1;
+ wxAny m_anyUnsignedShort1;
+ wxAny m_anyUnsignedInt1;
+ wxAny m_anyUnsignedLong1;
+ wxAny m_anyUnsignedLongLong1;
+ wxAny m_anyStringString1;
+ wxAny m_anyCharString1;
+ wxAny m_anyWcharString1;
+ wxAny m_anyBool1;
+ wxAny m_anyFloatDouble1;
+ wxAny m_anyDoubleDouble1;
+ wxAny m_anyWxObjectPtr1;
+ wxAny m_anyVoidPtr1;
+ wxAny m_anyDateTime1;
+
+ wxAny m_anySignedChar2;
+ wxAny m_anySignedShort2;
+ wxAny m_anySignedInt2;
+ wxAny m_anySignedLong2;
+ wxAny m_anySignedLongLong2;
+ wxAny m_anyUnsignedChar2;
+ wxAny m_anyUnsignedShort2;
+ wxAny m_anyUnsignedInt2;
+ wxAny m_anyUnsignedLong2;
+ wxAny m_anyUnsignedLongLong2;
+ wxAny m_anyStringString2;
+ wxAny m_anyCharString2;
+ wxAny m_anyWcharString2;
+ wxAny m_anyBool2;
+ wxAny m_anyFloatDouble2;
+ wxAny m_anyDoubleDouble2;
+ wxAny m_anyWxObjectPtr2;
+ wxAny m_anyVoidPtr2;
+ wxAny m_anyDateTime2;
+
+ DECLARE_NO_COPY_CLASS(wxAnyTestCase)
+};
+
+// register in the unnamed registry so that these tests are run by default
+CPPUNIT_TEST_SUITE_REGISTRATION( wxAnyTestCase );
+
+// also include in it's own registry so that these tests can be run alone
+CPPUNIT_TEST_SUITE_NAMED_REGISTRATION( wxAnyTestCase, "wxAnyTestCase" );
+
+// Let's use a number with first digit after decimal dot less than 5,
+// so that we don't have to worry about whether conversion from float
+// to int truncates or rounds.
+const double TEST_FLOAT_CONST = 123.456;
+
+const double FEQ_DELTA = 0.001;
+
+wxObject* dummyWxObjectPointer = reinterpret_cast(1234);
+void* dummyVoidPointer = reinterpret_cast(1234);
+
+
+//
+// Test both 'creation' methods
+wxAnyTestCase::wxAnyTestCase()
+ : m_anySignedChar1((signed char)15),
+ m_anySignedShort1((signed short)15),
+ m_anySignedInt1((signed int)15),
+ m_anySignedLong1((signed long)15),
+#ifdef wxLongLong_t
+ m_anySignedLongLong1((wxLongLong_t)15),
+#endif
+ m_anyUnsignedChar1((unsigned char)15),
+ m_anyUnsignedShort1((unsigned short)15),
+ m_anyUnsignedInt1((unsigned int)15),
+ m_anyUnsignedLong1((unsigned long)15),
+#ifdef wxLongLong_t
+ m_anyUnsignedLongLong1((wxULongLong_t)15),
+#endif
+ m_anyStringString1(wxString("abc")),
+ m_anyCharString1("abc"),
+ m_anyWcharString1(L"abc"),
+ m_anyBool1(true),
+ m_anyFloatDouble1((float)TEST_FLOAT_CONST),
+ m_anyDoubleDouble1((double)TEST_FLOAT_CONST),
+ m_anyWxObjectPtr1(dummyWxObjectPointer),
+ m_anyVoidPtr1(dummyVoidPointer),
+ m_anyDateTime1(wxDateTime::Now())
+{
+ m_testDateTime = wxDateTime::Now();
+ m_anySignedChar2 = (signed char)15;
+ m_anySignedShort2 = (signed short)15;
+ m_anySignedInt2 = (signed int)15;
+ m_anySignedLong2 = (signed long)15;
+#ifdef wxLongLong_t
+ m_anySignedLongLong2 = (wxLongLong_t)15;
+#endif
+ m_anyUnsignedChar2 = (unsigned char)15;
+ m_anyUnsignedShort2 = (unsigned short)15;
+ m_anyUnsignedInt2 = (unsigned int)15;
+ m_anyUnsignedLong2 = (unsigned long)15;
+#ifdef wxLongLong_t
+ m_anyUnsignedLongLong2 = (wxULongLong_t)15;
+#endif
+ m_anyStringString2 = wxString("abc");
+ m_anyCharString2 = "abc";
+ m_anyWcharString2 = L"abc";
+ m_anyBool2 = true;
+ m_anyFloatDouble2 = (float)TEST_FLOAT_CONST;
+ m_anyDoubleDouble2 = (double)TEST_FLOAT_CONST;
+ m_anyDateTime2 = m_testDateTime;
+ m_anyWxObjectPtr2 = dummyWxObjectPointer;
+ m_anyVoidPtr2 = dummyVoidPointer;
+}
+
+void wxAnyTestCase::Equality()
+{
+ //
+ // Currently this should work
+ CPPUNIT_ASSERT(m_anyUnsignedLong1 == 15L);
+ CPPUNIT_ASSERT(m_anyUnsignedLong1 != 30L);
+ CPPUNIT_ASSERT(m_anyUnsignedLong1 == 15UL);
+ CPPUNIT_ASSERT(m_anyUnsignedLong1 != 30UL);
+ CPPUNIT_ASSERT(m_anyStringString1 == wxString("abc"));
+ CPPUNIT_ASSERT(m_anyStringString1 != wxString("ABC"));
+ CPPUNIT_ASSERT(m_anyStringString1 == "abc");
+ CPPUNIT_ASSERT(m_anyStringString1 != "ABC");
+ CPPUNIT_ASSERT(m_anyStringString1 == L"abc");
+ CPPUNIT_ASSERT(m_anyStringString1 != L"ABC");
+ CPPUNIT_ASSERT(m_anyBool1 == true);
+ CPPUNIT_ASSERT(m_anyBool1 != false);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(wxANY_AS(m_anyFloatDouble1, double),
+ wxANY_AS(m_anyDoubleDouble1, double),
+ FEQ_DELTA);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(wxANY_AS(m_anyFloatDouble1, double),
+ TEST_FLOAT_CONST,
+ FEQ_DELTA);
+ CPPUNIT_ASSERT(m_anyWxObjectPtr1.As() == dummyWxObjectPointer);
+ CPPUNIT_ASSERT(m_anyVoidPtr1.As() == dummyVoidPointer);
+
+ CPPUNIT_ASSERT(m_anySignedLong2 == 15);
+ CPPUNIT_ASSERT(m_anyStringString2 == wxString("abc"));
+ CPPUNIT_ASSERT(m_anyStringString2 == "abc");
+ CPPUNIT_ASSERT(m_anyStringString2 == L"abc");
+ CPPUNIT_ASSERT(m_anyBool2 == true);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(wxANY_AS(m_anyFloatDouble2, double),
+ wxANY_AS(m_anyDoubleDouble2, double),
+ FEQ_DELTA);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(wxANY_AS(m_anyFloatDouble2, double),
+ TEST_FLOAT_CONST,
+ FEQ_DELTA);
+ CPPUNIT_ASSERT(m_anyWxObjectPtr2.As() == dummyWxObjectPointer);
+ CPPUNIT_ASSERT(m_anyVoidPtr2.As() == dummyVoidPointer);
+}
+
+void wxAnyTestCase::As()
+{
+ //
+ // Test getting C++ data from wxAny without dynamic conversion
+ signed char a = wxANY_AS(m_anySignedChar1, signed char);
+ CPPUNIT_ASSERT(a == (signed int)15);
+ signed short b = wxANY_AS(m_anySignedShort1, signed short);
+ CPPUNIT_ASSERT(b == (signed int)15);
+ signed int c = wxANY_AS(m_anySignedInt1, signed int);
+ CPPUNIT_ASSERT(c == (signed int)15);
+ signed long d = wxANY_AS(m_anySignedLong1, signed long);
+ CPPUNIT_ASSERT(d == (signed int)15);
+#ifdef wxLongLong_t
+ wxLongLong_t e = wxANY_AS(m_anySignedLongLong1, wxLongLong_t);
+ CPPUNIT_ASSERT(e == (signed int)15);
+#endif
+ unsigned char f = wxANY_AS(m_anyUnsignedChar1, unsigned char);
+ CPPUNIT_ASSERT(f == (unsigned int)15);
+ unsigned short g = wxANY_AS(m_anyUnsignedShort1, unsigned short);
+ CPPUNIT_ASSERT(g == (unsigned int)15);
+ unsigned int h = wxANY_AS(m_anyUnsignedInt1, unsigned int);
+ CPPUNIT_ASSERT(h == (unsigned int)15);
+ unsigned long i = wxANY_AS(m_anyUnsignedLong1, unsigned long);
+ CPPUNIT_ASSERT(i == (unsigned int)15);
+#ifdef wxLongLong_t
+ wxULongLong_t j = wxANY_AS(m_anyUnsignedLongLong1, wxULongLong_t);
+ CPPUNIT_ASSERT(j == (unsigned int)15);
+#endif
+ wxString k = wxANY_AS(m_anyStringString1, wxString);
+ CPPUNIT_ASSERT(k == "abc");
+ wxString l = wxANY_AS(m_anyCharString1, wxString);
+ CPPUNIT_ASSERT(l == "abc");
+ wxString m = wxANY_AS(m_anyWcharString1, wxString);
+ CPPUNIT_ASSERT(m == "abc");
+ bool n = wxANY_AS(m_anyBool1, bool);
+ CPPUNIT_ASSERT(n);
+ float o = wxANY_AS(m_anyFloatDouble1, float);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(o, TEST_FLOAT_CONST, FEQ_DELTA);
+ double p = wxANY_AS(m_anyDoubleDouble1, double);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(p, TEST_FLOAT_CONST, FEQ_DELTA);
+ wxDateTime q = wxANY_AS(m_anyDateTime1, wxDateTime);
+ CPPUNIT_ASSERT(q == m_testDateTime);
+ wxObject* r = wxANY_AS(m_anyWxObjectPtr1, wxObject*);
+ CPPUNIT_ASSERT(r == dummyWxObjectPointer);
+ void* s = wxANY_AS(m_anyVoidPtr1, void*);
+ CPPUNIT_ASSERT(s == dummyVoidPointer);
+}
+
+void wxAnyTestCase::Null()
+{
+ wxAny a;
+ CPPUNIT_ASSERT(a.IsNull());
+ a = -127;
+ CPPUNIT_ASSERT(a == -127);
+ a.MakeNull();
+ CPPUNIT_ASSERT(a.IsNull());
+}
+
+void wxAnyTestCase::GetAs()
+{
+ //
+ // Test dynamic conversion
+ bool res;
+ long l = 0;
+ unsigned long ul = 0;
+ wxString s;
+ // Let's test against float instead of double, since the former
+ // is not the native underlying type the code converts to, but
+ // should still work, all the same.
+ float f = 0.0;
+ bool b = false;
+
+ // Conversions from signed long type
+ res = m_anySignedLong1.GetAs(&ul);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_EQUAL(ul, static_cast(15));
+ res = m_anySignedLong1.GetAs(&s);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(s == "15");
+ res = m_anySignedLong1.GetAs(&f);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(f, 15.0, FEQ_DELTA);
+ res = m_anySignedLong1.GetAs(&b);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(b == true);
+
+ // Conversions from unsigned long type
+ res = m_anyUnsignedLong1.GetAs(&l);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(l == static_cast(15));
+ res = m_anyUnsignedLong1.GetAs(&s);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(s == "15");
+ res = m_anyUnsignedLong1.GetAs(&f);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(f, 15.0, FEQ_DELTA);
+ res = m_anyUnsignedLong1.GetAs(&b);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(b == true);
+
+ // Conversions from default "abc" string to other types
+ // should not work.
+ CPPUNIT_ASSERT(!m_anyStringString1.GetAs(&l));
+ CPPUNIT_ASSERT(!m_anyStringString1.GetAs(&ul));
+ CPPUNIT_ASSERT(!m_anyStringString1.GetAs(&f));
+ CPPUNIT_ASSERT(!m_anyStringString1.GetAs(&b));
+
+ // Let's test some other conversions from string that should work.
+ wxAny anyString;
+
+ anyString = "15";
+ res = anyString.GetAs(&l);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(l == static_cast(15));
+ res = anyString.GetAs(&ul);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_EQUAL(ul, static_cast(15));
+ res = anyString.GetAs(&f);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(f, 15.0, FEQ_DELTA);
+ anyString = "TRUE";
+ res = anyString.GetAs(&b);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(b == true);
+ anyString = "0";
+ res = anyString.GetAs(&b);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(b == false);
+
+ // Conversions from bool type
+ res = m_anyBool1.GetAs(&l);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(l == static_cast(1));
+ res = m_anyBool1.GetAs(&ul);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_EQUAL(ul, static_cast(1));
+ res = m_anyBool1.GetAs(&s);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(s == "true");
+ CPPUNIT_ASSERT(!m_anyBool1.GetAs(&f));
+
+ // Conversions from floating point type
+ res = m_anyDoubleDouble1.GetAs(&l);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT(l == static_cast(123));
+ res = m_anyDoubleDouble1.GetAs(&ul);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_EQUAL(ul, static_cast(123));
+ res = m_anyDoubleDouble1.GetAs(&s);
+ CPPUNIT_ASSERT(res);
+ double d2;
+ res = s.ToDouble(&d2);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_DOUBLES_EQUAL(d2, TEST_FLOAT_CONST, FEQ_DELTA);
+}
+
+//
+// Test user data type specialization of wxAnyValueTypeImpl
+//
+
+class MyClass
+{
+public:
+ MyClass( int someValue = 32768 )
+ {
+ m_someValue = someValue;
+ }
+
+ wxString ToString()
+ {
+ return wxString::Format("%i", m_someValue);
+ }
+
+private:
+ int m_someValue;
+};
+
+
+template<>
+class wxAnyValueTypeImpl :
+ public wxAnyValueTypeImplBase
+{
+ WX_DECLARE_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+public:
+ wxAnyValueTypeImpl() :
+ wxAnyValueTypeImplBase() { }
+ virtual ~wxAnyValueTypeImpl() { }
+
+ virtual bool ConvertValue(const wxAnyValueBuffer& src,
+ wxAnyValueType* dstType,
+ wxAnyValueBuffer& dst) const
+ {
+ MyClass value = GetValue(src);
+
+ if ( wxANY_VALUE_TYPE_CHECK_TYPE(dstType, wxString) )
+ {
+ wxString s = value.ToString();
+ wxAnyValueTypeImpl::SetValue(s, dst);
+ }
+ else
+ return false;
+
+ return true;
+ }
+};
+
+//
+// Following must be placed somewhere in your source code
+WX_IMPLEMENT_ANY_VALUE_TYPE(wxAnyValueTypeImpl)
+
+void wxAnyTestCase::CustomTemplateSpecialization()
+{
+ // Do only a minimal CheckType() test, as dynamic type conversion already
+ // uses it a lot.
+ bool res;
+ MyClass myObject;
+ wxAny any = myObject;
+
+ CPPUNIT_ASSERT( wxANY_CHECK_TYPE(any, MyClass) );
+ MyClass myObject2 = wxANY_AS(any, MyClass);
+ wxUnusedVar(myObject2);
+
+ wxString str;
+ res = any.GetAs(&str);
+ CPPUNIT_ASSERT(res);
+ CPPUNIT_ASSERT_EQUAL(str, myObject.ToString());
+}
+
+#endif // wxUSE_ANY
+
diff --git a/tests/makefile.bcc b/tests/makefile.bcc
index 77e128c2ba..eb3cc79ecd 100644
--- a/tests/makefile.bcc
+++ b/tests/makefile.bcc
@@ -38,6 +38,7 @@ TEST_CXXFLAGS = $(__RUNTIME_LIBS) -I$(BCCDIR)\include $(__DEBUGINFO) \
TEST_OBJECTS = \
$(OBJS)\test_dummy.obj \
$(OBJS)\test_test.obj \
+ $(OBJS)\test_anytest.obj \
$(OBJS)\test_archivetest.obj \
$(OBJS)\test_ziptest.obj \
$(OBJS)\test_tartest.obj \
@@ -378,6 +379,9 @@ $(OBJS)\test_dummy.obj: .\dummy.cpp
$(OBJS)\test_test.obj: .\test.cpp
$(CXX) -q -c -P -o$@ $(TEST_CXXFLAGS) .\test.cpp
+$(OBJS)\test_anytest.obj: .\any\anytest.cpp
+ $(CXX) -q -c -P -o$@ $(TEST_CXXFLAGS) .\any\anytest.cpp
+
$(OBJS)\test_archivetest.obj: .\archive\archivetest.cpp
$(CXX) -q -c -P -o$@ $(TEST_CXXFLAGS) .\archive\archivetest.cpp
diff --git a/tests/makefile.gcc b/tests/makefile.gcc
index 08f2802a74..bdfd9ecd1f 100644
--- a/tests/makefile.gcc
+++ b/tests/makefile.gcc
@@ -30,6 +30,7 @@ TEST_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) $(GCCFLAGS) \
TEST_OBJECTS = \
$(OBJS)\test_dummy.o \
$(OBJS)\test_test.o \
+ $(OBJS)\test_anytest.o \
$(OBJS)\test_archivetest.o \
$(OBJS)\test_ziptest.o \
$(OBJS)\test_tartest.o \
@@ -359,6 +360,9 @@ $(OBJS)\test_dummy.o: ./dummy.cpp
$(OBJS)\test_test.o: ./test.cpp
$(CXX) -c -o $@ $(TEST_CXXFLAGS) $(CPPDEPS) $<
+$(OBJS)\test_anytest.o: ./any/anytest.cpp
+ $(CXX) -c -o $@ $(TEST_CXXFLAGS) $(CPPDEPS) $<
+
$(OBJS)\test_archivetest.o: ./archive/archivetest.cpp
$(CXX) -c -o $@ $(TEST_CXXFLAGS) $(CPPDEPS) $<
diff --git a/tests/makefile.vc b/tests/makefile.vc
index 92c2b269a2..6dc5ddc78c 100644
--- a/tests/makefile.vc
+++ b/tests/makefile.vc
@@ -31,6 +31,7 @@ TEST_CXXFLAGS = /M$(__RUNTIME_LIBS_8)$(__DEBUGRUNTIME) /DWIN32 $(__DEBUGINFO) \
TEST_OBJECTS = \
$(OBJS)\test_dummy.obj \
$(OBJS)\test_test.obj \
+ $(OBJS)\test_anytest.obj \
$(OBJS)\test_archivetest.obj \
$(OBJS)\test_ziptest.obj \
$(OBJS)\test_tartest.obj \
@@ -461,6 +462,9 @@ $(OBJS)\test_dummy.obj: .\dummy.cpp
$(OBJS)\test_test.obj: .\test.cpp
$(CXX) /c /nologo /TP /Fo$@ $(TEST_CXXFLAGS) .\test.cpp
+$(OBJS)\test_anytest.obj: .\any\anytest.cpp
+ $(CXX) /c /nologo /TP /Fo$@ $(TEST_CXXFLAGS) .\any\anytest.cpp
+
$(OBJS)\test_archivetest.obj: .\archive\archivetest.cpp
$(CXX) /c /nologo /TP /Fo$@ $(TEST_CXXFLAGS) .\archive\archivetest.cpp
diff --git a/tests/makefile.wat b/tests/makefile.wat
index bdaba4b6d0..b5164a0f18 100644
--- a/tests/makefile.wat
+++ b/tests/makefile.wat
@@ -259,6 +259,7 @@ TEST_CXXFLAGS = $(__DEBUGINFO) $(__OPTIMIZEFLAG) $(__THREADSFLAG) &
TEST_OBJECTS = &
$(OBJS)\test_dummy.obj &
$(OBJS)\test_test.obj &
+ $(OBJS)\test_anytest.obj &
$(OBJS)\test_archivetest.obj &
$(OBJS)\test_ziptest.obj &
$(OBJS)\test_tartest.obj &
@@ -416,6 +417,9 @@ $(OBJS)\test_dummy.obj : .AUTODEPEND .\dummy.cpp
$(OBJS)\test_test.obj : .AUTODEPEND .\test.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(TEST_CXXFLAGS) $<
+$(OBJS)\test_anytest.obj : .AUTODEPEND .\any\anytest.cpp
+ $(CXX) -bt=nt -zq -fo=$^@ $(TEST_CXXFLAGS) $<
+
$(OBJS)\test_archivetest.obj : .AUTODEPEND .\archive\archivetest.cpp
$(CXX) -bt=nt -zq -fo=$^@ $(TEST_CXXFLAGS) $<
diff --git a/tests/test.bkl b/tests/test.bkl
index 80c71cce9b..d692755fa3 100644
--- a/tests/test.bkl
+++ b/tests/test.bkl
@@ -29,6 +29,7 @@
template_append="wx_append_base">
test.cpp
+ any/anytest.cpp
archive/archivetest.cpp
archive/ziptest.cpp
archive/tartest.cpp
diff --git a/tests/test_test.dsp b/tests/test_test.dsp
index 031f525889..2ccdd77129 100644
--- a/tests/test_test.dsp
+++ b/tests/test_test.dsp
@@ -235,6 +235,10 @@ LINK32=link.exe
# PROP Default_Filter ""
# Begin Source File
+SOURCE=.\any\anytest.cpp
+# End Source File
+# Begin Source File
+
SOURCE=.\archive\archivetest.cpp
# End Source File
# Begin Source File
diff --git a/tests/test_vc7_test.vcproj b/tests/test_vc7_test.vcproj
index cc848ea3bf..75e9df0f90 100644
--- a/tests/test_vc7_test.vcproj
+++ b/tests/test_vc7_test.vcproj
@@ -557,6 +557,9 @@
Name="Source Files"
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}">
+
+
diff --git a/tests/test_vc8_test.vcproj b/tests/test_vc8_test.vcproj
index e8fccf8fbf..8e9f601b2b 100644
--- a/tests/test_vc8_test.vcproj
+++ b/tests/test_vc8_test.vcproj
@@ -819,6 +819,10 @@
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
>
+
+
diff --git a/tests/test_vc9_test.vcproj b/tests/test_vc9_test.vcproj
index 55021dba01..160f9e9f97 100644
--- a/tests/test_vc9_test.vcproj
+++ b/tests/test_vc9_test.vcproj
@@ -791,6 +791,10 @@
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
>
+
+
diff --git a/wxGTK.spec b/wxGTK.spec
index 3201cb8f96..360a94825e 100644
--- a/wxGTK.spec
+++ b/wxGTK.spec
@@ -206,6 +206,7 @@ rm -rf $RPM_BUILD_ROOT
# --- wxBase headers list begins here ---
cat <wxbase-headers.files
wx/afterstd.h
+wx/any.h
wx/anystr.h
wx/app.h
wx/apptrait.h
diff --git a/wxMotif.spec b/wxMotif.spec
index d40578bfdf..dd9c15d14d 100644
--- a/wxMotif.spec
+++ b/wxMotif.spec
@@ -111,6 +111,7 @@ rm -rf $RPM_BUILD_ROOT
# --- wxBase headers list begins here ---
cat <wxbase-headers.files
wx/afterstd.h
+wx/any.h
wx/anystr.h
wx/app.h
wx/apptrait.h
diff --git a/wxX11.spec b/wxX11.spec
index e28c0d4b17..2e604a33a0 100644
--- a/wxX11.spec
+++ b/wxX11.spec
@@ -135,6 +135,7 @@ rm -rf $RPM_BUILD_ROOT
# --- wxBase headers list begins here ---
cat <wxbase-headers.files
wx/afterstd.h
+wx/any.h
wx/anystr.h
wx/app.h
wx/apptrait.h