summaryrefslogtreecommitdiff
path: root/sw/source/core
diff options
context:
space:
mode:
authorMike Kaganski <mike.kaganski@collabora.com>2024-02-09 11:56:19 +0600
committerMike Kaganski <mike.kaganski@collabora.com>2024-02-14 21:54:55 +0100
commit0c96119895b347f8eb5bb89f393351bd3c02b9f1 (patch)
tree00523cee811e15bd688452453c5590301cca756d /sw/source/core
parent3a0807b08f0254e89d361322bce1ef13df3427f2 (diff)
tdf#159565 prerequisite: make hidden sections have zero-height frames
As mentioned in commit bb733957dd39e6f0b9d80bb59eb0177188794797 (tdf#114973 sw: enable SelectAll with hidden para at start/end, 2023-01-27), the hidden sections didn't have frames. That prevented correct handling of the case when such a frame was in the beginning of the document. This change re-implements the hidden section to use 0-height frames, like hidden paragraphs, as a pre-requisite for a follow-up change. Some layout breakages noticed while working on this are unit-tested now. This change needed to handle the case when the first section is hidden, and then goes a page break with page style. In this case, the page style must apply to the very first page of the document. Implementing this now, when the frame that defines the page style is not the first in the document, I accidentally fixed also the previously broken case when the first paragraph was hidden. Now the page style defined in the second paragraph's page break will apply correctly. This change makes hidden sections break outer section's frames. This means that when text borders are shown, there will be an artifact in the place of the hidden sections (a horizontal line breaking outer frame). I suppose it's not a problem, actually helping to see the layout better, so in line with the "show text borders" helper functionality. If this proves to be problematic, this can be handled specially in a follow-up. Change-Id: I14ebf0559b463186aba28902cd10c5cc978ba456 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/163151 Tested-by: Mike Kaganski <mike.kaganski@collabora.com> Reviewed-by: Mike Kaganski <mike.kaganski@collabora.com>
Diffstat (limited to 'sw/source/core')
-rw-r--r--sw/source/core/crsr/crsrsh.cxx12
-rw-r--r--sw/source/core/crsr/pam.cxx5
-rw-r--r--sw/source/core/doc/docedt.cxx4
-rw-r--r--sw/source/core/docnode/ndsect.cxx4
-rw-r--r--sw/source/core/docnode/nodes.cxx6
-rw-r--r--sw/source/core/docnode/section.cxx7
-rw-r--r--sw/source/core/edit/editsh.cxx2
-rw-r--r--sw/source/core/inc/frame.hxx2
-rw-r--r--sw/source/core/inc/sectfrm.hxx2
-rw-r--r--sw/source/core/inc/txtfrm.hxx2
-rw-r--r--sw/source/core/layout/calcmove.cxx13
-rw-r--r--sw/source/core/layout/findfrm.cxx8
-rw-r--r--sw/source/core/layout/flowfrm.cxx119
-rw-r--r--sw/source/core/layout/frmtool.cxx23
-rw-r--r--sw/source/core/layout/ftnfrm.cxx10
-rw-r--r--sw/source/core/layout/pagechg.cxx5
-rw-r--r--sw/source/core/layout/sectfrm.cxx37
-rw-r--r--sw/source/core/layout/tabfrm.cxx6
-rw-r--r--sw/source/core/layout/trvlfrm.cxx25
-rw-r--r--sw/source/core/text/txtfrm.cxx19
20 files changed, 159 insertions, 152 deletions
diff --git a/sw/source/core/crsr/crsrsh.cxx b/sw/source/core/crsr/crsrsh.cxx
index 15883b2a80e2..13d2776d83dd 100644
--- a/sw/source/core/crsr/crsrsh.cxx
+++ b/sw/source/core/crsr/crsrsh.cxx
@@ -944,14 +944,14 @@ bool SwCursorShell::MovePage( SwWhichPage fnWhichPage, SwPosPage fnPosPage )
return bRet;
}
-bool SwCursorShell::isInHiddenTextFrame(SwShellCursor* pShellCursor)
+bool SwCursorShell::isInHiddenFrame(SwShellCursor* pShellCursor)
{
SwContentNode *pCNode = pShellCursor->GetPointContentNode();
std::pair<Point, bool> tmp(pShellCursor->GetPtPos(), false);
SwContentFrame *const pFrame = pCNode
? pCNode->getLayoutFrame(GetLayout(), pShellCursor->GetPoint(), &tmp)
: nullptr;
- return !pFrame || (pFrame->IsTextFrame() && static_cast<SwTextFrame*>(pFrame)->IsHiddenNow());
+ return !pFrame || pFrame->IsHiddenNow();
}
// sw_redlinehide: this should work for all cases: GoCurrPara, GoNextPara, GoPrevPara
@@ -992,7 +992,7 @@ bool SwCursorShell::MovePara(SwWhichPara fnWhichPara, SwMoveFnCollection const &
//which is what SwCursorShell::UpdateCursorPos will reset
//the position to if we pass it a position in an
//invisible hidden paragraph field
- while (isInHiddenTextFrame(pTmpCursor)
+ while (isInHiddenFrame(pTmpCursor)
|| !IsAtStartOrEndOfFrame(this, pTmpCursor, fnPosPara))
{
if (!pTmpCursor->MovePara(fnWhichPara, fnPosPara))
@@ -1799,7 +1799,7 @@ void SwCursorShell::UpdateCursorPos()
SwShellCursor* pShellCursor = getShellCursor( true );
Size aOldSz( GetDocSize() );
- if (isInHiddenTextFrame(pShellCursor) && !ExtendedSelectedAll())
+ if (isInHiddenFrame(pShellCursor) && !ExtendedSelectedAll())
{
SwCursorMoveState aTmpState(CursorMoveState::SetOnlyText);
aTmpState.m_bSetInReadOnly = IsReadOnlyAvailable();
@@ -1808,14 +1808,14 @@ void SwCursorShell::UpdateCursorPos()
pShellCursor->DeleteMark();
// kde45196-1.html: try to get to a non-hidden paragraph, there must
// be one in the document body
- while (isInHiddenTextFrame(pShellCursor))
+ while (isInHiddenFrame(pShellCursor))
{
if (!pShellCursor->MovePara(GoNextPara, fnParaStart))
{
break;
}
}
- while (isInHiddenTextFrame(pShellCursor))
+ while (isInHiddenFrame(pShellCursor))
{
if (!pShellCursor->MovePara(GoPrevPara, fnParaStart))
{
diff --git a/sw/source/core/crsr/pam.cxx b/sw/source/core/crsr/pam.cxx
index aba72cb08795..92f17cbbd24d 100644
--- a/sw/source/core/crsr/pam.cxx
+++ b/sw/source/core/crsr/pam.cxx
@@ -1060,7 +1060,7 @@ SwContentNode* GetNode( SwPaM & rPam, bool& rbFirst, SwMoveFnCollection const &
(
nullptr == pFrame ||
( !bInReadOnly && pFrame->IsProtected() ) ||
- (pFrame->IsTextFrame() && static_cast<SwTextFrame const*>(pFrame)->IsHiddenNow())
+ pFrame->IsHiddenNow()
) ||
( !bInReadOnly && pNd->FindSectionNode() &&
pNd->FindSectionNode()->GetSection().IsProtect()
@@ -1101,8 +1101,7 @@ SwContentNode* GetNode( SwPaM & rPam, bool& rbFirst, SwMoveFnCollection const &
SwContentFrame const*const pFrame(pNd->getLayoutFrame(pLayout));
if (nullptr == pFrame ||
( !bInReadOnly && pFrame->IsProtected() ) ||
- ( pFrame->IsTextFrame() &&
- static_cast<SwTextFrame const*>(pFrame)->IsHiddenNow()))
+ pFrame->IsHiddenNow())
{
pNd = nullptr;
continue;
diff --git a/sw/source/core/doc/docedt.cxx b/sw/source/core/doc/docedt.cxx
index c78d8e18b633..2a5aad64de21 100644
--- a/sw/source/core/doc/docedt.cxx
+++ b/sw/source/core/doc/docedt.cxx
@@ -553,7 +553,7 @@ uno::Any SwDoc::Spell( SwPaM& rPaM,
{
nCurrNd = pNd->EndOfSectionIndex();
}
- else if( !static_cast<SwTextFrame*>(pContentFrame)->IsHiddenNow() )
+ else if( !pContentFrame->IsHiddenNow() )
{
if( pPageCnt && *pPageCnt && pPageSt )
{
@@ -766,7 +766,7 @@ static bool lcl_HyphenateNode( SwNode* pNd, void* pArgs )
// sw_redlinehide: this will be called once per node for merged nodes;
// the fully deleted ones won't have frames so are skipped.
SwContentFrame* pContentFrame = pNode->getLayoutFrame( pNode->GetDoc().getIDocumentLayoutAccess().GetCurrentLayout() );
- if( pContentFrame && !static_cast<SwTextFrame*>(pContentFrame)->IsHiddenNow() )
+ if( pContentFrame && !pContentFrame->IsHiddenNow() )
{
sal_uInt16 *pPageSt = pHyphArgs->GetPageSt();
sal_uInt16 *pPageCnt = pHyphArgs->GetPageCnt();
diff --git a/sw/source/core/docnode/ndsect.cxx b/sw/source/core/docnode/ndsect.cxx
index cf96e1d5094b..1da9ecb43ed6 100644
--- a/sw/source/core/docnode/ndsect.cxx
+++ b/sw/source/core/docnode/ndsect.cxx
@@ -1022,9 +1022,9 @@ SwSectionNode::~SwSectionNode()
}
}
-SwFrame *SwSectionNode::MakeFrame( SwFrame *pSib )
+SwFrame* SwSectionNode::MakeFrame(SwFrame* pSib, bool bHidden)
{
- m_pSection->m_Data.SetHiddenFlag(false);
+ m_pSection->m_Data.SetHiddenFlag(bHidden);
return new SwSectionFrame( *m_pSection, pSib );
}
diff --git a/sw/source/core/docnode/nodes.cxx b/sw/source/core/docnode/nodes.cxx
index 79efa02cf417..1808e42ab59c 100644
--- a/sw/source/core/docnode/nodes.cxx
+++ b/sw/source/core/docnode/nodes.cxx
@@ -1963,7 +1963,7 @@ SwContentNode* SwNodes::GoNextSection( SwNodeIndex * pIdx,
if (SwNodeType::Section == pNd->GetNodeType())
{
const SwSection& rSect = static_cast<const SwSectionNode*>(pNd)->GetSection();
- if( (bSkipHidden && rSect.IsHiddenFlag()) ||
+ if( (bSkipHidden && rSect.CalcHiddenFlag()) ||
(bSkipProtect && rSect.IsProtectFlag()) )
// than skip the section
aTmp = *pNd->EndOfSectionNode();
@@ -1974,7 +1974,7 @@ SwContentNode* SwNodes::GoNextSection( SwNodeIndex * pIdx,
{
const SwSection& rSect = static_cast<SwSectionNode*>(pNd->
m_pStartOfSection)->GetSection();
- if( (bSkipHidden && rSect.IsHiddenFlag()) ||
+ if( (bSkipHidden && rSect.CalcHiddenFlag()) ||
(bSkipProtect && rSect.IsProtectFlag()) )
// than skip the section
aTmp = *pNd->EndOfSectionNode();
@@ -1985,7 +1985,7 @@ SwContentNode* SwNodes::GoNextSection( SwNodeIndex * pIdx,
const SwSectionNode* pSectNd;
if( ( bSkipHidden || bSkipProtect ) &&
nullptr != (pSectNd = pNd->FindSectionNode() ) &&
- ( ( bSkipHidden && pSectNd->GetSection().IsHiddenFlag() ) ||
+ ( ( bSkipHidden && pSectNd->GetSection().CalcHiddenFlag() ) ||
( bSkipProtect && pSectNd->GetSection().IsProtectFlag() )) )
{
aTmp = *pSectNd->EndOfSectionNode();
diff --git a/sw/source/core/docnode/section.cxx b/sw/source/core/docnode/section.cxx
index 000d4fc15527..d655cf4acc8a 100644
--- a/sw/source/core/docnode/section.cxx
+++ b/sw/source/core/docnode/section.cxx
@@ -299,14 +299,11 @@ void SwSection::ImplSetHiddenFlag(bool const bTmpHidden, bool const bCondition)
// Tell all Children that they are hidden
const sw::SectionHidden aHint;
pFormat->CallSwClientNotify(aHint);
-
- // Delete all Frames
- pFormat->DelFrames();
}
}
else if (m_Data.IsHiddenFlag()) // show Nodes again
{
- // Show all Frames (Child Sections are accounted for by MakeFrames)
+ // Show all Frames
// Only if the Parent Section is not restricting us!
SwSection* pParentSect = pFormat->GetParentSection();
if( !pParentSect || !pParentSect->IsHiddenFlag() )
@@ -314,8 +311,6 @@ void SwSection::ImplSetHiddenFlag(bool const bTmpHidden, bool const bCondition)
// Tell all Children that the Parent is not hidden anymore
const sw::SectionHidden aHint(false);
pFormat->CallSwClientNotify(aHint);
-
- pFormat->MakeFrames();
}
}
}
diff --git a/sw/source/core/edit/editsh.cxx b/sw/source/core/edit/editsh.cxx
index 333eecd35262..0400dc887169 100644
--- a/sw/source/core/edit/editsh.cxx
+++ b/sw/source/core/edit/editsh.cxx
@@ -796,7 +796,7 @@ void SwEditShell::SetNumberingRestart()
if( nullptr != pContentFrame )
{
// skip hidden frames - ignore protection!
- if( !static_cast<SwTextFrame*>(pContentFrame)->IsHiddenNow() )
+ if( !pContentFrame->IsHiddenNow() )
{
// if the node is numbered and the starting value of the numbering equals the
// start value of the numbering rule then set this value as hard starting value
diff --git a/sw/source/core/inc/frame.hxx b/sw/source/core/inc/frame.hxx
index ebfe4a0f2bb4..65f392b3eadc 100644
--- a/sw/source/core/inc/frame.hxx
+++ b/sw/source/core/inc/frame.hxx
@@ -894,6 +894,8 @@ public:
// Fly in ... and footnotes
bool IsProtected() const;
+ virtual bool IsHiddenNow() const;
+
bool IsColLocked() const { return mbColLocked; }
virtual bool IsDeleteForbidden() const { return mnForbidDelete > 0; }
diff --git a/sw/source/core/inc/sectfrm.hxx b/sw/source/core/inc/sectfrm.hxx
index c07d78b12ba9..69158b335863 100644
--- a/sw/source/core/inc/sectfrm.hxx
+++ b/sw/source/core/inc/sectfrm.hxx
@@ -88,6 +88,8 @@ public:
virtual void Cut() override;
virtual void Paste( SwFrame* pParent, SwFrame* pSibling = nullptr ) override;
+ virtual bool IsHiddenNow() const override;
+
inline const SwSectionFrame *GetFollow() const;
inline SwSectionFrame *GetFollow();
SwSectionFrame* FindMaster() const;
diff --git a/sw/source/core/inc/txtfrm.hxx b/sw/source/core/inc/txtfrm.hxx
index a906571487f2..e4b568996b66 100644
--- a/sw/source/core/inc/txtfrm.hxx
+++ b/sw/source/core/inc/txtfrm.hxx
@@ -558,7 +558,7 @@ public:
#endif
/// Hidden
- bool IsHiddenNow() const; // bHidden && pOut == pPrt
+ virtual bool IsHiddenNow() const override; // bHidden && pOut == pPrt
void HideHidden(); // Remove appendage if Hidden
void HideFootnotes(TextFrameIndex nStart, TextFrameIndex nEnd);
diff --git a/sw/source/core/layout/calcmove.cxx b/sw/source/core/layout/calcmove.cxx
index c2bbdd8904f8..e13fdf012143 100644
--- a/sw/source/core/layout/calcmove.cxx
+++ b/sw/source/core/layout/calcmove.cxx
@@ -177,7 +177,7 @@ bool SwContentFrame::ShouldBwdMoved( SwLayoutFrame *pNewUpper, bool & )
if ( nMoveAnyway < 3 )
{
- if ( nSpace )
+ if (nSpace || IsHiddenNow())
{
// Do not notify footnotes which are stuck to the paragraph:
// This would require extremely confusing code, taking into
@@ -209,7 +209,7 @@ bool SwContentFrame::ShouldBwdMoved( SwLayoutFrame *pNewUpper, bool & )
}
// Check for space left in new upper
- return nSpace != 0;
+ return nSpace != 0 || IsHiddenNow();
}
}
return false;
@@ -532,7 +532,7 @@ static SwFrame* lcl_NotHiddenPrev( SwFrame* pFrame )
do
{
pRet = lcl_Prev( pRet );
- } while ( pRet && pRet->IsTextFrame() && static_cast<SwTextFrame*>(pRet)->IsHiddenNow() );
+ } while ( pRet && pRet->IsHiddenNow() );
return pRet;
}
@@ -1083,9 +1083,8 @@ void SwContentFrame::MakePrtArea( const SwBorderAttrs &rAttrs )
setFramePrintAreaValid(true);
SwRectFnSet aRectFnSet(this);
- const bool bTextFrame = IsTextFrame();
SwTwips nUpper = 0;
- if ( bTextFrame && static_cast<SwTextFrame*>(this)->IsHiddenNow() )
+ if (IsTextFrame() && IsHiddenNow())
{
if ( static_cast<SwTextFrame*>(this)->HasFollow() )
static_cast<SwTextFrame*>(this)->JoinFrame();
@@ -1715,7 +1714,7 @@ void SwContentFrame::MakeAll(vcl::RenderContext* /*pRenderContext*/)
const bool bMoveFwdInvalid = nullptr != GetIndNext();
const bool bNxtNew =
( 0 == aRectFnSet.GetHeight(pNxt->getFramePrintArea()) ) &&
- (!pNxt->IsTextFrame() ||!static_cast<SwTextFrame*>(pNxt)->IsHiddenNow());
+ !pNxt->IsHiddenNow();
pNxt->Calc(getRootFrame()->GetCurrShell()->GetOut());
@@ -2217,7 +2216,7 @@ bool SwContentFrame::WouldFit_( SwTwips nSpace,
pTmpPrev = nullptr;
else
{
- if( pFrame->IsTextFrame() && static_cast<SwTextFrame*>(pFrame)->IsHiddenNow() )
+ if (pFrame->IsHiddenNow())
pTmpPrev = lcl_NotHiddenPrev( pFrame );
else
pTmpPrev = pFrame;
diff --git a/sw/source/core/layout/findfrm.cxx b/sw/source/core/layout/findfrm.cxx
index 912e6166d2d9..466bb59b76be 100644
--- a/sw/source/core/layout/findfrm.cxx
+++ b/sw/source/core/layout/findfrm.cxx
@@ -1015,7 +1015,7 @@ SwFrame *SwFrame::FindNext_()
(!bFootnote || pSct->IsInFootnote() ) )
return pSct;
}
- return pRet;
+ return pRet == this ? nullptr : pRet;
}
// #i27138# - add parameter <_bInSameFootnote>
@@ -1401,11 +1401,7 @@ void SwFrame::InvalidateNextPrtArea()
SwFrame* pNextFrame = FindNext();
// skip empty section frames and hidden text frames
{
- while ( pNextFrame &&
- ( ( pNextFrame->IsSctFrame() &&
- !static_cast<SwSectionFrame*>(pNextFrame)->GetSection() ) ||
- ( pNextFrame->IsTextFrame() &&
- static_cast<SwTextFrame*>(pNextFrame)->IsHiddenNow() ) ) )
+ while (pNextFrame && pNextFrame->IsHiddenNow())
{
pNextFrame = pNextFrame->FindNext();
}
diff --git a/sw/source/core/layout/flowfrm.cxx b/sw/source/core/layout/flowfrm.cxx
index da509e2a6bea..88158161c530 100644
--- a/sw/source/core/layout/flowfrm.cxx
+++ b/sw/source/core/layout/flowfrm.cxx
@@ -1271,8 +1271,7 @@ bool SwFlowFrame::IsPageBreak( bool bAct ) const
// Determine predecessor
const SwFrame *pPrev = m_rThis.FindPrev();
- while ( pPrev && ( !pPrev->IsInDocBody() ||
- ( pPrev->IsTextFrame() && static_cast<const SwTextFrame*>(pPrev)->IsHiddenNow() ) ) )
+ while (pPrev && (!pPrev->IsInDocBody() || pPrev->IsHiddenNow()))
pPrev = pPrev->FindPrev();
if ( pPrev )
@@ -1333,7 +1332,7 @@ bool SwFlowFrame::IsColBreak( bool bAct ) const
// Determine predecessor
const SwFrame *pPrev = m_rThis.FindPrev();
while( pPrev && ( ( !pPrev->IsInDocBody() && !m_rThis.IsInFly() && !m_rThis.FindFooterOrHeader() ) ||
- ( pPrev->IsTextFrame() && static_cast<const SwTextFrame*>(pPrev)->IsHiddenNow() ) ) )
+ pPrev->IsHiddenNow() ) )
pPrev = pPrev->FindPrev();
if ( pPrev )
@@ -1364,6 +1363,14 @@ bool SwFlowFrame::IsColBreak( bool bAct ) const
return false;
}
+// Skip hidden paragraphs and empty sections on the same level
+static const SwFrame* skipHiddenSiblingFrames_(const SwFrame* pFrame)
+{
+ while (pFrame && pFrame->IsHiddenNow())
+ pFrame = pFrame->GetPrev();
+ return pFrame;
+}
+
bool SwFlowFrame::HasParaSpaceAtPages( bool bSct ) const
{
if( m_rThis.IsInSct() )
@@ -1379,7 +1386,7 @@ bool SwFlowFrame::HasParaSpaceAtPages( bool bSct ) const
return !pTmp->GetPrev() || IsPageBreak(true);
if( pTmp->IsColumnFrame() && pTmp->GetPrev() )
return IsColBreak( true );
- if( pTmp->IsSctFrame() && ( !bSct || pTmp->GetPrev() ) )
+ if (pTmp->IsSctFrame() && (!bSct || skipHiddenSiblingFrames_(pTmp->GetPrev())))
return false;
pTmp = pTmp->GetUpper();
}
@@ -1401,6 +1408,31 @@ bool SwFlowFrame::HasParaSpaceAtPages( bool bSct ) const
return pTmp && !pTmp->GetPrev();
}
+// Skip hidden paragraphs and empty sections
+static const SwFrame* skipHiddenFrames_(const SwFrame* pFrame)
+{
+ do
+ {
+ pFrame = skipHiddenSiblingFrames_(pFrame);
+ if (!pFrame || !pFrame->IsSctFrame())
+ return pFrame;
+ // Special case: found previous frame is a section
+ // Search for the last content in the section
+ auto pSectFrame = static_cast<const SwSectionFrame*>(pFrame);
+ pFrame = pSectFrame->FindLastContent();
+ // If the last content is in a table _inside_ the section,
+ // take the table herself.
+ // Correction: Check directly, if table is inside table, instead of indirectly
+ // by checking, if section isn't inside a table
+ if (pFrame && pFrame->IsInTab())
+ {
+ const SwTabFrame* pTableFrame = pFrame->FindTabFrame();
+ if (pSectFrame->IsAnLower(pTableFrame))
+ return pTableFrame;
+ }
+ } while (true);
+}
+
/** helper method to determine previous frame for calculation of the
upper space
@@ -1408,73 +1440,21 @@ bool SwFlowFrame::HasParaSpaceAtPages( bool bSct ) const
*/
const SwFrame* SwFlowFrame::GetPrevFrameForUpperSpaceCalc_( const SwFrame* _pProposedPrevFrame ) const
{
- const SwFrame* pPrevFrame = _pProposedPrevFrame
- ? _pProposedPrevFrame
- : m_rThis.GetPrev();
-
- // Skip hidden paragraphs and empty sections
- while ( pPrevFrame &&
- ( ( pPrevFrame->IsTextFrame() &&
- static_cast<const SwTextFrame*>(pPrevFrame)->IsHiddenNow() ) ||
- ( pPrevFrame->IsSctFrame() &&
- !static_cast<const SwSectionFrame*>(pPrevFrame)->GetSection() ) ) )
- {
- pPrevFrame = pPrevFrame->GetPrev();
- }
+ const SwFrame* pPrevFrame
+ = skipHiddenFrames_(_pProposedPrevFrame ? _pProposedPrevFrame : m_rThis.GetPrev());
+ if (pPrevFrame || !m_rThis.IsInFootnote()
+ || !(m_rThis.IsSctFrame() || !m_rThis.IsInSct() || !m_rThis.FindSctFrame()->IsInFootnote()))
+ return pPrevFrame;
// Special case: no direct previous frame is found but frame is in footnote
// Search for a previous frame in previous footnote,
// if frame isn't in a section, which is also in the footnote
- if ( !pPrevFrame && m_rThis.IsInFootnote() &&
- ( m_rThis.IsSctFrame() ||
- !m_rThis.IsInSct() || !m_rThis.FindSctFrame()->IsInFootnote() ) )
- {
- const SwFootnoteFrame* pPrevFootnoteFrame =
- static_cast<const SwFootnoteFrame*>(m_rThis.FindFootnoteFrame()->GetPrev());
- if ( pPrevFootnoteFrame )
- {
- pPrevFrame = pPrevFootnoteFrame->GetLastLower();
-
- // Skip hidden paragraphs and empty sections
- while ( pPrevFrame &&
- ( ( pPrevFrame->IsTextFrame() &&
- static_cast<const SwTextFrame*>(pPrevFrame)->IsHiddenNow() ) ||
- ( pPrevFrame->IsSctFrame() &&
- !static_cast<const SwSectionFrame*>(pPrevFrame)->GetSection() ) ) )
- {
- pPrevFrame = pPrevFrame->GetPrev();
- }
- }
- }
- // Special case: found previous frame is a section
- // Search for the last content in the section
- if( pPrevFrame && pPrevFrame->IsSctFrame() )
- {
- const SwSectionFrame* pPrevSectFrame =
- static_cast<const SwSectionFrame*>(pPrevFrame);
- pPrevFrame = pPrevSectFrame->FindLastContent();
- // If the last content is in a table _inside_ the section,
- // take the table herself.
- // Correction: Check directly, if table is inside table, instead of indirectly
- // by checking, if section isn't inside a table
- if ( pPrevFrame && pPrevFrame->IsInTab() )
- {
- const SwTabFrame* pTableFrame = pPrevFrame->FindTabFrame();
- if ( pPrevSectFrame->IsAnLower( pTableFrame ) )
- {
- pPrevFrame = pTableFrame;
- }
- }
- // Correction: skip hidden text frames
- while ( pPrevFrame &&
- pPrevFrame->IsTextFrame() &&
- static_cast<const SwTextFrame*>(pPrevFrame)->IsHiddenNow() )
- {
- pPrevFrame = pPrevFrame->GetPrev();
- }
- }
+ const SwFootnoteFrame* pPrevFootnoteFrame =
+ static_cast<const SwFootnoteFrame*>(m_rThis.FindFootnoteFrame()->GetPrev());
+ if ( pPrevFootnoteFrame )
+ return skipHiddenFrames_(pPrevFootnoteFrame->GetLastLower());
- return pPrevFrame;
+ return nullptr;
}
// This should be renamed to something like lcl_UseULSpacing
@@ -1912,6 +1892,8 @@ SwTwips SwFlowFrame::CalcAddLowerSpaceAsLastInTableCell(
/// Moves the Frame forward if it seems necessary regarding the current conditions and attributes.
bool SwFlowFrame::CheckMoveFwd( bool& rbMakePage, bool bKeep, bool bIgnoreMyOwnKeepValue )
{
+ if (m_rThis.IsHiddenNow())
+ return false;
const SwFrame* pNxt = m_rThis.GetIndNext();
if ( bKeep && //!bMovedBwd &&
@@ -2299,7 +2281,8 @@ bool SwFlowFrame::MoveBwd( bool &rbReformat )
)
pNewUpper = m_rThis.GetLeaf( MAKEPAGE_FTN, false );
}
- else if ( IsPageBreak( true ) ) // Do we have to respect a PageBreak?
+ // Do we have to respect a PageBreak?
+ else if (IsPageBreak(true) && (!m_rThis.IsInSct() || !m_rThis.FindSctFrame()->IsHiddenNow()))
{
// If the previous page doesn't have a Frame in the body,
// flowing back makes sense despite the PageBreak (otherwise,
@@ -2366,7 +2349,7 @@ bool SwFlowFrame::MoveBwd( bool &rbReformat )
}
}
}
- else if ( IsColBreak( true ) )
+ else if (IsColBreak(true))
{
// If the previous column doesn't contain a ContentFrame, flowing back
// makes sense despite the ColumnBreak, as otherwise we'd get
diff --git a/sw/source/core/layout/frmtool.cxx b/sw/source/core/layout/frmtool.cxx
index 423c08306919..635ed3ee3aec 100644
--- a/sw/source/core/layout/frmtool.cxx
+++ b/sw/source/core/layout/frmtool.cxx
@@ -844,11 +844,7 @@ void SwContentNotify::ImplDestroy()
SwFrame* pPrevFrame = pCnt->FindPrev();
// skip empty section frames and hidden text frames
{
- while ( pPrevFrame &&
- ( ( pPrevFrame->IsSctFrame() &&
- !static_cast<SwSectionFrame*>(pPrevFrame)->GetSection() ) ||
- ( pPrevFrame->IsTextFrame() &&
- static_cast<SwTextFrame*>(pPrevFrame)->IsHiddenNow() ) ) )
+ while (pPrevFrame && pPrevFrame->IsHiddenNow())
{
pPrevFrame = pPrevFrame->FindPrev();
}
@@ -1608,7 +1604,7 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
pFrame = pNode->IsTextNode()
? sw::MakeTextFrame(*pNode->GetTextNode(), pLay, eMode)
: pNode->MakeFrame(pLay);
- if( pPageMaker )
+ if (pPageMaker && !pLay->IsHiddenNow())
pPageMaker->CheckInsert( nIndex );
pFrame->InsertBehind( pLay, pPrv );
@@ -1766,15 +1762,11 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
continue; // skip it
}
SwSectionNode *pNode = static_cast<SwSectionNode*>(pNd);
- if( pNode->GetSection().CalcHiddenFlag() )
- // is hidden, skip the area
- nIndex = pNode->EndOfSectionIndex();
- else
{
if (pActualSection)
pActualSection->SetLastPos(pPrv);
- pFrame = pNode->MakeFrame( pLay );
+ pFrame = pNode->MakeFrame(pLay, pNode->GetSection().CalcHiddenFlag());
pActualSection.reset( new SwActualSection( pActualSection.release(),
static_cast<SwSectionFrame*>(pFrame), pNode ) );
if ( pActualSection->GetUpper() )
@@ -1945,7 +1937,8 @@ void InsertCnt_( SwLayoutFrame *pLay, SwDoc *pDoc,
}
else
{
- pFrame = pActualSection->GetSectionNode()->MakeFrame( pLay );
+ pFrame = pActualSection->GetSectionNode()->MakeFrame(
+ pLay, pActualSection->GetSectionNode()->GetSection().IsHiddenFlag());
pFrame->InsertBehind( pLay, pPrv );
static_cast<SwSectionFrame*>(pFrame)->Init();
@@ -2523,8 +2516,7 @@ void SwBorderAttrs::CalcJoinedWithPrev( const SwFrame& _rFrame,
// one as previous frame.
const SwFrame* pPrevFrame = _pPrevFrame ? _pPrevFrame : _rFrame.GetPrev();
// OD 2004-02-13 #i25029# - skip hidden text frames.
- while ( pPrevFrame && pPrevFrame->IsTextFrame() &&
- static_cast<const SwTextFrame*>(pPrevFrame)->IsHiddenNow() )
+ while (pPrevFrame && pPrevFrame->IsHiddenNow())
{
pPrevFrame = pPrevFrame->GetPrev();
}
@@ -2555,8 +2547,7 @@ void SwBorderAttrs::CalcJoinedWithNext( const SwFrame& _rFrame ) const
// corresponding attribute set is set at current text frame.
// OD 2004-02-13 #i25029# - get next frame, but skip hidden text frames.
const SwFrame* pNextFrame = _rFrame.GetNext();
- while ( pNextFrame && pNextFrame->IsTextFrame() &&
- static_cast<const SwTextFrame*>(pNextFrame)->IsHiddenNow() )
+ while (pNextFrame && pNextFrame->IsHiddenNow())
{
pNextFrame = pNextFrame->GetNext();
}
diff --git a/sw/source/core/layout/ftnfrm.cxx b/sw/source/core/layout/ftnfrm.cxx
index 350ec7034bc8..2c8583f85b65 100644
--- a/sw/source/core/layout/ftnfrm.cxx
+++ b/sw/source/core/layout/ftnfrm.cxx
@@ -2983,13 +2983,9 @@ SwContentFrame* SwFootnoteFrame::FindLastContent()
while ( pTmpLastLower && pTmpLastLower->GetNext() )
{
pTmpLastLower = pTmpLastLower->GetNext();
- if ( ( pTmpLastLower->IsTextFrame() &&
- !static_cast<SwTextFrame*>(pTmpLastLower)->IsHiddenNow() ) ||
- ( pTmpLastLower->IsSctFrame() &&
- static_cast<SwSectionFrame*>(pTmpLastLower)->GetSection() &&
- static_cast<SwSectionFrame*>(pTmpLastLower)->ContainsContent() ) ||
- ( pTmpLastLower->IsTabFrame() &&
- static_cast<SwTabFrame*>(pTmpLastLower)->ContainsContent() ) )
+ if (!pTmpLastLower->IsHiddenNow()
+ && (!pTmpLastLower->IsLayoutFrame()
+ || static_cast<SwLayoutFrame*>(pTmpLastLower)->ContainsContent()))
{
pLastLowerOfFootnote = pTmpLastLower;
}
diff --git a/sw/source/core/layout/pagechg.cxx b/sw/source/core/layout/pagechg.cxx
index bf4bcc45ea3a..f8c029ea12cd 100644
--- a/sw/source/core/layout/pagechg.cxx
+++ b/sw/source/core/layout/pagechg.cxx
@@ -789,7 +789,10 @@ SwPageDesc *SwPageFrame::FindPageDesc()
return pRet;
}
- SwFrame *pFlow = FindFirstBodyContent();
+ SwContentFrame* pFirstContent = FindFirstBodyContent();
+ while (pFirstContent && pFirstContent->IsHiddenNow())
+ pFirstContent = pFirstContent->GetNextContentFrame();
+ SwFrame* pFlow = pFirstContent;
if ( pFlow && pFlow->IsInTab() )
pFlow = pFlow->FindTabFrame();
diff --git a/sw/source/core/layout/sectfrm.cxx b/sw/source/core/layout/sectfrm.cxx
index a1fd849ec495..3967a1f56442 100644
--- a/sw/source/core/layout/sectfrm.cxx
+++ b/sw/source/core/layout/sectfrm.cxx
@@ -189,6 +189,13 @@ SwSectionFrame::~SwSectionFrame()
{
}
+//virtual
+bool SwSectionFrame::IsHiddenNow() const
+{
+ const auto* pSection = GetSection();
+ return !pSection || pSection->CalcHiddenFlag();
+}
+
void SwSectionFrame::DelEmpty( bool bRemove )
{
if( IsColLocked() )
@@ -1371,6 +1378,20 @@ void SwSectionFrame::Format( vcl::RenderContext* pRenderContext, const SwBorderA
SwRectFnSet aRectFnSet(this);
+ if (GetSection()->CalcHiddenFlag())
+ {
+ {
+ SwFrameAreaDefinition::FrameAreaWriteAccess aFrm(*this);
+ aRectFnSet.SetHeight(aFrm, 0);
+ }
+ {
+ SwFrameAreaDefinition::FramePrintAreaWriteAccess aPrt(*this);
+ aRectFnSet.SetHeight(aPrt, 0);
+ }
+ setFrameAreaSizeValid(true);
+ setFramePrintAreaValid(true);
+ }
+
if ( !isFramePrintAreaValid() )
{
PROTOCOL( this, PROT::PrintArea, DbgAction::NONE, nullptr )
@@ -2182,6 +2203,11 @@ bool SwSectionFrame::Growable() const
SwTwips SwSectionFrame::Grow_( SwTwips nDist, bool bTst )
{
+ if (GetSection()->CalcHiddenFlag())
+ {
+ return 0;
+ }
+
if ( !IsColLocked() && !HasFixSize() )
{
SwRectFnSet aRectFnSet(this);
@@ -2646,6 +2672,17 @@ void SwSectionFrame::SwClientNotify(const SwModify& rMod, const SfxHint& rHint)
return;
SwSectionFrame::MoveContentAndDelete(this, pHint->IsSaveContent());
}
+ else if (rHint.GetId() == SfxHintId::SwSectionHidden)
+ {
+ InvalidateAll();
+ InvalidateObjs(false);
+
+ for (SwFrame* pLowerFrame = Lower(); pLowerFrame; pLowerFrame = pLowerFrame->GetNext())
+ {
+ pLowerFrame->InvalidateAll();
+ pLowerFrame->InvalidateObjs(false);
+ }
+ }
else
SwFrame::SwClientNotify(rMod, rHint);
}
diff --git a/sw/source/core/layout/tabfrm.cxx b/sw/source/core/layout/tabfrm.cxx
index 98dc1f2743b4..a9efde0d3708 100644
--- a/sw/source/core/layout/tabfrm.cxx
+++ b/sw/source/core/layout/tabfrm.cxx
@@ -1454,6 +1454,8 @@ namespace
auto IsAllHiddenSection(SwSectionFrame const& rSection) -> bool
{
+ if (rSection.IsHiddenNow())
+ return true;
for (SwFrame const* pFrame = rSection.Lower(); pFrame; pFrame = pFrame->GetNext())
{
if (pFrame->IsColumnFrame())
@@ -1474,7 +1476,7 @@ namespace
}
else if (pFrame->IsTextFrame())
{
- if (!static_cast<SwTextFrame const*>(pFrame)->IsHiddenNow())
+ if (!pFrame->IsHiddenNow())
{
return false;
}
@@ -1509,7 +1511,7 @@ namespace
}
else if (pFrame->IsTextFrame())
{
- if (!static_cast<SwTextFrame const*>(pFrame)->IsHiddenNow())
+ if (!pFrame->IsHiddenNow())
{
return false;
}
diff --git a/sw/source/core/layout/trvlfrm.cxx b/sw/source/core/layout/trvlfrm.cxx
index 8d8da2a3b724..14096ae308ce 100644
--- a/sw/source/core/layout/trvlfrm.cxx
+++ b/sw/source/core/layout/trvlfrm.cxx
@@ -52,6 +52,7 @@
#include <ndtxt.hxx>
#include <undobj.hxx>
#include <flyfrms.hxx>
+#include <sectfrm.hxx>
#include <swselectionlist.hxx>
#include <comphelper/lok.hxx>
@@ -816,8 +817,7 @@ static bool lcl_UpDown( SwPaM *pPam, const SwContentFrame *pStart,
//If I'm in the DocumentBody, I want to stay there.
if ( pStart->IsInDocBody() )
{
- while ( pCnt && (!pCnt->IsInDocBody() ||
- (pCnt->IsTextFrame() && static_cast<const SwTextFrame*>(pCnt)->IsHiddenNow())))
+ while (pCnt && (!pCnt->IsInDocBody() || pCnt->IsHiddenNow()))
{
pCnt = (*fnNxtPrv)( pCnt );
pCnt = ::lcl_MissProtectedFrames( pCnt, fnNxtPrv, true, bInReadOnly, bTableSel );
@@ -828,8 +828,7 @@ static bool lcl_UpDown( SwPaM *pPam, const SwContentFrame *pStart,
//case of necessity.
else if ( pStart->IsInFootnote() )
{
- while ( pCnt && (!pCnt->IsInFootnote() ||
- (pCnt->IsTextFrame() && static_cast<const SwTextFrame*>(pCnt)->IsHiddenNow())))
+ while (pCnt && (!pCnt->IsInFootnote() || pCnt->IsHiddenNow()))
{
pCnt = (*fnNxtPrv)( pCnt );
pCnt = ::lcl_MissProtectedFrames( pCnt, fnNxtPrv, true, bInReadOnly, bTableSel );
@@ -839,7 +838,7 @@ static bool lcl_UpDown( SwPaM *pPam, const SwContentFrame *pStart,
//In Flys we can go ahead blindly as long as we find a Content.
else if ( pStart->IsInFly() )
{
- if ( pCnt && pCnt->IsTextFrame() && static_cast<const SwTextFrame*>(pCnt)->IsHiddenNow() )
+ if (pCnt && pCnt->IsHiddenNow())
{
pCnt = (*fnNxtPrv)( pCnt );
pCnt = ::lcl_MissProtectedFrames( pCnt, fnNxtPrv, true, bInReadOnly, bTableSel );
@@ -863,7 +862,7 @@ static bool lcl_UpDown( SwPaM *pPam, const SwContentFrame *pStart,
}
if ( !bSame )
pCnt = nullptr;
- else if (pCnt->IsTextFrame() && static_cast<const SwTextFrame*>(pCnt)->IsHiddenNow()) // i73332
+ else if (pCnt->IsHiddenNow()) // i73332
{
pCnt = (*fnNxtPrv)( pCnt );
pCnt = ::lcl_MissProtectedFrames( pCnt, fnNxtPrv, true, bInReadOnly, bTableSel );
@@ -946,8 +945,7 @@ static bool lcl_UpDown( SwPaM *pPam, const SwContentFrame *pStart,
}
}
- } while ( !bEnd ||
- (pCnt && pCnt->IsTextFrame() && static_cast<const SwTextFrame*>(pCnt)->IsHiddenNow()));
+ } while (!bEnd || (pCnt && pCnt->IsHiddenNow()));
if (pCnt == nullptr)
{
@@ -1234,7 +1232,7 @@ const SwContentFrame *SwLayoutFrame::GetContentPos( Point& rPoint,
if ( pComp != pContent )
continue;
- if ( !pContent->IsTextFrame() || !static_cast<const SwTextFrame*>(pContent)->IsHiddenNow() )
+ if (!pContent->IsHiddenNow())
{
SwRect aContentFrame( pContent->UnionFrame() );
if ( aContentFrame.Contains( rPoint ) )
@@ -1718,6 +1716,15 @@ bool SwFrame::IsProtected() const
return false;
}
+// virtual
+bool SwFrame::IsHiddenNow() const
+{
+ if (const auto* pSectFrame = FindSctFrame())
+ return pSectFrame->IsHiddenNow();
+
+ return false;
+}
+
/** @return the physical page number */
sal_uInt16 SwFrame::GetPhyPageNum() const
{
diff --git a/sw/source/core/text/txtfrm.cxx b/sw/source/core/text/txtfrm.cxx
index c3b4f76e8a5f..4ce78faf1e4f 100644
--- a/sw/source/core/text/txtfrm.cxx
+++ b/sw/source/core/text/txtfrm.cxx
@@ -1484,6 +1484,9 @@ bool SwTextFrame::IsHiddenNow() const
return true;
}
+ if (SwContentFrame::IsHiddenNow())
+ return true;
+
bool bHiddenCharsHidePara(false);
bool bHiddenParaField(false);
if (m_pMergedPara)
@@ -1553,22 +1556,14 @@ bool SwTextFrame::IsHiddenNow() const
// be visible - check this for the 1st body paragraph
if (IsInDocBody() && FindPrevCnt() == nullptr)
{
- bool isAllHidden(true);
for (SwContentFrame const* pNext = FindNextCnt(true);
pNext != nullptr; pNext = pNext->FindNextCnt(true))
{
- if (!pNext->IsTextFrame()
- || !static_cast<SwTextFrame const*>(pNext)->IsHiddenNow())
- {
- isAllHidden = false;
- break;
- }
- }
- if (isAllHidden)
- {
- SAL_INFO("sw.core", "unhiding one body paragraph");
- return false;
+ if (!pNext->IsHiddenNow())
+ return true;
}
+ SAL_INFO("sw.core", "unhiding one body paragraph");
+ return false;
}
return true;
}