Index: sw/source/filter/ww8/escher.hxx =================================================================== --- sw/source/filter/ww8/escher.hxx (revision 1414498) +++ sw/source/filter/ww8/escher.hxx (working copy) @@ -134,6 +134,13 @@ virtual void WriteFrmExtraData(const SwFrmFmt&); virtual void WritePictures(); virtual ~SwBasicEscherEx(); + //i120927,this function is added to export hyperlink info,such as graphic/frame/OLE + bool IsRelUrl(); + String GetBasePath(); + String BuildFileName(sal_uInt16& rnLevel, bool& rbRel, const String& rUrl ); + void WriteHyperlinkWithinFly( SvMemoryStream& rStrm, const SwFmtURL* pINetFmtArg); + void PreWriteHyperlinkWithinFly(const SwFrmFmt& rFmt,EscherPropertyContainer& rPropOpt); + private: //No copying SwBasicEscherEx(const SwBasicEscherEx&); Index: sw/source/filter/ww8/wrtw8esh.cxx =================================================================== --- sw/source/filter/ww8/wrtw8esh.cxx (revision 1414498) +++ sw/source/filter/ww8/wrtw8esh.cxx (working copy) @@ -103,12 +103,233 @@ // <-- #include "WW8FFData.hxx" #include +#include +#include +#include +#include +#include "sfx2/sfxsids.hrc" +#include +#include using namespace com::sun::star; using namespace sw::util; using namespace sw::types; using namespace nsFieldFlags; +using ::com::sun::star::uno::Reference; +using ::com::sun::star::uno::UNO_QUERY; +using ::com::sun::star::beans::XPropertySet; +using ::com::sun::star::drawing::XShape; +bool SwBasicEscherEx::IsRelUrl() +{ + SvtSaveOptions aSaveOpt; + bool bRelUrl = false; + SfxMedium * pMedium = rWrt.GetWriter().GetMedia(); + if ( pMedium ) + bRelUrl = pMedium->IsRemote() ? aSaveOpt.IsSaveRelINet() : aSaveOpt.IsSaveRelFSys(); + return bRelUrl; +} + +String SwBasicEscherEx::GetBasePath() +{ + String sDocUrl; + String sBasePath; + SfxMedium * pMedium = rWrt.GetWriter().GetMedia(); + if ( pMedium ) + { + const SfxItemSet* pPItemSet = pMedium->GetItemSet(); + if( pPItemSet ) + { + const SfxStringItem* pPItem = dynamic_cast< const SfxStringItem* >( pPItemSet->GetItem( SID_FILE_NAME ) ); + if ( pPItem ) + sDocUrl = pPItem->GetValue(); + } + } + + sBasePath = sDocUrl.Copy( 0, sDocUrl.SearchBackward( '/' ) + 1 ); + return sBasePath; + +} + +String SwBasicEscherEx::BuildFileName(sal_uInt16& rnLevel, bool& rbRel, const String& rUrl ) +{ + String aDosName( INetURLObject( rUrl ).getFSysPath( INetURLObject::FSYS_DOS ) ); + rnLevel = 0; + rbRel = IsRelUrl(); + + if( rbRel ) + { + // try to convert to relative file name + String aTmpName( aDosName ); + aDosName = INetURLObject::GetRelURL( GetBasePath(), rUrl, + INetURLObject::WAS_ENCODED, INetURLObject::DECODE_WITH_CHARSET ); + + if( aDosName.SearchAscii( INET_FILE_SCHEME ) == 0 ) + { + // not converted to rel -> back to old, return absolute flag + aDosName = aTmpName; + rbRel = false; + } + else if( aDosName.SearchAscii( "./" ) == 0 ) + { + aDosName.Erase( 0, 2 ); + } + else + { + while( aDosName.SearchAndReplaceAscii( "../", String::EmptyString() ) == 0 ) + ++rnLevel; + } + } + return aDosName; +} + +void SwBasicEscherEx::WriteHyperlinkWithinFly( SvMemoryStream& rStrm, const SwFmtURL* pINetFmtArg) +{ + if ( !pINetFmtArg ) return; + + sal_uInt8 maGuidStdLink[ 16 ] ={ + 0xD0, 0xC9, 0xEA, 0x79, 0xF9, 0xBA, 0xCE, 0x11, 0x8C, 0x82, 0x00, 0xAA, 0x00, 0x4B, 0xA9, 0x0B }; + sal_uInt8 maGuidUrlMoniker[ 16 ] = { + 0xE0, 0xC9, 0xEA, 0x79, 0xF9, 0xBA, 0xCE, 0x11, 0x8C, 0x82, 0x00, 0xAA, 0x00, 0x4B, 0xA9, 0x0B }; + + sal_uInt8 maGuidFileMoniker[ 16 ] = { + 0x03, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46 }; + sal_uInt8 maGuidFileTail[] = { + 0xFF, 0xFF, 0xAD, 0xDE, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 + }; + const sal_uInt16 WW8_ID_HLINK = 0x01B8; + const sal_uInt32 WW8_HLINK_BODY = 0x00000001; /// Contains file link or URL. + const sal_uInt32 WW8_HLINK_ABS = 0x00000002; /// Absolute path. + const sal_uInt32 WW8_HLINK_DESCR = 0x00000014; /// Description. + const sal_uInt32 WW8_HLINK_MARK = 0x00000008; /// Text mark. + const sal_uInt32 WW8_HLINK_FRAME = 0x00000080; /// Target frame. + const sal_uInt32 WW8_HLINK_UNC = 0x00000100; /// UNC path. + SvMemoryStream tmpStrm; + String tmpTextMark; + + String rUrl = pINetFmtArg->GetURL(); + String rTarFrm = pINetFmtArg->GetTargetFrameName(); + sal_uInt32 mnFlags = 0; + + INetURLObject aUrlObj( rUrl ); + const INetProtocol eProtocol = aUrlObj.GetProtocol(); + + //Target Frame + if( rTarFrm.Len() > 0 ) + { + SwWW8Writer::WriteLong( tmpStrm, rTarFrm.Len()+1 ); + SwWW8Writer::WriteString16( tmpStrm, rTarFrm, false); + + tmpStrm << sal_uInt16( 0 ); + + mnFlags |= WW8_HLINK_FRAME; + } + + // file link or URL + if( eProtocol == INET_PROT_FILE || (eProtocol == INET_PROT_NOT_VALID && rUrl.GetChar( 0 ) != '#') ) + { + sal_uInt16 nLevel; + bool bRel; + String aFileName( BuildFileName( nLevel, bRel, rUrl )); + + if( !bRel ) + mnFlags |= WW8_HLINK_ABS; + + mnFlags |= WW8_HLINK_BODY; + + tmpStrm.Write( maGuidFileMoniker,sizeof(maGuidFileMoniker) ); + tmpStrm << nLevel; + SwWW8Writer::WriteLong( tmpStrm, aFileName.Len()+1); + SwWW8Writer::WriteString8( tmpStrm, aFileName, true, RTL_TEXTENCODING_MS_1252 ); + tmpStrm.Write( maGuidFileTail,sizeof(maGuidFileTail) ); + + //For UNICODE + SwWW8Writer::WriteLong( tmpStrm, 2*aFileName.Len()+6); + SwWW8Writer::WriteLong( tmpStrm, 2*aFileName.Len()); + tmpStrm << sal_uInt16(0x0003); + SwWW8Writer::WriteString16(tmpStrm, aFileName, false); + } + else if( eProtocol != INET_PROT_NOT_VALID ) + { + tmpStrm.Write( maGuidUrlMoniker,sizeof(maGuidUrlMoniker) ); + SwWW8Writer::WriteLong( tmpStrm, 2*(rUrl.Len()+1)); + + SwWW8Writer::WriteString16(tmpStrm, rUrl, true); + mnFlags |= WW8_HLINK_BODY | WW8_HLINK_ABS; + } + else if( rUrl.GetChar( 0 ) == '#' ) + { + String aTextMark( rUrl.Copy( 1 ) ); + aTextMark.SearchAndReplace( '.', '!' ); + sal_uInt8 tmpLen = aTextMark.Len(); + tmpTextMark = aTextMark; + } + + if( tmpTextMark.Len() == 0 && aUrlObj.HasMark() ) + { + tmpTextMark = aUrlObj.GetMark(); + } + + if( tmpTextMark.Len()>0 ) + { + SwWW8Writer::WriteLong( tmpStrm, tmpTextMark.Len()+1); + SwWW8Writer::WriteString16(tmpStrm, tmpTextMark, true); + + mnFlags |= WW8_HLINK_MARK; + } + + rStrm.Write( maGuidStdLink,16 ); + rStrm << sal_uInt32( 2 ) + << mnFlags; + tmpStrm.Seek( STREAM_SEEK_TO_BEGIN ); + sal_uInt32 nStrmPos = tmpStrm.Tell(); + tmpStrm.Seek( STREAM_SEEK_TO_END ); + sal_uInt32 nStrmSize = tmpStrm.Tell(); + tmpStrm.Seek( nStrmPos ); + sal_uInt32 nLen; + nLen = nStrmSize - nStrmPos; + if(nLen >0) + { + sal_uInt8* pBuffer = new sal_uInt8[ nLen ]; + tmpStrm.Read(pBuffer, nLen); + rStrm.Write( pBuffer, nLen ); + delete[] pBuffer; + } +} +void SwBasicEscherEx::PreWriteHyperlinkWithinFly(const SwFrmFmt& rFmt,EscherPropertyContainer& rPropOpt) +{ + const SfxPoolItem* pItem; + const SwAttrSet& rAttrSet = rFmt.GetAttrSet(); + if (SFX_ITEM_SET == rAttrSet.GetItemState(RES_URL, true, &pItem)) + { + const SwFmtURL *pINetFmt = dynamic_cast(pItem); + if(pINetFmt && pINetFmt->GetURL().Len()>0) + { + SvMemoryStream *rStrm = new SvMemoryStream ; + String tmpstr=pINetFmt->GetURL(); + WriteHyperlinkWithinFly( *rStrm, pINetFmt ); + sal_uInt8* pBuf = (sal_uInt8*) rStrm->GetData(); + sal_uInt32 nSize = rStrm->Seek( STREAM_SEEK_TO_END ); + rPropOpt.AddOpt( ESCHER_Prop_pihlShape, sal_True, nSize, pBuf, nSize ); + sal_uInt32 nValue; + String aNamestr = pINetFmt->GetName(); + if(aNamestr.Len()>0) + { + rPropOpt.AddOpt(ESCHER_Prop_wzName, aNamestr ); + } + if(rPropOpt.GetOpt( ESCHER_Prop_fPrint, nValue)) + { + nValue|=0x03080008; + rPropOpt.AddOpt(ESCHER_Prop_fPrint, nValue ); + } + else + rPropOpt.AddOpt(ESCHER_Prop_fPrint, 0x03080008 ); + } + } +} + //#110185# get a part fix for this type of element bool WW8Export::MiserableFormFieldExportHack(const SwFrmFmt& rFrmFmt) { @@ -1842,6 +2063,8 @@ { rPropOpt.AddOpt( ESCHER_Prop_fPrint, 0x200020 ); } + + PreWriteHyperlinkWithinFly(rFmt,rPropOpt); return nLineWidth; } @@ -1936,6 +2159,8 @@ } } + PreWriteHyperlinkWithinFly(rFmt,rPropOpt); + return nLineWidth; } Index: sw/source/filter/ww8/wrtww8.hxx =================================================================== --- sw/source/filter/ww8/wrtww8.hxx (revision 1414498) +++ sw/source/filter/ww8/wrtww8.hxx (working copy) @@ -901,6 +901,8 @@ using StgWriter::Write; virtual sal_uLong Write( SwPaM&, SfxMedium&, const String* = 0 ); + //Seems not an expected to provide method to access the private member + SfxMedium* GetMedia(){ return mpMedium;}; private: /// No copying. Index: sw/source/filter/ww8/ww8graf.cxx =================================================================== --- sw/source/filter/ww8/ww8graf.cxx (revision 1414498) +++ sw/source/filter/ww8/ww8graf.cxx (working copy) @@ -99,6 +99,11 @@ #include +#include +#include +#include +#include "ww8par2.hxx" + using namespace ::com::sun::star; using namespace sw::types; using namespace sw::util; @@ -2728,6 +2733,39 @@ if (pRecord->bHidden) return 0; + if(pObject) + { + sal_uInt16 nCount = pObject ? pObject->GetUserDataCount() : 0; + if(nCount) + { + String lnName, aObjName, aTarFrm; + for (sal_uInt16 i = 0; i < nCount; i++ ) + { + SdrObjUserData* pData = pObject->GetUserData( i ); + if( pData && pData->GetInventor() == SW_DRAWLAYER + && pData->GetId() == SW_UD_IMAPDATA) + { + SwMacroInfo* macInf = dynamic_cast(pData); + if( macInf->GetShapeId() == pF->nSpId) + { + lnName = macInf->GetHlink(); + aObjName = macInf->GetName(); + aTarFrm = macInf->GetTarFrm(); + break; + } + } + } + SwFmtURL* pFmtURL = new SwFmtURL(); + pFmtURL->SetURL( lnName, false ); + if(aObjName.Len() > 0) + pFmtURL->SetName(aObjName); + if(aTarFrm.Len()>0) + pFmtURL->SetTargetFrameName(aTarFrm); + pFmtURL->SetMap(0); + aFlySet.Put(*pFmtURL); + } + } + // If we are to be "below text" then we are not to be opaque // #i14045# MM If we are in a header or footer then make the object transparent // Not exactly like word but close enough for now Index: sw/source/filter/ww8/ww8par.cxx =================================================================== --- sw/source/filter/ww8/ww8par.cxx (revision 1414498) +++ sw/source/filter/ww8/ww8par.cxx (working copy) @@ -141,7 +141,7 @@ #include #include #endif - +#include #include "WW8Sttbf.hxx" #include "WW8FibData.hxx" #define MM_250 1417 // WW-Default fuer Hor. Seitenraender: 2.5 cm @@ -152,7 +152,248 @@ using namespace sw::types; using namespace nsHdFtFlags; +#define VT_EMPTY 0 +#define VT_I4 3 +#define VT_LPSTR 30 +#define VT_LPWSTR 31 +#define VT_BLOB 65 +#define VT_TYPEMASK 0xFFF +/** Expands to a pointer behind the last element of a STATIC data array (like STL end()). */ +#define STATIC_TABLE_END( array ) ((array)+STATIC_TABLE_SIZE(array)) +/** Expands to the size of a STATIC data array. */ +#define STATIC_TABLE_SIZE( array ) (sizeof(array)/sizeof(*(array))) +SwMacroInfo* GetMacroInfo( SdrObject* pObj, sal_Bool bCreate ) // static +{ + if ( pObj ) + { + sal_uInt16 nCount = pObj->GetUserDataCount(); + for( sal_uInt16 i = 0; i < nCount; i++ ) + { + SdrObjUserData* pData = pObj->GetUserData( i ); + if( pData && pData->GetInventor() == SW_DRAWLAYER + && pData->GetId() == SW_UD_IMAPDATA) + return dynamic_cast(pData); + } + if ( bCreate ) + { + SwMacroInfo* pData = new SwMacroInfo; + pObj->InsertUserData( pData, 0 ); + return pData; + } + } + + return 0; +}; + +void lclGetAbsPath( String& rPath, sal_uInt16 nLevel, SwDocShell* pDocShell) +{ + String aTmpStr; + while( nLevel ) + { + aTmpStr.AppendAscii( "../" ); + --nLevel; + } + if(aTmpStr.Len()) + aTmpStr += rPath; + else + aTmpStr = rPath; + + if(aTmpStr.Len()) + { + bool bWasAbs = false; + rPath = pDocShell->GetMedium()->GetURLObject().smartRel2Abs( aTmpStr, bWasAbs ).GetMainURL( INetURLObject::NO_DECODE ); + // full path as stored in SvxURLField must be encoded + } +} + +void lclIgnoreString32( SvMemoryStream& rStrm, bool b16Bit ) +{ + sal_uInt32 nChars; + rStrm >> nChars; + if( b16Bit ) + nChars *= 2; + rStrm.SeekRel( nChars ); +} + +String SwWW8ImplReader::ReadRawUniString( SvMemoryStream& rStrm,sal_uInt16 nChars, bool b16Bit ) +{ + // Fixed-size characters + const sal_uInt8 WW8_NUL_C = '\x00'; /// NUL chararcter. + const sal_uInt16 WW8_NUL = WW8_NUL_C; /// NUL chararcter (unicode). + String aRet; + sal_Unicode mcNulSubst = '\0'; + + sal_uInt16 nCharsLeft = nChars; + sal_Unicode* pcBuffer = new sal_Unicode[ nCharsLeft + 1 ]; + + sal_Unicode* pcUniChar = pcBuffer; + sal_Unicode* pcEndChar = pcBuffer + nCharsLeft; + + if( b16Bit ) + { + sal_uInt16 nReadChar; + for( ; (pcUniChar < pcEndChar); ++pcUniChar ) + { + rStrm >> (nReadChar); + (*pcUniChar) = (nReadChar == WW8_NUL) ? mcNulSubst : static_cast< sal_Unicode >( nReadChar ); + } + } + else + { + sal_uInt8 nReadChar; + for( ; (pcUniChar < pcEndChar); ++pcUniChar ) + { + rStrm >> nReadChar ; + (*pcUniChar) = (nReadChar == WW8_NUL_C) ? mcNulSubst : static_cast< sal_Unicode >( nReadChar ); + } + } + + *pcEndChar = '\0'; + aRet.Append( pcBuffer ); + delete[] pcBuffer; + return aRet; +} + +void lclAppendString32( String& rString, SvMemoryStream& rStrm, sal_uInt32 nChars, bool b16Bit ) +{ + sal_uInt16 nReadChars = ulimit_cast< sal_uInt16 >( nChars ); + String urlStr = SwWW8ImplReader::ReadRawUniString( rStrm, nReadChars, b16Bit ); + rString.Append( urlStr ); +} + +void lclAppendString32( String& rString, SvMemoryStream& rStrm, bool b16Bit ) +{ + sal_uInt32 nValue; + rStrm >>( nValue ); + lclAppendString32( rString, rStrm, nValue, b16Bit ); +} + +void SwWW8ImplReader::ReadEmbeddedData( SvMemoryStream& rStrm, SwDocShell* pDocShell, struct HyperLinksTable& hlStr) +{ + // (0x01B8) HLINK ------------------------------------------------------------- + const sal_uInt16 WW8_ID_HLINK = 0x01B8; + const sal_uInt32 WW8_HLINK_BODY = 0x00000001; /// Contains file link or URL. + const sal_uInt32 WW8_HLINK_ABS = 0x00000002; /// Absolute path. + const sal_uInt32 WW8_HLINK_DESCR = 0x00000014; /// Description. + const sal_uInt32 WW8_HLINK_MARK = 0x00000008; /// Text mark. + const sal_uInt32 WW8_HLINK_FRAME = 0x00000080; /// Target frame. + const sal_uInt32 WW8_HLINK_UNC = 0x00000100; /// UNC path. + + sal_uInt8 maGuidStdLink[ 16 ] ={ + 0xD0, 0xC9, 0xEA, 0x79, 0xF9, 0xBA, 0xCE, 0x11, 0x8C, 0x82, 0x00, 0xAA, 0x00, 0x4B, 0xA9, 0x0B }; + + sal_uInt8 maGuidUrlMoniker[ 16 ] = { + 0xE0, 0xC9, 0xEA, 0x79, 0xF9, 0xBA, 0xCE, 0x11, 0x8C, 0x82, 0x00, 0xAA, 0x00, 0x4B, 0xA9, 0x0B }; + + sal_uInt8 maGuidFileMoniker[ 16 ] = { + 0x03, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46 }; + + sal_uInt8* aGuid = new sal_uInt8[ 16 ]; + sal_uInt32 nFlags; + + + rStrm.Read( aGuid, 16); + rStrm.SeekRel( 4 ); + rStrm >> nFlags; + + sal_uInt16 nLevel = 0; // counter for level to climb down in path + ::std::auto_ptr< String > xLongName; // link / file name + ::std::auto_ptr< String > xShortName; // 8.3-representation of file name + ::std::auto_ptr< String > xTextMark; // text mark + + // description (ignore) + if( ::get_flag( nFlags, WW8_HLINK_DESCR ) ) + lclIgnoreString32( rStrm, true ); + + // target frame + if( ::get_flag( nFlags, WW8_HLINK_FRAME ) ) + { + ::std::auto_ptr< String > FrmName; + FrmName.reset( new String ); + lclAppendString32(*FrmName , rStrm , true); + hlStr.tarFrm = *FrmName; + } + + // UNC path + if( ::get_flag( nFlags, WW8_HLINK_UNC ) ) + { + xLongName.reset( new String ); + lclAppendString32( *xLongName, rStrm, true ); + lclGetAbsPath( *xLongName, 0 , pDocShell); + } + // file link or URL + else if( ::get_flag( nFlags, WW8_HLINK_BODY ) ) + { + rStrm.Read( aGuid, 16); + + if( (memcmp(aGuid, maGuidFileMoniker, 16) == 0) ) + { + rStrm >> nLevel; + xShortName.reset( new String ); + lclAppendString32( *xShortName,rStrm, false ); + rStrm.SeekRel( 24 ); + + sal_uInt32 nStrLen; + rStrm >> nStrLen; + if( nStrLen ) + { + rStrm >> nStrLen; + nStrLen /= 2; + rStrm.SeekRel( 2 ); + xLongName.reset( new String ); + lclAppendString32( *xLongName, rStrm,nStrLen, true ); + lclGetAbsPath( *xLongName, nLevel, pDocShell); + } + else + lclGetAbsPath( *xShortName, nLevel, pDocShell); + } + else if( (memcmp(aGuid, maGuidUrlMoniker, 16) == 0) ) + { + sal_uInt32 nStrLen; + rStrm >> nStrLen; + nStrLen /= 2; + xLongName.reset( new String ); + lclAppendString32( *xLongName,rStrm, nStrLen, true ); + if( !::get_flag( nFlags, WW8_HLINK_ABS ) ) + lclGetAbsPath( *xLongName, 0 ,pDocShell); + } + else + { + DBG_ERRORFILE( "WW8Hyperlink::ReadEmbeddedData - unknown content GUID" ); + } + } + + // text mark + if( ::get_flag( nFlags, WW8_HLINK_MARK ) ) + { + xTextMark.reset( new String ); + lclAppendString32( *xTextMark, rStrm, true ); + } + + DBG_ASSERT( rStrm.GetRecLeft() == 0, "WW8Hyperlink::ReadEmbeddedData - record size mismatch" ); + + if( !xLongName.get() && xShortName.get() ) + { + xLongName.reset( new String ); + xLongName->Append(*xShortName); + } + else if( !xLongName.get() && xTextMark.get() ) + xLongName.reset( new String ); + + if( xLongName.get() ) + { + if( xTextMark.get() ) + { + if( xLongName->Len() == 0 ) + xTextMark->SearchAndReplaceAll( '!', '.' ); + xLongName->Append( '#' ); + xLongName->Append( *xTextMark ); + } + hlStr.hLinkAddr = *xLongName; + } +} + SwMSDffManager::SwMSDffManager( SwWW8ImplReader& rRdr ) : SvxMSDffManager(*rRdr.pTableStream, rRdr.GetBaseURL(), rRdr.pWwFib->fcDggInfo, rRdr.pDataStream, 0, 0, COL_WHITE, 12, rRdr.pStrm, @@ -752,6 +993,51 @@ delete pImpRec; } + sal_uInt32 nBufferSize = GetPropertyValue( DFF_Prop_pihlShape ); + if( (0 < nBufferSize) && (nBufferSize <= 0xFFFF) && SeekToContent( DFF_Prop_pihlShape, rSt ) ) + { + SvMemoryStream aMemStream; + String aStrURL; + struct HyperLinksTable hlStr; + sal_uInt16 mnRawRecId,mnRawRecSize; + aMemStream << sal_uInt16( 0 ) << static_cast< sal_uInt16 >( nBufferSize ); + + // copy from DFF stream to memory stream + ::std::vector< sal_uInt8 > aBuffer( nBufferSize ); + sal_uInt8* pnData = &aBuffer.front(); + sal_uInt8 mnStreamSize; + if( pnData && rSt.Read( pnData, nBufferSize ) == nBufferSize ) + { + aMemStream.Write( pnData, nBufferSize ); + aMemStream.Seek( STREAM_SEEK_TO_END ); + mnStreamSize = aMemStream.Tell(); + aMemStream.Seek( STREAM_SEEK_TO_BEGIN ); + bool bRet = 4 <= mnStreamSize; + if( bRet ) + aMemStream >> mnRawRecId >> mnRawRecSize; + SwDocShell* pDocShell = rReader.mpDocShell; + if(pDocShell) + { + rReader.ReadEmbeddedData( aMemStream, pDocShell, hlStr); + } + } + + if(pObj && hlStr.hLinkAddr.Len() > 0) + { + SwMacroInfo* pInfo = GetMacroInfo( pObj, true ); + if( pInfo ) + { + pInfo->SetShapeId( rObjData.nShapeId ); + pInfo->SetHlink( hlStr.hLinkAddr ); + if(hlStr.tarFrm.Len() > 0) + pInfo->SetTarFrm( hlStr.tarFrm ); + String aNameStr = GetPropertyString( DFF_Prop_wzName, rSt ); + if(aNameStr.Len() > 0) + pInfo->SetName( aNameStr ); + } + } + } + return pObj; } @@ -5424,3 +5710,20 @@ } /* vi:set tabstop=4 shiftwidth=4 expandtab: */ + +SwMacroInfo::SwMacroInfo() : + SdrObjUserData( SW_DRAWLAYER, SW_UD_IMAPDATA, 0 ) +{ +} + +SwMacroInfo::~SwMacroInfo() +{ +} + +SdrObjUserData* SwMacroInfo::Clone( SdrObject* /*pObj*/ ) const +{ + return new SwMacroInfo( *this ); +} + + + Index: sw/source/filter/ww8/ww8par.hxx =================================================================== --- sw/source/filter/ww8/ww8par.hxx (revision 1414498) +++ sw/source/filter/ww8/ww8par.hxx (working copy) @@ -31,6 +31,10 @@ #include #include // fuer den Attribut Stack +#include +#define SW_DRAWLAYER 0x30334353 +#define SW_UD_IMAPDATA 2 + #include #include #include @@ -365,7 +369,49 @@ SwWW8FltRefStack& operator=(const SwWW8FltRefStack&); }; +template< typename Type > +inline bool get_flag( Type nBitField, Type nMask ) +{ return (nBitField & nMask) != 0; } +template< typename ReturnType, typename Type > +inline ReturnType ulimit_cast( Type nValue, ReturnType nMax ) +{ return static_cast< ReturnType >( ::std::min< Type >( nValue, nMax ) ); } + + +template< typename ReturnType, typename Type > +inline ReturnType ulimit_cast( Type nValue ) +{ return ulimit_cast( nValue, ::std::numeric_limits< ReturnType >::max() ); } + +class SwMacroInfo : public SdrObjUserData +{ +public: + SwMacroInfo(); + virtual ~SwMacroInfo(); + + virtual SdrObjUserData* Clone( SdrObject* pObj ) const; + + + void SetHlink( const rtl::OUString& rHlink ) { maHlink = rHlink; } + const rtl::OUString& GetHlink() const { return maHlink; } + void SetTarFrm( const rtl::OUString& rTarFrm ) { maTarFrm = rTarFrm; } + const rtl::OUString& GetTarFrm() const { return maTarFrm; } + void SetShapeId( const sal_uInt32& rShapeId ) { maShapeId = rShapeId; } + const sal_uInt32& GetShapeId() const { return maShapeId; } + void SetName( const rtl::OUString& rName ) { maNameStr = rName; } + const rtl::OUString& GetName() const { return maNameStr; } + +private: + sal_uInt32 maShapeId; + rtl::OUString maHlink; + rtl::OUString maNameStr; + rtl::OUString maTarFrm; +}; +struct HyperLinksTable +{ + String hLinkAddr; + String tarFrm; +}; + namespace sw { namespace hack @@ -1667,6 +1713,8 @@ CharSet GetCurrentCJKCharSet(); void PostProcessAttrs(); + static void ReadEmbeddedData(SvMemoryStream& rStrm, SwDocShell* pDocShell ,struct HyperLinksTable& hlStr); + static String ReadRawUniString( SvMemoryStream& rStrm,sal_uInt16 nChars, bool b16Bit ); }; bool CanUseRemoteLink(const String &rGrfName);