Index: vcl/source/gdi/outdev2.cxx
===================================================================
RCS file: /cvs/gsl/vcl/source/gdi/outdev2.cxx,v
retrieving revision 1.29
diff -u -p -u -r1.29 outdev2.cxx
--- vcl/source/gdi/outdev2.cxx	9 Sep 2005 12:06:08 -0000	1.29
+++ vcl/source/gdi/outdev2.cxx	20 Jun 2006 14:07:23 -0000
@@ -1183,13 +1183,6 @@ void OutputDevice::DrawImage( const Poin
 		}
 		break;
 
-		case IMAGETYPE_IMAGEREF:
-		{
-			ImplImageRefData* pData = static_cast< ImplImageRefData* >( rImage.mpImplData->mpData );
-			pData->mpImplData->mpImageBitmap->Draw( pData->mnIndex, this, rPos, nStyle );
-		}
-		break;
-
 		default:
 		break;
 	}
@@ -1225,14 +1218,7 @@ void OutputDevice::DrawImage( const Poin
 				pData->mpImageBitmap->Draw( 0, this, rPos, nStyle, &rSize );
 			}
 			break;
-	
-			case IMAGETYPE_IMAGEREF:
-			{
-				ImplImageRefData* pData = static_cast< ImplImageRefData* >( rImage.mpImplData->mpData );
-				pData->mpImplData->mpImageBitmap->Draw( pData->mnIndex, this, rPos, nStyle, &rSize );
-			}
-			break;
-			
+				
 			default:
 			break;
 		}
Index: vcl/source/gdi/bitmapex.cxx
===================================================================
RCS file: /cvs/gsl/vcl/source/gdi/bitmapex.cxx,v
retrieving revision 1.17
diff -u -p -u -r1.17 bitmapex.cxx
--- vcl/source/gdi/bitmapex.cxx	5 Jan 2006 18:07:16 -0000	1.17
+++ vcl/source/gdi/bitmapex.cxx	20 Jun 2006 14:07:23 -0000
@@ -93,6 +93,28 @@ BitmapEx::BitmapEx( const BitmapEx& rBit
 {
 }
 
+BitmapEx::BitmapEx( const BitmapEx& rBitmapEx, Point aSrc, Size aSize ) :
+		eTransparent( TRANSPARENT_NONE ),
+		bAlpha		( FALSE )
+{
+	if( rBitmapEx.IsEmpty() )
+		return;
+
+	aBitmap = Bitmap( aSize, rBitmapEx.aBitmap.GetBitCount() );
+	aBitmapSize = aSize;
+	if( rBitmapEx.IsAlpha() )
+	{
+		bAlpha = TRUE;
+		aMask = AlphaMask( aSize ).ImplGetBitmap();
+	}
+	else if( rBitmapEx.IsTransparent() )
+		aMask = Bitmap( aSize, rBitmapEx.aMask.GetBitCount() );
+				
+	Rectangle aDestRect( Point( 0, 0 ), aSize );
+	Rectangle aSrcRect( aSrc, aSize );
+	CopyPixel( aDestRect, aSrcRect, &rBitmapEx );
+}
+
 // ------------------------------------------------------------------
 
 BitmapEx::BitmapEx( const ResId& rResId ) :
Index: vcl/inc/bitmapex.hxx
===================================================================
RCS file: /cvs/gsl/vcl/inc/bitmapex.hxx,v
retrieving revision 1.11
diff -u -p -u -r1.11 bitmapex.hxx
--- vcl/inc/bitmapex.hxx	9 Sep 2005 10:48:00 -0000	1.11
+++ vcl/inc/bitmapex.hxx	20 Jun 2006 14:07:23 -0000
@@ -94,6 +94,7 @@ public:
 						BitmapEx();
 						BitmapEx( const ResId& rResId );
 						BitmapEx( const BitmapEx& rBitmapEx );
+						BitmapEx( const BitmapEx& rBitmapEx, Point aSrc, Size aSize );
 						BitmapEx( const Bitmap& rBmp );
 						BitmapEx( const Bitmap& rBmp, const Bitmap& rMask );
 						BitmapEx( const Bitmap& rBmp, const AlphaMask& rAlphaMask );
Index: vcl/source/gdi/impimage.cxx
===================================================================
RCS file: /cvs/gsl/vcl/source/gdi/impimage.cxx,v
retrieving revision 1.18
diff -u -p -u -r1.18 impimage.cxx
--- vcl/source/gdi/impimage.cxx	9 Sep 2005 12:01:31 -0000	1.18
+++ vcl/source/gdi/impimage.cxx	21 Jun 2006 14:50:59 -0000
@@ -70,8 +70,9 @@
 // ----------------
 
 ImageAryData::ImageAryData() :
+	maName(),
 	mnId( 0 ),
-	mnRefCount( 0 )
+	maBitmapEx()
 {
 }
 
@@ -80,7 +81,13 @@ ImageAryData::ImageAryData() :
 ImageAryData::ImageAryData( const ImageAryData& rData ) :
 	maName( rData.maName ),
 	mnId( rData.mnId ),
-	mnRefCount( rData.mnRefCount )
+	maBitmapEx( rData.maBitmapEx )
+{
+}
+
+ImageAryData::ImageAryData( const rtl::OUString &aName,
+							USHORT nId, const BitmapEx &aBitmap )
+		: maName( aName ), mnId( nId ), maBitmapEx( aBitmap )
 {
 }
 
@@ -96,7 +103,7 @@ ImageAryData& ImageAryData::operator=( c
 {
 	maName = rData.maName;
 	mnId = rData.mnId;
-	mnRefCount = rData.mnRefCount;
+	maBitmapEx = rData.maBitmapEx;
 
 	return *this;
 }
@@ -109,38 +116,41 @@ ImplImageList::ImplImageList()
 {
 }
 
-// -----------------------------------------------------------------------
+ImplImageList::ImplImageList( const ImplImageList &aSrc )
+{
+	maImageSize = aSrc.maImageSize;
+	maPrefix = aSrc.maPrefix;
+	maImages.reserve( aSrc.maImages.size() );
+	mnRefCount = 1;
+	for (sal_uInt32 i = 0; i < aSrc.maImages.size(); i++)
+	{
+		maImages[ i ] = new ImageAryData( *aSrc.maImages[ i ] );
+		if( maImages[ i ]->maName.getLength() )
+			maNameHash [ maImages[ i ]->maName ] = maImages[ i ];
+	}
+}
 
 ImplImageList::~ImplImageList()
 {
-	delete mpImageBitmap;
-	delete[] mpAry;
+	for (int i = 0; i < maImages.size(); i++)
+		delete maImages[i];
 }
 
-// --------------------
-// - ImplImageRefData -
-// --------------------
-
-ImplImageRefData::~ImplImageRefData()
+void ImplImageList::AddImage( const ::rtl::OUString &aName,
+							  USHORT nId, const BitmapEx &aBitmapEx )
 {
-	--mpImplData->mnIRefCount;
-	
-	if( mpImplData->mnRefCount || mpImplData->mnIRefCount )
-	{
-		--mpImplData->mpAry[mnIndex].mnRefCount;
-		
-		if( !mpImplData->mpAry[mnIndex].mnRefCount )
-			--mpImplData->mnRealCount;
-	}
-	else
-		delete mpImplData;
+	ImageAryData *pImg = new ImageAryData( aName, nId, aBitmapEx );
+	maImages.push_back( pImg );
+	if( aName.getLength() )
+		maNameHash [ aName ] = pImg;
 }
 
-// -----------------------------------------------------------------------
-
-BOOL ImplImageRefData::IsEqual( const ImplImageRefData& rData )
+void ImplImageList::RemoveImage( USHORT nPos )
 {
-	return( ( mpImplData == rData.mpImplData ) && ( mnIndex == rData.mnIndex ) );
+	ImageAryData *pImg = maImages[ nPos ];
+	if( pImg->maName.getLength() )
+		maNameHash.erase( pImg->maName );
+	maImages.erase( maImages.begin() + nPos );
 }
 
 // -----------------
@@ -190,10 +200,6 @@ ImplImage::~ImplImage()
 		case IMAGETYPE_IMAGE:
 			delete static_cast< ImplImageData* >( mpData );
 		break;
-
-		case IMAGETYPE_IMAGEREF:
-			delete static_cast< ImplImageRefData* >( mpData );
-		break;
 	}
 }
 
