Line data Source code
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 : #include <hintids.hxx>
21 : #include <tools/helpers.hxx>
22 : #include <tools/urlobj.hxx>
23 : #include <svl/undo.hxx>
24 : #include <svl/fstathelper.hxx>
25 : #include <svtools/imap.hxx>
26 : #include <vcl/graphicfilter.hxx>
27 : #include <sot/storage.hxx>
28 : #include <sfx2/docfile.hxx>
29 : #include <sfx2/linkmgr.hxx>
30 : #include <editeng/boxitem.hxx>
31 : #include <sot/formats.hxx>
32 : #include <fmtfsize.hxx>
33 : #include <fmturl.hxx>
34 : #include <frmfmt.hxx>
35 : #include <doc.hxx>
36 : #include <frmatr.hxx>
37 : #include <grfatr.hxx>
38 : #include <swtypes.hxx>
39 : #include <ndgrf.hxx>
40 : #include <fmtcol.hxx>
41 : #include <hints.hxx>
42 : #include <swbaslnk.hxx>
43 : #include <pagefrm.hxx>
44 : #include <editsh.hxx>
45 : #include <pam.hxx>
46 :
47 : #include <rtl/ustring.hxx>
48 : #include <unotools/ucbstreamhelper.hxx>
49 : #include <com/sun/star/embed/ElementModes.hpp>
50 : #include <com/sun/star/embed/XTransactedObject.hpp>
51 : #include <vcl/svapp.hxx>
52 : #include <com/sun/star/io/XSeekable.hpp>
53 : #include <retrieveinputstreamconsumer.hxx>
54 : #include <drawinglayer/processor2d/objectinfoextractor2d.hxx>
55 : #include <drawinglayer/primitive2d/objectinfoprimitive2d.hxx>
56 :
57 : using namespace com::sun::star;
58 :
59 0 : SwGrfNode::SwGrfNode(
60 : const SwNodeIndex & rWhere,
61 : const OUString& rGrfName, const OUString& rFltName,
62 : const Graphic* pGraphic,
63 : SwGrfFmtColl *pGrfColl,
64 : SwAttrSet* pAutoAttr ) :
65 : SwNoTxtNode( rWhere, ND_GRFNODE, pGrfColl, pAutoAttr ),
66 : maGrfObj(),
67 : mpReplacementGraphic(0),
68 : // #i73788#
69 : mbLinkedInputStreamReady( false ),
70 0 : mbIsStreamReadOnly( false )
71 : {
72 0 : maGrfObj.SetSwapStreamHdl( LINK(this, SwGrfNode, SwapGraphic) );
73 : bInSwapIn = bChgTwipSize = bChgTwipSizeFromPixel =
74 0 : bFrameInPaint = bScaleImageMap = false;
75 :
76 0 : bGraphicArrived = true;
77 :
78 : // fdo#50763 inline image has already been read into memory
79 0 : if (rGrfName.startsWith("data:")) {
80 0 : maGrfObj.SetGraphic( *pGraphic, rGrfName );
81 : }
82 : else {
83 0 : ReRead(rGrfName,rFltName, pGraphic, 0, false);
84 : }
85 0 : }
86 :
87 0 : SwGrfNode::SwGrfNode( const SwNodeIndex & rWhere,
88 : const GraphicObject& rGrfObj,
89 : SwGrfFmtColl *pGrfColl, SwAttrSet* pAutoAttr ) :
90 : SwNoTxtNode( rWhere, ND_GRFNODE, pGrfColl, pAutoAttr ),
91 : maGrfObj(rGrfObj),
92 : mpReplacementGraphic(0),
93 : // #i73788#
94 : mbLinkedInputStreamReady( false ),
95 0 : mbIsStreamReadOnly( false )
96 : {
97 0 : maGrfObj.SetSwapStreamHdl( LINK(this, SwGrfNode, SwapGraphic) );
98 0 : if( rGrfObj.HasUserData() && rGrfObj.IsSwappedOut() )
99 0 : maGrfObj.SetSwapState();
100 : bInSwapIn = bChgTwipSize = bChgTwipSizeFromPixel =
101 0 : bFrameInPaint = bScaleImageMap = false;
102 0 : bGraphicArrived = true;
103 0 : }
104 :
105 : /** Create new SW/G reader.
106 : *
107 : * Use this ctor if you want to read a linked graphic.
108 : *
109 : * @note Does not read/open the image itself!
110 : */
111 0 : SwGrfNode::SwGrfNode( const SwNodeIndex & rWhere,
112 : const OUString& rGrfName, const OUString& rFltName,
113 : SwGrfFmtColl *pGrfColl,
114 : SwAttrSet* pAutoAttr ) :
115 : SwNoTxtNode( rWhere, ND_GRFNODE, pGrfColl, pAutoAttr ),
116 : maGrfObj(),
117 : mpReplacementGraphic(0),
118 : // #i73788#
119 : mbLinkedInputStreamReady( false ),
120 0 : mbIsStreamReadOnly( false )
121 : {
122 0 : maGrfObj.SetSwapStreamHdl( LINK(this, SwGrfNode, SwapGraphic) );
123 :
124 0 : Graphic aGrf; aGrf.SetDefaultType();
125 0 : maGrfObj.SetGraphic( aGrf, rGrfName );
126 :
127 : bInSwapIn = bChgTwipSize = bChgTwipSizeFromPixel =
128 0 : bFrameInPaint = bScaleImageMap = false;
129 0 : bGraphicArrived = true;
130 :
131 0 : InsertLink( rGrfName, rFltName );
132 0 : if( IsLinkedFile() )
133 : {
134 0 : INetURLObject aUrl( rGrfName );
135 0 : if( INET_PROT_FILE == aUrl.GetProtocol() &&
136 0 : FStatHelper::IsDocument( aUrl.GetMainURL( INetURLObject::NO_DECODE ) ))
137 : {
138 : // file exists, so create connection without an update
139 0 : ((SwBaseLink*)&refLink)->Connect();
140 0 : }
141 0 : }
142 0 : }
143 :
144 0 : bool SwGrfNode::ReRead(
145 : const OUString& rGrfName, const OUString& rFltName,
146 : const Graphic* pGraphic, const GraphicObject* pGrfObj,
147 : bool bNewGrf )
148 : {
149 0 : bool bReadGrf = false;
150 0 : bool bSetTwipSize = true;
151 0 : delete mpReplacementGraphic;
152 0 : mpReplacementGraphic = 0;
153 :
154 : OSL_ENSURE( pGraphic || pGrfObj || !rGrfName.isEmpty(),
155 : "GraphicNode without a name, Graphic or GraphicObject" );
156 :
157 : // with name
158 0 : if( refLink.Is() )
159 : {
160 : OSL_ENSURE( !bInSwapIn, "ReRead: I am still in SwapIn" );
161 :
162 0 : if( !rGrfName.isEmpty() )
163 : {
164 : // Note: If there is DDE in the FltName, than it is a DDE-linked graphic
165 0 : OUString sCmd( rGrfName );
166 0 : if( !rFltName.isEmpty() )
167 : {
168 : sal_uInt16 nNewType;
169 0 : if( rFltName == "DDE" )
170 0 : nNewType = OBJECT_CLIENT_DDE;
171 : else
172 : {
173 0 : sfx2::MakeLnkName( sCmd, 0, rGrfName, OUString(), &rFltName );
174 0 : nNewType = OBJECT_CLIENT_GRF;
175 : }
176 :
177 0 : if( nNewType != refLink->GetObjType() )
178 : {
179 0 : refLink->Disconnect();
180 0 : ((SwBaseLink*)&refLink)->SetObjType( nNewType );
181 : }
182 : }
183 :
184 0 : refLink->SetLinkSourceName( sCmd );
185 : }
186 : else // no name anymore, so remove link
187 : {
188 0 : GetDoc()->GetLinkManager().Remove( refLink );
189 0 : refLink.Clear();
190 : }
191 :
192 0 : if( pGraphic )
193 : {
194 0 : maGrfObj.SetGraphic( *pGraphic, rGrfName );
195 0 : onGraphicChanged();
196 0 : bReadGrf = true;
197 : }
198 0 : else if( pGrfObj )
199 : {
200 0 : maGrfObj = *pGrfObj;
201 0 : if( pGrfObj->HasUserData() && pGrfObj->IsSwappedOut() )
202 0 : maGrfObj.SetSwapState();
203 0 : maGrfObj.SetLink( rGrfName );
204 0 : onGraphicChanged();
205 0 : bReadGrf = true;
206 : }
207 : else
208 : {
209 : // reset data of the old graphic so that the correct placeholder is
210 : // shown in case the new link could not be loaded
211 0 : Graphic aGrf; aGrf.SetDefaultType();
212 0 : maGrfObj.SetGraphic( aGrf, rGrfName );
213 :
214 0 : if( refLink.Is() )
215 : {
216 0 : if( getLayoutFrm( GetDoc()->GetCurrentLayout() ) )
217 : {
218 0 : SwMsgPoolItem aMsgHint( RES_GRF_REREAD_AND_INCACHE );
219 0 : ModifyNotification( &aMsgHint, &aMsgHint );
220 : }
221 : // #i59688# - do not load linked graphic, if it isn't a new linked graphic.
222 0 : else if ( bNewGrf )
223 : {
224 : //TODO refLink->setInputStream(getInputStream());
225 0 : ((SwBaseLink*)&refLink)->SwapIn();
226 : }
227 : }
228 0 : onGraphicChanged();
229 0 : bSetTwipSize = false;
230 : }
231 : }
232 0 : else if( pGraphic && rGrfName.isEmpty() )
233 : {
234 : // Old stream must be deleted before the new one is set.
235 0 : if( HasStreamName() )
236 0 : DelStreamName();
237 :
238 0 : maGrfObj.SetGraphic( *pGraphic );
239 0 : onGraphicChanged();
240 0 : bReadGrf = true;
241 : }
242 0 : else if( pGrfObj && rGrfName.isEmpty() )
243 : {
244 : // Old stream must be deleted before the new one is set.
245 0 : if( HasStreamName() )
246 0 : DelStreamName();
247 :
248 0 : maGrfObj = *pGrfObj;
249 0 : onGraphicChanged();
250 0 : if( pGrfObj->HasUserData() && pGrfObj->IsSwappedOut() )
251 0 : maGrfObj.SetSwapState();
252 0 : bReadGrf = true;
253 : }
254 : // Was the graphic already loaded?
255 0 : else if( !bNewGrf && GRAPHIC_NONE != maGrfObj.GetType() )
256 0 : return true;
257 : else
258 : {
259 0 : if( HasStreamName() )
260 0 : DelStreamName();
261 :
262 : // create new link for the graphic object
263 0 : InsertLink( rGrfName, rFltName );
264 :
265 0 : if( GetNodes().IsDocNodes() )
266 : {
267 0 : if( pGraphic )
268 : {
269 0 : maGrfObj.SetGraphic( *pGraphic, rGrfName );
270 0 : onGraphicChanged();
271 0 : bReadGrf = true;
272 : // create connection without update, as we have the graphic
273 0 : ((SwBaseLink*)&refLink)->Connect();
274 : }
275 0 : else if( pGrfObj )
276 : {
277 0 : maGrfObj = *pGrfObj;
278 0 : maGrfObj.SetLink( rGrfName );
279 0 : onGraphicChanged();
280 0 : bReadGrf = true;
281 : // create connection without update, as we have the graphic
282 0 : ((SwBaseLink*)&refLink)->Connect();
283 : }
284 : else
285 : {
286 : // reset data of the old graphic so that the correct placeholder is
287 : // shown in case the new link could not be loaded
288 0 : Graphic aGrf; aGrf.SetDefaultType();
289 0 : maGrfObj.SetGraphic( aGrf, rGrfName );
290 0 : onGraphicChanged();
291 : // #i59688# - do not load linked graphic, if it isn't a new linked graphic.
292 0 : if ( bNewGrf )
293 : {
294 0 : ((SwBaseLink*)&refLink)->SwapIn();
295 0 : }
296 : }
297 : }
298 : }
299 :
300 : // Bug 39281: Do not delete Size immediately - Events on ImageMaps should have
301 : // something to work with when swapping
302 0 : if( bSetTwipSize )
303 0 : SetTwipSize( ::GetGraphicSizeTwip( maGrfObj.GetGraphic(), 0 ) );
304 :
305 : // create an updates for the frames
306 0 : if( bReadGrf && bNewGrf )
307 : {
308 0 : SwMsgPoolItem aMsgHint( RES_UPDATE_ATTR );
309 0 : ModifyNotification( &aMsgHint, &aMsgHint );
310 : }
311 :
312 0 : return bReadGrf;
313 : }
314 :
315 0 : SwGrfNode::~SwGrfNode()
316 : {
317 0 : delete mpReplacementGraphic;
318 0 : mpReplacementGraphic = 0;
319 :
320 : // #i73788#
321 0 : mpThreadConsumer.reset();
322 :
323 0 : SwDoc* pDoc = GetDoc();
324 0 : if( refLink.Is() )
325 : {
326 : OSL_ENSURE( !bInSwapIn, "DTOR: I am still in SwapIn" );
327 0 : pDoc->GetLinkManager().Remove( refLink );
328 0 : refLink->Disconnect();
329 : }
330 : else
331 : {
332 : // #i40014# - A graphic node, which is in a linked
333 : // section, whose link is another section in the document, doesn't
334 : // have to remove the stream from the storage.
335 : // Because it's hard to detect this case here and it would only fix
336 : // one problem with shared graphic files - there are also problems,
337 : // a certain graphic file is referenced by two independent graphic nodes,
338 : // brush item or drawing objects, the stream isn't no longer removed here.
339 : // To do this stuff correctly, a reference counting on shared streams
340 : // inside one document has to be implemented.
341 : }
342 : //#39289# delete frames already here since the Frms' dtor needs the graphic for its StopAnimation
343 0 : if( GetDepends() )
344 0 : DelFrms();
345 0 : }
346 :
347 : /// allow reaction on change of content of GraphicObject
348 0 : void SwGrfNode::onGraphicChanged()
349 : {
350 0 : if (GetGrfObj().IsSwappedOut()) // don't force swap-in for this
351 0 : return;
352 :
353 : // try to access SwFlyFrmFmt; since title/desc/name are set there, there is no
354 : // use to continue if it is not yet set. If not yet set, call onGraphicChanged()
355 : // when it is set.
356 0 : SwFlyFrmFmt* pFlyFmt = dynamic_cast< SwFlyFrmFmt* >(GetFlyFmt());
357 :
358 0 : if(pFlyFmt)
359 : {
360 0 : OUString aName;
361 0 : OUString aTitle;
362 0 : OUString aDesc;
363 0 : const SvgDataPtr& rSvgDataPtr = GetGrf().getSvgData();
364 :
365 0 : if(rSvgDataPtr.get())
366 : {
367 0 : const drawinglayer::primitive2d::Primitive2DSequence aSequence(rSvgDataPtr->getPrimitive2DSequence());
368 :
369 0 : if(aSequence.hasElements())
370 : {
371 0 : drawinglayer::geometry::ViewInformation2D aViewInformation2D;
372 0 : drawinglayer::processor2d::ObjectInfoPrimitiveExtractor2D aProcessor(aViewInformation2D);
373 :
374 0 : aProcessor.process(aSequence);
375 :
376 0 : const drawinglayer::primitive2d::ObjectInfoPrimitive2D* pResult = aProcessor.getResult();
377 :
378 0 : if(pResult)
379 : {
380 0 : aName = pResult->getName();
381 0 : aTitle = pResult->getTitle();
382 0 : aDesc = pResult->getDesc();
383 0 : }
384 0 : }
385 : }
386 :
387 0 : if(!aTitle.isEmpty())
388 : {
389 0 : SetTitle(aTitle);
390 : }
391 :
392 0 : if(!aDesc.isEmpty())
393 : {
394 0 : SetDescription(aDesc);
395 0 : }
396 : }
397 : }
398 :
399 0 : void SwGrfNode::SetGraphic(const Graphic& rGraphic, const OUString& rLink)
400 : {
401 0 : maGrfObj.SetGraphic(rGraphic, rLink);
402 0 : onGraphicChanged();
403 0 : }
404 :
405 0 : const GraphicObject* SwGrfNode::GetReplacementGrfObj() const
406 : {
407 0 : if(!mpReplacementGraphic)
408 : {
409 0 : const SvgDataPtr& rSvgDataPtr = GetGrfObj().GetGraphic().getSvgData();
410 :
411 0 : if(rSvgDataPtr.get())
412 : {
413 0 : const_cast< SwGrfNode* >(this)->mpReplacementGraphic = new GraphicObject(rSvgDataPtr->getReplacement());
414 : }
415 : }
416 :
417 0 : return mpReplacementGraphic;
418 : }
419 :
420 0 : SwCntntNode *SwGrfNode::SplitCntntNode( const SwPosition & )
421 : {
422 0 : return this;
423 : }
424 :
425 0 : SwGrfNode * SwNodes::MakeGrfNode( const SwNodeIndex & rWhere,
426 : const OUString& rGrfName,
427 : const OUString& rFltName,
428 : const Graphic* pGraphic,
429 : SwGrfFmtColl* pGrfColl,
430 : SwAttrSet* pAutoAttr,
431 : sal_Bool bDelayed )
432 : {
433 : OSL_ENSURE( pGrfColl, "MakeGrfNode: Formatpointer ist 0." );
434 : SwGrfNode *pNode;
435 : // create object delayed, only from a SW/G-reader
436 0 : if( bDelayed )
437 : pNode = new SwGrfNode( rWhere, rGrfName,
438 0 : rFltName, pGrfColl, pAutoAttr );
439 : else
440 : pNode = new SwGrfNode( rWhere, rGrfName,
441 0 : rFltName, pGraphic, pGrfColl, pAutoAttr );
442 0 : return pNode;
443 : }
444 :
445 0 : SwGrfNode * SwNodes::MakeGrfNode( const SwNodeIndex & rWhere,
446 : const GraphicObject& rGrfObj,
447 : SwGrfFmtColl* pGrfColl,
448 : SwAttrSet* pAutoAttr )
449 : {
450 : OSL_ENSURE( pGrfColl, "MakeGrfNode: Formatpointer ist 0." );
451 0 : return new SwGrfNode( rWhere, rGrfObj, pGrfColl, pAutoAttr );
452 : }
453 :
454 0 : Size SwGrfNode::GetTwipSize() const
455 : {
456 0 : return nGrfSize;
457 : }
458 :
459 0 : bool SwGrfNode::ImportGraphic( SvStream& rStrm )
460 : {
461 0 : Graphic aGraphic;
462 0 : const OUString aURL(maGrfObj.GetUserData());
463 :
464 0 : if(!GraphicFilter::GetGraphicFilter().ImportGraphic(aGraphic, aURL, rStrm))
465 : {
466 0 : delete mpReplacementGraphic;
467 0 : mpReplacementGraphic = 0;
468 :
469 0 : maGrfObj.SetGraphic( aGraphic );
470 0 : maGrfObj.SetUserData( aURL );
471 0 : onGraphicChanged();
472 0 : return true;
473 : }
474 :
475 0 : return false;
476 : }
477 :
478 : namespace
479 : {
480 :
481 0 : struct StreamAndStorageNames
482 : {
483 : OUString sStream;
484 : OUString sStorage;
485 : };
486 :
487 0 : StreamAndStorageNames lcl_GetStreamStorageNames( const OUString& sUserData )
488 : {
489 0 : StreamAndStorageNames aNames;
490 0 : if( sUserData.isEmpty() )
491 0 : return aNames;
492 :
493 0 : const OUString aProt( "vnd.sun.star.Package:" );
494 0 : if (sUserData.startsWithIgnoreAsciiCase(aProt))
495 : {
496 : // 6.0 (XML) Package
497 0 : const sal_Int32 nPos = sUserData.indexOf('/');
498 0 : if (nPos<0)
499 : {
500 0 : aNames.sStream = sUserData.copy(aProt.getLength());
501 : }
502 : else
503 : {
504 0 : const sal_Int32 nPathStart = aProt.getLength();
505 0 : aNames.sStorage = sUserData.copy( nPathStart, nPos-nPathStart );
506 0 : aNames.sStream = sUserData.copy( nPos+1 );
507 : }
508 : }
509 : else
510 : {
511 : OSL_FAIL( "<lcl_GetStreamStorageNames(..)> - unknown graphic URL type. Code for handling 3.1 - 5.2 storages has been deleted by issue i53025." );
512 : }
513 : OSL_ENSURE( aNames.sStream.indexOf('/')<0, "invalid graphic stream name" );
514 0 : return aNames;
515 : }
516 :
517 : }
518 :
519 : /**
520 : * @return true if ReRead or reading successful,
521 : * false if not loaded
522 : */
523 0 : bool SwGrfNode::SwapIn( bool bWaitForData )
524 : {
525 0 : if( bInSwapIn ) // not recursively!
526 0 : return !maGrfObj.IsSwappedOut();
527 :
528 0 : bool bRet = false;
529 0 : bInSwapIn = true;
530 0 : SwBaseLink* pLink = (SwBaseLink*)(::sfx2::SvBaseLink*) refLink;
531 :
532 0 : if( pLink )
533 : {
534 0 : if( GRAPHIC_NONE == maGrfObj.GetType() ||
535 0 : GRAPHIC_DEFAULT == maGrfObj.GetType() )
536 : {
537 : // link was not loaded yet
538 0 : if( pLink->SwapIn( bWaitForData ) )
539 : {
540 0 : bRet = true;
541 : }
542 0 : else if( GRAPHIC_DEFAULT == maGrfObj.GetType() )
543 : {
544 : // no default bitmap anymore, thus re-paint
545 0 : delete mpReplacementGraphic;
546 0 : mpReplacementGraphic = 0;
547 :
548 0 : maGrfObj.SetGraphic( Graphic() );
549 0 : onGraphicChanged();
550 0 : SwMsgPoolItem aMsgHint( RES_GRAPHIC_PIECE_ARRIVED );
551 0 : ModifyNotification( &aMsgHint, &aMsgHint );
552 : }
553 : }
554 0 : else if( maGrfObj.IsSwappedOut() )
555 : {
556 : // link to download
557 0 : bRet = pLink->SwapIn( bWaitForData );
558 : }
559 : else
560 0 : bRet = true;
561 : }
562 0 : else if( maGrfObj.IsSwappedOut() )
563 : {
564 : // graphic is in storage or in a temp file
565 0 : if( !HasStreamName() )
566 : {
567 0 : bRet = maGrfObj.SwapIn();
568 : }
569 : else
570 : {
571 : try
572 : {
573 0 : const StreamAndStorageNames aNames = lcl_GetStreamStorageNames( maGrfObj.GetUserData() );
574 0 : uno::Reference < embed::XStorage > refPics = _GetDocSubstorageOrRoot( aNames.sStorage );
575 0 : SvStream* pStrm = _GetStreamForEmbedGrf( refPics, aNames.sStream );
576 0 : if ( pStrm )
577 : {
578 0 : bRet = ImportGraphic( *pStrm );
579 0 : delete pStrm;
580 0 : }
581 : }
582 0 : catch (const uno::Exception&)
583 : {
584 : // #i48434#
585 : OSL_FAIL( "<SwGrfNode::SwapIn(..)> - unhandled exception!" );
586 : }
587 : }
588 :
589 0 : if( bRet )
590 : {
591 0 : SwMsgPoolItem aMsg( RES_GRAPHIC_SWAPIN );
592 0 : ModifyNotification( &aMsg, &aMsg );
593 : }
594 : }
595 : else
596 0 : bRet = true;
597 : OSL_ENSURE( bRet, "Cannot swap in graphic" );
598 :
599 0 : if( bRet )
600 : {
601 0 : if( !nGrfSize.Width() && !nGrfSize.Height() )
602 0 : SetTwipSize( ::GetGraphicSizeTwip( maGrfObj.GetGraphic(), 0 ) );
603 : }
604 0 : bInSwapIn = false;
605 0 : return bRet;
606 : }
607 :
608 0 : bool SwGrfNode::SwapOut()
609 : {
610 0 : if( maGrfObj.GetType() != GRAPHIC_DEFAULT &&
611 0 : maGrfObj.GetType() != GRAPHIC_NONE &&
612 0 : !maGrfObj.IsSwappedOut() && !bInSwapIn )
613 : {
614 0 : if( !refLink.Is() )
615 : {
616 : // Swapping is only needed for embedded pictures.
617 : // The graphic will be written into a temp file if it is new, i.e.
618 : // if there is no stream name in the storage yet
619 0 : if( !HasStreamName() )
620 0 : if( !maGrfObj.SwapOut() )
621 0 : return false;
622 : }
623 : // written graphics and links are removed here
624 0 : return maGrfObj.SwapOut( NULL );
625 : }
626 0 : return true;
627 : }
628 :
629 0 : bool SwGrfNode::GetFileFilterNms( OUString* pFileNm, OUString* pFilterNm ) const
630 : {
631 0 : bool bRet = false;
632 0 : if( refLink.Is() && refLink->GetLinkManager() )
633 : {
634 0 : sal_uInt16 nType = refLink->GetObjType();
635 0 : if( OBJECT_CLIENT_GRF == nType )
636 : bRet = refLink->GetLinkManager()->GetDisplayNames(
637 0 : refLink, 0, pFileNm, 0, pFilterNm );
638 0 : else if( OBJECT_CLIENT_DDE == nType && pFileNm && pFilterNm )
639 : {
640 0 : OUString sApp;
641 0 : OUString sTopic;
642 0 : OUString sItem;
643 0 : if( refLink->GetLinkManager()->GetDisplayNames(
644 0 : refLink, &sApp, &sTopic, &sItem ) )
645 : {
646 0 : *pFileNm = sApp + OUString(sfx2::cTokenSeparator)
647 0 : + sTopic + OUString(sfx2::cTokenSeparator)
648 0 : + sItem;
649 0 : *pFilterNm = "DDE";
650 0 : bRet = true;
651 0 : }
652 : }
653 : }
654 0 : return bRet;
655 : }
656 :
657 : /** Make a graphic object ready for UNDO.
658 : *
659 : * If it is already in storage, it needs to be loaded.
660 : */
661 0 : bool SwGrfNode::SavePersistentData()
662 : {
663 0 : if( refLink.Is() )
664 : {
665 : OSL_ENSURE( !bInSwapIn, "SavePersistentData: I am still in SwapIn" );
666 0 : GetDoc()->GetLinkManager().Remove( refLink );
667 0 : return true;
668 : }
669 :
670 : // swap in first if already in storage
671 0 : if( HasStreamName() && !SwapIn() )
672 0 : return false;
673 :
674 : // #i44367#
675 : // Do not delete graphic file in storage, because the graphic file could
676 : // be referenced by other graphic nodes.
677 : // Because it's hard to detect this case here and it would only fix
678 : // one problem with shared graphic files - there are also problems, if
679 : // a certain graphic file is referenced by two independent graphic nodes,
680 : // brush item or drawing objects, the stream isn't no longer removed here.
681 : // To do this stuff correct, a reference counting on shared streams
682 : // inside one document has to be implemented.
683 : // Important note: see also fix for #i40014#
684 :
685 : // swap out into temp file
686 0 : return SwapOut();
687 : }
688 :
689 0 : bool SwGrfNode::RestorePersistentData()
690 : {
691 0 : if( refLink.Is() )
692 : {
693 0 : IDocumentLinksAdministration* pIDLA = getIDocumentLinksAdministration();
694 0 : refLink->SetVisible( pIDLA->IsVisibleLinks() );
695 0 : pIDLA->GetLinkManager().InsertDDELink( refLink );
696 0 : if( getIDocumentLayoutAccess()->GetCurrentLayout() )
697 0 : refLink->Update();
698 : }
699 0 : return true;
700 : }
701 :
702 0 : void SwGrfNode::InsertLink( const OUString& rGrfName, const OUString& rFltName )
703 : {
704 0 : refLink = new SwBaseLink( sfx2::LINKUPDATE_ONCALL, FORMAT_GDIMETAFILE, this );
705 :
706 0 : IDocumentLinksAdministration* pIDLA = getIDocumentLinksAdministration();
707 0 : if( GetNodes().IsDocNodes() )
708 : {
709 0 : refLink->SetVisible( pIDLA->IsVisibleLinks() );
710 0 : if( rFltName == "DDE" )
711 : {
712 0 : sal_Int32 nTmp = 0;
713 0 : OUString sApp, sTopic, sItem;
714 0 : sApp = rGrfName.getToken( 0, sfx2::cTokenSeparator, nTmp );
715 0 : sTopic = rGrfName.getToken( 0, sfx2::cTokenSeparator, nTmp );
716 0 : sItem = rGrfName.copy( nTmp );
717 0 : pIDLA->GetLinkManager().InsertDDELink( refLink,
718 0 : sApp, sTopic, sItem );
719 : }
720 : else
721 : {
722 0 : const bool bSync = rFltName == "SYNCHRON";
723 0 : refLink->SetSynchron( bSync );
724 0 : refLink->SetContentType( SOT_FORMATSTR_ID_SVXB );
725 :
726 0 : pIDLA->GetLinkManager().InsertFileLink( *refLink,
727 : OBJECT_CLIENT_GRF, rGrfName,
728 0 : (!bSync && !rFltName.isEmpty() ? &rFltName : 0) );
729 : }
730 : }
731 0 : maGrfObj.SetLink( rGrfName );
732 0 : }
733 :
734 0 : void SwGrfNode::ReleaseLink()
735 : {
736 0 : if( refLink.Is() )
737 : {
738 : // #i15508# remember some stuff from the linked graphic
739 0 : const OUString aFileName(maGrfObj.GetLink());
740 0 : const Graphic aLocalGraphic(maGrfObj.GetGraphic());
741 0 : const bool bHasOriginalData(aLocalGraphic.IsLink());
742 :
743 : {
744 0 : bInSwapIn = true;
745 0 : SwBaseLink* pLink = (SwBaseLink*)(::sfx2::SvBaseLink*) refLink;
746 0 : pLink->SwapIn( true, true );
747 0 : bInSwapIn = false;
748 : }
749 :
750 0 : getIDocumentLinksAdministration()->GetLinkManager().Remove( refLink );
751 0 : refLink.Clear();
752 0 : maGrfObj.SetLink();
753 :
754 : // #i15508# added extra processing after getting rid of the link. Use whatever is
755 : // known from the formally linked graphic to get to a state as close to a directly
756 : // unlinked insterted graphic as possible. Goal is to have a valid GfxLink at the
757 : // ImplGraphic (see there) that holds temporary data to the original data and type
758 : // information about the original data. Only when this is given will
759 : // SvXMLGraphicHelper::ImplInsertGraphicURL which is used at export use that type
760 : // and use the original graphic at export for the ODF, without evtl. recoding
761 : // of trhe bitmap graphic data to something without loss (e.g. PNG) but bigger
762 0 : if(bHasOriginalData)
763 : {
764 : // #i15508# if we have the original data at the Graphic, let it survive
765 : // by using that Graphic again, this time at a GraphicObject without link.
766 : // This happens e.g. when inserting a linked graphic and breaking the link
767 0 : maGrfObj.SetGraphic(aLocalGraphic);
768 : }
769 0 : else if(!aFileName.isEmpty())
770 : {
771 : // #i15508# we have no original data, but a file name. This happens e.g.
772 : // when inserting a linked graphic and save, reload document. Try to access
773 : // that data from the original file; if this works, use it. Else use the
774 : // data we have (but without knowing the original format)
775 0 : GraphicFilter& rFlt = GraphicFilter::GetGraphicFilter();
776 0 : Graphic aNew;
777 0 : int nRes = GraphicFilter::LoadGraphic( aFileName, OUString(), aNew, &rFlt);
778 :
779 0 : if(GRFILTER_OK == nRes)
780 : {
781 0 : maGrfObj.SetGraphic(aNew);
782 0 : }
783 0 : }
784 : }
785 0 : }
786 :
787 0 : void SwGrfNode::SetTwipSize( const Size& rSz )
788 : {
789 0 : nGrfSize = rSz;
790 0 : if( IsScaleImageMap() && nGrfSize.Width() && nGrfSize.Height() )
791 : {
792 : // resize Image-Map to size of the graphic
793 0 : ScaleImageMap();
794 :
795 : // do not re-scale Image-Map
796 0 : SetScaleImageMap( false );
797 : }
798 0 : }
799 :
800 0 : void SwGrfNode::ScaleImageMap()
801 : {
802 0 : if( !nGrfSize.Width() || !nGrfSize.Height() )
803 0 : return;
804 :
805 : // re-scale Image-Map
806 0 : SwFrmFmt* pFmt = GetFlyFmt();
807 :
808 0 : if( !pFmt )
809 0 : return;
810 :
811 0 : SwFmtURL aURL( pFmt->GetURL() );
812 0 : if ( !aURL.GetMap() )
813 0 : return;
814 :
815 0 : bool bScale = false;
816 0 : Fraction aScaleX( 1, 1 );
817 0 : Fraction aScaleY( 1, 1 );
818 :
819 0 : const SwFmtFrmSize& rFrmSize = pFmt->GetFrmSize();
820 0 : const SvxBoxItem& rBox = pFmt->GetBox();
821 :
822 0 : if( !rFrmSize.GetWidthPercent() )
823 : {
824 0 : SwTwips nWidth = rFrmSize.GetWidth();
825 :
826 0 : nWidth -= rBox.CalcLineSpace(BOX_LINE_LEFT) +
827 0 : rBox.CalcLineSpace(BOX_LINE_RIGHT);
828 :
829 : OSL_ENSURE( nWidth>0, "Do any 0 twip wide graphics exist!?" );
830 :
831 0 : if( nGrfSize.Width() != nWidth )
832 : {
833 0 : aScaleX = Fraction( nGrfSize.Width(), nWidth );
834 0 : bScale = true;
835 : }
836 : }
837 0 : if( !rFrmSize.GetHeightPercent() )
838 : {
839 0 : SwTwips nHeight = rFrmSize.GetHeight();
840 :
841 0 : nHeight -= rBox.CalcLineSpace(BOX_LINE_TOP) +
842 0 : rBox.CalcLineSpace(BOX_LINE_BOTTOM);
843 :
844 : OSL_ENSURE( nHeight>0, "Do any 0 twip high graphics exist!?" );
845 :
846 0 : if( nGrfSize.Height() != nHeight )
847 : {
848 0 : aScaleY = Fraction( nGrfSize.Height(), nHeight );
849 0 : bScale = true;
850 : }
851 : }
852 :
853 0 : if( bScale )
854 : {
855 0 : aURL.GetMap()->Scale( aScaleX, aScaleY );
856 0 : pFmt->SetFmtAttr( aURL );
857 0 : }
858 : }
859 :
860 0 : void SwGrfNode::DelStreamName()
861 : {
862 0 : if( HasStreamName() )
863 : {
864 : // then remove graphic from storage
865 0 : uno::Reference < embed::XStorage > xDocStg = GetDoc()->GetDocStorage();
866 0 : if( xDocStg.is() )
867 : {
868 : try
869 : {
870 0 : const StreamAndStorageNames aNames = lcl_GetStreamStorageNames( maGrfObj.GetUserData() );
871 0 : uno::Reference < embed::XStorage > refPics = xDocStg;
872 0 : if ( !aNames.sStorage.isEmpty() )
873 0 : refPics = xDocStg->openStorageElement( aNames.sStorage, embed::ElementModes::READWRITE );
874 0 : refPics->removeElement( aNames.sStream );
875 0 : uno::Reference < embed::XTransactedObject > xTrans( refPics, uno::UNO_QUERY );
876 0 : if ( xTrans.is() )
877 0 : xTrans->commit();
878 : }
879 0 : catch (const uno::Exception&)
880 : {
881 : // #i48434#
882 : OSL_FAIL( "<SwGrfNode::DelStreamName()> - unhandled exception!" );
883 : }
884 : }
885 :
886 0 : maGrfObj.SetUserData();
887 : }
888 0 : }
889 :
890 : /** helper method to get a substorage of the document storage for readonly access.
891 :
892 : OD, MAV 2005-08-17 #i53025#
893 : A substorage with the specified name will be opened readonly. If the provided
894 : name is empty the root storage will be returned.
895 : */
896 0 : uno::Reference< embed::XStorage > SwGrfNode::_GetDocSubstorageOrRoot( const OUString& aStgName ) const
897 : {
898 : uno::Reference < embed::XStorage > refStor =
899 0 : const_cast<SwGrfNode*>(this)->GetDoc()->GetDocStorage();
900 : OSL_ENSURE( refStor.is(), "Kein Storage am Doc" );
901 :
902 0 : if ( !aStgName.isEmpty() )
903 : {
904 0 : if( refStor.is() )
905 0 : return refStor->openStorageElement( aStgName, embed::ElementModes::READ );
906 : }
907 :
908 0 : return refStor;
909 : }
910 :
911 : /** helper method to determine stream for the embedded graphic.
912 :
913 : OD 2005-05-04 #i48434#
914 : Important note: caller of this method has to handle the thrown exceptions
915 : OD, MAV 2005-08-17 #i53025#
916 : Storage, which should contain the stream of the embedded graphic, is
917 : provided via parameter. Otherwise the returned stream will be closed
918 : after the method returns, because its parent stream is closed and deleted.
919 : Proposed name of embedded graphic stream is also provided by parameter.
920 : */
921 0 : SvStream* SwGrfNode::_GetStreamForEmbedGrf(
922 : const uno::Reference< embed::XStorage >& _refPics,
923 : const OUString& rStreamName ) const
924 : {
925 0 : SvStream* pStrm( 0L );
926 :
927 0 : if( _refPics.is() && !rStreamName.isEmpty() )
928 : {
929 0 : OUString sStreamName(rStreamName);
930 : // If stream doesn't exist in the storage, try access the graphic file by
931 : // re-generating its name.
932 : // A save action can have changed the filename of the embedded graphic,
933 : // because a changed unique ID of the graphic is calculated.
934 : // --> recursive calls of <GetUniqueID()> have to be avoided.
935 : // Thus, use local static boolean to assure this.
936 0 : if ( !_refPics->hasByName( sStreamName ) ||
937 0 : !_refPics->isStreamElement( sStreamName ) )
938 : {
939 0 : if ( GetGrfObj().GetType() != GRAPHIC_NONE )
940 : {
941 0 : const sal_Int32 nExtPos = sStreamName.indexOf('.');
942 0 : const OUString aExtStr = (nExtPos>=0) ? sStreamName.copy( nExtPos ) : OUString();
943 0 : sStreamName = OStringToOUString(GetGrfObj().GetUniqueID(),
944 0 : RTL_TEXTENCODING_ASCII_US) + aExtStr;
945 : }
946 : }
947 :
948 : // assure that graphic file exist in the storage.
949 0 : if ( _refPics->hasByName( sStreamName ) &&
950 0 : _refPics->isStreamElement( sStreamName ) )
951 : {
952 0 : uno::Reference < io::XStream > refStrm = _refPics->openStreamElement( sStreamName, embed::ElementModes::READ );
953 0 : pStrm = utl::UcbStreamHelper::CreateStream( refStrm );
954 : }
955 : else
956 : {
957 : OSL_FAIL( "<SwGrfNode::_GetStreamForEmbedGrf(..)> - embedded graphic file not found!" );
958 0 : }
959 : }
960 :
961 0 : return pStrm;
962 : }
963 :
964 0 : SwCntntNode* SwGrfNode::MakeCopy( SwDoc* pDoc, const SwNodeIndex& rIdx ) const
965 : {
966 : // copy formats into the other document
967 0 : SwGrfFmtColl* pColl = pDoc->CopyGrfColl( *GetGrfColl() );
968 :
969 0 : Graphic aTmpGrf;
970 0 : SwBaseLink* pLink = (SwBaseLink*)(::sfx2::SvBaseLink*) refLink;
971 0 : if( !pLink && HasStreamName() )
972 : {
973 : try
974 : {
975 0 : const StreamAndStorageNames aNames = lcl_GetStreamStorageNames( maGrfObj.GetUserData() );
976 0 : uno::Reference < embed::XStorage > refPics = _GetDocSubstorageOrRoot( aNames.sStorage );
977 0 : SvStream* pStrm = _GetStreamForEmbedGrf( refPics, aNames.sStream );
978 0 : if ( pStrm )
979 : {
980 0 : const OUString aURL(maGrfObj.GetUserData());
981 0 : GraphicFilter::GetGraphicFilter().ImportGraphic(aTmpGrf, aURL, *pStrm);
982 0 : delete pStrm;
983 0 : }
984 : }
985 0 : catch (const uno::Exception& e)
986 : {
987 : // #i48434#
988 : SAL_WARN("sw.core", "<SwGrfNode::MakeCopy(..)> - unhandled exception!" << e.Message);
989 : }
990 : }
991 : else
992 : {
993 0 : if( maGrfObj.IsSwappedOut() )
994 0 : const_cast<SwGrfNode*>(this)->SwapIn();
995 0 : aTmpGrf = maGrfObj.GetGraphic();
996 : }
997 :
998 0 : const sfx2::LinkManager& rMgr = getIDocumentLinksAdministration()->GetLinkManager();
999 0 : OUString sFile, sFilter;
1000 0 : if( IsLinkedFile() )
1001 0 : rMgr.GetDisplayNames( refLink, 0, &sFile, 0, &sFilter );
1002 0 : else if( IsLinkedDDE() )
1003 : {
1004 0 : OUString sTmp1, sTmp2;
1005 0 : rMgr.GetDisplayNames( refLink, &sTmp1, &sTmp2, &sFilter );
1006 0 : sfx2::MakeLnkName( sFile, &sTmp1, sTmp2, sFilter );
1007 0 : sFilter = "DDE";
1008 : }
1009 :
1010 0 : SwGrfNode* pGrfNd = pDoc->GetNodes().MakeGrfNode( rIdx, sFile, sFilter,
1011 : &aTmpGrf, pColl,
1012 0 : (SwAttrSet*)GetpSwAttrSet() );
1013 0 : pGrfNd->SetTitle( GetTitle() );
1014 0 : pGrfNd->SetDescription( GetDescription() );
1015 0 : pGrfNd->SetContour( HasContour(), HasAutomaticContour() );
1016 0 : return pGrfNd;
1017 : }
1018 :
1019 0 : IMPL_LINK( SwGrfNode, SwapGraphic, GraphicObject*, pGrfObj )
1020 : {
1021 : SvStream* pRet;
1022 :
1023 : // Keep graphic while in swap in. That's at least important
1024 : // when breaking links, because in this situation a reschedule call and
1025 : // a DataChanged call lead to a paint of the graphic.
1026 0 : if( pGrfObj->IsInSwapOut() && (IsSelected() || bInSwapIn) )
1027 0 : pRet = GRFMGR_AUTOSWAPSTREAM_NONE;
1028 0 : else if( refLink.Is() )
1029 : {
1030 0 : if( pGrfObj->IsInSwapIn() )
1031 : {
1032 : // then make it by your self
1033 0 : if( !bInSwapIn )
1034 : {
1035 0 : const bool bIsModifyLocked = IsModifyLocked();
1036 0 : LockModify();
1037 0 : SwapIn( false );
1038 0 : if( !bIsModifyLocked )
1039 0 : UnlockModify();
1040 : }
1041 0 : pRet = GRFMGR_AUTOSWAPSTREAM_NONE;
1042 : }
1043 : else
1044 0 : pRet = GRFMGR_AUTOSWAPSTREAM_LINK;
1045 : }
1046 : else
1047 : {
1048 0 : pRet = GRFMGR_AUTOSWAPSTREAM_TEMP;
1049 :
1050 0 : if( HasStreamName() )
1051 : {
1052 : try
1053 : {
1054 0 : const StreamAndStorageNames aNames = lcl_GetStreamStorageNames( maGrfObj.GetUserData() );
1055 0 : uno::Reference < embed::XStorage > refPics = _GetDocSubstorageOrRoot( aNames.sStorage );
1056 0 : SvStream* pStrm = _GetStreamForEmbedGrf( refPics, aNames.sStream );
1057 0 : if ( pStrm )
1058 : {
1059 0 : if( pGrfObj->IsInSwapOut() )
1060 : {
1061 0 : pRet = GRFMGR_AUTOSWAPSTREAM_LINK;
1062 : }
1063 : else
1064 : {
1065 0 : ImportGraphic( *pStrm );
1066 0 : pRet = GRFMGR_AUTOSWAPSTREAM_LOADED;
1067 : }
1068 0 : delete pStrm;
1069 0 : }
1070 : }
1071 0 : catch (const uno::Exception&)
1072 : {
1073 : // #i48434#
1074 : OSL_FAIL( "<SwapGraphic> - unhandled exception!" );
1075 : }
1076 : }
1077 : }
1078 :
1079 0 : return (sal_IntPtr)pRet;
1080 : }
1081 :
1082 : /// delete all QuickDraw-Bitmaps in the specified document
1083 0 : void DelAllGrfCacheEntries( SwDoc* pDoc )
1084 : {
1085 0 : if( pDoc )
1086 : {
1087 : // delete all Graphic-Links with this name from cache
1088 0 : const sfx2::LinkManager& rLnkMgr = pDoc->GetLinkManager();
1089 0 : const ::sfx2::SvBaseLinks& rLnks = rLnkMgr.GetLinks();
1090 : SwGrfNode* pGrfNd;
1091 0 : OUString sFileNm;
1092 0 : for( sal_uInt16 n = rLnks.size(); n; )
1093 : {
1094 0 : ::sfx2::SvBaseLink* pLnk = &(*rLnks[ --n ]);
1095 0 : if( pLnk && OBJECT_CLIENT_GRF == pLnk->GetObjType() &&
1096 0 : rLnkMgr.GetDisplayNames( pLnk, 0, &sFileNm ) &&
1097 0 : pLnk->ISA( SwBaseLink ) && 0 != ( pGrfNd =
1098 0 : ((SwBaseLink*)pLnk)->GetCntntNode()->GetGrfNode()) )
1099 : {
1100 0 : pGrfNd->ReleaseGraphicFromCache();
1101 : }
1102 0 : }
1103 : }
1104 0 : }
1105 :
1106 : /// returns the Graphic-Attr-Structure filled with our graphic attributes
1107 0 : GraphicAttr& SwGrfNode::GetGraphicAttr( GraphicAttr& rGA,
1108 : const SwFrm* pFrm ) const
1109 : {
1110 0 : const SwAttrSet& rSet = GetSwAttrSet();
1111 :
1112 0 : rGA.SetDrawMode( (GraphicDrawMode)rSet.GetDrawModeGrf().GetValue() );
1113 :
1114 0 : const SwMirrorGrf & rMirror = rSet.GetMirrorGrf();
1115 0 : sal_uLong nMirror = BMP_MIRROR_NONE;
1116 0 : if( rMirror.IsGrfToggle() && pFrm && !pFrm->FindPageFrm()->OnRightPage() )
1117 : {
1118 0 : switch( rMirror.GetValue() )
1119 : {
1120 0 : case RES_MIRROR_GRAPH_DONT: nMirror = BMP_MIRROR_HORZ; break;
1121 0 : case RES_MIRROR_GRAPH_VERT: nMirror = BMP_MIRROR_NONE; break;
1122 0 : case RES_MIRROR_GRAPH_HOR: nMirror = BMP_MIRROR_HORZ|BMP_MIRROR_VERT;
1123 0 : break;
1124 0 : default: nMirror = BMP_MIRROR_VERT; break;
1125 : }
1126 : }
1127 : else
1128 0 : switch( rMirror.GetValue() )
1129 : {
1130 0 : case RES_MIRROR_GRAPH_BOTH: nMirror = BMP_MIRROR_HORZ|BMP_MIRROR_VERT;
1131 0 : break;
1132 0 : case RES_MIRROR_GRAPH_VERT: nMirror = BMP_MIRROR_HORZ; break;
1133 0 : case RES_MIRROR_GRAPH_HOR: nMirror = BMP_MIRROR_VERT; break;
1134 : }
1135 :
1136 0 : rGA.SetMirrorFlags( nMirror );
1137 :
1138 0 : const SwCropGrf& rCrop = rSet.GetCropGrf();
1139 0 : rGA.SetCrop( convertTwipToMm100( rCrop.GetLeft() ),
1140 0 : convertTwipToMm100( rCrop.GetTop() ),
1141 0 : convertTwipToMm100( rCrop.GetRight() ),
1142 0 : convertTwipToMm100( rCrop.GetBottom() ));
1143 :
1144 0 : const SwRotationGrf& rRotation = rSet.GetRotationGrf();
1145 0 : rGA.SetRotation( rRotation.GetValue() );
1146 :
1147 0 : rGA.SetLuminance( rSet.GetLuminanceGrf().GetValue() );
1148 0 : rGA.SetContrast( rSet.GetContrastGrf().GetValue() );
1149 0 : rGA.SetChannelR( rSet.GetChannelRGrf().GetValue() );
1150 0 : rGA.SetChannelG( rSet.GetChannelGGrf().GetValue() );
1151 0 : rGA.SetChannelB( rSet.GetChannelBGrf().GetValue() );
1152 0 : rGA.SetGamma( rSet.GetGammaGrf().GetValue() );
1153 0 : rGA.SetInvert( rSet.GetInvertGrf().GetValue() );
1154 :
1155 0 : const sal_uInt16 nTrans = rSet.GetTransparencyGrf().GetValue();
1156 : rGA.SetTransparency( (sal_uInt8) FRound(
1157 0 : std::min( nTrans, (sal_uInt16) 100 ) * 2.55 ) );
1158 :
1159 0 : return rGA;
1160 : }
1161 :
1162 0 : bool SwGrfNode::IsTransparent() const
1163 : {
1164 0 : return maGrfObj.IsTransparent() ||
1165 0 : GetSwAttrSet().GetTransparencyGrf().GetValue() != 0;
1166 : }
1167 :
1168 0 : bool SwGrfNode::IsSelected() const
1169 : {
1170 0 : bool bRet = false;
1171 0 : const SwEditShell* pESh = GetDoc()->GetEditShell();
1172 0 : if( pESh )
1173 : {
1174 0 : const SwNode* pN = this;
1175 0 : const SwViewShell* pV = pESh;
1176 0 : do {
1177 0 : if( pV->ISA( SwEditShell ) && pN == &((SwCrsrShell*)pV)
1178 0 : ->GetCrsr()->GetPoint()->nNode.GetNode() )
1179 : {
1180 0 : bRet = true;
1181 0 : break;
1182 : }
1183 : }
1184 0 : while( pESh != ( pV = (SwViewShell*)pV->GetNext() ));
1185 : }
1186 0 : return bRet;
1187 : }
1188 :
1189 : // #i73788#
1190 0 : boost::weak_ptr< SwAsyncRetrieveInputStreamThreadConsumer > SwGrfNode::GetThreadConsumer()
1191 : {
1192 0 : return mpThreadConsumer;
1193 : }
1194 :
1195 0 : void SwGrfNode::TriggerAsyncRetrieveInputStream()
1196 : {
1197 0 : if ( !IsLinkedFile() )
1198 : {
1199 : OSL_FAIL( "<SwGrfNode::TriggerAsyncLoad()> - Method is misused. Method call is only valid for graphic nodes, which refer a linked graphic file" );
1200 0 : return;
1201 : }
1202 :
1203 0 : if ( mpThreadConsumer.get() == 0 )
1204 : {
1205 0 : mpThreadConsumer.reset( new SwAsyncRetrieveInputStreamThreadConsumer( *this ) );
1206 :
1207 0 : OUString sGrfNm;
1208 0 : refLink->GetLinkManager()->GetDisplayNames( refLink, 0, &sGrfNm, 0, 0 );
1209 0 : OUString sReferer;
1210 0 : SfxObjectShell * sh = GetDoc()->GetPersist();
1211 0 : if (sh != 0 && sh->HasName())
1212 : {
1213 0 : sReferer = sh->GetMedium()->GetName();
1214 : }
1215 0 : mpThreadConsumer->CreateThread( sGrfNm, sReferer );
1216 : }
1217 : }
1218 :
1219 0 : bool SwGrfNode::IsLinkedInputStreamReady() const
1220 : {
1221 0 : return mbLinkedInputStreamReady;
1222 : }
1223 :
1224 0 : void SwGrfNode::ApplyInputStream(
1225 : com::sun::star::uno::Reference<com::sun::star::io::XInputStream> xInputStream,
1226 : const bool bIsStreamReadOnly )
1227 : {
1228 0 : if ( IsLinkedFile() )
1229 : {
1230 0 : if ( xInputStream.is() )
1231 : {
1232 0 : mxInputStream = xInputStream;
1233 0 : mbIsStreamReadOnly = bIsStreamReadOnly;
1234 0 : mbLinkedInputStreamReady = true;
1235 0 : SwMsgPoolItem aMsgHint( RES_LINKED_GRAPHIC_STREAM_ARRIVED );
1236 0 : ModifyNotification( &aMsgHint, &aMsgHint );
1237 : }
1238 : }
1239 0 : }
1240 :
1241 0 : void SwGrfNode::UpdateLinkWithInputStream()
1242 : {
1243 : // do not work on link, if a <SwapIn> has been triggered.
1244 0 : if ( !bInSwapIn && IsLinkedFile() )
1245 : {
1246 0 : GetLink()->setStreamToLoadFrom( mxInputStream, mbIsStreamReadOnly );
1247 0 : GetLink()->Update();
1248 0 : SwMsgPoolItem aMsgHint( RES_GRAPHIC_ARRIVED );
1249 0 : ModifyNotification( &aMsgHint, &aMsgHint );
1250 :
1251 : // #i88291#
1252 0 : mxInputStream.clear();
1253 0 : GetLink()->clearStreamToLoadFrom();
1254 0 : mbLinkedInputStreamReady = false;
1255 0 : mpThreadConsumer.reset();
1256 : }
1257 0 : }
1258 :
1259 : // #i90395#
1260 0 : bool SwGrfNode::IsAsyncRetrieveInputStreamPossible() const
1261 : {
1262 0 : bool bRet = false;
1263 :
1264 0 : if ( IsLinkedFile() )
1265 : {
1266 0 : OUString sGrfNm;
1267 0 : refLink->GetLinkManager()->GetDisplayNames( refLink, 0, &sGrfNm, 0, 0 );
1268 0 : if ( !sGrfNm.startsWith( "vnd.sun.star.pkg:" ) )
1269 : {
1270 0 : bRet = true;
1271 0 : }
1272 : }
1273 :
1274 0 : return bRet;
1275 : }
1276 :
1277 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|