LibreOffice Module sfx2 (master) 1
graphhelp.cxx
Go to the documentation of this file.
1/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2/*
3 * This file is part of the LibreOffice project.
4 *
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 *
9 * This file incorporates work covered by the following license notice:
10 *
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 */
19
20
21#ifdef _WIN32
22#include <prewin.h>
23#include <postwin.h>
24#endif
25
26#include <com/sun/star/uno/Exception.hpp>
27#include <com/sun/star/graphic/GraphicProvider.hpp>
28#include <com/sun/star/graphic/XGraphicProvider.hpp>
29#include <com/sun/star/graphic/XGraphic.hpp>
30
31
32#include <vcl/gdimtf.hxx>
33#include <vcl/graph.hxx>
34#include <vcl/cvtgrf.hxx>
35#include <vcl/bitmapex.hxx>
36#include <vcl/graphicfilter.hxx>
37
38#include <tools/stream.hxx>
43#include <o3tl/string_view.hxx>
44
45#include "graphhelp.hxx"
46#include <bitmaps.hlst>
47
48#include <memory>
49
50#if defined _WIN32
51#include <unotools/tempfile.hxx>
52#include <vcl/outdev.hxx>
53#endif
54
55using namespace css;
56
57std::unique_ptr<SvMemoryStream> GraphicHelper::getFormatStrFromGDI_Impl( const GDIMetaFile* pGDIMeta, ConvertDataFormat nFormat )
58{
59 std::unique_ptr<SvMemoryStream> pResult;
60 if ( pGDIMeta )
61 {
62 std::unique_ptr<SvMemoryStream> pStream(new SvMemoryStream( 65535, 65535 ));
63 Graphic aGraph( *pGDIMeta );
64 if ( GraphicConverter::Export( *pStream, aGraph, nFormat ) == ERRCODE_NONE )
65 pResult = std::move(pStream);
66 }
67
68 return pResult;
69}
70
71
72// static
73void* GraphicHelper::getEnhMetaFileFromGDI_Impl( const GDIMetaFile* pGDIMeta )
74{
75 void* pResult = nullptr;
76
77#ifdef _WIN32
78 if ( pGDIMeta )
79 {
80 ::utl::TempFileNamed aTempFile( u"", true, u".emf" );
81
82 OUString aMetaFile = aTempFile.GetFileName();
83 OUString aMetaURL = aTempFile.GetURL();
84
85 std::unique_ptr<SvStream> pStream = ::utl::UcbStreamHelper::CreateStream( aMetaURL, StreamMode::STD_READWRITE );
86 if ( pStream )
87 {
88 Graphic aGraph( *pGDIMeta );
89 ErrCode nFailed = GraphicConverter::Export( *pStream, aGraph, ConvertDataFormat::EMF );
90 pStream->Flush();
91 pStream.reset();
92
93 if ( !nFailed )
94 pResult = GetEnhMetaFileW( o3tl::toW(aMetaFile.getStr()) );
95 }
96 }
97#else
98 (void)pGDIMeta; // unused
99#endif
100
101 return pResult;
102}
103
104
105// static
106void* GraphicHelper::getWinMetaFileFromGDI_Impl( const GDIMetaFile* pGDIMeta, const Size& aMetaSize )
107{
108 void* pResult = nullptr;
109
110#ifdef _WIN32
111 if ( pGDIMeta )
112 {
113 SvMemoryStream pStream( 65535, 65535 );
114 Graphic aGraph( *pGDIMeta );
115 ErrCode nFailed = GraphicConverter::Export( pStream, aGraph, ConvertDataFormat::WMF );
116 pStream.Flush();
117 if ( !nFailed )
118 {
119 sal_Int32 nLength = pStream.TellEnd();
120 if ( nLength > 22 )
121 {
122 HMETAFILE hMeta = SetMetaFileBitsEx( nLength - 22,
123 static_cast< const unsigned char*>( pStream.GetData() ) + 22 );
124
125 if ( hMeta )
126 {
127 HGLOBAL hMemory = GlobalAlloc( GMEM_DDESHARE | GMEM_MOVEABLE, sizeof( METAFILEPICT ) );
128
129 if ( hMemory )
130 {
131 METAFILEPICT* pMF = static_cast<METAFILEPICT*>(GlobalLock( hMemory ));
132
133 pMF->hMF = hMeta;
134 pMF->mm = MM_ANISOTROPIC;
135
136 MapMode aWinMode( MapUnit::Map100thMM );
137
138 if ( aWinMode == pGDIMeta->GetPrefMapMode() )
139 {
140 pMF->xExt = aMetaSize.Width();
141 pMF->yExt = aMetaSize.Height();
142 }
143 else
144 {
145 Size aWinSize = OutputDevice::LogicToLogic( Size( aMetaSize.Width(), aMetaSize.Height() ),
146 pGDIMeta->GetPrefMapMode(),
147 aWinMode );
148 pMF->xExt = aWinSize.Width();
149 pMF->yExt = aWinSize.Height();
150 }
151
152 GlobalUnlock( hMemory );
153 pResult = static_cast<void*>(hMemory);
154 }
155 else
156 DeleteMetaFile( hMeta );
157 }
158 }
159 }
160 }
161#else
162 (void)pGDIMeta; // unused
163 (void)aMetaSize; // unused
164#endif
165
166
167 return pResult;
168}
169
170
171// static
172bool GraphicHelper::getThumbnailFormatFromBitmap_Impl(const BitmapEx& rBitmap, const uno::Reference<io::XStream>& xStream)
173{
174 if (rBitmap.IsEmpty() || !xStream.is())
175 return false;
176
177 std::unique_ptr<SvStream> pStream(utl::UcbStreamHelper::CreateStream(xStream));
178
179 if (pStream->GetError())
180 return false;
181
182 BitmapEx bitmap(rBitmap);
183 bitmap.Convert(BmpConversion::N8BitColors);
184
186
187 if (rFilter.compressAsPNG(bitmap, *pStream) != ERRCODE_NONE)
188 return false;
189
190 pStream->FlushBuffer();
191
192 return !pStream->GetError();
193}
194
195// static
196bool GraphicHelper::getThumbnailReplacement_Impl(std::u16string_view rResID, const uno::Reference< io::XStream >& xStream )
197{
198 bool bResult = false;
199 if (!rResID.empty() && xStream.is())
200 {
201 uno::Reference< uno::XComponentContext > xContext = ::comphelper::getProcessComponentContext();
202 try
203 {
204 uno::Reference< graphic::XGraphicProvider > xGraphProvider(graphic::GraphicProvider::create(xContext));
205 const OUString aURL{OUString::Concat("private:graphicrepository/") + rResID};
206
207 uno::Sequence< beans::PropertyValue > aMediaProps{ comphelper::makePropertyValue("URL",
208 aURL) };
209
210 uno::Reference< graphic::XGraphic > xGraphic = xGraphProvider->queryGraphic( aMediaProps );
211 if ( xGraphic.is() )
212 {
213 uno::Sequence< beans::PropertyValue > aStoreProps{
214 comphelper::makePropertyValue("OutputStream", xStream),
215 comphelper::makePropertyValue("MimeType", OUString("image/png"))
216 };
217
218 xGraphProvider->storeGraphic( xGraphic, aStoreProps );
219 bResult = true;
220 }
221 }
222 catch(const uno::Exception&)
223 {
224 }
225 }
226
227 return bResult;
228}
229
230// static
231OUString GraphicHelper::getThumbnailReplacementIDByFactoryName_Impl( std::u16string_view aFactoryShortName )
232{
233 OUString sResult;
234
235 if ( aFactoryShortName == u"scalc" )
236 {
237 sResult = BMP_128X128_CALC_DOC;
238 }
239 else if ( aFactoryShortName == u"sdraw" )
240 {
241 sResult = BMP_128X128_DRAW_DOC;
242 }
243 else if ( aFactoryShortName == u"simpress" )
244 {
245 sResult = BMP_128X128_IMPRESS_DOC;
246 }
247 else if ( aFactoryShortName == u"smath" )
248 {
249 sResult = BMP_128X128_MATH_DOC;
250 }
251 else if ( aFactoryShortName == u"swriter" || o3tl::starts_with(aFactoryShortName, u"swriter/") )
252 {
253 sResult = BMP_128X128_WRITER_DOC;
254 }
255
256 return sResult;
257}
258
259/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
Reference< XInputStream > xStream
bool IsEmpty() const
const MapMode & GetPrefMapMode() const
static ErrCode Export(SvStream &rOStm, const Graphic &rGraphic, ConvertDataFormat nFormat)
static GraphicFilter & GetGraphicFilter()
ErrCode compressAsPNG(const Graphic &rGraphic, SvStream &rOutputStream)
SAL_WARN_UNUSED_RESULT Point LogicToLogic(const Point &rPtSource, const MapMode *pMapModeSource, const MapMode *pMapModeDest) const
constexpr tools::Long Height() const
constexpr tools::Long Width() const
static std::unique_ptr< SvStream > CreateStream(const OUString &rFileName, StreamMode eOpenMode, css::uno::Reference< css::awt::XWindow > xParentWin=nullptr)
URL aURL
css::beans::PropertyValue makePropertyValue(const OUString &rName, T &&rValue)
MM_ANISOTROPIC
constexpr bool starts_with(std::basic_string_view< charT, traits > sv, std::basic_string_view< charT, traits > x) noexcept
ConvertDataFormat
sal_Int32 nLength