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 "doc.hxx"
21 : #include "frmtool.hxx"
22 : #include "hints.hxx"
23 : #include <fmtornt.hxx>
24 : #include "txtfrm.hxx"
25 : #include "flyfrms.hxx"
26 : #include <dflyobj.hxx>
27 : #include <IDocumentSettingAccess.hxx>
28 : #include <IDocumentDrawModelAccess.hxx>
29 :
30 774 : SwFlyInCntFrm::SwFlyInCntFrm( SwFlyFrameFormat *pFormat, SwFrm* pSib, SwFrm *pAnch ) :
31 774 : SwFlyFrm( pFormat, pSib, pAnch )
32 : {
33 774 : bInCnt = bInvalidLayout = bInvalidContent = true;
34 774 : SwTwips nRel = pFormat->GetVertOrient().GetPos();
35 : // OD 2004-05-27 #i26791# - member <aRelPos> moved to <SwAnchoredObject>
36 774 : Point aRelPos;
37 774 : if( pAnch && pAnch->IsVertical() )
38 0 : aRelPos.setX(pAnch->IsReverse() ? nRel : -nRel);
39 : else
40 774 : aRelPos.setY(nRel);
41 774 : SetCurrRelPos( aRelPos );
42 774 : }
43 :
44 774 : void SwFlyInCntFrm::DestroyImpl()
45 : {
46 774 : if ( !GetFormat()->GetDoc()->IsInDtor() && GetAnchorFrm() )
47 : {
48 774 : SwRect aTmp( GetObjRectWithSpaces() );
49 774 : SwFlyInCntFrm::NotifyBackground( FindPageFrm(), aTmp, PREP_FLY_LEAVE );
50 : }
51 :
52 774 : SwFlyFrm::DestroyImpl();
53 774 : }
54 :
55 1548 : SwFlyInCntFrm::~SwFlyInCntFrm()
56 : {
57 1548 : }
58 :
59 : // #i28701#
60 17148355 : TYPEINIT1(SwFlyInCntFrm,SwFlyFrm);
61 :
62 1443 : void SwFlyInCntFrm::SetRefPoint( const Point& rPoint,
63 : const Point& rRelAttr,
64 : const Point& rRelPos )
65 : {
66 : // OD 2004-05-27 #i26791# - member <aRelPos> moved to <SwAnchoredObject>
67 : OSL_ENSURE( rPoint != aRef || rRelAttr != GetCurrRelPos(), "SetRefPoint: no change" );
68 1443 : SwFlyNotify *pNotify = NULL;
69 : // No notify at a locked fly frame, if a fly frame is locked, there's
70 : // already a SwFlyNotify object on the stack (MakeAll).
71 1443 : if( !IsLocked() )
72 1443 : pNotify = new SwFlyNotify( this );
73 1443 : aRef = rPoint;
74 1443 : SetCurrRelPos( rRelAttr );
75 1443 : SWRECTFN( GetAnchorFrm() )
76 1443 : (Frm().*fnRect->fnSetPos)( rPoint + rRelPos );
77 : // #i68520#
78 1443 : InvalidateObjRectWithSpaces();
79 1443 : if( pNotify )
80 : {
81 1443 : InvalidatePage();
82 1443 : mbValidPos = false;
83 1443 : bInvalid = true;
84 1443 : Calc();
85 1443 : delete pNotify;
86 : }
87 1443 : }
88 :
89 63 : void SwFlyInCntFrm::Modify( const SfxPoolItem* pOld, const SfxPoolItem *pNew )
90 : {
91 63 : bool bCallPrepare = false;
92 63 : const sal_uInt16 nWhich = pOld ? pOld->Which() : pNew ? pNew->Which() : 0;
93 63 : if (RES_ATTRSET_CHG == nWhich && pNew)
94 : {
95 9 : if(pOld &&
96 4 : (SfxItemState::SET == static_cast<const SwAttrSetChg*>(pNew)->GetChgSet()->
97 7 : GetItemState(RES_SURROUND, false) ||
98 3 : SfxItemState::SET == static_cast<const SwAttrSetChg*>(pNew)->GetChgSet()->
99 3 : GetItemState(RES_FRMMACRO, false)) )
100 : {
101 1 : SwAttrSetChg aOld( *static_cast<const SwAttrSetChg*>(pOld) );
102 2 : SwAttrSetChg aNew( *static_cast<const SwAttrSetChg*>(pNew) );
103 :
104 1 : aOld.ClearItem( RES_SURROUND );
105 1 : aNew.ClearItem( RES_SURROUND );
106 1 : aOld.ClearItem( RES_FRMMACRO );
107 1 : aNew.ClearItem( RES_FRMMACRO );
108 1 : if( aNew.Count() )
109 : {
110 0 : SwFlyFrm::Modify( &aOld, &aNew );
111 0 : bCallPrepare = true;
112 1 : }
113 : }
114 3 : else if( static_cast<const SwAttrSetChg*>(pNew)->GetChgSet()->Count())
115 : {
116 3 : SwFlyFrm::Modify( pOld, pNew );
117 3 : bCallPrepare = true;
118 4 : }
119 : }
120 59 : else if( nWhich != RES_SURROUND && RES_FRMMACRO != nWhich )
121 : {
122 59 : SwFlyFrm::Modify( pOld, pNew );
123 59 : bCallPrepare = true;
124 : }
125 :
126 63 : if ( bCallPrepare && GetAnchorFrm() )
127 62 : AnchorFrm()->Prepare( PREP_FLY_ATTR_CHG, GetFormat() );
128 63 : }
129 :
130 : /// Here the content gets formatted initially.
131 1562 : void SwFlyInCntFrm::Format( const SwBorderAttrs *pAttrs )
132 : {
133 1562 : if ( !Frm().Height() )
134 : {
135 0 : Lock(); //don't format the anchor on the crook.
136 0 : SwContentFrm *pContent = ContainsContent();
137 0 : while ( pContent )
138 0 : { pContent->Calc();
139 0 : pContent = pContent->GetNextContentFrm();
140 : }
141 0 : Unlock();
142 : }
143 1562 : SwFlyFrm::Format( pAttrs );
144 1562 : }
145 :
146 : /** Calculate object position
147 : *
148 : * @note: In contrast to other Frames, we only calculate the relative position
149 : * here. The absolute position is only calculated using SetAbsPos.
150 : **/
151 2177 : void SwFlyInCntFrm::MakeObjPos()
152 : {
153 2177 : if ( !mbValidPos )
154 : {
155 2177 : mbValidPos = true;
156 2177 : SwFlyFrameFormat *pFormat = GetFormat();
157 2177 : const SwFormatVertOrient &rVert = pFormat->GetVertOrient();
158 : //Update the current values in the format if needed, during this we of
159 : //course must not send any Modify.
160 2177 : const bool bVert = GetAnchorFrm()->IsVertical();
161 2177 : const bool bRev = GetAnchorFrm()->IsReverse();
162 2177 : SwTwips nOld = rVert.GetPos();
163 2177 : SwTwips nAct = bVert ? -GetCurrRelPos().X() : GetCurrRelPos().Y();
164 2177 : if( bRev )
165 0 : nAct = -nAct;
166 2177 : if( nAct != nOld )
167 : {
168 801 : SwFormatVertOrient aVert( rVert );
169 801 : aVert.SetPos( nAct );
170 801 : pFormat->LockModify();
171 801 : pFormat->SetFormatAttr( aVert );
172 801 : pFormat->UnlockModify();
173 : }
174 : }
175 2177 : }
176 :
177 : // #115759#
178 819 : void SwFlyInCntFrm::_ActionOnInvalidation( const InvalidationType _nInvalid )
179 : {
180 819 : if ( INVALID_POS == _nInvalid || INVALID_ALL == _nInvalid )
181 25 : AnchorFrm()->Prepare( PREP_FLY_ATTR_CHG, &GetFrameFormat() );
182 819 : }
183 :
184 1618 : void SwFlyInCntFrm::NotifyBackground( SwPageFrm *, const SwRect& rRect,
185 : PrepareHint eHint)
186 : {
187 1618 : if ( eHint == PREP_FLY_ATTR_CHG )
188 0 : AnchorFrm()->Prepare( PREP_FLY_ATTR_CHG );
189 : else
190 1618 : AnchorFrm()->Prepare( eHint, static_cast<void const *>(&rRect) );
191 1618 : }
192 :
193 541 : const Point SwFlyInCntFrm::GetRelPos() const
194 : {
195 541 : Calc();
196 541 : return GetCurrRelPos();
197 : }
198 :
199 : /// @see SwRowFrm::RegistFlys()
200 713 : void SwFlyInCntFrm::RegistFlys()
201 : {
202 713 : SwPageFrm *pPage = FindPageFrm();
203 : OSL_ENSURE( pPage, "Register Flys without pages?" );
204 713 : ::RegistFlys( pPage, this );
205 713 : }
206 :
207 2948 : void SwFlyInCntFrm::MakeAll()
208 : {
209 : // OD 2004-01-19 #110582#
210 2948 : if ( !GetFormat()->GetDoc()->getIDocumentDrawModelAccess().IsVisibleLayerId( GetVirtDrawObj()->GetLayer() ) )
211 : {
212 0 : return;
213 : }
214 :
215 2948 : if ( !GetAnchorFrm() || IsLocked() || IsColLocked() || !FindPageFrm() )
216 0 : return;
217 :
218 2948 : Lock(); // The curtain falls
219 :
220 : //does the notification in the DTor
221 2948 : const SwFlyNotify aNotify( this );
222 5896 : SwBorderAttrAccess aAccess( SwFrm::GetCache(), this );
223 2948 : const SwBorderAttrs &rAttrs = *aAccess.Get();
224 :
225 2948 : if ( IsClipped() )
226 0 : mbValidSize = bHeightClipped = bWidthClipped = false;
227 :
228 8844 : while ( !mbValidPos || !mbValidSize || !mbValidPrtArea || !m_bValidContentPos )
229 : {
230 : //Only stop, if the flag is set!!
231 2948 : if ( !mbValidSize )
232 : {
233 1562 : mbValidPrtArea = false;
234 : }
235 :
236 2948 : if ( !mbValidPrtArea )
237 : {
238 1562 : MakePrtArea( rAttrs );
239 1562 : m_bValidContentPos = false;
240 : }
241 :
242 2948 : if ( !mbValidSize )
243 1562 : Format( &rAttrs );
244 :
245 2948 : if ( !mbValidPos )
246 : {
247 2177 : MakeObjPos();
248 : }
249 :
250 2948 : if ( !m_bValidContentPos )
251 1562 : MakeContentPos( rAttrs );
252 :
253 : // re-activate clipping of as-character anchored Writer fly frames
254 : // depending on compatibility option <ClipAsCharacterAnchoredWriterFlyFrames>
255 5896 : if ( mbValidPos && mbValidSize &&
256 2948 : GetFormat()->getIDocumentSettingAccess()->get( DocumentSettingId::CLIP_AS_CHARACTER_ANCHORED_WRITER_FLY_FRAME ) )
257 : {
258 0 : SwFrm* pFrm = AnchorFrm();
259 0 : if ( Frm().Left() == (pFrm->Frm().Left()+pFrm->Prt().Left()) &&
260 0 : Frm().Width() > pFrm->Prt().Width() )
261 : {
262 0 : Frm().Width( pFrm->Prt().Width() );
263 0 : mbValidPrtArea = false;
264 0 : bWidthClipped = true;
265 : }
266 : }
267 : }
268 5896 : Unlock();
269 177 : }
270 :
271 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|