Index: vcl/inc/image.h
===================================================================
RCS file: /cvs/gsl/vcl/inc/image.h,v
retrieving revision 1.8
diff -u -p -u -r1.8 image.h
--- vcl/inc/image.h	9 Sep 2005 11:01:36 -0000	1.8
+++ vcl/inc/image.h	21 Jun 2006 14:50:59 -0000
@@ -40,6 +40,8 @@
 #include <bitmapex.hxx>
 #endif
 
+#include <hash_map>
+
 // ----------------
 // - ImplImageBmp -
 // ----------------
@@ -85,7 +87,7 @@ private:
 // - ImageTypes -
 // --------------
 
-enum ImageType { IMAGETYPE_BITMAP, IMAGETYPE_IMAGE, IMAGETYPE_IMAGEREF };
+enum ImageType { IMAGETYPE_BITMAP, IMAGETYPE_IMAGE };
 
 // -----------------
 // - ImplImageList -
@@ -94,13 +96,19 @@ enum ImageType { IMAGETYPE_BITMAP, IMAGE
 struct ImageAryData
 {
 	::rtl::OUString	maName;
-	USHORT			mnId;					
-	ULONG			mnRefCount;
+	// Images identified by either name, or by id
+	USHORT			mnId;				
+	BitmapEx        maBitmapEx;
 	
-					ImageAryData();
-					ImageAryData( const ImageAryData& rData );
-					~ImageAryData();
+	ImageAryData();
+	ImageAryData( const rtl::OUString &aName,
+				  USHORT nId, const BitmapEx &aBitmap );
+	ImageAryData( const ImageAryData& rData );
+	~ImageAryData();
 					
+	bool IsLoadable() { return maBitmapEx.IsEmpty() && maName.getLength(); }
+	void Load(const rtl::OUString &rPrefix);
+	
 	ImageAryData&	operator=( const ImageAryData& rData );
 };
 
@@ -108,17 +116,20 @@ struct ImageAryData
 
 struct ImplImageList
 {
-	ULONG			mnRefCount; 			
-	ULONG			mnIRefCount;			
-	USHORT			mnCount;				
-	USHORT			mnRealCount;			
-	USHORT			mnArySize;				
-	ImageAryData*	mpAry;					
-	Size			maImageSize;			
-	ImplImageBmp*	mpImageBitmap;			
-
-					ImplImageList();
-					~ImplImageList();
+	ULONG			            mnRefCount;
+	std::vector<ImageAryData *> maImages;
+	rtl::OUString               maPrefix;
+	Size			            maImageSize;
+	std::hash_map< rtl::OUString, ImageAryData *,
+				   rtl::OUStringHash > maNameHash;
+
+	ImplImageList();
+	ImplImageList( const ImplImageList &aSrc );
+	~ImplImageList();
+
+	void AddImage( const ::rtl::OUString &aName,
+				   USHORT nId, const BitmapEx &aBitmapEx );
+	void RemoveImage( USHORT nPos );
 };
 
 // --------------------
Index: vcl/inc/image.hxx
===================================================================
RCS file: /cvs/gsl/vcl/inc/image.hxx,v
retrieving revision 1.13
diff -u -p -u -r1.13 image.hxx
--- vcl/inc/image.hxx	5 Jan 2006 18:06:22 -0000	1.13
+++ vcl/inc/image.hxx	21 Jun 2006 14:50:59 -0000
@@ -137,39 +137,24 @@ public:
 							   const ::rtl::OUString& rPrefix,
 							   const Color* pMaskColor = NULL );
 					ImageList( const ImageList& rImageList );
-					ImageList( const BitmapEx& rBitmapEx,
-							   USHORT nInitSize, 
-							   USHORT* pIdAry = NULL,
-							   USHORT nGrow = 4 );
-					ImageList( const BitmapEx& rBitmapEx,
-							   const ::std::vector< ::rtl::OUString >& rNameVector,
-							   USHORT nGrow = 4 );
-					
-					ImageList( const Bitmap& rBitmap,
-							   USHORT nInitSize, USHORT* pIdAry = NULL,
-							   USHORT nGrow = 4 );
-					ImageList( const Bitmap& rBitmap, const Bitmap& rMaskBmp,
-							   USHORT nInitSize, USHORT* pIdAry = NULL,
-							   USHORT nGrow = 4 );
-					ImageList( const Bitmap& rBitmap, const Color& rColor,
-							   USHORT nInitSize, USHORT* pIdAry = NULL,
-							   USHORT nGrow = 4 );
 					~ImageList();
 
 	void			Clear();
-
+	void            InsertFromHorizontalStrip( const BitmapEx &rBitmapEx,
+											   const std::vector< rtl::OUString > &rNameVector );
+	void            InsertFromHorizontalBitmap( const ResId& rResId,
+												USHORT       nCount,
+												const Color *pNonAlphaMaskColor,
+												const Color *pSearchColors = NULL,
+												const Color *pReplaceColors = NULL,
+												ULONG        nColorCount = 0);
+	BitmapEx		GetAsHorizontalStrip() const;
 	USHORT			GetImageCount() const;
 	Size			GetImageSize() const;
-	BitmapEx		GetBitmapEx() const;
-    ImageList       GetColorTransformedImageList( ImageColorTransform eColorTransform ) const;
-   	void            Invert();
 					
 	void			AddImage( USHORT nNewId, const Image& rImage );
 	void			AddImage( const ::rtl::OUString& rImageName, const Image& rImage );
-	
-	void			CopyImage( USHORT nNewId, USHORT nCopyId );
-	void			CopyImage( const ::rtl::OUString& rImageName, const ::rtl::OUString& rCopyName );
-	
+		
 	void			ReplaceImage( USHORT nId, const Image& rImage );
 	void			ReplaceImage( const ::rtl::OUString& rImageName, const Image& rImage );
 	
@@ -183,6 +168,7 @@ public:
 	Image			GetImage( const ::rtl::OUString& rImageName ) const;
 	
 	USHORT			GetImagePos( USHORT nId ) const;
+	bool			HasImageAtPos( USHORT nId ) const;
 	USHORT			GetImagePos( const ::rtl::OUString& rImageName ) const;
 	
 	USHORT			GetImageId( USHORT nPos ) const;
@@ -195,9 +181,6 @@ public:
 	BOOL			operator==( const ImageList& rImageList ) const;
 	BOOL			operator!=( const ImageList& rImageList ) const { return !(ImageList::operator==( rImageList )); }
 
-	friend VCL_DLLPUBLIC SvStream& operator>>( SvStream& rIStream, ImageList& rImageList );
-	friend VCL_DLLPUBLIC SvStream& operator<<( SvStream& rOStream, const ImageList& rImageList );
-
 private:
 
 	ImplImageList*	mpImplData;
@@ -209,7 +192,7 @@ private:
                                              const ::rtl::OUString& rSymbolsStyle,
                                              BitmapEx& rBmpEx,
                                              const Color* pMaskColor ) const;
-	SAL_DLLPRIVATE void    ImplInit( const BitmapEx& rBitmapEx, USHORT nInit, const USHORT* pIdAry, const ::std::vector< ::rtl::OUString >* pNames, USHORT nGrow );
+	SAL_DLLPRIVATE void    ImplInit( USHORT nItems, const Size &rSize );
 	SAL_DLLPRIVATE USHORT  ImplGetImageId( const ::rtl::OUString& rImageName ) const;
 	SAL_DLLPRIVATE void    ImplMakeUnique();
 };
