Update ooo320-m1
[ooovba.git] / svtools / source / misc / imap.cxx
blobf2330d60bc8b37c5c0a2afff6fc30b3a95d3cfa3
1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: imap.cxx,v $
10 * $Revision: 1.11 $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_svtools.hxx"
34 #include <tools/urlobj.hxx>
35 #include <vcl/svapp.hxx>
36 #include <vcl/mapmod.hxx>
37 #include <vcl/window.hxx>
39 #include "urihelper.hxx"
40 #include <svtools/imap.hxx>
41 #include <svtools/imapobj.hxx>
42 #include <svtools/imapcirc.hxx>
43 #include <svtools/imaprect.hxx>
44 #include <svtools/imappoly.hxx>
46 #include <string.h>
47 #include <math.h>
49 DBG_NAME( ImageMap )
52 #define SCALEPOINT(aPT,aFracX,aFracY) (aPT).X()=((aPT).X()*(aFracX).GetNumerator())/(aFracX).GetDenominator(); \
53 (aPT).Y()=((aPT).Y()*(aFracY).GetNumerator())/(aFracY).GetDenominator();
56 /******************************************************************************/
58 UINT16 IMapObject::nActualTextEncoding = (UINT16) RTL_TEXTENCODING_DONTKNOW;
60 /******************************************************************************/
63 #ifdef WIN
64 #pragma optimize ( "", off )
65 #endif
67 IMapObject::IMapObject( const String& rURL, const String& rAltText, const String& rDesc,
68 const String& rTarget, const String& rName, BOOL bURLActive )
69 : aURL( rURL )
70 , aAltText( rAltText )
71 , aDesc( rDesc )
72 , aTarget( rTarget )
73 , aName( rName )
74 , bActive( bURLActive )
79 /******************************************************************************
81 |* Freigabe des internen Speichers
83 \******************************************************************************/
85 UINT16 IMapObject::GetVersion() const
87 return IMAP_OBJ_VERSION;
91 /******************************************************************************
95 \******************************************************************************/
97 void IMapObject::Write( SvStream& rOStm, const String& rBaseURL ) const
99 IMapCompat* pCompat;
100 const rtl_TextEncoding eEncoding = gsl_getSystemTextEncoding();
102 rOStm << GetType();
103 rOStm << GetVersion();
104 rOStm << ( (UINT16) eEncoding );
106 const ByteString aRelURL = ByteString( String(URIHelper::simpleNormalizedMakeRelative( rBaseURL, aURL )), eEncoding );
107 rOStm.WriteByteString( aRelURL );
108 rOStm.WriteByteString( ByteString( aAltText, eEncoding ) );
109 rOStm << bActive;
110 rOStm.WriteByteString( ByteString( aTarget, eEncoding ) );
112 pCompat = new IMapCompat( rOStm, STREAM_WRITE );
114 WriteIMapObject( rOStm );
115 aEventList.Write( rOStm ); // V4
116 rOStm.WriteByteString( ByteString( aName, eEncoding ) ); // V5
118 delete pCompat;
122 /******************************************************************************
124 |* Binaer-Import
126 \******************************************************************************/
128 void IMapObject::Read( SvStream& rIStm, const String& rBaseURL )
130 IMapCompat* pCompat;
131 rtl_TextEncoding nTextEncoding;
132 ByteString aString;
134 // Typ und Version ueberlesen wir
135 rIStm.SeekRel( 2 );
136 rIStm >> nReadVersion;
137 rIStm >> nTextEncoding;
138 rIStm.ReadByteString( aString ); aURL = String( aString.GetBuffer(), nTextEncoding );
139 rIStm.ReadByteString( aString ); aAltText = String( aString.GetBuffer(), nTextEncoding );
140 rIStm >> bActive;
141 rIStm.ReadByteString( aString ); aTarget = String( aString.GetBuffer(), nTextEncoding );
143 // URL absolut machen
144 aURL = URIHelper::SmartRel2Abs( INetURLObject(rBaseURL), aURL, URIHelper::GetMaybeFileHdl(), true, false, INetURLObject::WAS_ENCODED, INetURLObject::DECODE_UNAMBIGUOUS );
145 pCompat = new IMapCompat( rIStm, STREAM_READ );
147 ReadIMapObject( rIStm );
149 // ab Version 4 lesen wir eine EventListe
150 if ( nReadVersion >= 0x0004 )
152 aEventList.Read(rIStm);
154 // ab Version 5 kann ein Objektname vorhanden sein
155 if ( nReadVersion >= 0x0005 )
157 rIStm.ReadByteString( aString ); aName = String( aString.GetBuffer(), nTextEncoding );
161 delete pCompat;
165 /******************************************************************************
167 |* Konvertierung der logischen Koordianten in Pixel
169 \******************************************************************************/
171 Point IMapObject::GetPixelPoint( const Point& rLogPoint )
173 return Application::GetDefaultDevice()->LogicToPixel( rLogPoint, MapMode( MAP_100TH_MM ) );
177 /******************************************************************************
179 |* Konvertierung der logischen Koordianten in Pixel
181 \******************************************************************************/
183 Point IMapObject::GetLogPoint( const Point& rPixelPoint )
185 return Application::GetDefaultDevice()->PixelToLogic( rPixelPoint, MapMode( MAP_100TH_MM ) );
189 /******************************************************************************
193 \******************************************************************************/
195 BOOL IMapObject::IsEqual( const IMapObject& rEqObj )
197 return ( ( aURL == rEqObj.aURL ) &&
198 ( aAltText == rEqObj.aAltText ) &&
199 ( aDesc == rEqObj.aDesc ) &&
200 ( aTarget == rEqObj.aTarget ) &&
201 ( aName == rEqObj.aName ) &&
202 ( bActive == rEqObj.bActive ) );
206 /******************************************************************************/
207 /******************************************************************************/
208 /******************************************************************************/
210 IMapRectangleObject::IMapRectangleObject( const Rectangle& rRect,
211 const String& rURL,
212 const String& rAltText,
213 const String& rDesc,
214 const String& rTarget,
215 const String& rName,
216 BOOL bURLActive,
217 BOOL bPixelCoords ) :
218 IMapObject ( rURL, rAltText, rDesc, rTarget, rName, bURLActive )
220 ImpConstruct( rRect, bPixelCoords );
224 /******************************************************************************
228 \******************************************************************************/
230 void IMapRectangleObject::ImpConstruct( const Rectangle& rRect, BOOL bPixel )
232 if ( bPixel )
233 aRect = Application::GetDefaultDevice()->PixelToLogic( rRect, MapMode( MAP_100TH_MM ) );
234 else
235 aRect = rRect;
239 /******************************************************************************
241 |* Binaer-Export
243 \******************************************************************************/
245 void IMapRectangleObject::WriteIMapObject( SvStream& rOStm ) const
247 rOStm << aRect;
251 /******************************************************************************
253 |* Binaer-Import
255 \******************************************************************************/
257 void IMapRectangleObject::ReadIMapObject( SvStream& rIStm )
259 rIStm >> aRect;
263 /******************************************************************************
265 |* Typ-Rueckgabe
267 \******************************************************************************/
269 UINT16 IMapRectangleObject::GetType() const
271 return IMAP_OBJ_RECTANGLE;
275 /******************************************************************************
277 |* Hit-Test
279 \******************************************************************************/
281 BOOL IMapRectangleObject::IsHit( const Point& rPoint ) const
283 return aRect.IsInside( rPoint );
287 /******************************************************************************
291 \******************************************************************************/
293 Rectangle IMapRectangleObject::GetRectangle( BOOL bPixelCoords ) const
295 Rectangle aNewRect;
297 if ( bPixelCoords )
298 aNewRect = Application::GetDefaultDevice()->LogicToPixel( aRect, MapMode( MAP_100TH_MM ) );
299 else
300 aNewRect = aRect;
302 return aNewRect;
306 /******************************************************************************
310 \******************************************************************************/
312 void IMapRectangleObject::Scale( const Fraction& rFracX, const Fraction& rFracY )
314 Point aTL( aRect.TopLeft() );
315 Point aBR( aRect.BottomRight() );
317 if ( rFracX.GetDenominator() && rFracY.GetDenominator() )
319 SCALEPOINT( aTL, rFracX, rFracY );
320 SCALEPOINT( aBR, rFracX, rFracY );
323 aRect = Rectangle( aTL, aBR );
327 /******************************************************************************
331 \******************************************************************************/
333 BOOL IMapRectangleObject::IsEqual( const IMapRectangleObject& rEqObj )
335 return ( IMapObject::IsEqual( rEqObj ) && ( aRect == rEqObj.aRect ) );
339 /******************************************************************************/
340 /******************************************************************************/
341 /******************************************************************************/
343 IMapCircleObject::IMapCircleObject( const Point& rCenter, ULONG nCircleRadius,
344 const String& rURL,
345 const String& rAltText,
346 const String& rDesc,
347 const String& rTarget,
348 const String& rName,
349 BOOL bURLActive,
350 BOOL bPixelCoords ) :
351 IMapObject ( rURL, rAltText, rDesc, rTarget, rName, bURLActive )
353 ImpConstruct( rCenter, nCircleRadius, bPixelCoords );
357 /******************************************************************************
361 \******************************************************************************/
363 void IMapCircleObject::ImpConstruct( const Point& rCenter, ULONG nRad, BOOL bPixel )
365 if ( bPixel )
367 MapMode aMap100( MAP_100TH_MM );
369 aCenter = Application::GetDefaultDevice()->PixelToLogic( rCenter, aMap100 );
370 nRadius = Application::GetDefaultDevice()->PixelToLogic( Size( nRad, 0 ), aMap100 ).Width();
372 else
374 aCenter = rCenter;
375 nRadius = nRad;
380 /******************************************************************************
382 |* Binaer-Export
384 \******************************************************************************/
386 void IMapCircleObject::WriteIMapObject( SvStream& rOStm ) const
388 UINT32 nTmp = nRadius;
390 rOStm << aCenter;
391 rOStm << nTmp;
395 /******************************************************************************
397 |* Binaer-Import
399 \******************************************************************************/
401 void IMapCircleObject::ReadIMapObject( SvStream& rIStm )
403 UINT32 nTmp;
405 rIStm >> aCenter;
406 rIStm >> nTmp;
408 nRadius = nTmp;
412 /******************************************************************************
414 |* Typ-Rueckgabe
416 \******************************************************************************/
418 UINT16 IMapCircleObject::GetType() const
420 return IMAP_OBJ_CIRCLE;
424 /******************************************************************************
426 |* Hit-Test
428 \******************************************************************************/
430 BOOL IMapCircleObject::IsHit( const Point& rPoint ) const
432 const Point aPoint( aCenter - rPoint );
433 BOOL bRet = FALSE;
435 if ( (ULONG) sqrt( (double) aPoint.X() * aPoint.X() +
436 aPoint.Y() * aPoint.Y() ) <= nRadius )
438 bRet = TRUE;
441 return bRet;
445 /******************************************************************************
449 \******************************************************************************/
451 Point IMapCircleObject::GetCenter( BOOL bPixelCoords ) const
453 Point aNewPoint;
455 if ( bPixelCoords )
456 aNewPoint = Application::GetDefaultDevice()->LogicToPixel( aCenter, MapMode( MAP_100TH_MM ) );
457 else
458 aNewPoint = aCenter;
460 return aNewPoint;
464 /******************************************************************************
468 \******************************************************************************/
470 ULONG IMapCircleObject::GetRadius( BOOL bPixelCoords ) const
472 ULONG nNewRadius;
474 if ( bPixelCoords )
475 nNewRadius = Application::GetDefaultDevice()->LogicToPixel( Size( nRadius, 0 ), MapMode( MAP_100TH_MM ) ).Width();
476 else
477 nNewRadius = nRadius;
479 return nNewRadius;
483 /******************************************************************************
487 \******************************************************************************/
489 Rectangle IMapCircleObject::GetBoundRect() const
491 long nWidth = nRadius << 1;
493 return Rectangle( Point( aCenter.X() - nRadius, aCenter.Y() - nRadius ),
494 Size( nWidth, nWidth ) );
498 /******************************************************************************
502 \******************************************************************************/
504 void IMapCircleObject::Scale( const Fraction& rFracX, const Fraction& rFracY )
506 Fraction aAverage( rFracX );
508 aAverage += rFracY;
509 aAverage *= Fraction( 1, 2 );
511 if ( rFracX.GetDenominator() && rFracY.GetDenominator() )
513 SCALEPOINT( aCenter, rFracX, rFracY );
516 nRadius = ( nRadius * aAverage.GetNumerator() ) / aAverage.GetDenominator();
520 /******************************************************************************
524 \******************************************************************************/
526 BOOL IMapCircleObject::IsEqual( const IMapCircleObject& rEqObj )
528 return ( IMapObject::IsEqual( rEqObj ) &&
529 ( aCenter == rEqObj.aCenter ) &&
530 ( nRadius == rEqObj.nRadius ) );
534 /******************************************************************************/
535 /******************************************************************************/
536 /******************************************************************************/
537 IMapPolygonObject::IMapPolygonObject( const Polygon& rPoly,
538 const String& rURL,
539 const String& rAltText,
540 const String& rDesc,
541 const String& rTarget,
542 const String& rName,
543 BOOL bURLActive,
544 BOOL bPixelCoords ) :
545 IMapObject ( rURL, rAltText, rDesc, rTarget, rName, bURLActive ),
546 bEllipse ( FALSE )
548 ImpConstruct( rPoly, bPixelCoords );
552 /******************************************************************************
556 \******************************************************************************/
558 void IMapPolygonObject::ImpConstruct( const Polygon& rPoly, BOOL bPixel )
560 if ( bPixel )
561 aPoly = Application::GetDefaultDevice()->PixelToLogic( rPoly, MapMode( MAP_100TH_MM ) );
562 else
563 aPoly = rPoly;
567 /******************************************************************************
569 |* Binaer-Export
571 \******************************************************************************/
573 void IMapPolygonObject::WriteIMapObject( SvStream& rOStm ) const
575 rOStm << aPoly;
576 rOStm << bEllipse; // >= Version 2
577 rOStm << aEllipse; // >= Version 2
581 /******************************************************************************
583 |* Binaer-Import
585 \******************************************************************************/
587 void IMapPolygonObject::ReadIMapObject( SvStream& rIStm )
589 rIStm >> aPoly;
591 // Version >= 2 hat zusaetzlich Ellipsen-Information
592 if ( nReadVersion >= 2 )
594 rIStm >> bEllipse;
595 rIStm >> aEllipse;
600 /******************************************************************************
602 |* Typ-Rueckgabe
604 \******************************************************************************/
606 UINT16 IMapPolygonObject::GetType() const
608 return IMAP_OBJ_POLYGON;
612 /******************************************************************************
614 |* Hit-Test
616 \******************************************************************************/
618 BOOL IMapPolygonObject::IsHit( const Point& rPoint ) const
620 return aPoly.IsInside( rPoint );
624 /******************************************************************************
628 \******************************************************************************/
630 Polygon IMapPolygonObject::GetPolygon( BOOL bPixelCoords ) const
632 Polygon aNewPoly;
634 if ( bPixelCoords )
635 aNewPoly = Application::GetDefaultDevice()->LogicToPixel( aPoly, MapMode( MAP_100TH_MM ) );
636 else
637 aNewPoly = aPoly;
639 return aNewPoly;
643 /******************************************************************************
647 \******************************************************************************/
649 void IMapPolygonObject::SetExtraEllipse( const Rectangle& rEllipse )
651 if ( aPoly.GetSize() )
653 bEllipse = TRUE;
654 aEllipse = rEllipse;
659 /******************************************************************************
663 \******************************************************************************/
665 void IMapPolygonObject::Scale( const Fraction& rFracX, const Fraction& rFracY )
667 USHORT nCount = aPoly.GetSize();
669 for ( USHORT i = 0; i < nCount; i++ )
671 Point aScaledPt( aPoly[ i ] );
673 if ( rFracX.GetDenominator() && rFracY.GetDenominator() )
675 SCALEPOINT( aScaledPt, rFracX, rFracY );
678 aPoly[ i ] = aScaledPt;
681 if ( bEllipse )
683 Point aTL( aEllipse.TopLeft() );
684 Point aBR( aEllipse.BottomRight() );
686 if ( rFracX.GetDenominator() && rFracY.GetDenominator() )
688 SCALEPOINT( aTL, rFracX, rFracY );
689 SCALEPOINT( aBR, rFracX, rFracY );
692 aEllipse = Rectangle( aTL, aBR );
697 /******************************************************************************
701 \******************************************************************************/
703 BOOL IMapPolygonObject::IsEqual( const IMapPolygonObject& rEqObj )
705 BOOL bRet = FALSE;
707 if ( IMapObject::IsEqual( rEqObj ) )
709 const Polygon& rEqPoly = rEqObj.aPoly;
710 const USHORT nCount = aPoly.GetSize();
711 const USHORT nEqCount = rEqPoly.GetSize();
712 BOOL bDifferent = FALSE;
714 if ( nCount == nEqCount )
716 for ( USHORT i = 0; i < nCount; i++ )
718 if ( aPoly[ i ] != rEqPoly[ i ] )
720 bDifferent = TRUE;
721 break;
725 if ( !bDifferent )
726 bRet = TRUE;
730 return bRet;
734 /******************************************************************************/
735 /******************************************************************************/
736 /******************************************************************************/
739 /******************************************************************************
741 |* Ctor
743 \******************************************************************************/
745 ImageMap::ImageMap( const String& rName ) :
746 aName ( rName )
751 /******************************************************************************
753 |* Copy-Ctor
755 \******************************************************************************/
757 ImageMap::ImageMap( const ImageMap& rImageMap )
759 DBG_CTOR( ImageMap, NULL );
761 USHORT nCount = rImageMap.GetIMapObjectCount();
763 for ( USHORT i = 0; i < nCount; i++ )
765 IMapObject* pCopyObj = rImageMap.GetIMapObject( i );
767 switch( pCopyObj->GetType() )
769 case( IMAP_OBJ_RECTANGLE ):
770 maList.Insert( new IMapRectangleObject( *(IMapRectangleObject*) pCopyObj ), LIST_APPEND );
771 break;
773 case( IMAP_OBJ_CIRCLE ):
774 maList.Insert( new IMapCircleObject( *(IMapCircleObject*) pCopyObj ), LIST_APPEND );
775 break;
777 case( IMAP_OBJ_POLYGON ):
778 maList.Insert( new IMapPolygonObject( *(IMapPolygonObject*) pCopyObj ), LIST_APPEND );
779 break;
781 default:
782 break;
786 aName = rImageMap.aName;
790 /******************************************************************************
792 |* Dtor
794 \******************************************************************************/
796 ImageMap::~ImageMap()
798 DBG_DTOR( ImageMap, NULL );
800 ClearImageMap();
804 /******************************************************************************
806 |* Freigabe des internen Speichers
808 \******************************************************************************/
810 void ImageMap::ClearImageMap()
812 IMapObject* pObj = (IMapObject*) maList.First();
814 while ( pObj )
816 delete pObj;
817 pObj = (IMapObject*) maList.Next();
820 maList.Clear();
822 aName = String();
826 /******************************************************************************
828 |* Zuweisungsoperator
830 \******************************************************************************/
832 ImageMap& ImageMap::operator=( const ImageMap& rImageMap )
834 USHORT nCount = rImageMap.GetIMapObjectCount();
836 ClearImageMap();
838 for ( USHORT i = 0; i < nCount; i++ )
840 IMapObject* pCopyObj = rImageMap.GetIMapObject( i );
842 switch( pCopyObj->GetType() )
844 case( IMAP_OBJ_RECTANGLE ):
845 maList.Insert( new IMapRectangleObject( *(IMapRectangleObject*) pCopyObj ), LIST_APPEND );
846 break;
848 case( IMAP_OBJ_CIRCLE ):
849 maList.Insert( new IMapCircleObject( *(IMapCircleObject*) pCopyObj ), LIST_APPEND );
850 break;
852 case( IMAP_OBJ_POLYGON ):
853 maList.Insert( new IMapPolygonObject( *(IMapPolygonObject*) pCopyObj ), LIST_APPEND );
854 break;
856 default:
857 break;
861 aName = rImageMap.aName;
863 return *this;
867 /******************************************************************************
869 |* Vergleichsoperator I
871 \******************************************************************************/
873 BOOL ImageMap::operator==( const ImageMap& rImageMap )
875 const USHORT nCount = (USHORT) maList.Count();
876 const USHORT nEqCount = rImageMap.GetIMapObjectCount();
877 BOOL bRet = FALSE;
879 if ( nCount == nEqCount )
881 BOOL bDifferent = ( aName != rImageMap.aName );
883 for ( USHORT i = 0; ( i < nCount ) && !bDifferent; i++ )
885 IMapObject* pObj = (IMapObject*) maList.GetObject( i );
886 IMapObject* pEqObj = rImageMap.GetIMapObject( i );
888 if ( pObj->GetType() == pEqObj->GetType() )
890 switch( pObj->GetType() )
892 case( IMAP_OBJ_RECTANGLE ):
894 if ( !( (IMapRectangleObject*) pObj )->IsEqual( *(IMapRectangleObject*) pEqObj ) )
895 bDifferent = TRUE;
897 break;
899 case( IMAP_OBJ_CIRCLE ):
901 if ( !( (IMapCircleObject*) pObj )->IsEqual( *(IMapCircleObject*) pEqObj ) )
902 bDifferent = TRUE;
904 break;
906 case( IMAP_OBJ_POLYGON ):
908 if ( !( (IMapPolygonObject*) pObj )->IsEqual( *(IMapPolygonObject*) pEqObj ) )
909 bDifferent = TRUE;
911 break;
913 default:
914 break;
917 else
918 bDifferent = TRUE;
921 if ( !bDifferent )
922 bRet = TRUE;
925 return bRet;
929 /******************************************************************************
931 |* Vergleichsoperator II
933 \******************************************************************************/
935 BOOL ImageMap::operator!=( const ImageMap& rImageMap )
937 return !( *this == rImageMap );
941 /******************************************************************************
943 |* Freigabe des internen Speichers
945 \******************************************************************************/
947 UINT16 ImageMap::GetVersion() const
949 return IMAGE_MAP_VERSION;
953 /******************************************************************************
955 |* Einfuegen eines neuen Objekts
957 \******************************************************************************/
959 void ImageMap::InsertIMapObject( const IMapObject& rIMapObject )
961 switch( rIMapObject.GetType() )
963 case( IMAP_OBJ_RECTANGLE ):
964 maList.Insert( new IMapRectangleObject( (IMapRectangleObject&) rIMapObject ), LIST_APPEND );
965 break;
967 case( IMAP_OBJ_CIRCLE ):
968 maList.Insert( new IMapCircleObject( (IMapCircleObject&) rIMapObject ), LIST_APPEND );
969 break;
971 case( IMAP_OBJ_POLYGON ):
972 maList.Insert( new IMapPolygonObject( (IMapPolygonObject&) rIMapObject ), LIST_APPEND );
973 break;
975 default:
976 break;
981 /******************************************************************************
983 |* Hit-Test
985 \******************************************************************************/
987 IMapObject* ImageMap::GetHitIMapObject( const Size& rTotalSize,
988 const Size& rDisplaySize,
989 const Point& rRelHitPoint,
990 ULONG nFlags )
992 Point aRelPoint( rTotalSize.Width() * rRelHitPoint.X() / rDisplaySize.Width(),
993 rTotalSize.Height() * rRelHitPoint.Y() / rDisplaySize.Height() );
995 // Falls Flags zur Spiegelung etc. angegeben sind, wird
996 // der zu pruefende Punkt vor der Pruefung entspr. transformiert
997 if ( nFlags )
999 if ( nFlags & IMAP_MIRROR_HORZ )
1000 aRelPoint.X() = rTotalSize.Width() - aRelPoint.X();
1002 if ( nFlags & IMAP_MIRROR_VERT )
1003 aRelPoint.Y() = rTotalSize.Height() - aRelPoint.Y();
1006 // Alle Objekte durchlaufen und HitTest ausfuehren
1007 IMapObject* pObj = (IMapObject*) maList.First();
1008 while ( pObj )
1010 if ( pObj->IsHit( aRelPoint ) )
1011 break;
1013 pObj = (IMapObject*) maList.Next();
1016 return( pObj ? ( pObj->IsActive() ? pObj : NULL ) : NULL );
1020 /******************************************************************************
1024 \******************************************************************************/
1026 Rectangle ImageMap::GetBoundRect() const
1028 Rectangle aBoundRect;
1029 ULONG nCount = maList.Count();
1031 for ( ULONG i = 0; i < nCount; i++ )
1032 aBoundRect.Union( ( (IMapObject*) maList.GetObject( i ) )->GetBoundRect() );
1034 return aBoundRect;
1038 /******************************************************************************
1042 \******************************************************************************/
1044 void ImageMap::Scale( const Fraction& rFracX, const Fraction& rFracY )
1046 USHORT nCount = (USHORT) maList.Count();
1048 for ( USHORT i = 0; i < nCount; i++ )
1050 IMapObject* pObj = GetIMapObject( i );
1052 switch( pObj->GetType() )
1054 case( IMAP_OBJ_RECTANGLE ):
1055 ( (IMapRectangleObject*) pObj )->Scale( rFracX, rFracY );
1056 break;
1058 case( IMAP_OBJ_CIRCLE ):
1059 ( (IMapCircleObject*) pObj )->Scale( rFracX, rFracY );
1060 break;
1062 case( IMAP_OBJ_POLYGON ):
1063 ( (IMapPolygonObject*) pObj )->Scale( rFracX, rFracY );
1064 break;
1066 default:
1067 break;
1073 /******************************************************************************
1075 |* Objekte nacheinander wegschreiben
1077 \******************************************************************************/
1079 void ImageMap::ImpWriteImageMap( SvStream& rOStm, const String& rBaseURL ) const
1081 IMapObject* pObj;
1082 USHORT nCount = (USHORT) maList.Count();
1084 for ( USHORT i = 0; i < nCount; i++ )
1086 pObj = (IMapObject*) maList.GetObject( i );
1087 pObj->Write( rOStm, rBaseURL );
1092 /******************************************************************************
1094 |* Objekte nacheinander lesen
1096 \******************************************************************************/
1098 void ImageMap::ImpReadImageMap( SvStream& rIStm, USHORT nCount, const String& rBaseURL )
1100 // neue Objekte einlesen
1101 for ( USHORT i = 0; i < nCount; i++ )
1103 UINT16 nType;
1105 rIStm >> nType;
1106 rIStm.SeekRel( -2 );
1108 switch( nType )
1110 case ( IMAP_OBJ_RECTANGLE ):
1112 IMapRectangleObject* pObj = new IMapRectangleObject;
1113 pObj->Read( rIStm, rBaseURL );
1114 maList.Insert( pObj, LIST_APPEND );
1116 break;
1118 case ( IMAP_OBJ_CIRCLE ):
1120 IMapCircleObject* pObj = new IMapCircleObject;
1121 pObj->Read( rIStm, rBaseURL );
1122 maList.Insert( pObj, LIST_APPEND );
1124 break;
1126 case ( IMAP_OBJ_POLYGON ):
1128 IMapPolygonObject* pObj = new IMapPolygonObject;
1129 pObj->Read( rIStm, rBaseURL );
1130 maList.Insert( pObj, LIST_APPEND );
1132 break;
1134 default:
1135 break;
1141 /******************************************************************************
1143 |* Binaer speichern
1145 \******************************************************************************/
1147 void ImageMap::Write( SvStream& rOStm, const String& rBaseURL ) const
1149 IMapCompat* pCompat;
1150 String aImageName( GetName() );
1151 String aDummy;
1152 USHORT nOldFormat = rOStm.GetNumberFormatInt();
1153 UINT16 nCount = (UINT16) GetIMapObjectCount();
1154 const rtl_TextEncoding eEncoding = gsl_getSystemTextEncoding();
1156 rOStm.SetNumberFormatInt( NUMBERFORMAT_INT_LITTLEENDIAN );
1158 // MagicCode schreiben
1159 rOStm << IMAPMAGIC;
1160 rOStm << GetVersion();
1161 rOStm.WriteByteString( ByteString( aImageName, eEncoding ) );
1162 rOStm.WriteByteString( ByteString( aDummy, eEncoding ) );
1163 rOStm << nCount;
1164 rOStm.WriteByteString( ByteString( aImageName, eEncoding ) );
1166 pCompat = new IMapCompat( rOStm, STREAM_WRITE );
1168 // hier kann in neueren Versionen eingefuegt werden
1170 delete pCompat;
1172 ImpWriteImageMap( rOStm, rBaseURL );
1174 rOStm.SetNumberFormatInt( nOldFormat );
1178 /******************************************************************************
1180 |* Binaer laden
1182 \******************************************************************************/
1184 void ImageMap::Read( SvStream& rIStm, const String& rBaseURL )
1186 ByteString aString;
1187 char cMagic[6];
1188 USHORT nOldFormat = rIStm.GetNumberFormatInt();
1189 UINT16 nCount;
1191 rIStm.SetNumberFormatInt( NUMBERFORMAT_INT_LITTLEENDIAN );
1192 rIStm.Read( cMagic, sizeof( cMagic ) );
1194 if ( !memcmp( cMagic, IMAPMAGIC, sizeof( cMagic ) ) )
1196 IMapCompat* pCompat;
1198 // alten Inhalt loeschen
1199 ClearImageMap();
1201 // Version ueberlesen wir
1202 rIStm.SeekRel( 2 );
1204 rIStm.ReadByteString( aString ); aName = String( aString, gsl_getSystemTextEncoding() );
1205 rIStm.ReadByteString( aString ); // Dummy
1206 rIStm >> nCount;
1207 rIStm.ReadByteString( aString ); // Dummy
1209 pCompat = new IMapCompat( rIStm, STREAM_READ );
1211 // hier kann in neueren Versionen gelesen werden
1213 delete pCompat;
1214 ImpReadImageMap( rIStm, nCount, rBaseURL );
1217 else
1218 rIStm.SetError( SVSTREAM_GENERALERROR );
1220 rIStm.SetNumberFormatInt( nOldFormat );
1224 #ifdef WIN
1225 #pragma optimize ( "", on )
1226 #endif