diff options
Diffstat (limited to 'filter')
-rw-r--r-- | filter/inc/filter/msfilter/mscodec.hxx | 67 | ||||
-rw-r--r-- | filter/source/graphicfilter/itiff/itiff.cxx | 370 | ||||
-rw-r--r-- | filter/source/msfilter/mscodec.cxx | 140 | ||||
-rw-r--r-- | filter/source/msfilter/svdfppt.cxx | 16 | ||||
-rw-r--r-- | filter/source/pdf/impdialog.cxx | 81 | ||||
-rw-r--r-- | filter/source/pdf/impdialog.hrc | 5 | ||||
-rw-r--r-- | filter/source/pdf/impdialog.hxx | 21 | ||||
-rw-r--r-- | filter/source/pdf/impdialog.src | 35 | ||||
-rw-r--r-- | filter/source/pdf/makefile.mk | 1 | ||||
-rw-r--r-- | filter/source/pdf/pdfexport.cxx | 312 | ||||
-rw-r--r-- | filter/source/pdf/pdfexport.hxx | 8 | ||||
-rw-r--r-- | filter/source/pdf/pdffilter.component | 3 | ||||
-rw-r--r-- | filter/source/pdf/pdffilter.cxx | 5 | ||||
-rw-r--r-- | filter/source/pdf/pdffilter.hxx | 1 | ||||
-rw-r--r-- | filter/source/pdf/pdfinteract.cxx | 137 | ||||
-rw-r--r-- | filter/source/pdf/pdfinteract.hxx | 91 | ||||
-rw-r--r-- | filter/source/pdf/pdfuno.cxx | 8 |
17 files changed, 864 insertions, 437 deletions
diff --git a/filter/inc/filter/msfilter/mscodec.hxx b/filter/inc/filter/msfilter/mscodec.hxx index 7bad8af6b788..60e3adf1d5ba 100644 --- a/filter/inc/filter/msfilter/mscodec.hxx +++ b/filter/inc/filter/msfilter/mscodec.hxx @@ -28,8 +28,11 @@ #ifndef SVX_MSCODEC_HXX #define SVX_MSCODEC_HXX -#include "rtl/cipher.h" -#include "rtl/digest.h" +#include <com/sun/star/uno/Sequence.hxx> +#include <com/sun/star/beans/NamedValue.hpp> + +#include <rtl/cipher.h> +#include <rtl/digest.h> #include "filter/msfilter/msfilterdllapi.h" namespace msfilter { @@ -52,6 +55,23 @@ public: */ void InitKey( const sal_uInt8 pnPassData[ 16 ] ); + /** Initializes the algorithm with the encryption data. + + @param aData + The sequence contains the necessary data to initialize + the codec. + */ + sal_Bool InitCodec( const ::com::sun::star::uno::Sequence< ::com::sun::star::beans::NamedValue >& aData ); + + /** Retrieves the encryption data + + @return + The sequence contains the necessary data to initialize + the codec. + */ + ::com::sun::star::uno::Sequence< ::com::sun::star::beans::NamedValue > GetEncryptionData(); + + /** Verifies the validity of the password using the passed key and hash. @precond @@ -105,16 +125,6 @@ public: */ void Skip( sal_Size nBytes ); - // static ----------------------------------------------------------------- - - /** Calculates the 16-bit hash value for the given password. - - The password data may be longer than 16 bytes. The array does not need - to be terminated with a NULL byte (but it can without invalidating the - result). - */ - static sal_uInt16 GetHash( const sal_uInt8* pnPassData, sal_Size nSize ); - protected: sal_uInt8 mpnKey[ 16 ]; /// Encryption key. sal_Size mnOffset; /// Key offset. @@ -185,17 +195,34 @@ public: explicit MSCodec_Std97(); ~MSCodec_Std97(); + /** Initializes the algorithm with the encryption data. + + @param aData + The sequence contains the necessary data to initialize + the codec. + */ + sal_Bool InitCodec( const ::com::sun::star::uno::Sequence< ::com::sun::star::beans::NamedValue >& aData ); + + /** Retrieves the encryption data + + @return + The sequence contains the necessary data to initialize + the codec. + */ + ::com::sun::star::uno::Sequence< ::com::sun::star::beans::NamedValue > GetEncryptionData(); + + /** Initializes the algorithm with the specified password and document ID. @param pPassData Wide character array containing the password. Must be zero terminated, which results in a maximum length of 15 characters. - @param pUnique + @param pDocId Unique document identifier read from or written to the file. */ void InitKey( const sal_uInt16 pPassData[ 16 ], - const sal_uInt8 pUnique[ 16 ] ); + const sal_uInt8 pDocId[ 16 ] ); /** Verifies the validity of the password using the passed salt data. @@ -320,16 +347,26 @@ public: sal_uInt8 pSaltData[16], sal_uInt8 pSaltDigest[16]); -private: + /* allows to get the unique document id from the codec + */ + void GetDocId( sal_uInt8 pDocId[16] ); + void GetDigestFromSalt( const sal_uInt8 pSaltData[16], sal_uInt8 pDigest[16] ); private: + void InitKeyImpl( + const sal_uInt8 pKeyData[64], + const sal_uInt8 pDocId[16] ); + + +private: MSFILTER_DLLPRIVATE MSCodec_Std97( const MSCodec_Std97& ); MSFILTER_DLLPRIVATE MSCodec_Std97& operator=( const MSCodec_Std97& ); rtlCipher m_hCipher; rtlDigest m_hDigest; sal_uInt8 m_pDigestValue[ RTL_DIGEST_LENGTH_MD5 ]; + sal_uInt8 m_pDocId[16]; }; // ============================================================================ diff --git a/filter/source/graphicfilter/itiff/itiff.cxx b/filter/source/graphicfilter/itiff/itiff.cxx index f10b8a15f3ef..6f356b042d28 100644 --- a/filter/source/graphicfilter/itiff/itiff.cxx +++ b/filter/source/graphicfilter/itiff/itiff.cxx @@ -764,245 +764,259 @@ BOOL TIFFReader::ConvertScanline( ULONG nY ) } else if ( nPhotometricInterpretation == 2 && nSamplesPerPixel >= 3 ) { - ULONG nMinMax = nMinSampleValue * 255 / ( nMaxSampleValue - nMinSampleValue ); - for ( nx = 0; nx < nImageWidth; nx++ ) + if ( nMaxSampleValue > nMinSampleValue ) { - if ( nPlanes < 3 ) - { - nRed = GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + 0 ) * nBitsPerSample, nBitsPerSample ); - nGreen = GetBits( pMap[ 1 ], ( nx * nSamplesPerPixel + 1 ) * nBitsPerSample, nBitsPerSample ); - nBlue = GetBits( pMap[ 2 ], ( nx * nSamplesPerPixel + 2 ) * nBitsPerSample, nBitsPerSample ); - } - else + ULONG nMinMax = nMinSampleValue * 255 / ( nMaxSampleValue - nMinSampleValue ); + for ( nx = 0; nx < nImageWidth; nx++ ) { - nRed = GetBits( pMap[ 0 ], nx * nBitsPerSample, nBitsPerSample ); - nGreen = GetBits( pMap[ 1 ], nx * nBitsPerSample, nBitsPerSample ); - nBlue = GetBits( pMap[ 2 ], nx * nBitsPerSample, nBitsPerSample ); + if ( nPlanes < 3 ) + { + nRed = GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + 0 ) * nBitsPerSample, nBitsPerSample ); + nGreen = GetBits( pMap[ 1 ], ( nx * nSamplesPerPixel + 1 ) * nBitsPerSample, nBitsPerSample ); + nBlue = GetBits( pMap[ 2 ], ( nx * nSamplesPerPixel + 2 ) * nBitsPerSample, nBitsPerSample ); + } + else + { + nRed = GetBits( pMap[ 0 ], nx * nBitsPerSample, nBitsPerSample ); + nGreen = GetBits( pMap[ 1 ], nx * nBitsPerSample, nBitsPerSample ); + nBlue = GetBits( pMap[ 2 ], nx * nBitsPerSample, nBitsPerSample ); + } + pAcc->SetPixel( nY, nx, Color( (BYTE)( nRed - nMinMax ), (BYTE)( nGreen - nMinMax ), (BYTE)(nBlue - nMinMax) ) ); } - pAcc->SetPixel( nY, nx, Color( (BYTE)( nRed - nMinMax ), (BYTE)( nGreen - nMinMax ), (BYTE)(nBlue - nMinMax) ) ); } } else if ( nPhotometricInterpretation == 5 && nSamplesPerPixel == 3 ) { - ULONG nMinMax = nMinSampleValue * 255 / ( nMaxSampleValue - nMinSampleValue ); - for ( nx = 0; nx < nImageWidth; nx++ ) + if ( nMaxSampleValue > nMinSampleValue ) { - if ( nPlanes < 3 ) - { - nRed = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 0 ) * nBitsPerSample, nBitsPerSample ); - nGreen = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 1 ) * nBitsPerSample, nBitsPerSample ); - nBlue = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 2 ) * nBitsPerSample, nBitsPerSample ); - } - else + ULONG nMinMax = nMinSampleValue * 255 / ( nMaxSampleValue - nMinSampleValue ); + for ( nx = 0; nx < nImageWidth; nx++ ) { - nRed = GetBits( pMap[ 0 ], nx * nBitsPerSample, nBitsPerSample ); - nGreen = GetBits( pMap[ 1 ], nx * nBitsPerSample, nBitsPerSample ); - nBlue = GetBits( pMap[ 2 ], nx * nBitsPerSample, nBitsPerSample ); + if ( nPlanes < 3 ) + { + nRed = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 0 ) * nBitsPerSample, nBitsPerSample ); + nGreen = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 1 ) * nBitsPerSample, nBitsPerSample ); + nBlue = GetBits( pMap[ 0 ],( nx * nSamplesPerPixel + 2 ) * nBitsPerSample, nBitsPerSample ); + } + else + { + nRed = GetBits( pMap[ 0 ], nx * nBitsPerSample, nBitsPerSample ); + nGreen = GetBits( pMap[ 1 ], nx * nBitsPerSample, nBitsPerSample ); + nBlue = GetBits( pMap[ 2 ], nx * nBitsPerSample, nBitsPerSample ); + } + nRed = 255 - (BYTE)( nRed - nMinMax ); + nGreen = 255 - (BYTE)( nGreen - nMinMax ); + nBlue = 255 - (BYTE)( nBlue - nMinMax ); + pAcc->SetPixel( nY, nx, Color( (BYTE) nRed, (BYTE) nGreen, (BYTE) nBlue ) ); } - nRed = 255 - (BYTE)( nRed - nMinMax ); - nGreen = 255 - (BYTE)( nGreen - nMinMax ); - nBlue = 255 - (BYTE)( nBlue - nMinMax ); - pAcc->SetPixel( nY, nx, Color( (BYTE) nRed, (BYTE) nGreen, (BYTE) nBlue ) ); } } else if( nPhotometricInterpretation == 5 && nSamplesPerPixel == 4 ) { - BYTE nSamp[ 4 ]; - BYTE nSampLast[ 4 ] = { 0, 0, 0, 0 }; - long nBlack; - - for( nx = 0; nx < nImageWidth; nx++ ) + if ( nMaxSampleValue > nMinSampleValue ) { - // sind die Werte als Differenz abgelegt? - if( 2 == nPredictor ) + BYTE nSamp[ 4 ]; + BYTE nSampLast[ 4 ] = { 0, 0, 0, 0 }; + long nBlack; + + for( nx = 0; nx < nImageWidth; nx++ ) { - for( ns = 0; ns < 4; ns++ ) + // sind die Werte als Differenz abgelegt? + if( 2 == nPredictor ) { - if( nPlanes < 3 ) - nSampLast[ ns ] = nSampLast[ ns ] + (BYTE) GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + ns ) * nBitsPerSample, nBitsPerSample ); - else - nSampLast[ ns ] = nSampLast[ ns ] + (BYTE) GetBits( pMap[ ns ], nx * nBitsPerSample, nBitsPerSample ); - nSamp[ ns ] = nSampLast[ ns ]; + for( ns = 0; ns < 4; ns++ ) + { + if( nPlanes < 3 ) + nSampLast[ ns ] = nSampLast[ ns ] + (BYTE) GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + ns ) * nBitsPerSample, nBitsPerSample ); + else + nSampLast[ ns ] = nSampLast[ ns ] + (BYTE) GetBits( pMap[ ns ], nx * nBitsPerSample, nBitsPerSample ); + nSamp[ ns ] = nSampLast[ ns ]; + } } - } - else - { - for( ns = 0; ns < 4; ns++ ) + else { - if( nPlanes < 3 ) - nSamp[ ns ] = (BYTE) GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + ns ) * nBitsPerSample, nBitsPerSample ); - else - nSamp[ ns ]= (BYTE) GetBits( pMap[ ns ], nx * nBitsPerSample, nBitsPerSample ); + for( ns = 0; ns < 4; ns++ ) + { + if( nPlanes < 3 ) + nSamp[ ns ] = (BYTE) GetBits( pMap[ 0 ], ( nx * nSamplesPerPixel + ns ) * nBitsPerSample, nBitsPerSample ); + else + nSamp[ ns ]= (BYTE) GetBits( pMap[ ns ], nx * nBitsPerSample, nBitsPerSample ); + } } + nBlack = nSamp[ 3 ]; + nRed = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 0 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * + 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); + nGreen = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 1 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * + 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); + nBlue = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 2 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * + 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); + pAcc->SetPixel( nY, nx, Color ( (BYTE)nRed, (BYTE)nGreen, (BYTE)nBlue ) ); } - nBlack = nSamp[ 3 ]; - nRed = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 0 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * - 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); - nGreen = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 1 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * - 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); - nBlue = (BYTE) Max( 0L, 255L - ( ( (long) nSamp[ 2 ] + nBlack - ( ( (long) nMinSampleValue ) << 1 ) ) * - 255L/(long)(nMaxSampleValue-nMinSampleValue) ) ); - pAcc->SetPixel( nY, nx, Color ( (BYTE)nRed, (BYTE)nGreen, (BYTE)nBlue ) ); - } } } else if ( nSamplesPerPixel == 1 && ( nPhotometricInterpretation <= 1 || nPhotometricInterpretation == 3 ) ) { - ULONG nMinMax = ( ( 1 << nDstBitsPerPixel ) - 1 ) / ( nMaxSampleValue - nMinSampleValue ); - BYTE* pt = pMap[ 0 ]; - BYTE nShift; - - switch ( nDstBitsPerPixel ) + if ( nMaxSampleValue > nMinSampleValue ) { - case 8 : + ULONG nMinMax = ( ( 1 << nDstBitsPerPixel ) - 1 ) / ( nMaxSampleValue - nMinSampleValue ); + BYTE* pt = pMap[ 0 ]; + BYTE nShift; + + switch ( nDstBitsPerPixel ) { - BYTE nLast; - if ( bByteSwap ) + case 8 : { - if ( nPredictor == 2 ) + BYTE nLast; + if ( bByteSwap ) { - nLast = BYTESWAP( (BYTE)*pt++ ); - for ( nx = 0; nx < nImageWidth; nx++ ) + if ( nPredictor == 2 ) { - pAcc->SetPixel( nY, nx, nLast ); - nLast = nLast + *pt++; + nLast = BYTESWAP( (BYTE)*pt++ ); + for ( nx = 0; nx < nImageWidth; nx++ ) + { + pAcc->SetPixel( nY, nx, nLast ); + nLast = nLast + *pt++; + } } - } - else - { - for ( nx = 0; nx < nImageWidth; nx++ ) + else { - nLast = *pt++; - pAcc->SetPixel( nY, nx, (BYTE)( ( (BYTESWAP((ULONG)nLast ) - nMinSampleValue ) * nMinMax ) ) ); + for ( nx = 0; nx < nImageWidth; nx++ ) + { + nLast = *pt++; + pAcc->SetPixel( nY, nx, (BYTE)( ( (BYTESWAP((ULONG)nLast ) - nMinSampleValue ) * nMinMax ) ) ); + } } } - } - else - { - if ( nPredictor == 2 ) + else { - nLast = *pt++; - for ( nx = 0; nx < nImageWidth; nx++ ) + if ( nPredictor == 2 ) { - pAcc->SetPixel( nY, nx, nLast ); - nLast = nLast + *pt++; + nLast = *pt++; + for ( nx = 0; nx < nImageWidth; nx++ ) + { + pAcc->SetPixel( nY, nx, nLast ); + nLast = nLast + *pt++; + } } - } - else - { - for ( nx = 0; nx < nImageWidth; nx++ ) + else { - pAcc->SetPixel( nY, nx, (BYTE)( ( (ULONG)*pt++ - nMinSampleValue ) * nMinMax ) ); + for ( nx = 0; nx < nImageWidth; nx++ ) + { + pAcc->SetPixel( nY, nx, (BYTE)( ( (ULONG)*pt++ - nMinSampleValue ) * nMinMax ) ); + } } } } - } - break; + break; - case 7 : - case 6 : - case 5 : - case 4 : - case 3 : - case 2 : - { - for ( nx = 0; nx < nImageWidth; nx++ ) + case 7 : + case 6 : + case 5 : + case 4 : + case 3 : + case 2 : { - nVal = ( GetBits( pt, nx * nBitsPerSample, nBitsPerSample ) - nMinSampleValue ) * nMinMax; - pAcc->SetPixel( nY, nx, (BYTE)nVal ); + for ( nx = 0; nx < nImageWidth; nx++ ) + { + nVal = ( GetBits( pt, nx * nBitsPerSample, nBitsPerSample ) - nMinSampleValue ) * nMinMax; + pAcc->SetPixel( nY, nx, (BYTE)nVal ); + } } - } - break; + break; - case 1 : - { - if ( bByteSwap ) + case 1 : { - nx = 0; - nByteCount = ( nImageWidth >> 3 ) + 1; - while ( --nByteCount ) + if ( bByteSwap ) { - nByteVal = *pt++; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, nx++, nByteVal ); - } - if ( nImageWidth & 7 ) - { - nByteVal = *pt++; - while ( nx < nImageWidth ) + nx = 0; + nByteCount = ( nImageWidth >> 3 ) + 1; + while ( --nByteCount ) { + nByteVal = *pt++; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; pAcc->SetPixel( nY, nx++, nByteVal & 1 ); nByteVal >>= 1; + pAcc->SetPixel( nY, nx++, nByteVal ); + } + if ( nImageWidth & 7 ) + { + nByteVal = *pt++; + while ( nx < nImageWidth ) + { + pAcc->SetPixel( nY, nx++, nByteVal & 1 ); + nByteVal >>= 1; + } } } - } - else - { - nx = 7; - nByteCount = ( nImageWidth >> 3 ) + 1; - while ( --nByteCount ) - { - nByteVal = *pt++; - pAcc->SetPixel( nY, nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal & 1 ); - nByteVal >>= 1; - pAcc->SetPixel( nY, --nx, nByteVal ); - nx += 15; - } - if ( nImageWidth & 7 ) + else { - nx -= 7; - nByteVal = *pt++; - nShift = 7; - while ( nx < nImageWidth ) + nx = 7; + nByteCount = ( nImageWidth >> 3 ) + 1; + while ( --nByteCount ) { - pAcc->SetPixel( nY, nx++, ( nByteVal >> nShift ) & 1); + nByteVal = *pt++; + pAcc->SetPixel( nY, nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal & 1 ); + nByteVal >>= 1; + pAcc->SetPixel( nY, --nx, nByteVal ); + nx += 15; + } + if ( nImageWidth & 7 ) + { + nx -= 7; + nByteVal = *pt++; + nShift = 7; + while ( nx < nImageWidth ) + { + pAcc->SetPixel( nY, nx++, ( nByteVal >> nShift ) & 1); + } } } } - } - break; + break; - default : - return FALSE; + default : + return FALSE; + } } } else if ( ( nSamplesPerPixel == 2 ) && ( nBitsPerSample == 8 ) && ( nPlanarConfiguration == 1 ) && ( pColorMap == 0 ) ) // grayscale { - ULONG nMinMax = ( ( 1 << 8 /*nDstBitsPerPixel*/ ) - 1 ) / ( nMaxSampleValue - nMinSampleValue ); - BYTE* pt = pMap[ 0 ]; - if ( nByte1 == 'I' ) - pt++; - for ( nx = 0; nx < nImageWidth; nx++, pt += 2 ) + if ( nMaxSampleValue > nMinSampleValue ) { - pAcc->SetPixel( nY, nx, (BYTE)( ( (ULONG)*pt - nMinSampleValue ) * nMinMax ) ); + ULONG nMinMax = ( ( 1 << 8 /*nDstBitsPerPixel*/ ) - 1 ) / ( nMaxSampleValue - nMinSampleValue ); + BYTE* pt = pMap[ 0 ]; + if ( nByte1 == 'I' ) + pt++; + for ( nx = 0; nx < nImageWidth; nx++, pt += 2 ) + { + pAcc->SetPixel( nY, nx, (BYTE)( ( (ULONG)*pt - nMinSampleValue ) * nMinMax ) ); + } } } else @@ -1207,11 +1221,17 @@ BOOL TIFFReader::ReadTIFF(SvStream & rTIFF, Graphic & rGraphic ) if ( pTIFF->IsEof() ) nNextIfd = 0; } + if ( !nBitsPerSample || ( nBitsPerSample > 32 ) ) + bStatus = FALSE; if ( bStatus ) { if ( nMaxSampleValue == 0 ) - nMaxSampleValue = ( 1 << nBitsPerSample ) - 1; - + { + if ( nBitsPerSample == 32 ) // sj: i93300, compiler bug, 1 << 32 gives 1 one 32bit windows platforms, + nMaxSampleValue = 0xffffffff; // (up from 80286 only the lower 5 bits are used when shifting a 32bit register) + else + nMaxSampleValue = ( 1 << nBitsPerSample ) - 1; + } if ( nPhotometricInterpretation == 2 || nPhotometricInterpretation == 5 || nPhotometricInterpretation == 6 ) nDstBitsPerPixel = 24; else if ( nBitsPerSample*nSamplesPerPixel <= 1 ) diff --git a/filter/source/msfilter/mscodec.cxx b/filter/source/msfilter/mscodec.cxx index de17da6bde59..c6feb4fb57dd 100644 --- a/filter/source/msfilter/mscodec.cxx +++ b/filter/source/msfilter/mscodec.cxx @@ -34,12 +34,16 @@ #include <string.h> #include <tools/solar.h> +#include <comphelper/sequenceashashmap.hxx> +#include <comphelper/docpasswordhelper.hxx> + #define DEBUG_MSO_ENCRYPTION_STD97 0 #if DEBUG_MSO_ENCRYPTION_STD97 #include <stdio.h> #endif +using namespace ::com::sun::star; namespace msfilter { @@ -169,6 +173,37 @@ void MSCodec_Xor95::InitKey( const sal_uInt8 pnPassData[ 16 ] ) } } +sal_Bool MSCodec_Xor95::InitCodec( const uno::Sequence< beans::NamedValue >& aData ) +{ + sal_Bool bResult = sal_False; + + ::comphelper::SequenceAsHashMap aHashData( aData ); + uno::Sequence< sal_Int8 > aKey = aHashData.getUnpackedValueOrDefault( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95EncryptionKey" ) ), uno::Sequence< sal_Int8 >() ); + + if ( aKey.getLength() == 16 ) + { + (void)memcpy( mpnKey, aKey.getConstArray(), 16 ); + bResult = sal_True; + + mnKey = (sal_uInt16)aHashData.getUnpackedValueOrDefault( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95BaseKey" ) ), (sal_Int16)0 ); + mnHash = (sal_uInt16)aHashData.getUnpackedValueOrDefault( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95PasswordHash" ) ), (sal_Int16)0 ); + } + else + OSL_ENSURE( sal_False, "Unexpected key size!\n" ); + + return bResult; +} + +uno::Sequence< beans::NamedValue > MSCodec_Xor95::GetEncryptionData() +{ + ::comphelper::SequenceAsHashMap aHashData; + aHashData[ ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95EncryptionKey" ) ) ] <<= uno::Sequence<sal_Int8>( (sal_Int8*)mpnKey, 16 ); + aHashData[ ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95BaseKey" ) ) ] <<= (sal_Int16)mnKey; + aHashData[ ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XOR95PasswordHash" ) ) ] <<= (sal_Int16)mnHash; + + return aHashData.getAsConstNamedValueList(); +} + bool MSCodec_Xor95::VerifyKey( sal_uInt16 nKey, sal_uInt16 nHash ) const { return (nKey == mnKey) && (nHash == mnHash); @@ -218,11 +253,6 @@ void MSCodec_Xor95::Skip( sal_Size nBytes ) mnOffset = (mnOffset + nBytes) & 0x0F; } -sal_uInt16 MSCodec_Xor95::GetHash( const sal_uInt8* pnPassData, sal_Size nSize ) -{ - return lclGetHash( pnPassData, nSize ); -} - // ============================================================================ MSCodec_Std97::MSCodec_Std97 () @@ -236,15 +266,18 @@ MSCodec_Std97::MSCodec_Std97 () OSL_ASSERT(m_hDigest != 0); (void)memset (m_pDigestValue, 0, sizeof(m_pDigestValue)); + (void)memset (m_pDocId, 0, sizeof(m_pDocId)); } MSCodec_Std97::~MSCodec_Std97 () { (void)memset (m_pDigestValue, 0, sizeof(m_pDigestValue)); + (void)memset (m_pDocId, 0, sizeof(m_pDocId)); rtl_digest_destroy (m_hDigest); rtl_cipher_destroy (m_hCipher); } +#if 0 #if DEBUG_MSO_ENCRYPTION_STD97 static void lcl_PrintKeyData(const sal_uInt8* pKeyData, const char* msg) { @@ -261,6 +294,7 @@ static void lcl_PrintKeyData(const sal_uInt8* /*pKeyData*/, const char* /*msg*/) { } #endif +#endif #if DEBUG_MSO_ENCRYPTION_STD97 static void lcl_PrintDigest(const sal_uInt8* pDigest, const char* msg) @@ -276,65 +310,65 @@ static void lcl_PrintDigest(const sal_uInt8* /*pDigest*/, const char* /*msg*/) } #endif -void MSCodec_Std97::InitKey ( - const sal_uInt16 pPassData[16], - const sal_uInt8 pUnique[16]) +sal_Bool MSCodec_Std97::InitCodec( const uno::Sequence< beans::NamedValue >& aData ) { #if DEBUG_MSO_ENCRYPTION_STD97 - fprintf(stdout, "MSCodec_Std97::InitKey: --begin\n");fflush(stdout); + fprintf(stdout, "MSCodec_Std97::InitCodec: --begin\n");fflush(stdout); #endif - sal_uInt8 pKeyData[64]; - int i, n; + sal_Bool bResult = sal_False; - // Fill PassData into KeyData. - (void)memset (pKeyData, 0, sizeof(pKeyData)); - lcl_PrintKeyData(pKeyData, "initial"); - for (i = 0, n = 16; (i < n) && pPassData[i]; i++) - { - pKeyData[2*i ] = sal::static_int_cast< sal_uInt8 >( - (pPassData[i] >> 0) & 0xff); - pKeyData[2*i + 1] = sal::static_int_cast< sal_uInt8 >( - (pPassData[i] >> 8) & 0xff); - } - pKeyData[2*i] = 0x80; - pKeyData[ 56] = sal::static_int_cast< sal_uInt8 >(i << 4); + ::comphelper::SequenceAsHashMap aHashData( aData ); + uno::Sequence< sal_Int8 > aKey = aHashData.getUnpackedValueOrDefault( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "STD97EncryptionKey" ) ), uno::Sequence< sal_Int8 >() ); - lcl_PrintKeyData(pKeyData, "password data"); - - // Fill raw digest of KeyData into KeyData. - (void)rtl_digest_updateMD5 ( - m_hDigest, pKeyData, sizeof(pKeyData)); - (void)rtl_digest_rawMD5 ( - m_hDigest, pKeyData, RTL_DIGEST_LENGTH_MD5); - - lcl_PrintKeyData(pKeyData, "raw digest of key data"); - - // Update digest with KeyData and Unique. - for (i = 0; i < 16; i++) + if ( aKey.getLength() == RTL_DIGEST_LENGTH_MD5 ) { - rtl_digest_updateMD5 (m_hDigest, pKeyData, 5); - rtl_digest_updateMD5 (m_hDigest, pUnique, 16); + (void)memcpy( m_pDigestValue, aKey.getConstArray(), RTL_DIGEST_LENGTH_MD5 ); + uno::Sequence< sal_Int8 > aUniqueID = aHashData.getUnpackedValueOrDefault( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "STD97UniqueID" ) ), uno::Sequence< sal_Int8 >() ); + if ( aUniqueID.getLength() == 16 ) + { + (void)memcpy( m_pDocId, aUniqueID.getConstArray(), 16 ); + bResult = sal_True; + lcl_PrintDigest(m_pDigestValue, "digest value"); + lcl_PrintDigest(m_pDocId, "DocId value"); + } + else + OSL_ENSURE( sal_False, "Unexpected document ID!\n" ); } + else + OSL_ENSURE( sal_False, "Unexpected key size!\n" ); - // Update digest with padding. - pKeyData[16] = 0x80; - (void)memset (pKeyData + 17, 0, sizeof(pKeyData) - 17); - pKeyData[56] = 0x80; - pKeyData[57] = 0x0a; + return bResult; +} - lcl_PrintKeyData(pKeyData, "update digest with padding"); +uno::Sequence< beans::NamedValue > MSCodec_Std97::GetEncryptionData() +{ + ::comphelper::SequenceAsHashMap aHashData; + aHashData[ ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "STD97EncryptionKey" ) ) ] <<= uno::Sequence< sal_Int8 >( (sal_Int8*)m_pDigestValue, RTL_DIGEST_LENGTH_MD5 ); + aHashData[ ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "STD97UniqueID" ) ) ] <<= uno::Sequence< sal_Int8 >( (sal_Int8*)m_pDocId, 16 ); - rtl_digest_updateMD5 ( - m_hDigest, &(pKeyData[16]), sizeof(pKeyData) - 16); + return aHashData.getAsConstNamedValueList(); +} +void MSCodec_Std97::InitKey ( + const sal_uInt16 pPassData[16], + const sal_uInt8 pDocId[16]) +{ +#if DEBUG_MSO_ENCRYPTION_STD97 + fprintf(stdout, "MSCodec_Std97::InitKey: --begin\n");fflush(stdout); +#endif + uno::Sequence< sal_Int8 > aKey = ::comphelper::DocPasswordHelper::GenerateStd97Key( pPassData, uno::Sequence< sal_Int8 >( (sal_Int8*)pDocId, 16 ) ); // Fill raw digest of above updates into DigestValue. - rtl_digest_rawMD5 ( - m_hDigest, m_pDigestValue, sizeof(m_pDigestValue)); + + if ( aKey.getLength() == sizeof(m_pDigestValue) ) + (void)memcpy ( m_pDigestValue, aKey.getConstArray(), sizeof(m_pDigestValue) ); + else + memset( m_pDigestValue, 0, sizeof(m_pDigestValue) ); lcl_PrintDigest(m_pDigestValue, "digest value"); - // Erase KeyData array and leave. - (void)memset (pKeyData, 0, sizeof(pKeyData)); + (void)memcpy (m_pDocId, pDocId, 16); + + lcl_PrintDigest(m_pDocId, "DocId value"); } bool MSCodec_Std97::VerifyKey ( @@ -411,7 +445,7 @@ bool MSCodec_Std97::InitCipher (sal_uInt32 nCounter) bool MSCodec_Std97::CreateSaltDigest( const sal_uInt8 nSaltData[16], sal_uInt8 nSaltDigest[16] ) { #if DEBUG_MSO_ENCRYPTION_STD97 - lcl_PrintDigest(pSaltData, "salt data"); + lcl_PrintDigest(nSaltData, "salt data"); #endif bool result = false; @@ -528,6 +562,12 @@ void MSCodec_Std97::GetEncryptKey ( } } +void MSCodec_Std97::GetDocId( sal_uInt8 pDocId[16] ) +{ + if ( sizeof( m_pDocId ) == 16 ) + (void)memcpy( pDocId, m_pDocId, 16 ); +} + // ============================================================================ } // namespace svx diff --git a/filter/source/msfilter/svdfppt.cxx b/filter/source/msfilter/svdfppt.cxx index f334c86bbc5f..05f99aa36813 100644 --- a/filter/source/msfilter/svdfppt.cxx +++ b/filter/source/msfilter/svdfppt.cxx @@ -1468,12 +1468,16 @@ SdrPowerPointImport::SdrPowerPointImport( PowerPointImportParam& rParam, const S if ( bOk ) { - // PersistPtrs lesen (alle) - nPersistPtrAnz = aUserEditAtom.nMaxPersistWritten + 1; // 1 mehr, damit ich immer direkt indizieren kann - pPersistPtr = new UINT32[ nPersistPtrAnz ]; // (die fangen naemlich eigentlich bei 1 an) + nPersistPtrAnz = aUserEditAtom.nMaxPersistWritten + 1; + if ( ( nPersistPtrAnz >> 2 ) > nStreamLen ) // sj: at least nPersistPtrAnz is not allowed to be greater than filesize + bOk = FALSE; // (it should not be greater than the PPT_PST_PersistPtrIncrementalBlock, but + // we are reading this block later, so we do not have access yet) + + if ( bOk && ( nPersistPtrAnz < ( SAL_MAX_UINT32 / sizeof( UINT32 ) ) ) ) + pPersistPtr = new (std::nothrow) UINT32[ nPersistPtrAnz ]; if ( !pPersistPtr ) bOk = FALSE; - else + if ( bOk ) { memset( pPersistPtr, 0x00, nPersistPtrAnz * 4 ); @@ -5087,8 +5091,8 @@ void PPTStyleTextPropReader::ReadParaProps( SvStream& rIn, SdrPowerPointImport& rIn >> nCharCount >> aParaPropSet.pParaSet->mnDepth; // Einruecktiefe - aParaPropSet.pParaSet->mnDepth = - std::min(sal_uInt16(9), + aParaPropSet.pParaSet->mnDepth = // taking care of about using not more than 9 outliner levels + std::min(sal_uInt16(8), aParaPropSet.pParaSet->mnDepth); nCharCount--; diff --git a/filter/source/pdf/impdialog.cxx b/filter/source/pdf/impdialog.cxx index bb125bd37a47..1adbbc63619c 100644 --- a/filter/source/pdf/impdialog.cxx +++ b/filter/source/pdf/impdialog.cxx @@ -33,7 +33,9 @@ #include "vcl/svapp.hxx" #include "vcl/msgbox.hxx" #include "sfx2/passwd.hxx" -#include "com/sun/star/uno/Sequence.hxx" + +#include "comphelper/storagehelper.hxx" + #include "com/sun/star/text/XTextRange.hpp" #include "com/sun/star/drawing/XShapes.hpp" #include "com/sun/star/container/XIndexAccess.hpp" @@ -382,8 +384,8 @@ Sequence< PropertyValue > ImpPDFTabDialog::GetFilterData() nElementAdded--; // add the open password - aRet[ aRet.getLength() - nElementAdded ].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "DocumentOpenPassword" ) ); - aRet[ aRet.getLength() - nElementAdded ].Value <<= OUString( msUserPassword ); + aRet[ aRet.getLength() - nElementAdded ].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "PreparedPasswords" ) ); + aRet[ aRet.getLength() - nElementAdded ].Value <<= mxPreparedPasswords; nElementAdded--; //the restrict permission flag (needed to have the scripting consistent with the dialog) @@ -392,8 +394,8 @@ Sequence< PropertyValue > ImpPDFTabDialog::GetFilterData() nElementAdded--; //add the permission password - aRet[ aRet.getLength() - nElementAdded ].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "PermissionPassword" ) ); - aRet[ aRet.getLength() - nElementAdded ].Value <<= OUString( msOwnerPassword ); + aRet[ aRet.getLength() - nElementAdded ].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "PreparedPermissionPassword" ) ); + aRet[ aRet.getLength() - nElementAdded ].Value <<= maPreparedOwnerPassword; nElementAdded--; // this should be the last added... @@ -1017,12 +1019,12 @@ void ImpPDFTabViewerPage::SetFilterConfigItem( const ImpPDFTabDialog* paParent ImpPDFTabSecurityPage::ImpPDFTabSecurityPage( Window* i_pParent, const SfxItemSet& i_rCoreSet ) : SfxTabPage( i_pParent, PDFFilterResId( RID_PDF_TAB_SECURITY ), i_rCoreSet ), - maPbUserPwd( this, PDFFilterResId( BTN_USER_PWD ) ), + maFlGroup( this, PDFFilterResId( FL_PWD_GROUP ) ), + maPbSetPwd( this, PDFFilterResId( BTN_SET_PWD ) ), maFtUserPwd( this, PDFFilterResId( FT_USER_PWD ) ), maUserPwdSet( PDFFilterResId( STR_USER_PWD_SET ) ), maUserPwdUnset( PDFFilterResId( STR_USER_PWD_UNSET ) ), - - maPbOwnerPwd( this, PDFFilterResId( BTN_OWNER_PWD ) ), + maStrSetPwd( PDFFilterResId( STR_SET_PWD ) ), maFtOwnerPwd( this, PDFFilterResId( FT_OWNER_PWD ) ), maOwnerPwdSet( PDFFilterResId( STR_OWNER_PWD_SET ) ), maOwnerPwdUnset( PDFFilterResId( STR_OWNER_PWD_UNSET ) ), @@ -1043,6 +1045,8 @@ ImpPDFTabSecurityPage::ImpPDFTabSecurityPage( Window* i_pParent, maCbEnableAccessibility( this, PDFFilterResId( CB_ENAB_ACCESS ) ), msUserPwdTitle( PDFFilterResId( STR_PDF_EXPORT_UDPWD ) ), + mbHaveOwnerPassword( false ), + mbHaveUserPassword( false ), msOwnerPwdTitle( PDFFilterResId( STR_PDF_EXPORT_ODPWD ) ) { @@ -1081,6 +1085,8 @@ ImpPDFTabSecurityPage::ImpPDFTabSecurityPage( Window* i_pParent, (*pCurrent++)->SetPosPixel( aNewPos ); } } + + maPbSetPwd.SetClickHdl( LINK( this, ImpPDFTabSecurityPage, ClickmaPbSetPwdHdl ) ); } // ----------------------------------------------------------------------------- @@ -1100,13 +1106,11 @@ void ImpPDFTabSecurityPage::GetFilterConfigItem( ImpPDFTabDialog* paParent ) { // please note that in PDF/A-1a mode even if this are copied back, // the security settings are forced disabled in PDFExport::Export - paParent->mbEncrypt = (msUserPassword.Len() > 0); - if( paParent->mbEncrypt ) - paParent->msUserPassword = msUserPassword; + paParent->mbEncrypt = mbHaveUserPassword; + paParent->mxPreparedPasswords = mxPreparedPasswords; - paParent->mbRestrictPermissions = (msOwnerPassword.Len() > 0); - if( msOwnerPassword.Len() > 0 ) - paParent->msOwnerPassword = msOwnerPassword; + paParent->mbRestrictPermissions = mbHaveOwnerPassword; + paParent->maPreparedOwnerPassword = maPreparedOwnerPassword; //verify print status paParent->mnPrint = 0; @@ -1135,10 +1139,6 @@ void ImpPDFTabSecurityPage::GetFilterConfigItem( ImpPDFTabDialog* paParent ) // ----------------------------------------------------------------------------- void ImpPDFTabSecurityPage::SetFilterConfigItem( const ImpPDFTabDialog* paParent ) { - maPbUserPwd.SetClickHdl( LINK( this, ImpPDFTabSecurityPage, ClickmaPbUserPwdHdl ) ); - - maPbOwnerPwd.SetClickHdl( LINK( this, ImpPDFTabSecurityPage, ClickmaPbOwnerPwdHdl ) ); - switch( paParent->mnPrint ) { default: @@ -1184,39 +1184,44 @@ void ImpPDFTabSecurityPage::SetFilterConfigItem( const ImpPDFTabDialog* paParen !( ( ImpPDFTabGeneralPage* )paParent->GetTabPage( RID_PDF_TAB_GENER ) )->IsPdfaSelected() ); } -//method common to both the password entry procedures -void ImpPDFTabSecurityPage::ImplPwdPushButton( const String & i_rDlgTitle, String & io_rDestPassword ) +IMPL_LINK( ImpPDFTabSecurityPage, ClickmaPbSetPwdHdl, void*, EMPTYARG ) { -// string needed: dialog title, message box text, depending on the button clicked - SfxPasswordDialog aPwdDialog( this ); + SfxPasswordDialog aPwdDialog( this, &msUserPwdTitle ); aPwdDialog.SetMinLen( 0 ); - aPwdDialog.ShowExtras( SHOWEXTRAS_CONFIRM ); - aPwdDialog.SetText( i_rDlgTitle ); + aPwdDialog.ShowExtras( SHOWEXTRAS_CONFIRM | SHOWEXTRAS_PASSWORD2 | SHOWEXTRAS_CONFIRM2 ); + aPwdDialog.SetText( maStrSetPwd ); + aPwdDialog.SetGroup2Text( msOwnerPwdTitle ); aPwdDialog.AllowAsciiOnly(); if( aPwdDialog.Execute() == RET_OK ) //OK issued get password and set it - io_rDestPassword = aPwdDialog.GetPassword(); - enablePermissionControls(); -} + { + rtl::OUString aUserPW( aPwdDialog.GetPassword() ); + rtl::OUString aOwnerPW( aPwdDialog.GetPassword2() ); -IMPL_LINK( ImpPDFTabSecurityPage, ClickmaPbUserPwdHdl, void*, EMPTYARG ) -{ - ImplPwdPushButton(msUserPwdTitle, msUserPassword ); - return 0; -} + mbHaveUserPassword = (aUserPW.getLength() != 0); + mbHaveOwnerPassword = (aOwnerPW.getLength() != 0); -IMPL_LINK( ImpPDFTabSecurityPage, ClickmaPbOwnerPwdHdl, void*, EMPTYARG ) -{ - ImplPwdPushButton( msOwnerPwdTitle, msOwnerPassword ); + mxPreparedPasswords = vcl::PDFWriter::InitEncryption( aOwnerPW, aUserPW, true ); + + if( mbHaveOwnerPassword ) + { + maPreparedOwnerPassword = comphelper::OStorageHelper::CreatePackageEncryptionData( aOwnerPW ); + } + else + maPreparedOwnerPassword = Sequence< NamedValue >(); + // trash clear text passwords string memory + rtl_zeroMemory( (void*)aUserPW.getStr(), aUserPW.getLength() ); + rtl_zeroMemory( (void*)aOwnerPW.getStr(), aOwnerPW.getLength() ); + } + enablePermissionControls(); return 0; } void ImpPDFTabSecurityPage::enablePermissionControls() { - maFtUserPwd.SetText( (msUserPassword.Len() > 0 && IsEnabled()) ? maUserPwdSet : maUserPwdUnset ); - - sal_Bool bLocalEnable = (msOwnerPassword.Len() > 0) && IsEnabled(); + maFtUserPwd.SetText( (mbHaveUserPassword && IsEnabled()) ? maUserPwdSet : maUserPwdUnset ); + sal_Bool bLocalEnable = mbHaveOwnerPassword && IsEnabled(); maFtOwnerPwd.SetText( bLocalEnable ? maOwnerPwdSet : maOwnerPwdUnset ); maFlPrintPermissions.Enable( bLocalEnable ); diff --git a/filter/source/pdf/impdialog.hrc b/filter/source/pdf/impdialog.hrc index cc438255650f..dccdc2cad11b 100644 --- a/filter/source/pdf/impdialog.hrc +++ b/filter/source/pdf/impdialog.hrc @@ -144,14 +144,15 @@ #define NUM_BOOKMARKLEVELS 114 //controls for security preferences tab page -#define BTN_USER_PWD 120 +#define FL_PWD_GROUP 119 +#define BTN_SET_PWD 120 #define FT_USER_PWD 121 #define STR_USER_PWD_SET 122 #define STR_USER_PWD_ENC 123 #define STR_USER_PWD_UNSET 124 #define STR_USER_PWD_UNENC 125 +#define STR_SET_PWD 126 -#define BTN_OWNER_PWD 127 #define FT_OWNER_PWD 128 #define STR_OWNER_PWD_SET 129 #define STR_OWNER_PWD_REST 130 diff --git a/filter/source/pdf/impdialog.hxx b/filter/source/pdf/impdialog.hxx index 38da273c2fbd..3fd98c775e0d 100644 --- a/filter/source/pdf/impdialog.hxx +++ b/filter/source/pdf/impdialog.hxx @@ -44,6 +44,8 @@ #include "sfx2/tabdlg.hxx" +#include "com/sun/star/beans/NamedValue.hpp" + // ---------------- // - ImpPDFDialog - // ---------------- @@ -126,14 +128,14 @@ protected: sal_Bool mbFirstPageLeft; sal_Bool mbEncrypt; - String msUserPassword; sal_Bool mbRestrictPermissions; - String msOwnerPassword; + com::sun::star::uno::Sequence< com::sun::star::beans::NamedValue > maPreparedOwnerPassword; sal_Int32 mnPrint; sal_Int32 mnChangesAllowed; sal_Bool mbCanCopyOrExtract; sal_Bool mbCanExtractForAccessibility; + com::sun::star::uno::Reference< com::sun::star::beans::XMaterialHolder > mxPreparedPasswords; sal_Bool mbIsRangeChecked; String msPageRange; @@ -314,12 +316,13 @@ public: //class security tab page class ImpPDFTabSecurityPage : public SfxTabPage { - PushButton maPbUserPwd; + FixedLine maFlGroup; + PushButton maPbSetPwd; FixedText maFtUserPwd; String maUserPwdSet; String maUserPwdUnset; + String maStrSetPwd; - PushButton maPbOwnerPwd; FixedText maFtOwnerPwd; String maOwnerPwdSet; String maOwnerPwdUnset; @@ -339,16 +342,18 @@ class ImpPDFTabSecurityPage : public SfxTabPage CheckBox maCbEnableCopy; CheckBox maCbEnableAccessibility; - String msUserPassword; String msUserPwdTitle; - String msOwnerPassword; + bool mbHaveOwnerPassword; + bool mbHaveUserPassword; + com::sun::star::uno::Sequence< com::sun::star::beans::NamedValue > maPreparedOwnerPassword; String msOwnerPwdTitle; + com::sun::star::uno::Reference< com::sun::star::beans::XMaterialHolder > mxPreparedPasswords; + long nWidth; - DECL_LINK( ClickmaPbUserPwdHdl, void* ); - DECL_LINK( ClickmaPbOwnerPwdHdl, void* ); + DECL_LINK( ClickmaPbSetPwdHdl, void* ); void enablePermissionControls(); diff --git a/filter/source/pdf/impdialog.src b/filter/source/pdf/impdialog.src index 248d7d8491f7..1c941d6a9972 100644 --- a/filter/source/pdf/impdialog.src +++ b/filter/source/pdf/impdialog.src @@ -39,13 +39,13 @@ String STR_PDF_EXPORT //password dialog title String STR_PDF_EXPORT_UDPWD { - Text[ en-US ] = "Set Open Password"; + Text[ en-US ] = "Set open password"; }; //password dialog title String STR_PDF_EXPORT_ODPWD { - Text[ en-US ] = "Set Permission Password"; + Text[ en-US ] = "Set permission password"; }; ////////////////////////////////////////////////////////////// @@ -561,20 +561,29 @@ TabPage RID_PDF_TAB_SECURITY TAB_PDF_SIZE; Hide = TRUE; -////////////////////////////////////// - PushButton BTN_USER_PWD + FixedLine FL_PWD_GROUP + { + Pos = MAP_APPFONT( 5, 5 ); + Size = MAP_APPFONT( 125, 10 ); + Text[ en-US ] = "File encryption and permission"; + }; + PushButton BTN_SET_PWD { - HelpID = "filter:PushButton:RID_PDF_TAB_SECURITY:BTN_USER_PWD"; + HelpID = "filter:PushButton:RID_PDF_TAB_SECURITY:BTN_PWD"; TabStop = TRUE ; Disable = TRUE ; - Pos = MAP_APPFONT ( 12, 5 ) ; + Pos = MAP_APPFONT ( 12, 20 ) ; Size = MAP_APPFONT ( 120 , 13 ) ; - Text[ en-US ] = "Set ~open password..."; + Text[ en-US ] = "Set ~passwords..."; + }; + String STR_SET_PWD + { + Text[ en-US ] = "Set passwords"; }; FixedText FT_USER_PWD { - Pos = MAP_APPFONT(12 , 25 ); + Pos = MAP_APPFONT(12 , 40 ); Size = MAP_APPFONT( 160, 20 ); }; @@ -598,16 +607,6 @@ TabPage RID_PDF_TAB_SECURITY Text [ en-US ] = "PDF document will not be encrypted"; }; - PushButton BTN_OWNER_PWD - { - HelpID = "filter:PushButton:RID_PDF_TAB_SECURITY:BTN_OWNER_PWD"; - TabStop = TRUE ; - Disable = TRUE ; - Pos = MAP_APPFONT ( 12, 45 ) ; - Size = MAP_APPFONT ( 120 , 13 ) ; - Text[ en-US ] = "Set ~permission password..."; - }; - FixedText FT_OWNER_PWD { Pos = MAP_APPFONT( 12 , 65 ); diff --git a/filter/source/pdf/makefile.mk b/filter/source/pdf/makefile.mk index 776729ac0d97..65028c7d5d8d 100644 --- a/filter/source/pdf/makefile.mk +++ b/filter/source/pdf/makefile.mk @@ -47,6 +47,7 @@ SLOFILES= $(SLO)$/pdfuno.obj \ $(SLO)$/pdfdialog.obj \ $(SLO)$/impdialog.obj \ $(SLO)$/pdffilter.obj \ + $(SLO)$/pdfinteract.obj \ $(SLO)$/pdfexport.obj # --- Library ----------------------------------- diff --git a/filter/source/pdf/pdfexport.cxx b/filter/source/pdf/pdfexport.cxx index a8d4e1d0d14c..382dd12eeb83 100644 --- a/filter/source/pdf/pdfexport.cxx +++ b/filter/source/pdf/pdfexport.cxx @@ -32,49 +32,58 @@ #include "impdialog.hxx" #include "pdf.hrc" -#include <tools/urlobj.hxx> -#include <tools/fract.hxx> -#include <tools/poly.hxx> -#include <vcl/mapmod.hxx> -#include <vcl/virdev.hxx> -#include <vcl/metaact.hxx> -#include <vcl/gdimtf.hxx> -#include <vcl/jobset.hxx> -#include <vcl/salbtype.hxx> -#include <vcl/bmpacc.hxx> +#include "tools/urlobj.hxx" +#include "tools/fract.hxx" +#include "tools/poly.hxx" +#include "vcl/mapmod.hxx" +#include "vcl/virdev.hxx" +#include "vcl/metaact.hxx" +#include "vcl/gdimtf.hxx" +#include "vcl/jobset.hxx" +#include "vcl/salbtype.hxx" +#include "vcl/bmpacc.hxx" #include "vcl/svapp.hxx" -#include <toolkit/awt/vclxdevice.hxx> -#include <unotools/localfilehelper.hxx> -#include <unotools/processfactory.hxx> -#include <svtools/FilterConfigItem.hxx> -#include <svtools/filter.hxx> -#include <svl/solar.hrc> -#include <comphelper/string.hxx> -#include <unotools/streamwrap.hxx> -#include <com/sun/star/io/XSeekable.hpp> +#include "toolkit/awt/vclxdevice.hxx" +#include "unotools/localfilehelper.hxx" +#include "unotools/processfactory.hxx" +#include "svtools/FilterConfigItem.hxx" +#include "svtools/filter.hxx" +#include "svl/solar.hrc" +#include "comphelper/string.hxx" +#include "comphelper/storagehelper.hxx" +#include "unotools/streamwrap.hxx" +#include "com/sun/star/io/XSeekable.hpp" + #include "basegfx/polygon/b2dpolygon.hxx" #include "basegfx/polygon/b2dpolypolygon.hxx" #include "basegfx/polygon/b2dpolygontools.hxx" -#include <unotools/saveopt.hxx> // only for testing of relative saving options in PDF - -#include <vcl/graphictools.hxx> -#include <com/sun/star/beans/XPropertySet.hpp> -#include <com/sun/star/awt/Rectangle.hpp> -#include <com/sun/star/awt/XDevice.hpp> -#include <com/sun/star/util/MeasureUnit.hpp> -#include <com/sun/star/frame/XModel.hpp> -#include <com/sun/star/frame/XModuleManager.hpp> -#include <com/sun/star/frame/XStorable.hpp> -#include <com/sun/star/frame/XController.hpp> -#include <com/sun/star/document/XDocumentProperties.hpp> -#include <com/sun/star/document/XDocumentPropertiesSupplier.hpp> -#include <com/sun/star/container/XNameAccess.hpp> -#include <com/sun/star/view/XViewSettingsSupplier.hpp> -#include <unotools/configmgr.hxx> -#include <com/sun/star/lang/XServiceInfo.hpp> -#include <com/sun/star/drawing/XShapes.hpp> -#include <com/sun/star/graphic/XGraphicProvider.hpp> +#include "unotools/saveopt.hxx" // only for testing of relative saving options in PDF + +#include "vcl/graphictools.hxx" +#include "com/sun/star/beans/XPropertySet.hpp" +#include "com/sun/star/awt/Rectangle.hpp" +#include "com/sun/star/awt/XDevice.hpp" +#include "com/sun/star/util/MeasureUnit.hpp" +#include "com/sun/star/frame/XModel.hpp" +#include "com/sun/star/frame/XModuleManager.hpp" +#include "com/sun/star/frame/XStorable.hpp" +#include "com/sun/star/frame/XController.hpp" +#include "com/sun/star/document/XDocumentProperties.hpp" +#include "com/sun/star/document/XDocumentPropertiesSupplier.hpp" +#include "com/sun/star/container/XNameAccess.hpp" +#include "com/sun/star/view/XViewSettingsSupplier.hpp" +#include "com/sun/star/task/XInteractionRequest.hpp" +#include "com/sun/star/task/PDFExportException.hpp" + +#include "unotools/configmgr.hxx" +#include "cppuhelper/exc_hlp.hxx" +#include "cppuhelper/compbase1.hxx" +#include "cppuhelper/basemutex.hxx" + +#include "com/sun/star/lang/XServiceInfo.hpp" +#include "com/sun/star/drawing/XShapes.hpp" +#include "com/sun/star/graphic/XGraphicProvider.hpp" using namespace ::rtl; using namespace ::vcl; @@ -89,10 +98,14 @@ using namespace ::com::sun::star::graphic; // - PDFExport - // ------------- -PDFExport::PDFExport( const Reference< XComponent >& rxSrcDoc, Reference< task::XStatusIndicator >& rxStatusIndicator, const Reference< lang::XMultiServiceFactory >& xFactory ) : +PDFExport::PDFExport( const Reference< XComponent >& rxSrcDoc, + const Reference< task::XStatusIndicator >& rxStatusIndicator, + const Reference< task::XInteractionHandler >& rxIH, + const Reference< lang::XMultiServiceFactory >& xFactory ) : mxSrcDoc ( rxSrcDoc ), mxMSF ( xFactory ), mxStatusIndicator ( rxStatusIndicator ), + mxIH ( rxIH ), mbUseTaggedPDF ( sal_False ), mnPDFTypeSelection ( 0 ), mbExportNotes ( sal_True ), @@ -130,9 +143,7 @@ PDFExport::PDFExport( const Reference< XComponent >& rxSrcDoc, Reference< task:: mbFirstPageLeft ( sal_False ), mbEncrypt ( sal_False ), - msOpenPassword (), mbRestrictPermissions ( sal_False ), - msPermissionPassword (), mnPrintAllowed ( 2 ), mnChangesAllowed ( 4 ), mbCanCopyOrExtract ( sal_True ), @@ -250,12 +261,12 @@ sal_Bool PDFExport::ExportSelection( vcl::PDFWriter& rPDFWriter, Reference< com: class PDFExportStreamDoc : public vcl::PDFOutputStream { - Reference< XComponent > m_xSrcDoc; - rtl::OUString m_aPassWd; + Reference< XComponent > m_xSrcDoc; + Sequence< beans::NamedValue > m_aPreparedPassword; public: - PDFExportStreamDoc( const Reference< XComponent >& xDoc, const rtl::OUString& rPwd ) + PDFExportStreamDoc( const Reference< XComponent >& xDoc, const Sequence<beans::NamedValue>& rPwd ) : m_xSrcDoc( xDoc ), - m_aPassWd( rPwd ) + m_aPreparedPassword( rPwd ) {} virtual ~PDFExportStreamDoc(); @@ -271,15 +282,16 @@ void PDFExportStreamDoc::write( const Reference< XOutputStream >& xStream ) Reference< com::sun::star::frame::XStorable > xStore( m_xSrcDoc, UNO_QUERY ); if( xStore.is() ) { - Sequence< beans::PropertyValue > aArgs( m_aPassWd.getLength() ? 3 : 2 ); + Sequence< beans::PropertyValue > aArgs( 2 + ((m_aPreparedPassword.getLength() > 0) ? 1 : 0) ); aArgs.getArray()[0].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "FilterName" ) ); aArgs.getArray()[1].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "OutputStream" ) ); aArgs.getArray()[1].Value <<= xStream; - if( m_aPassWd.getLength() ) + if( m_aPreparedPassword.getLength() ) { - aArgs.getArray()[2].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "Password" ) ); - aArgs.getArray()[2].Value <<= m_aPassWd; + aArgs.getArray()[2].Name = OUString( RTL_CONSTASCII_USTRINGPARAM( "EncryptionData" ) ); + aArgs.getArray()[2].Value <<= m_aPreparedPassword; } + try { xStore->storeToURL( OUString( RTL_CONSTASCII_USTRINGPARAM( "private:stream" ) ), @@ -390,6 +402,11 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue VCLXDevice* pXDevice = new VCLXDevice; OUString aPageRange; Any aSelection; + PDFWriter::PDFWriterContext aContext; + rtl::OUString aOpenPassword, aPermissionPassword; + Reference< beans::XMaterialHolder > xEnc; + Sequence< beans::NamedValue > aPreparedPermissionPassword; + // getting the string for the creator String aCreator; @@ -408,7 +425,34 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue aCreator.AppendAscii( "Math" ); } - PDFWriter::PDFWriterContext aContext; + Reference< document::XDocumentPropertiesSupplier > xDocumentPropsSupplier( mxSrcDoc, UNO_QUERY ); + if ( xDocumentPropsSupplier.is() ) + { + Reference< document::XDocumentProperties > xDocumentProps( xDocumentPropsSupplier->getDocumentProperties() ); + if ( xDocumentProps.is() ) + { + aContext.DocumentInfo.Title = xDocumentProps->getTitle(); + aContext.DocumentInfo.Author = xDocumentProps->getAuthor(); + aContext.DocumentInfo.Subject = xDocumentProps->getSubject(); + aContext.DocumentInfo.Keywords = ::comphelper::string::convertCommaSeparated(xDocumentProps->getKeywords()); + } + } + // getting the string for the producer + String aProducer; + ::utl::ConfigManager* pMgr = ::utl::ConfigManager::GetConfigManager(); + if ( pMgr ) + { + Any aProductName = pMgr->GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTNAME ); + ::rtl::OUString sProductName; + aProductName >>= sProductName; + aProducer = sProductName; + aProductName = pMgr->GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTVERSION ); + aProductName >>= sProductName; + aProducer.AppendAscii(" "); + aProducer += String( sProductName ); + } + aContext.DocumentInfo.Producer = aProducer; + aContext.DocumentInfo.Creator = aCreator; for( sal_Int32 nData = 0, nDataCount = rFilterData.getLength(); nData < nDataCount; ++nData ) { @@ -482,11 +526,15 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "EncryptFile" ) ) ) rFilterData[ nData ].Value >>= mbEncrypt; else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "DocumentOpenPassword" ) ) ) - rFilterData[ nData ].Value >>= msOpenPassword; + rFilterData[ nData ].Value >>= aOpenPassword; else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "RestrictPermissions" ) ) ) rFilterData[ nData ].Value >>= mbRestrictPermissions; else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "PermissionPassword" ) ) ) - rFilterData[ nData ].Value >>= msPermissionPassword; + rFilterData[ nData ].Value >>= aPermissionPassword; + else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "PreparedPasswords" ) ) ) + rFilterData[ nData ].Value >>= xEnc; + else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "PreparedPermissionPassword" ) ) ) + rFilterData[ nData ].Value >>= aPreparedPermissionPassword; else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "Printing" ) ) ) rFilterData[ nData ].Value >>= mnPrintAllowed; else if ( rFilterData[ nData ].Name == OUString( RTL_CONSTASCII_USTRINGPARAM( "Changes" ) ) ) @@ -521,14 +569,17 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue break; case 1: aContext.Version = PDFWriter::PDF_A_1; -//force the tagged PDF as well + //force the tagged PDF as well mbUseTaggedPDF = sal_True; -//force embedding of standard fonts + //force embedding of standard fonts mbEmbedStandardFonts = sal_True; -//force disabling of form conversion + //force disabling of form conversion mbExportFormFields = sal_False; -// PDF/A does not allow transparencies + // PDF/A does not allow transparencies mbRemoveTransparencies = sal_True; + // no encryption + mbEncrypt = sal_False; + xEnc.clear(); break; } @@ -604,23 +655,17 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue if( aContext.Version != PDFWriter::PDF_A_1 ) { //set values needed in encryption - aContext.Encrypt = mbEncrypt; //set encryption level, fixed, but here it can set by the UI if needed. // true is 128 bit, false 40 //note that in 40 bit mode the UI needs reworking, since the current UI is meaningfull only for //128bit security mode - aContext.Security128bit = sal_True; - -//set the open password - if( aContext.Encrypt && msOpenPassword.getLength() > 0 ) - aContext.UserPassword = msOpenPassword; + aContext.Encryption.Security128bit = sal_True; //set check for permission change password // if not enabled and no permission password, force permissions to default as if PDF where without encryption - if( mbRestrictPermissions && msPermissionPassword.getLength() > 0 ) + if( mbRestrictPermissions && (xEnc.is() || aPermissionPassword.getLength() > 0) ) { - aContext.OwnerPassword = msPermissionPassword; - aContext.Encrypt = sal_True; + mbEncrypt = sal_True; //permission set as desired, done after } else @@ -638,9 +683,9 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue break; default: case 2: - aContext.AccessPermissions.CanPrintFull = sal_True; + aContext.Encryption.CanPrintFull = sal_True; case 1: - aContext.AccessPermissions.CanPrintTheDocument = sal_True; + aContext.Encryption.CanPrintTheDocument = sal_True; break; } @@ -649,26 +694,36 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue case 0: //already in struct PDFSecPermissions CTOR break; case 1: - aContext.AccessPermissions.CanAssemble = sal_True; + aContext.Encryption.CanAssemble = sal_True; break; case 2: - aContext.AccessPermissions.CanFillInteractive = sal_True; + aContext.Encryption.CanFillInteractive = sal_True; break; case 3: - aContext.AccessPermissions.CanAddOrModify = sal_True; + aContext.Encryption.CanAddOrModify = sal_True; break; default: case 4: - aContext.AccessPermissions.CanModifyTheContent = - aContext.AccessPermissions.CanCopyOrExtract = - aContext.AccessPermissions.CanAddOrModify = - aContext.AccessPermissions.CanFillInteractive = sal_True; + aContext.Encryption.CanModifyTheContent = + aContext.Encryption.CanCopyOrExtract = + aContext.Encryption.CanAddOrModify = + aContext.Encryption.CanFillInteractive = sal_True; break; } - aContext.AccessPermissions.CanCopyOrExtract = mbCanCopyOrExtract; - aContext.AccessPermissions.CanExtractForAccessibility = mbCanExtractForAccessibility; + aContext.Encryption.CanCopyOrExtract = mbCanCopyOrExtract; + aContext.Encryption.CanExtractForAccessibility = mbCanExtractForAccessibility; + if( mbEncrypt && ! xEnc.is() ) + xEnc = PDFWriter::InitEncryption( aPermissionPassword, aOpenPassword, aContext.Encryption.Security128bit ); + if( mbEncrypt && aPermissionPassword.getLength() && ! aPreparedPermissionPassword.getLength() ) + aPreparedPermissionPassword = comphelper::OStorageHelper::CreatePackageEncryptionData( aPermissionPassword ); } + // after this point we don't need the legacy clear passwords anymore + // however they are still inside the passed filter data sequence + // which is sadly out out our control + aPermissionPassword = rtl::OUString(); + aOpenPassword = rtl::OUString(); + /* * FIXME: the entries are only implicitly defined by the resource file. Should there * ever be an additional form submit format this could get invalid. @@ -731,7 +786,7 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue //<--- } // all context data set, time to create the printing device - PDFWriter* pPDFWriter = new PDFWriter( aContext ); + PDFWriter* pPDFWriter = new PDFWriter( aContext, xEnc ); OutputDevice* pOut = pPDFWriter->GetReferenceDevice(); vcl::PDFExtOutDevData* pPDFExtOutDevData = NULL; @@ -744,41 +799,10 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue // get mimetype OUString aSrcMimetype = getMimetypeForDocument( mxMSF, mxSrcDoc ); pPDFWriter->AddStream( aSrcMimetype, - new PDFExportStreamDoc( mxSrcDoc, msPermissionPassword ), + new PDFExportStreamDoc( mxSrcDoc, aPreparedPermissionPassword ), false ); } - PDFDocInfo aDocInfo; - Reference< document::XDocumentPropertiesSupplier > xDocumentPropsSupplier( mxSrcDoc, UNO_QUERY ); - if ( xDocumentPropsSupplier.is() ) - { - Reference< document::XDocumentProperties > xDocumentProps( xDocumentPropsSupplier->getDocumentProperties() ); - if ( xDocumentProps.is() ) - { - aDocInfo.Title = xDocumentProps->getTitle(); - aDocInfo.Author = xDocumentProps->getAuthor(); - aDocInfo.Subject = xDocumentProps->getSubject(); - aDocInfo.Keywords = ::comphelper::string::convertCommaSeparated(xDocumentProps->getKeywords()); - } - } - // getting the string for the producer - String aProducer; - ::utl::ConfigManager* pMgr = ::utl::ConfigManager::GetConfigManager(); - if ( pMgr ) - { - Any aProductName = pMgr->GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTNAME ); - ::rtl::OUString sProductName; - aProductName >>= sProductName; - aProducer = sProductName; - aProductName = pMgr->GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTVERSION ); - aProductName >>= sProductName; - aProducer.AppendAscii(" "); - aProducer += String( sProductName ); - } - aDocInfo.Producer = aProducer; - aDocInfo.Creator = aCreator; - - pPDFWriter->SetDocInfo( aDocInfo ); if ( pOut ) { @@ -926,12 +950,59 @@ sal_Bool PDFExport::Export( const OUString& rFile, const Sequence< PropertyValue return bRet; } +namespace +{ + +typedef cppu::WeakComponentImplHelper1< task::XInteractionRequest > PDFErrorRequestBase; + +class PDFErrorRequest : private cppu::BaseMutex, + public PDFErrorRequestBase +{ + task::PDFExportException maExc; +public: + PDFErrorRequest( const task::PDFExportException& i_rExc ); + + // XInteractionRequest + virtual uno::Any SAL_CALL getRequest() throw (uno::RuntimeException); + virtual uno::Sequence< uno::Reference< task::XInteractionContinuation > > SAL_CALL getContinuations() throw (uno::RuntimeException); +}; + +PDFErrorRequest::PDFErrorRequest( const task::PDFExportException& i_rExc ) : + PDFErrorRequestBase( m_aMutex ), + maExc( i_rExc ) +{ +} + +uno::Any SAL_CALL PDFErrorRequest::getRequest() throw (uno::RuntimeException) +{ + osl::MutexGuard const guard( m_aMutex ); + + uno::Any aRet; + aRet <<= maExc; + return aRet; +} + +uno::Sequence< uno::Reference< task::XInteractionContinuation > > SAL_CALL PDFErrorRequest::getContinuations() throw (uno::RuntimeException) +{ + return uno::Sequence< uno::Reference< task::XInteractionContinuation > >(); +} + +} // namespace + void PDFExport::showErrors( const std::set< PDFWriter::ErrorCode >& rErrors ) { - if( ! rErrors.empty() ) + if( ! rErrors.empty() && mxIH.is() ) { - ImplErrorDialog aDlg( rErrors ); - aDlg.Execute(); + task::PDFExportException aExc; + aExc.ErrorCodes.realloc( sal_Int32(rErrors.size()) ); + sal_Int32 i = 0; + for( std::set< PDFWriter::ErrorCode >::const_iterator it = rErrors.begin(); + it != rErrors.end(); ++it, i++ ) + { + aExc.ErrorCodes.getArray()[i] = (sal_Int32)*it; + } + Reference< task::XInteractionRequest > xReq( new PDFErrorRequest( aExc ) ); + mxIH->handle( xReq ); } } @@ -939,8 +1010,15 @@ void PDFExport::showErrors( const std::set< PDFWriter::ErrorCode >& rErrors ) sal_Bool PDFExport::ImplExportPage( PDFWriter& rWriter, PDFExtOutDevData& rPDFExtOutDevData, const GDIMetaFile& rMtf ) { - vcl::PDFWriter::PlayMetafileContext aCtx; + const Size aSizePDF( OutputDevice::LogicToLogic( rMtf.GetPrefSize(), rMtf.GetPrefMapMode(), MAP_POINT ) ); + Point aOrigin; + Rectangle aPageRect( aOrigin, rMtf.GetPrefSize() ); + sal_Bool bRet = sal_True; + + rWriter.NewPage( aSizePDF.Width(), aSizePDF.Height() ); + rWriter.SetMapMode( rMtf.GetPrefMapMode() ); + vcl::PDFWriter::PlayMetafileContext aCtx; GDIMetaFile aMtf; if( mbRemoveTransparencies ) { @@ -957,14 +1035,6 @@ sal_Bool PDFExport::ImplExportPage( PDFWriter& rWriter, PDFExtOutDevData& rPDFEx aCtx.m_nJPEGQuality = mnQuality; - const Size aSizePDF( OutputDevice::LogicToLogic( rMtf.GetPrefSize(), rMtf.GetPrefMapMode(), MAP_POINT ) ); - Point aOrigin; - Rectangle aPageRect( aOrigin, rMtf.GetPrefSize() ); - sal_Bool bRet = sal_True; - - rWriter.NewPage( aSizePDF.Width(), aSizePDF.Height() ); - rWriter.SetMapMode( rMtf.GetPrefMapMode() ); - basegfx::B2DRectangle aB2DRect( aPageRect.Left(), aPageRect.Top(), aPageRect.Right(), aPageRect.Bottom() ); rWriter.SetClipRegion( basegfx::B2DPolyPolygon( basegfx::tools::createPolygonFromRect( aB2DRect ) ) ); diff --git a/filter/source/pdf/pdfexport.hxx b/filter/source/pdf/pdfexport.hxx index 71bee383133c..5b07a50765b1 100644 --- a/filter/source/pdf/pdfexport.hxx +++ b/filter/source/pdf/pdfexport.hxx @@ -56,6 +56,7 @@ private: Reference< XComponent > mxSrcDoc; Reference< lang::XMultiServiceFactory > mxMSF; Reference< task::XStatusIndicator > mxStatusIndicator; + Reference< task::XInteractionHandler > mxIH; sal_Bool mbUseTaggedPDF; sal_Int32 mnPDFTypeSelection; @@ -98,9 +99,7 @@ private: sal_Bool mbFirstPageLeft; sal_Bool mbEncrypt; - rtl::OUString msOpenPassword; sal_Bool mbRestrictPermissions; - rtl::OUString msPermissionPassword; sal_Int32 mnPrintAllowed; sal_Int32 mnChangesAllowed; sal_Bool mbCanCopyOrExtract; @@ -120,7 +119,10 @@ private: void ImplWriteWatermark( ::vcl::PDFWriter& rWriter, const Size& rPageSize ); public: - PDFExport( const Reference< XComponent >& rxSrcDoc, Reference< task::XStatusIndicator >& xStatusIndicator, const Reference< lang::XMultiServiceFactory >& xFact ); + PDFExport( const Reference< XComponent >& rxSrcDoc, + const Reference< task::XStatusIndicator >& xStatusIndicator, + const Reference< task::XInteractionHandler >& xIH, + const Reference< lang::XMultiServiceFactory >& xFact ); ~PDFExport(); sal_Bool ExportSelection( vcl::PDFWriter& rPDFWriter, Reference< com::sun::star::view::XRenderable >& rRenderable, Any& rSelection, diff --git a/filter/source/pdf/pdffilter.component b/filter/source/pdf/pdffilter.component index 36766b61eb97..438d697a77b1 100644 --- a/filter/source/pdf/pdffilter.component +++ b/filter/source/pdf/pdffilter.component @@ -34,4 +34,7 @@ <implementation name="com.sun.star.comp.PDF.PDFFilter"> <service name="com.sun.star.document.PDFFilter"/> </implementation> + <implementation name="com.sun.star.comp.PDF.PDFExportInteractionHandler"> + <service name="com.sun.star.filter.pdfexport.PDFExportInteractionHandler"/> + </implementation> </component> diff --git a/filter/source/pdf/pdffilter.cxx b/filter/source/pdf/pdffilter.cxx index 0c08be6d8a66..0abb2eb1d3da 100644 --- a/filter/source/pdf/pdffilter.cxx +++ b/filter/source/pdf/pdffilter.cxx @@ -60,6 +60,7 @@ sal_Bool PDFFilter::implExport( const Sequence< PropertyValue >& rDescriptor ) const PropertyValue* pValue = rDescriptor.getConstArray(); sal_Bool bRet = sal_False; Reference< task::XStatusIndicator > xStatusIndicator; + Reference< task::XInteractionHandler > xIH; for ( sal_Int32 i = 0 ; ( i < nLength ) && !xOStm.is(); ++i) { @@ -69,6 +70,8 @@ sal_Bool PDFFilter::implExport( const Sequence< PropertyValue >& rDescriptor ) pValue[ i ].Value >>= aFilterData; else if ( pValue[ i ].Name.equalsAscii( "StatusIndicator" ) ) pValue[ i ].Value >>= xStatusIndicator; + else if( pValue[i].Name.equalsAscii( "InteractionHandler" ) ) + pValue[i].Value >>= xIH; } /* we don't get FilterData if we are exporting directly @@ -117,7 +120,7 @@ sal_Bool PDFFilter::implExport( const Sequence< PropertyValue >& rDescriptor ) } if( mxSrcDoc.is() && xOStm.is() ) { - PDFExport aExport( mxSrcDoc, xStatusIndicator, mxMSF ); + PDFExport aExport( mxSrcDoc, xStatusIndicator, xIH, mxMSF ); ::utl::TempFile aTempFile; aTempFile.EnableKillingFile(); diff --git a/filter/source/pdf/pdffilter.hxx b/filter/source/pdf/pdffilter.hxx index b4720c1627c7..ea223496522e 100644 --- a/filter/source/pdf/pdffilter.hxx +++ b/filter/source/pdf/pdffilter.hxx @@ -42,6 +42,7 @@ #include <com/sun/star/beans/XPropertyAccess.hpp> #include <comphelper/property.hxx> #include <com/sun/star/task/XStatusIndicator.hpp> +#include <com/sun/star/task/XInteractionHandler.hpp> #include <osl/diagnose.h> #include <rtl/process.h> diff --git a/filter/source/pdf/pdfinteract.cxx b/filter/source/pdf/pdfinteract.cxx new file mode 100644 index 000000000000..23ea98d6bf51 --- /dev/null +++ b/filter/source/pdf/pdfinteract.cxx @@ -0,0 +1,137 @@ + /************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +// MARKER(update_precomp.py): autogen include statement, do not remove +#include "precompiled_filter.hxx" + +#include "pdfinteract.hxx" +#include "impdialog.hxx" + +#include "com/sun/star/task/XInteractionRequest.hpp" +#include "com/sun/star/task/PDFExportException.hpp" + +// ------------- +// - PDFInteractionHandler - +// ------------- + +PDFInteractionHandler::PDFInteractionHandler( const Reference< XMultiServiceFactory > &rxMSF ) : + mxMSF( rxMSF ) +{ +} + +// ----------------------------------------------------------------------------- + +PDFInteractionHandler::~PDFInteractionHandler() +{ +} + + +void SAL_CALL PDFInteractionHandler::handle( const Reference< task::XInteractionRequest >& i_xRequest ) + throw (RuntimeException) +{ + handleInteractionRequest( i_xRequest ); +} + +sal_Bool SAL_CALL PDFInteractionHandler::handleInteractionRequest( const Reference< task::XInteractionRequest >& i_xRequest ) + throw (RuntimeException) +{ + sal_Bool bHandled = sal_False; + + Any aRequest( i_xRequest->getRequest() ); + task::PDFExportException aExc; + if( aRequest >>= aExc ) + { + std::set< vcl::PDFWriter::ErrorCode > aCodes; + sal_Int32 nCodes = aExc.ErrorCodes.getLength(); + for( sal_Int32 i = 0; i < nCodes; i++ ) + aCodes.insert( (vcl::PDFWriter::ErrorCode)aExc.ErrorCodes.getConstArray()[i] ); + ImplErrorDialog aDlg( aCodes ); + aDlg.Execute(); + bHandled = sal_True; + } + return bHandled; +} + +// ----------------------------------------------------------------------------- + +OUString PDFInteractionHandler_getImplementationName () + throw (RuntimeException) +{ + return OUString ( RTL_CONSTASCII_USTRINGPARAM ( "com.sun.star.comp.PDF.PDFExportInteractionHandler" ) ); +} + +// ----------------------------------------------------------------------------- + +#define SERVICE_NAME "com.sun.star.filter.pdfexport.PDFExportInteractionHandler" + +sal_Bool SAL_CALL PDFInteractionHandler_supportsService( const OUString& ServiceName ) + throw (RuntimeException) +{ + return ServiceName.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM ( SERVICE_NAME ) ); +} + +// ----------------------------------------------------------------------------- + +Sequence< OUString > SAL_CALL PDFInteractionHandler_getSupportedServiceNames( ) throw (RuntimeException) +{ + Sequence < OUString > aRet(1); + OUString* pArray = aRet.getArray(); + pArray[0] = OUString ( RTL_CONSTASCII_USTRINGPARAM ( SERVICE_NAME ) ); + return aRet; +} + +#undef SERVICE_NAME + +// ----------------------------------------------------------------------------- + +Reference< XInterface > SAL_CALL PDFInteractionHandler_createInstance( const Reference< XMultiServiceFactory > & rSMgr) throw( Exception ) +{ + return (cppu::OWeakObject*) new PDFInteractionHandler( rSMgr ); +} + +// ----------------------------------------------------------------------------- + +OUString SAL_CALL PDFInteractionHandler::getImplementationName() + throw (RuntimeException) +{ + return PDFInteractionHandler_getImplementationName(); +} + +// ----------------------------------------------------------------------------- + +sal_Bool SAL_CALL PDFInteractionHandler::supportsService( const OUString& rServiceName ) + throw (RuntimeException) +{ + return PDFInteractionHandler_supportsService( rServiceName ); +} + +// ----------------------------------------------------------------------------- + +::com::sun::star::uno::Sequence< OUString > SAL_CALL PDFInteractionHandler::getSupportedServiceNames( ) throw (RuntimeException) +{ + return PDFInteractionHandler_getSupportedServiceNames(); +} diff --git a/filter/source/pdf/pdfinteract.hxx b/filter/source/pdf/pdfinteract.hxx new file mode 100644 index 000000000000..4cffc70c962a --- /dev/null +++ b/filter/source/pdf/pdfinteract.hxx @@ -0,0 +1,91 @@ +/************************************************************************* + * + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * Copyright 2000, 2010 Oracle and/or its affiliates. + * + * OpenOffice.org - a multi-platform office productivity suite + * + * This file is part of OpenOffice.org. + * + * OpenOffice.org is free software: you can redistribute it and/or modify + * it under the terms of the GNU Lesser General Public License version 3 + * only, as published by the Free Software Foundation. + * + * OpenOffice.org is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Lesser General Public License version 3 for more details + * (a copy is included in the LICENSE file that accompanied this code). + * + * You should have received a copy of the GNU Lesser General Public License + * version 3 along with OpenOffice.org. If not, see + * <http://www.openoffice.org/license.html> + * for a copy of the LGPLv3 License. + * + ************************************************************************/ + +#ifndef PDFINTERACT_HXX +#define PDFINTERACT_HXX + +#include "com/sun/star/lang/XServiceInfo.hpp" +#include "cppuhelper/implbase2.hxx" +#include "com/sun/star/lang/XMultiServiceFactory.hpp" +#include "com/sun/star/task/XInteractionHandler2.hpp" + +using namespace ::rtl; +using namespace ::com::sun::star; +using namespace ::com::sun::star::uno; +using namespace ::com::sun::star::lang; + +// ------------- +// - PDFFilter - +// ------------- + +class PDFInteractionHandler : public cppu::WeakImplHelper2 < task::XInteractionHandler2, + XServiceInfo > +{ +private: + + Reference< XMultiServiceFactory > mxMSF; + +protected: + // XServiceInfo + virtual OUString SAL_CALL getImplementationName() throw(RuntimeException); + virtual sal_Bool SAL_CALL supportsService( const OUString& ServiceName ) throw(RuntimeException); + virtual Sequence< OUString > SAL_CALL getSupportedServiceNames() throw(RuntimeException); + + // XIniteractionHandler + virtual void SAL_CALL handle( const Reference< task::XInteractionRequest >& ) throw(RuntimeException); + + // XIniteractionHandler2 + virtual sal_Bool SAL_CALL handleInteractionRequest( const Reference< task::XInteractionRequest >& ) throw(RuntimeException); +public: + + PDFInteractionHandler( const Reference< XMultiServiceFactory >& rxMSF ); + virtual ~PDFInteractionHandler(); +}; + +// ----------------------------------------------------------------------------- + +OUString PDFInteractionHandler_getImplementationName () + throw ( RuntimeException ); + +// ----------------------------------------------------------------------------- + +sal_Bool SAL_CALL PDFInteractionHandler_supportsService( const OUString& ServiceName ) + throw ( RuntimeException ); + +// ----------------------------------------------------------------------------- + +Sequence< OUString > SAL_CALL PDFInteractionHandler_getSupportedServiceNames( ) + throw ( RuntimeException ); + +// ----------------------------------------------------------------------------- + +Reference< XInterface > +SAL_CALL PDFInteractionHandler_createInstance( const Reference< XMultiServiceFactory > & rSMgr) + throw ( Exception ); + +#endif // PDFINTERACT_HXX + diff --git a/filter/source/pdf/pdfuno.cxx b/filter/source/pdf/pdfuno.cxx index 78bfff4c89f7..69b3d7a1ebc2 100644 --- a/filter/source/pdf/pdfuno.cxx +++ b/filter/source/pdf/pdfuno.cxx @@ -36,6 +36,7 @@ #include <pdffilter.hxx> #include <pdfdialog.hxx> +#include <pdfinteract.hxx> using namespace ::rtl; using namespace ::cppu; @@ -76,6 +77,13 @@ extern "C" PDFDialog_createInstance, PDFDialog_getSupportedServiceNames() ); } + else if( aImplName.equals( PDFInteractionHandler_getImplementationName() ) ) + { + xFactory = createSingleFactory( reinterpret_cast< XMultiServiceFactory* >( pServiceManager ), + OUString::createFromAscii( pImplName ), + PDFInteractionHandler_createInstance, PDFInteractionHandler_getSupportedServiceNames() ); + + } if( xFactory.is() ) { |