Index: vcl/source/gdi/image.cxx
===================================================================
RCS file: /cvs/gsl/vcl/source/gdi/image.cxx,v
retrieving revision 1.22
diff -u -p -u -r1.22 image.cxx
--- vcl/source/gdi/image.cxx	5 Jan 2006 18:07:31 -0000	1.22
+++ vcl/source/gdi/image.cxx	22 Jun 2006 16:47:34 -0000
@@ -1,3 +1,4 @@
+#include <stdio.h>
 /*************************************************************************
  *
  *  OpenOffice.org - a multi-platform office productivity suite
@@ -266,10 +267,6 @@ Size Image::GetSizePixel() const
 			case IMAGETYPE_IMAGE:
 				aRet = static_cast< ImplImageData* >( mpImplData->mpData )->maBmpEx.GetSizePixel();
 			break;
-
-			case IMAGETYPE_IMAGEREF:
-				aRet = static_cast< ImplImageRefData* >( mpImplData->mpData )->mpImplData->maImageSize;
-			break;
 		}
 	}
 
@@ -295,14 +292,6 @@ BitmapEx Image::GetBitmapEx() const
 			case IMAGETYPE_IMAGE:
 				aRet = static_cast< ImplImageData* >( mpImplData->mpData )->maBmpEx;
 			break;
-
-			case IMAGETYPE_IMAGEREF:
-			{
-				ImplImageRefData* pData = static_cast< ImplImageRefData* >( mpImplData->mpData );
-				
-				aRet = pData->mpImplData->mpImageBitmap->GetBitmapEx( 1, &pData->mnIndex );
-			}				
-			break;
 		}
 	}
 
@@ -446,10 +435,6 @@ BOOL Image::operator==( const Image& rIm
 			case IMAGETYPE_IMAGE:
 				bRet = static_cast< ImplImageData* >( rImage.mpImplData->mpData )->IsEqual( *static_cast< ImplImageData* >( mpImplData->mpData ) );
 			break;
-
-			case IMAGETYPE_IMAGEREF:
-				bRet = static_cast< ImplImageRefData* >( rImage.mpImplData->mpData )->IsEqual( *static_cast< ImplImageRefData* >( mpImplData->mpData ) );
-			break;
 			
 			default:
 				bRet = false;
@@ -509,42 +494,19 @@ ImageList::ImageList( const ResId& rResI
 				pResMgr->ReadLong();
 		}
 		
-        BitmapEx                           aBmpEx;
-		sal_Int32		                   nCount = pResMgr->ReadLong();
-        ::boost::scoped_array< USHORT >    aIdArray( new USHORT[ nCount ] ); 
-        ::std::vector< ::rtl::OUString >   aImageNames( nCount );   
-        ::rtl::OUString                    aResMgrName( pResMgr->GetFileName() );
-        ::rtl::OUString                    aUserImageName;
-        sal_Int32                          nPos = aResMgrName.lastIndexOf( '\\' );
-		
-		// load file entry list 
-		for( sal_Int32 i = 0; i < nCount; ++i )
-		{
-			aImageNames[ i ] = pResMgr->ReadString();
-			aIdArray[ i ] = static_cast< USHORT >( pResMgr->ReadLong() );
-		}
-
-		if( -1 == nPos )
-			nPos = aResMgrName.lastIndexOf( '/' );
+		sal_Int32 nCount = pResMgr->ReadLong();
+		ImplInit( nCount, Size() );
 
-		if( -1 != nPos++ )
+		BitmapEx aEmpty;
+		for( USHORT i = 0; i < nCount; ++i )
 		{
-			const sal_Int32	nSecondPos = aResMgrName.lastIndexOf( '.' );
-			aUserImageName = aResMgrName.copy( nPos, ( ( -1 != nSecondPos ) ? nSecondPos : aResMgrName.getLength() ) - nPos );
+			rtl::OUString aName = pResMgr->ReadString();
+			USHORT nId = static_cast< USHORT >( pResMgr->ReadLong() );
+			mpImplData->AddImage( aName, nId, aEmpty );
 		}
 
-        aUserImageName += ::rtl::OUString::valueOf( static_cast< sal_Int32 >( rResId.GetId() ) );
-        aUserImageName += ::rtl::OUString::valueOf( nCount );
-
-        ::rtl::OUString aCurrentSymbolsStyle = Application::GetSettings().GetStyleSettings().GetCurrentSymbolsStyleName();
-        aUserImageName += aCurrentSymbolsStyle;
-        
-        ImplInitBitmapEx( aUserImageName, aImageNames, aCurrentSymbolsStyle, aBmpEx, spMaskColor.get() );
-
 		if( nObjMask & RSC_IMAGELIST_IDCOUNT )
 			pResMgr->ReadShort();
-
-		ImplInit( aBmpEx, sal::static_int_cast<USHORT>(nCount), aIdArray.get(), NULL, 4 );
 	}
 }
 
@@ -561,22 +523,15 @@ ImageList::ImageList( const ::std::vecto
 
 	DBG_CTOR( ImageList, NULL );
 
-    BitmapEx                           aBmpEx;
-	::rtl::OUString		               aUserImageName( rPrefix );
-    ::std::vector< ::rtl::OUString >   aImageNames( rNameVector.size() );
-    const lang::Locale&                rLocale = Application::GetSettings().GetUILocale();
-
-    for( sal_Int32 i = 0, nCount = rNameVector.size(); i < nCount; ++i )
-       ( aImageNames[ i ] = rPrefix ) += rNameVector[ i ];
-        
-    aUserImageName = ( ( aUserImageName += rLocale.Language ) += rLocale.Country ).replace( '/', '_' );
-    aUserImageName += ::rtl::OUString::valueOf( static_cast< sal_Int32 >( rNameVector.size() ) );
-
-    ::rtl::OUString aCurrentSymbolsStyle = Application::GetSettings().GetStyleSettings().GetCurrentSymbolsStyleName();
-    aUserImageName += aCurrentSymbolsStyle;
-    
-    ImplInitBitmapEx( aUserImageName, aImageNames, aCurrentSymbolsStyle, aBmpEx, pMaskColor );
-	ImplInit( aBmpEx, static_cast< USHORT >( rNameVector.size() ), NULL, &rNameVector, 4 );
+	ImplInit( rNameVector.size(), Size() );
+
+	mpImplData->maPrefix = rPrefix;
+	for( USHORT i = 0; i < rNameVector.size(); ++i )
+	{
+//		fprintf (stderr, "List %p [%d]: '%s'\n",
+//				 this, i, rtl::OUStringToOString( rNameVector[i], RTL_TEXTENCODING_UTF8 ).getStr() );
+		mpImplData->AddImage( rNameVector[ i ], i + 1, BitmapEx() );
+	}
 }
 
 // -----------------------------------------------------------------------
@@ -594,250 +549,141 @@ ImageList::ImageList( const ImageList& r
 
 // -----------------------------------------------------------------------
 
-ImageList::ImageList( const BitmapEx& rBitmapEx,
-					  USHORT nInit, USHORT* pIdAry, USHORT nGrow ) :
-	mpImplData( NULL ),
-	mnInitSize( nInit ),
-	mnGrowSize( nGrow )
+ImageList::~ImageList()
 {
-	DBG_CTOR( ImageList, NULL );
+	DBG_DTOR( ImageList, NULL );
 
-	ImplInit( rBitmapEx, nInit, pIdAry, NULL, nGrow );
+	if( mpImplData && ( 0 == --mpImplData->mnRefCount ) )
+		delete mpImplData;
 }
 
-// -----------------------------------------------------------------------
-
-ImageList::ImageList( const BitmapEx& rBitmapEx,
-  				      const ::std::vector< ::rtl::OUString >& rNameVector, 
-					  USHORT nGrow ) :
-	mpImplData( NULL ),
-	mnInitSize( static_cast< USHORT >( rNameVector.size() ) ),
-	mnGrowSize( nGrow )
+void ImageList::ImplInit( USHORT nItems, const Size &rSize )
 {
-    RTL_LOGFILE_CONTEXT( aLog, "vcl: ImageList::ImageList( const BitmapEx& ..." );
-
-	DBG_CTOR( ImageList, NULL );
-
-	ImplInit( rBitmapEx, static_cast< USHORT >( rNameVector.size() ), NULL, &rNameVector, nGrow );
+	mpImplData = new ImplImageList;
+	mpImplData->mnRefCount = 1;
+	mpImplData->maImages.reserve( nItems );
+	mpImplData->maImageSize = rSize;
 }
 
 // -----------------------------------------------------------------------
 
-ImageList::ImageList( const Bitmap& rBitmap,
-					  USHORT nInit, USHORT* pIdAry, USHORT nGrow ) :
-	mpImplData( NULL ),
-	mnInitSize( nInit ),
-	mnGrowSize( nGrow )
+void ImageAryData::Load(const rtl::OUString &rPrefix)
 {
-	DBG_CTOR( ImageList, NULL );
+    static ImplImageTreeSingletonRef aImageTree;
 
-	ImplInit( rBitmap, nInit, pIdAry, NULL, nGrow );
-}
+	::rtl::OUString aSymbolsStyle = Application::GetSettings().GetStyleSettings().GetCurrentSymbolsStyleName();
 
-// -----------------------------------------------------------------------
+	BitmapEx aBmpEx;
 
-ImageList::ImageList( const Bitmap& rBitmap, const Bitmap& rMaskBmp,
-					  USHORT nInit, USHORT* pIdAry, USHORT nGrow ) :
-	mpImplData( NULL ),
-	mnInitSize( nInit ),
-	mnGrowSize( nGrow )
-{
-	DBG_CTOR( ImageList, NULL );
+//	fprintf (stderr, "Attempt load of '%s'\n",
+//			 rtl::OUStringToOString( maName, RTL_TEXTENCODING_UTF8 ).getStr() );
 
-	const BitmapEx aBmpEx( rBitmap, rMaskBmp );
-	
-	ImplInit( aBmpEx, nInit, pIdAry, NULL, nGrow );
+	rtl::OUString aFileName = rPrefix;
+	aFileName += maName;
+	if( !aImageTree->loadImage( aFileName, aSymbolsStyle, maBitmapEx, true ) )
+	    DBG_ASSERT (false, "ImageAryData::Failed to load image");
 }
 
 // -----------------------------------------------------------------------
 
-ImageList::ImageList( const Bitmap& rBitmap, const Color& rColor,
-					  USHORT nInit, USHORT* pIdAry, USHORT nGrow )
+void ImageList::ImplMakeUnique()
 {
-	DBG_CTOR( ImageList, NULL );
-
-	const BitmapEx aBmpEx( rBitmap, rColor );
-	
-	ImplInit( aBmpEx, nInit, pIdAry, NULL, nGrow );
+	if( mpImplData && mpImplData->mnRefCount > 1 )
+	{
+		--mpImplData->mnRefCount;
+		mpImplData = new ImplImageList( *mpImplData ) ;
+	}
 }
 
 // -----------------------------------------------------------------------
-
-ImageList::~ImageList()
+// Rather a performance hazard:
+BitmapEx ImageList::GetAsHorizontalStrip() const
 {
-	DBG_DTOR( ImageList, NULL );
+	Size aSize( mpImplData->maImageSize );
+	ULONG nCount = GetImageCount();
+	if( !nCount )
+		return BitmapEx();
+	aSize.Width() *= nCount;
 
-	if( mpImplData && ( 0 == --mpImplData->mnRefCount ) && ( 0 == mpImplData->mnIRefCount ) )
-		delete mpImplData;
-}
+	// Load any stragglers
+	for (ULONG nIdx = 0; nIdx < nCount; nIdx++)
+	{
+		ImageAryData *pData = mpImplData->maImages[ nIdx ];
+		if( pData->IsLoadable() )
+			pData->Load( mpImplData->maPrefix );
+	}
 
-// -----------------------------------------------------------------------
+	BitmapEx aTempl = mpImplData->maImages[ 0 ]->maBitmapEx;
+	BitmapEx aResult;
+	Bitmap aPixels( aSize, aTempl.GetBitmap().GetBitCount() );
+	if( aTempl.IsAlpha() )
+		aResult = BitmapEx( aPixels, AlphaMask( aSize ) );
+	else if( aTempl.IsTransparent() )
+		aResult = BitmapEx( aPixels, Bitmap( aSize, aTempl.GetMask().GetBitCount() ) );
+	else
+		aResult = BitmapEx( aPixels );
 
-void ImageList::ImplInitBitmapEx( const ::rtl::OUString& rUserImageName,
-                                  const ::std::vector< ::rtl::OUString >& rImageNames,
-                                  const ::rtl::OUString& rSymbolsStyle,
-                                  BitmapEx& rBmpEx, 
-                                  const Color* pMaskColor ) const
-{
-    static ImplImageTreeSingletonRef aImageTree;
-    
-    if( !aImageTree->loadImage( rUserImageName, rSymbolsStyle, rBmpEx ) )
-    {
-        BitmapEx    aCurBmpEx;
-        Size        aItemSizePixel;
-        bool        bInit = false;
-        
-        for( sal_Int32 i = 0, nCount = rImageNames.size(); i < nCount; ++i )
-        {
-            if( aImageTree->loadImage( rImageNames[ i ], rSymbolsStyle, aCurBmpEx, true ) )
-            {
-                const Size aCurSizePixel( aCurBmpEx.GetSizePixel() );
-           
-                if( !bInit )
-                {
-                    const Size      aTotalSize( aCurSizePixel.Width() * nCount, aCurSizePixel.Height() );
-                    BYTE            cTransparent = 255;
-                    const Bitmap    aBmp( aTotalSize, 24 );
-                    const AlphaMask aAlphaMask( aTotalSize, &cTransparent );
-                    
-                    aItemSizePixel = aCurSizePixel;
-                    rBmpEx = BitmapEx( aBmp, aAlphaMask );
-                    
-                    bInit = true;
-                }
-                    
-#ifdef DBG_UTIL
-                if( ( aItemSizePixel.Width() < aCurSizePixel.Width() ) ||
-                    ( aItemSizePixel.Height() < aCurSizePixel.Height() ) )
-                {   
-                    ByteString aStr( "Differerent dimensions in ItemList images: " );
-
-                    aStr += ByteString( String( rImageNames[ i ] ), RTL_TEXTENCODING_ASCII_US );
-                    aStr += " is ";
-                    aStr += ByteString::CreateFromInt32( aCurSizePixel.Width() );
-                    aStr += "x";
-                    aStr += ByteString::CreateFromInt32( aCurSizePixel.Height() );
-                    aStr += " but needs to be ";
-                    aStr += ByteString::CreateFromInt32( aItemSizePixel.Width() );
-                    aStr += "x";
-                    aStr += ByteString::CreateFromInt32( aItemSizePixel.Height() );
+	Rectangle aSrcRect( Point( 0, 0 ), mpImplData->maImageSize );
+	for (ULONG nIdx = 0; nIdx < nCount; nIdx++)
+	{
+		Rectangle aDestRect( Point( nIdx * mpImplData->maImageSize.Width(), 0 ),
+							 mpImplData->maImageSize );
+		ImageAryData *pData = mpImplData->maImages[ nIdx ];
+		aResult.CopyPixel( aDestRect, aSrcRect, &pData->maBitmapEx);
+	}
 
-                    DBG_ERROR( aStr.GetBuffer() );
-                }
-#endif
-                
-                const Rectangle aRectDst( Point( aItemSizePixel.Width() * i, 0 ), aItemSizePixel );
-                const Rectangle aRectSrc( Point( 0, 0 ), aCurSizePixel );
-                
-                rBmpEx.CopyPixel( aRectDst, aRectSrc, &aCurBmpEx );            
-            }
-#ifdef DBG_UTIL     
-            else
-            {
-                ByteString aErrorStr( "ImageList::ImplInitBitmapEx(...): could not load image <" );
-                DBG_ERROR( ( ( aErrorStr += ByteString( String( rImageNames[ i ] ), RTL_TEXTENCODING_ASCII_US ) ) += '>' ).GetBuffer() );
-            }
-#endif
-        }
-            
-        if( !rBmpEx.IsEmpty() )
-        {
-            if( !rBmpEx.IsTransparent() && pMaskColor )
-                rBmpEx = BitmapEx( rBmpEx.GetBitmap(), *pMaskColor );
-            
-            aImageTree->addUserImage( rUserImageName, rBmpEx );
-        }
-    }
+	return aResult;
 }
 
 // -----------------------------------------------------------------------
 
-void ImageList::ImplInit( const BitmapEx& rBitmapEx, 
-						  USHORT nInit, const USHORT* pIdAry, 
-						  const ::std::vector< ::rtl::OUString >* pNames,
-						  USHORT nGrow  )
-{
-    RTL_LOGFILE_CONTEXT( aLog, "vcl: ImageList::ImplInit" );
-
-	if( !nInit )
-	{
-		mpImplData  = NULL;
-		mnInitSize = 1;
-		mnGrowSize = nGrow;
-	}
-	else
-	{
-		DBG_ASSERT( !nInit || rBitmapEx.GetSizePixel().Width(), "ImageList::ImageList(): nInitSize != 0 and BmpSize.Width() == 0" );
-		DBG_ASSERT( (rBitmapEx.GetSizePixel().Width() % nInit) == 0, "ImageList::ImageList(): BmpSize % nInitSize != 0" );
+void ImageList::InsertFromHorizontalStrip( const BitmapEx &rBitmapEx,
+										   const std::vector< rtl::OUString > &rNameVector )
+{
+	sal_uInt32 nItems = rNameVector.size();
 
-		Size aBmpSize( rBitmapEx.GetSizePixel() );
-		
-		mpImplData = new ImplImageList;
-		mnInitSize = nInit;
-		mnGrowSize = nGrow;
+//	fprintf (stderr, "InsertFromHorizontalStrip (1) [%d items]\n", nItems);
 
-		mpImplData->mnRefCount = 1;
-		mpImplData->mnIRefCount = 0;
-		mpImplData->mnCount = nInit;
-		mpImplData->mnRealCount = nInit;
-		mpImplData->mnArySize = nInit;
-		mpImplData->mpAry = new ImageAryData[nInit];
-		mpImplData->maImageSize = Size( aBmpSize.Width() / nInit, aBmpSize.Height() );
-	
-		for( USHORT i = 0; i < nInit; i++ )
-		{
-			mpImplData->mpAry[ i ].mnId = pIdAry ? pIdAry[ i ] : ( i + 1 );
-			mpImplData->mpAry[ i ].mnRefCount = 1;
-		
-			if( pNames && ( i < pNames->size() ) )
-				mpImplData->mpAry[ i ].maName = (*pNames)[ i ];
-		}
-	
-		mpImplData->mpImageBitmap = new ImplImageBmp;
-		mpImplData->mpImageBitmap->Create( rBitmapEx,
-										   mpImplData->maImageSize.Width(),
-										   mpImplData->maImageSize.Height(),
-										   nInit );
+	if (!nItems)
+			return;
+
+	Size aSize( rBitmapEx.GetSizePixel() );
+	DBG_ASSERT (rBitmapEx.GetSizePixel().Width() % nItems != 0,
+				"ImageList::InsertFromHorizontalStrip - very odd size");
+	aSize.Width() /= nItems;
+	ImplInit( nItems, aSize );
+
+	for (ULONG nIdx = 0; nIdx < nItems; nIdx++)
+	{
+		BitmapEx aBitmap( rBitmapEx, Point( nIdx * aSize.Width(), 0 ), aSize );
+		mpImplData->AddImage( rNameVector[ nIdx ], nIdx + 1, aBitmap );
 	}
 }
 
 // -----------------------------------------------------------------------
 
-void ImageList::ImplMakeUnique()
+void ImageList::InsertFromHorizontalBitmap( const ResId& rResId,
+											USHORT       nCount,
+											const Color *pMaskColor,
+											const Color *pSearchColors, 
+											const Color *pReplaceColors,
+											ULONG        nColorCount)
 {
-	if( mpImplData && mpImplData->mnRefCount > 1 )
-	{
-		ImplImageList*	pNewData = new ImplImageList;
-		USHORT 			i = 0, n = 0;
-		
-		--mpImplData->mnRefCount;
-		
-		pNewData->mnRefCount = 1;
-		pNewData->mnIRefCount = 0;
-		pNewData->mnCount = mpImplData->mnCount;
-		pNewData->mnRealCount = mpImplData->mnRealCount;
-		pNewData->mnArySize = mpImplData->mnArySize;
-		pNewData->mpAry = new ImageAryData[ pNewData->mnArySize ];
-		pNewData->maImageSize = mpImplData->maImageSize;
-		pNewData->mpImageBitmap = new ImplImageBmp;
-		pNewData->mpImageBitmap->Create( pNewData->maImageSize.Width(), pNewData->maImageSize.Height(), pNewData->mnArySize );
+//	fprintf (stderr, "InsertFromHorizontalBitmap\n");
 
-		while( i < mpImplData->mnArySize )
-		{
-			if( mpImplData->mpAry[i].mnId )
-			{
-				pNewData->mpAry[n].maName = mpImplData->mpAry[i].maName;
-				pNewData->mpAry[n].mnId	= mpImplData->mpAry[i].mnId;
-				pNewData->mpAry[n].mnRefCount = 1;
-				pNewData->mpImageBitmap->Replace( n, *mpImplData->mpImageBitmap, i );
-				++n;
-			}
-
-			++i;
-		}
-
-		mpImplData = pNewData;
-	}
+	BitmapEx aBmpEx( rResId );
+	if (aBmpEx.IsEmpty())
+	{
+		fprintf (stderr, "InsertFromHorizontalBitmap - empty image!\n");
+		return;
+	}
+	if (!aBmpEx.IsTransparent() && pMaskColor)
+		aBmpEx = BitmapEx( aBmpEx.GetBitmap(), *pMaskColor );
+	if (nColorCount)
+		aBmpEx.Replace( pSearchColors, pReplaceColors, nColorCount );
+	
+	std::vector< rtl::OUString > aNames( nCount );
+	InsertFromHorizontalStrip( aBmpEx, aNames );
 }
 
 // -----------------------------------------------------------------------
@@ -846,23 +687,11 @@ USHORT ImageList::ImplGetImageId( const 
 {
 	DBG_CHKTHIS( ImageList, NULL );
 
-	if( mpImplData && rImageName.getLength() )
-	{
-		USHORT nPos = 0, i = 0;
-		
-		while( i < mpImplData->mnArySize )
-		{
-			if( mpImplData->mpAry[i].maName == rImageName )
-				return mpImplData->mpAry[i].mnId;
-
-			if ( mpImplData->mpAry[i].mnId )
-				++nPos;
-			
-			++i;
-		}
-	}
-
-	return 0;
+	ImageAryData *pImg = mpImplData->maNameHash[ rImageName ];
+	if( pImg )
+		return pImg->mnId;
+	else
+		return 0;
 }
 
 // -----------------------------------------------------------------------
@@ -876,106 +705,10 @@ void ImageList::AddImage( USHORT nId, co
 	DBG_ASSERT( rImage.mpImplData, "ImageList::AddImage(): Wrong Size" );
 	DBG_ASSERT( !mpImplData || (rImage.GetSizePixel() == mpImplData->maImageSize), "ImageList::AddImage(): Wrong Size" );
 
-	bool		bHasImage = ( rImage.mpImplData != 0 );
-	ImageType	eImageType	= IMAGETYPE_BITMAP;
-	Size		aImageSize;
-	USHORT		nIndex;
-
-	if( bHasImage )
-	{
-		eImageType = rImage.mpImplData->meType;
-		aImageSize = rImage.GetSizePixel();
-	}
-	else
-	{
-		if( mpImplData )
-		{
-			eImageType = IMAGETYPE_BITMAP;
-			aImageSize = mpImplData->maImageSize;
-		}
-		else
-			return;
-	}
-
 	if( !mpImplData )
-	{
-		mpImplData = new ImplImageList;
-		mpImplData->mnRefCount = 1;
-		mpImplData->mnIRefCount = 0;
-		mpImplData->mnCount = 0;
-		mpImplData->mnRealCount = 0;
-		mpImplData->mnArySize = mnInitSize;
-		mpImplData->mpAry = new ImageAryData[mnInitSize];
-		mpImplData->maImageSize = aImageSize;
-		mpImplData->mpImageBitmap = new ImplImageBmp;
-		mpImplData->mpImageBitmap->Create( aImageSize.Width(), aImageSize.Height(), mnInitSize );
-	}
-	else
-		ImplMakeUnique();
-
-	if( mpImplData->mnRealCount == mpImplData->mnArySize )
-	{
-		ImageAryData*	pOldAry  = mpImplData->mpAry;
-		USHORT			nOldSize = mpImplData->mnArySize;
-
-		mpImplData->mnArySize = sal::static_int_cast<USHORT>(mpImplData->mnArySize + mnGrowSize);
-		mpImplData->mpAry = new ImageAryData[mpImplData->mnArySize];
-		
-		for( USHORT i = 0; i < nOldSize; ++i )
-			mpImplData->mpAry[ i ] = pOldAry[ i ]; 
-		
-		mpImplData->mpImageBitmap->Expand( mnGrowSize );
-    	delete[] pOldAry;
-		nIndex = mpImplData->mnRealCount;
-	}
-	else
-	{
-		nIndex = 0;
-		
-		while( mpImplData->mpAry[nIndex].mnRefCount )
-			++nIndex;
-	}
+		ImplInit( 0, rImage.GetSizePixel() );
 
-	switch( eImageType )
-	{
-		case IMAGETYPE_BITMAP:
-		{
-			if( !bHasImage )
-			{
-				const Bitmap 	aBmp( aImageSize, 1 );
-				const BitmapEx	aBmpEx( aBmp, Color( COL_BLACK ) );
-				
-				mpImplData->mpImageBitmap->Replace( nIndex, aBmpEx );
-			}
-			else
-				mpImplData->mpImageBitmap->Replace( nIndex, *static_cast< Bitmap* >( rImage.mpImplData->mpData ) );
-		}
-		break;
-
-		case IMAGETYPE_IMAGE:
-		{
-			ImplImageData* pData = static_cast< ImplImageData* >( rImage.mpImplData->mpData );
-			
-			if( pData->mpImageBitmap )
-				mpImplData->mpImageBitmap->Replace( nIndex, *pData->mpImageBitmap, 0 );
-			else
-				mpImplData->mpImageBitmap->Replace( nIndex, pData->maBmpEx );
-		}
-		break;
-
-		case IMAGETYPE_IMAGEREF:
-		{
-			ImplImageRefData* pData = static_cast< ImplImageRefData* >( rImage.mpImplData->mpData );
-			
-			mpImplData->mpImageBitmap->Replace( nIndex, *pData->mpImplData->mpImageBitmap, pData->mnIndex );
-		}
-		break;
-	}
-
-	++mpImplData->mnCount;
-	++mpImplData->mnRealCount;
-	mpImplData->mpAry[nIndex].mnId = nId;
-	mpImplData->mpAry[nIndex].mnRefCount = 1;
+	mpImplData->AddImage( rtl::OUString(), nId, rImage.GetBitmapEx());
 }
 
 // -----------------------------------------------------------------------
@@ -984,101 +717,11 @@ void ImageList::AddImage( const ::rtl::O
 {
 	DBG_ASSERT( GetImagePos( rImageName ) == IMAGELIST_IMAGE_NOTFOUND, "ImageList::AddImage() - ImageName already exists" );
 
-	USHORT i, nMax = 0;
-
-	if( mpImplData )
-	{
-		for( i = 0; i < mpImplData->mnArySize; ++i )
-		{
-			if( mpImplData->mpAry[ i ].mnId > nMax )
-			{
-				nMax = mpImplData->mpAry[ i ].mnId;
-			}
-		}
-    }
-	
-	if( nMax < USHRT_MAX )
-    {
-	    AddImage( ++nMax, rImage );
-		
-		for( i = 0; i < mpImplData->mnArySize; ++i )
-		{
-			if( mpImplData->mpAry[ i ].mnId == nMax )
-			{
-				mpImplData->mpAry[ i ].maName = rImageName;
-				break;
-			}
-		}
-	}
-	else
-	{
-		DBG_ERROR( "No free image id left" );
-	}
-}
-
-// -----------------------------------------------------------------------
-
-void ImageList::CopyImage( USHORT nId, USHORT nCopyId )
-{
-	DBG_CHKTHIS( ImageList, NULL );
-	DBG_ASSERT( nId, "ImageList::CopyImage(): ImageId == 0" );
-	DBG_ASSERT( GetImagePos( nId ) == IMAGELIST_IMAGE_NOTFOUND, "ImageList::CopyImage(): ImageId already exists" );
-	DBG_ASSERT( GetImagePos( nCopyId ) != IMAGELIST_IMAGE_NOTFOUND, "ImageList::CopyImage(): Unknown nCopyId" );
-
-	USHORT nIndex, nCopyIndex = 0;
-
-	while( nCopyIndex < mpImplData->mnArySize )
-	{
-		if ( mpImplData->mpAry[nCopyIndex].mnId == nCopyId )
-			break;
-
-		++nCopyIndex;
-	}
-	
-	if( nCopyIndex < mpImplData->mnArySize )
-	{
-		ImplMakeUnique();
-
-		if( mpImplData->mnRealCount == mpImplData->mnArySize )
-		{
-			ImageAryData*	pOldAry  = mpImplData->mpAry;
-			USHORT			nOldSize = mpImplData->mnArySize;
-	
-			mpImplData->mnArySize = sal::static_int_cast<USHORT>(mpImplData->mnArySize + mnGrowSize);
-			mpImplData->mpAry = new ImageAryData[mpImplData->mnArySize];
-			
-			for( USHORT i = 0; i < nOldSize; ++i )
-				mpImplData->mpAry[ i ] = pOldAry[ i ]; 
-
-			mpImplData->mpImageBitmap->Expand( mnGrowSize );
-			delete[] pOldAry;
-			nIndex = mpImplData->mnRealCount;
-		}
-		else
-		{
-			nIndex = 0;
-			
-			while( mpImplData->mpAry[nIndex].mnRefCount )
-				nIndex++;
-		}
-	
-		mpImplData->mpImageBitmap->Replace( nIndex, *mpImplData->mpImageBitmap, nCopyIndex );
-	
-		++mpImplData->mnCount;
-		++mpImplData->mnRealCount;
-		mpImplData->mpAry[nIndex].mnId = nId;
-		mpImplData->mpAry[nIndex].mnRefCount = 1;
-	}
-}
-
-// -----------------------------------------------------------------------
-
-void ImageList::CopyImage( const ::rtl::OUString& rImageName, const ::rtl::OUString& rCopyName )
-{
-    const USHORT nId1 = ImplGetImageId( rImageName ), nId2 = ImplGetImageId( rCopyName );
+	if( !mpImplData )
+		ImplInit( 0, rImage.GetSizePixel() );
 
-	if( nId1 && nId2 )
-        CopyImage( nId1, nId2 );
+	mpImplData->AddImage( rImageName, mpImplData->maImages.size() + 1,
+						  rImage.GetBitmapEx() );
 }
 
 // -----------------------------------------------------------------------
@@ -1111,31 +754,13 @@ void ImageList::ReplaceImage( USHORT nId
 	DBG_ASSERT( GetImagePos( nId ) != IMAGELIST_IMAGE_NOTFOUND, "ImageList::ReplaceImage(): Unknown nId" );
 	DBG_ASSERT( GetImagePos( nReplaceId ) != IMAGELIST_IMAGE_NOTFOUND, "ImageList::ReplaceImage(): Unknown nReplaceId" );
 
-	USHORT nPos1 = 0, nPos2 = 0;
-
-	while( nPos1 < mpImplData->mnArySize )
-	{
-		if ( mpImplData->mpAry[nPos1].mnId == nId )
-			break;
-
-		++nPos1;
-	}
-	
-	if( nPos1 < mpImplData->mnArySize )
+	ULONG nPosDest = GetImagePos( nId );
+	ULONG nPosSrc = GetImagePos( nReplaceId );
+	if( nPosDest != IMAGELIST_IMAGE_NOTFOUND &&
+		nPosSrc != IMAGELIST_IMAGE_NOTFOUND )
 	{
-		while( nPos2 < mpImplData->mnArySize )
-		{
-			if( mpImplData->mpAry[nPos2].mnId == nReplaceId )
-				break;
-	
-			++nPos2;
-		}
-
-		if( nPos2 < mpImplData->mnArySize )
-		{
-			ImplMakeUnique();
-			mpImplData->mpImageBitmap->Replace( nPos1, nPos2 );
-		}
+		ImplMakeUnique();
+		mpImplData->maImages[nPosDest] = mpImplData->maImages[nPosSrc];
 	}
 }
 
@@ -1155,29 +780,12 @@ void ImageList::RemoveImage( USHORT nId 
 {
 	DBG_CHKTHIS( ImageList, NULL );
 
-	if( mpImplData )
+	for( USHORT i = 0; i < mpImplData->maImages.size(); i++ )
 	{
-		USHORT i = 0;
-
-		ImplMakeUnique();
-
-		while( i < mpImplData->mnArySize )
+		if( mpImplData->maImages[ i ]->mnId == nId )
 		{
-			if( mpImplData->mpAry[i].mnId == nId )
-				break;
-
-			++i;
-		}
-
-		if( i < mpImplData->mnArySize )
-		{
-			--mpImplData->mpAry[i].mnRefCount;
-			mpImplData->mpAry[i].mnId = 0;
-			
-			if( !mpImplData->mpAry[i].mnRefCount )
-				--mpImplData->mnRealCount;
-
-			--mpImplData->mnCount;
+			mpImplData->RemoveImage( i );
+			break;
 		}
 	}
 }
@@ -1198,49 +806,50 @@ Image ImageList::GetImage( USHORT nId ) 
 {
 	DBG_CHKTHIS( ImageList, NULL );
 
-	Image aImage;
+//	fprintf (stderr, "GetImage %d\n", nId);
+
+	Image aRet;
 
 	if( mpImplData )
 	{
-		USHORT i = 0;
-		
-		while( i < mpImplData->mnArySize )
-		{
-			if( mpImplData->mpAry[i].mnId == nId )
-				break;
-
-			++i;
-		}
-
-		if( i < mpImplData->mnArySize )
+		std::vector<ImageAryData *>::iterator aIter;
+		for( aIter = mpImplData->maImages.begin();
+			 aIter != mpImplData->maImages.end(); aIter++)
 		{
-			ImplImageRefData* mpData = new ImplImageRefData;
+			if ((*aIter)->mnId == nId)
+			{
+				if( (*aIter)->IsLoadable() )
+					(*aIter)->Load( mpImplData->maPrefix );
 
-			++mpImplData->mnIRefCount;
-			++mpImplData->mpAry[i].mnRefCount;
-			mpData->mpImplData = mpImplData;
-			mpData->mnIndex = i;
-
-			aImage.mpImplData = new ImplImage;
-			aImage.mpImplData->mnRefCount = 1;
-			aImage.mpImplData->meType = IMAGETYPE_IMAGEREF;
-			aImage.mpImplData->mpData = mpData;
+				aRet = Image( (*aIter)->maBitmapEx );
+			}
 		}
 	}
 
-	return aImage;
+	return aRet;
 }
 
 // -----------------------------------------------------------------------
 
 Image ImageList::GetImage( const ::rtl::OUString& rImageName ) const
 {
-    const USHORT nId = ImplGetImageId( rImageName );
+//	fprintf (stderr, "GetImage '%s'\n",
+//			 rtl::OUStringToOString( rImageName, RTL_TEXTENCODING_UTF8 ).getStr() );
 
-    if( nId )
-        return GetImage( nId );
-    else 
-        return Image();
+	if( mpImplData )
+	{
+		ImageAryData *pImg = mpImplData->maNameHash[ rImageName ];
+		
+		if( pImg )
+		{
+			if( pImg->IsLoadable() )
+				pImg->Load( mpImplData->maPrefix );
+			return Image( pImg->maBitmapEx );
+		}
+	}
+//	fprintf (stderr, "no such image\n");
+
+	return Image();
 }
 
 // -----------------------------------------------------------------------
@@ -1261,7 +870,7 @@ USHORT ImageList::GetImageCount() const
 {
 	DBG_CHKTHIS( ImageList, NULL );
 	
-	return( mpImplData ? mpImplData->mnCount : 0 );
+	return mpImplData ? mpImplData->maImages.size() : 0;
 }
 
 // -----------------------------------------------------------------------
@@ -1272,23 +881,21 @@ USHORT ImageList::GetImagePos( USHORT nI
 
 	if( mpImplData && nId )
 	{
-		USHORT nPos = 0, i = 0;
-		
-		while( i < mpImplData->mnArySize )
+		for( USHORT i = 0; i < mpImplData->maImages.size(); i++ )
 		{
-			if( mpImplData->mpAry[i].mnId == nId )
-				return nPos;
-
-			if ( mpImplData->mpAry[i].mnId )
-				++nPos;
-			
-			++i;
+			if (mpImplData->maImages[ i ]->mnId == nId)
+				return i;
 		}
 	}
 
 	return IMAGELIST_IMAGE_NOTFOUND;
 }
 
+bool ImageList::HasImageAtPos( USHORT nId ) const
+{
+	return GetImagePos( nId ) != IMAGELIST_IMAGE_NOTFOUND;
+}
+
 // -----------------------------------------------------------------------
 
 USHORT ImageList::GetImagePos( const ::rtl::OUString& rImageName ) const
@@ -1297,17 +904,10 @@ USHORT ImageList::GetImagePos( const ::r
 
 	if( mpImplData && rImageName.getLength() )
 	{
-		USHORT nPos = 0, i = 0;
-		
-		while( i < mpImplData->mnArySize )
+		for( USHORT i = 0; i < mpImplData->maImages.size(); i++ )
 		{
-			if( mpImplData->mpAry[i].maName == rImageName )
-				return nPos;
-
-			if ( mpImplData->mpAry[i].mnId )
-				++nPos;
-			
-			++i;
+			if (mpImplData->maImages[i]->maName == rImageName)
+				return i;
 		}
 	}
 
@@ -1320,21 +921,8 @@ USHORT ImageList::GetImageId( USHORT nPo
 {
 	DBG_CHKTHIS( ImageList, NULL );
 
-	if( mpImplData )
-	{
-		USHORT nRealPos = 0, i = 0;
-		
-		while( i < mpImplData->mnArySize )
-		{
-			if( (nPos == nRealPos) && (mpImplData->mpAry[i].mnId) )
-				return mpImplData->mpAry[i].mnId;
-
-			if ( mpImplData->mpAry[i].mnId )
-				++nRealPos;
-
-			++i;
-		}
-	}
+	if( mpImplData && nPos < mpImplData->maImages.size() )
+		return mpImplData->maImages[ nPos ]->mnId;
 
 	return 0;
 }
@@ -1351,11 +939,8 @@ void ImageList::GetImageIds( ::std::vect
 	
 	if( mpImplData )
 	{
-		for( USHORT i = 0; i < mpImplData->mnArySize; ++i )
-		{
-			if( mpImplData->mpAry[ i ].mnId )
-				rIds.push_back( mpImplData->mpAry[ i ].mnId );
-		}
+		for( USHORT i = 0; i < mpImplData->maImages.size(); i++ )
+			rIds.push_back( mpImplData->maImages[i]->mnId );
 	}
 }
 
@@ -1365,21 +950,8 @@ void ImageList::GetImageIds( ::std::vect
 {
 	DBG_CHKTHIS( ImageList, NULL );
 
-	if( mpImplData )
-	{
-		USHORT nRealPos = 0, i = 0;
-		
-		while( i < mpImplData->mnArySize )
-		{
-			if( (nPos == nRealPos) && (mpImplData->mpAry[i].mnId) )
-				return mpImplData->mpAry[i].maName;
-
-			if ( mpImplData->mpAry[i].mnId )
-				++nRealPos;
-
-			++i;
-		}
-	}
+	if( mpImplData && nPos < mpImplData->maImages.size() )
+		return mpImplData->maImages[ nPos ]->maName;
 
 	return ::rtl::OUString();
 }
@@ -1396,11 +968,8 @@ void ImageList::GetImageNames( ::std::ve
 	
 	if( mpImplData )
 	{
-		for( USHORT i = 0; i < mpImplData->mnArySize; ++i )
-		{
-			if( mpImplData->mpAry[ i ].mnId )
-				rNames.push_back( mpImplData->mpAry[ i ].maName );
-		}
+		for( USHORT i = 0; i < mpImplData->maImages.size(); i++ )
+			rNames.push_back( mpImplData->maImages[ i ]->maName );
 	}
 }
 
@@ -1413,92 +982,25 @@ Size ImageList::GetImageSize() const
 	Size aRet;
 
 	if( mpImplData )
+	{
 		aRet = mpImplData->maImageSize;
 
-	return aRet;
-}
-
-// -----------------------------------------------------------------------
-
-BitmapEx ImageList::GetBitmapEx() const
-{
-	DBG_CHKTHIS( ImageList, NULL );
-
-	BitmapEx aRet;
-
-	if( mpImplData )
-	{
-		USHORT* pPosAry = new USHORT[ mpImplData->mnCount ];
-		USHORT	nPosCount = 0;
-		
-		for( USHORT i = 0; i < mpImplData->mnArySize; i++ )
+		// force load of 1st image to see - uncommon case.
+		if( aRet.Width() == 0 && aRet.Height() == 0 &&
+			mpImplData->maImages.size() > 0 )
 		{
-			if( mpImplData->mpAry[i].mnId )
-			{
-				pPosAry[ nPosCount ] = i;
-				++nPosCount;
-			}
+			Image aTmp = GetImage( mpImplData->maImages[ 0 ]->mnId );
+			aRet = mpImplData->maImageSize = aTmp.GetSizePixel();
 		}
-
-		aRet = mpImplData->mpImageBitmap->GetBitmapEx( nPosCount, pPosAry );
-		delete[] pPosAry;
 	}
+//	fprintf (stderr, "GetImageSize returns %d, %d\n",
+//			 aRet.Width(), aRet.Height());
 
 	return aRet;
 }
 
 // -----------------------------------------------------------------------
 
-ImageList ImageList::GetColorTransformedImageList( ImageColorTransform eColorTransform ) const
-{
-	DBG_CHKTHIS( ImageList, NULL );
-
-    ImageList aRet;
-
-    if( IMAGECOLORTRANSFORM_HIGHCONTRAST == eColorTransform )
-    {
-        Color*  pSrcColors = NULL;
-        Color*  pDstColors = NULL;
-        ULONG   nColorCount = 0;
-
-        aRet = *this;
-        aRet.ImplMakeUnique();
-
-		Image::GetColorTransformArrays( eColorTransform, pSrcColors, pDstColors, nColorCount );
-
-        if( nColorCount && pSrcColors && pDstColors && mpImplData )
-    		aRet.mpImplData->mpImageBitmap->ReplaceColors( pSrcColors, pDstColors, nColorCount ); 
-
-        delete[] pSrcColors;
-        delete[] pDstColors;
-    }
-	else if( IMAGECOLORTRANSFORM_MONOCHROME_BLACK == eColorTransform ||
-			 IMAGECOLORTRANSFORM_MONOCHROME_WHITE == eColorTransform )
-	{
-		aRet = *this;
-        aRet.ImplMakeUnique();
-   		aRet.mpImplData->mpImageBitmap->ColorTransform( ( BmpColorMode )( eColorTransform ) );
-	}
-
-    if( !aRet.GetImageCount() )
-        aRet = *this;
-
-    return aRet;
-}
-
-// -----------------------------------------------------------------------
-
-void ImageList::Invert()
-{
-    ImageList aNew( *this );
-    aNew.ImplMakeUnique();
-    aNew.mpImplData->mpImageBitmap->Invert();
-    
-    *this = aNew;
-}
-
-// -----------------------------------------------------------------------
-
 ImageList& ImageList::operator=( const ImageList& rImageList )
 {
 	DBG_CHKTHIS( ImageList, NULL );
@@ -1507,12 +1009,10 @@ ImageList& ImageList::operator=( const I
 	if( rImageList.mpImplData )
 		++rImageList.mpImplData->mnRefCount;
 
-	if( mpImplData && ( 0 == --mpImplData->mnRefCount ) && ( 0 == mpImplData->mnIRefCount ) )
+	if( mpImplData && ( 0 == --mpImplData->mnRefCount ) )
 		delete mpImplData;
 
 	mpImplData = rImageList.mpImplData;
-	mnInitSize = rImageList.mnInitSize;
-	mnGrowSize = rImageList.mnGrowSize;
 
 	return *this;
 }
@@ -1530,140 +1030,9 @@ BOOL ImageList::operator==( const ImageL
 		bRet = true;
 	else if( !rImageList.mpImplData || !mpImplData )
 		bRet = false;
-	else if( ( rImageList.mpImplData->mnCount == mpImplData->mnCount ) &&
-		 	 ( rImageList.mpImplData->maImageSize == mpImplData->maImageSize ) )
-	{
-		bRet = true;
-	}
+	else if( rImageList.GetImageCount() == GetImageCount() &&
+		 	 rImageList.mpImplData->maImageSize == mpImplData->maImageSize )
+		bRet = true; // strange semantic
 
 	return bRet;
 }
-
-// -----------------------------------------------------------------------
-
-SvStream& operator>>( SvStream& rIStream, ImageList& rImageList )
-{
-	DBG_CHKOBJ( &rImageList, ImageList, NULL );
-
-	if( rImageList.mpImplData )
-	{
-		--rImageList.mpImplData->mnRefCount;
-		
-		if( ( 0 == rImageList.mpImplData->mnRefCount ) && ( 0 == rImageList.mpImplData->mnIRefCount ) )
-			delete rImageList.mpImplData;
-	}
-	
-	rImageList.mpImplData = NULL;
-
-	USHORT	nVersion;
-	Size	aImageSize;
-	BOOL	bImageList;
-	
-	rIStream >> nVersion >> rImageList.mnInitSize >> rImageList.mnGrowSize >> bImageList;
-
-	if( bImageList )
-	{
-		BitmapEx	aBmpEx;
-		Bitmap		aBmp;
-		BYTE		bMaskOrAlpha, bMaskColor;
-
-		rIStream >> aImageSize.Width() >> aImageSize.Height();
-
-		rImageList.mpImplData = new ImplImageList;
-		rImageList.mpImplData->mnRefCount = 1;
-		rImageList.mpImplData->mnIRefCount= 0;
-		rImageList.mpImplData->mnCount = rImageList.mnInitSize;
-		rImageList.mpImplData->mnRealCount = rImageList.mnInitSize;
-		rImageList.mpImplData->mnArySize = rImageList.mnInitSize;
-		rImageList.mpImplData->mpAry = new ImageAryData[ rImageList.mnInitSize ];
-		rImageList.mpImplData->maImageSize = aImageSize;
-
-		for( USHORT i = 0; i < rImageList.mnInitSize; ++i )
-		{
-			rIStream >> rImageList.mpImplData->mpAry[i].mnId;
-			rImageList.mpImplData->mpAry[i].mnRefCount = 1;
-		}
-	
-		rIStream >> aBmp >> bMaskOrAlpha;
-		
-		if( bMaskOrAlpha )
-		{
-			Bitmap aMaskOrAlpha;			
-		
-			rIStream >> aMaskOrAlpha;
-			
-			if( aMaskOrAlpha.GetBitCount() == 8 && aMaskOrAlpha.HasGreyPalette() )
-				aBmpEx = BitmapEx( aBmp, AlphaMask( aMaskOrAlpha ) );
-			else
-				aBmpEx = BitmapEx( aBmp, aMaskOrAlpha );
-		}
-		
-		rIStream >> bMaskColor;
-
-		if( bMaskColor )
-		{
-			Color aMaskColor;
-			
-			rIStream >> aMaskColor;
-			
-			if( !aBmpEx.IsAlpha() && !aBmpEx.IsTransparent() )
-				aBmpEx = BitmapEx( aBmp, aMaskColor );
-		}
-	
-		rImageList.mpImplData->mpImageBitmap = new ImplImageBmp;
-		rImageList.mpImplData->mpImageBitmap->Create( aBmpEx, aImageSize.Width(), aImageSize.Height(), rImageList.mnInitSize );
-	}
-	
-	return rIStream;
-}
-
-// -----------------------------------------------------------------------
-
-SvStream& operator<<( SvStream& rOStream, const ImageList& rImageList )
-{
-	DBG_CHKOBJ( &rImageList, ImageList, NULL );
-
-	USHORT	nVersion = IMAGE_FILE_VERSION;
-	BOOL	bImageList = rImageList.mpImplData ? true : false;
-
-	rOStream << nVersion;
-
-	if ( !bImageList || !rImageList.mpImplData->mnCount )
-		rOStream << rImageList.mnInitSize << rImageList.mnGrowSize << ( bImageList = FALSE );
-	else
-	{
-		rOStream << rImageList.mpImplData->mnCount;
-		rOStream << rImageList.mnGrowSize;
-		rOStream << bImageList;
-		rOStream << rImageList.mpImplData->maImageSize.Width();
-		rOStream << rImageList.mpImplData->maImageSize.Height();
-	
-		USHORT* mpPosAry = new USHORT[rImageList.mpImplData->mnCount];
-		USHORT	nPosCount = 0;
-		
-		for( USHORT i = 0; i < rImageList.mpImplData->mnArySize; ++i )
-		{
-			if( rImageList.mpImplData->mpAry[i].mnId )
-			{
-				rOStream << rImageList.mpImplData->mpAry[i].mnId;
-				mpPosAry[ nPosCount++ ] = i;
-			}
-		}
-	
-		BitmapEx	aBmpEx( rImageList.mpImplData->mpImageBitmap->GetBitmapEx( nPosCount, mpPosAry ) );
-		const BOOL	bMaskOrAlpha = aBmpEx.IsAlpha() || aBmpEx.IsTransparent();
-		const BOOL	bMaskColor = false;
-
-		rOStream << aBmpEx.GetBitmap() << bMaskOrAlpha;
-		
-		if( bMaskOrAlpha )
-			rOStream << ( aBmpEx.IsAlpha() ? aBmpEx.GetAlpha().ImplGetBitmap() : aBmpEx.GetMask() );
-	
-		// BitmapEx doesn't have internal mask colors anymore
-		rOStream << bMaskColor;
-
-		delete[] mpPosAry;
-	}
-
-	return rOStream;
-}

