1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
19 #ifndef INCLUDED_SW_INC_NDINDEX_HXX
20 #define INCLUDED_SW_INC_NDINDEX_HXX
27 #include "nodeoffset.hxx"
29 /// Marks a node in the document model.
30 class SAL_WARN_UNUSED SW_DLLPUBLIC SwNodeIndex final
: public sw::Ring
<SwNodeIndex
>
36 SwNodes
& rNodes
= GetNodes();
37 if(!rNodes
.m_vIndices
)
39 #if defined(__GNUC__) && (__GNUC__ == 12 || __GNUC__ == 13)
40 #pragma GCC diagnostic push
41 #pragma GCC diagnostic ignored "-Wdangling-pointer"
43 rNodes
.m_vIndices
= this;
44 #if defined(__GNUC__) && (__GNUC__ == 12 || __GNUC__ == 13)
45 #pragma GCC diagnostic pop
48 MoveTo(rNodes
.m_vIndices
);
50 void DeRegisterIndex()
52 SwNodes
& rNodes
= GetNodes();
53 if(rNodes
.m_vIndices
== this)
54 rNodes
.m_vIndices
= GetNextInRing();
56 if(rNodes
.m_vIndices
== this)
57 rNodes
.m_vIndices
= nullptr;
60 SwNodeIndex(SwNode
* pNode
) : m_pNode(pNode
) { RegisterIndex(); }
63 SwNodeIndex( SwNodes
& rNds
, sal_Int32 nIdx
) : SwNodeIndex(rNds
, SwNodeOffset(nIdx
)) {}
64 explicit SwNodeIndex( SwNodes
& rNds
, SwNodeOffset nIdx
= SwNodeOffset(0) )
65 : SwNodeIndex( rNds
[ nIdx
] ) {}
67 SwNodeIndex( const SwNodeIndex
& rIdx
, sal_Int32 nDiff
) : SwNodeIndex(rIdx
, SwNodeOffset(nDiff
)) {}
68 SwNodeIndex( const SwNodeIndex
& rIdx
, SwNodeOffset nDiff
= SwNodeOffset(0) )
69 : SwNodeIndex( nDiff
? rIdx
.GetNodes()[ rIdx
.GetIndex() + nDiff
] : rIdx
.m_pNode
) {}
71 SwNodeIndex( const SwNode
& rNd
, sal_Int32 nDiff
) : SwNodeIndex(rNd
, SwNodeOffset(nDiff
)) {}
72 explicit SwNodeIndex( const SwNode
& rNd
)
73 : SwNodeIndex( const_cast<SwNode
*>(&rNd
) ) {}
74 explicit SwNodeIndex( const SwNode
& rNd
, SwNodeOffset nDiff
)
75 : SwNodeIndex( nDiff
? *rNd
.GetNodes()[ rNd
.GetIndex() + nDiff
] : rNd
) {}
77 virtual ~SwNodeIndex() override
{ DeRegisterIndex(); }
79 SwNodeIndex
& operator++() { return operator+=(SwNodeOffset(1)); }
80 SwNodeIndex
& operator--() { return operator-=(SwNodeOffset(1)); }
82 SwNodeIndex
& operator+=( SwNodeOffset nOffset
) { return operator=(GetIndex() + nOffset
); }
83 SwNodeIndex
& operator-=( SwNodeOffset nOffset
) { return operator=(GetIndex() - nOffset
); }
85 bool operator<( const SwNodeIndex
& rIndex
) const { return operator<(rIndex
.GetNode()); }
86 bool operator<=( const SwNodeIndex
& rIndex
) const { return operator<=(rIndex
.GetNode()); }
87 bool operator>( const SwNodeIndex
& rIndex
) const { return operator>(rIndex
.GetNode()); }
88 bool operator>=( const SwNodeIndex
& rIndex
) const { return operator>=(rIndex
.GetNode()); }
89 bool operator==( const SwNodeIndex
& rIndex
) const { return operator==(rIndex
.GetNode()); }
90 bool operator!=( const SwNodeIndex
& rIndex
) const { return operator!=(rIndex
.GetNode()); }
92 bool operator<( SwNodeOffset nOther
) const { return GetIndex() < nOther
; }
93 bool operator<=( SwNodeOffset nOther
) const { return GetIndex() <= nOther
; }
94 bool operator>( SwNodeOffset nOther
) const { return GetIndex() > nOther
; }
95 bool operator>=( SwNodeOffset nOther
) const { return GetIndex() >= nOther
; }
96 bool operator==( SwNodeOffset nOther
) const { return GetIndex() == nOther
; }
97 bool operator!=( SwNodeOffset nOther
) const { return GetIndex() != nOther
; }
99 bool operator<( const SwNode
& rNd
) const { assert(&GetNodes() == &rNd
.GetNodes()); return operator<(rNd
.GetIndex()); }
100 bool operator<=( const SwNode
& rNd
) const { return operator==(rNd
) || operator<(rNd
); }
101 bool operator>( const SwNode
& rNd
) const { assert(&GetNodes() == &rNd
.GetNodes()); return operator>(rNd
.GetIndex()); }
102 bool operator>=( const SwNode
& rNd
) const { return operator==(rNd
) || operator>(rNd
); }
103 bool operator==( const SwNode
& rNd
) const { return m_pNode
== &rNd
; }
104 bool operator!=( const SwNode
& rNd
) const { return m_pNode
!= &rNd
; }
106 inline SwNodeIndex
& operator=( SwNodeOffset
);
107 SwNodeIndex
& operator=( const SwNodeIndex
& rIdx
) { return operator=(*rIdx
.m_pNode
); }
108 inline SwNodeIndex
& operator=( const SwNode
& );
110 // Return value of index as SwNodeOffset.
111 SwNodeOffset
GetIndex() const { return m_pNode
->GetIndex(); }
113 // Enables assignments without creation of a temporary object.
114 SwNodeIndex
& Assign( SwNodes
const & rNds
, SwNodeOffset nIdx
) { return operator=(*rNds
[nIdx
]); }
115 SwNodeIndex
& Assign( const SwNode
& rNd
, sal_Int32 nOffset
) { return Assign(rNd
, SwNodeOffset(nOffset
)); }
116 inline SwNodeIndex
& Assign( const SwNode
& rNd
, SwNodeOffset nOffset
= SwNodeOffset(0) );
118 // Gets pointer on NodesArray.
119 const SwNodes
& GetNodes() const { return m_pNode
->GetNodes(); }
120 SwNodes
& GetNodes() { return m_pNode
->GetNodes(); }
122 const SwNodeIndex
* GetNext() const { return GetNextInRing(); }
123 SwNode
& GetNode() const { return *m_pNode
; }
126 inline std::ostream
&operator <<(std::ostream
& s
, const SwNodeIndex
& index
)
128 return s
<< "SwNodeIndex (node " << sal_Int32(index
.GetIndex()) << ")";
133 class SW_DLLPUBLIC SwNodeRange
139 SwNodeRange( const SwNodeIndex
&rS
, const SwNodeIndex
&rE
)
140 : aStart( rS
), aEnd( rE
) {}
141 SwNodeRange( const SwNode
&rS
, const SwNode
&rE
)
142 : aStart( rS
), aEnd( rE
) {}
143 SwNodeRange( const SwNodeRange
&rRange
) = default;
145 SwNodeRange( SwNodes
& rNds
, SwNodeOffset nSttIdx
, SwNodeOffset nEndIdx
= SwNodeOffset(0) )
146 : aStart( rNds
, nSttIdx
), aEnd( rNds
, nEndIdx
) {}
148 SwNodeRange( const SwNodeIndex
& rS
, SwNodeOffset nSttDiff
, const SwNodeIndex
& rE
, SwNodeOffset nEndDiff
= SwNodeOffset(0) )
149 : aStart( rS
, nSttDiff
), aEnd( rE
, nEndDiff
) {}
150 SwNodeRange( const SwNode
& rS
, SwNodeOffset nSttDiff
, const SwNode
& rE
, SwNodeOffset nEndDiff
= SwNodeOffset(0) )
151 : aStart( rS
, nSttDiff
), aEnd( rE
, nEndDiff
) {}
154 // For inlines node.hxx is needed which in turn needs this one.
155 // Therefore all inlines accessing m_pNode are implemented here.
157 inline SwNodeIndex
& SwNodeIndex::operator=( SwNodeOffset
const nNew
)
159 m_pNode
= GetNodes()[ nNew
];
163 SwNodeIndex
& SwNodeIndex::operator=( const SwNode
& rNd
)
165 if (&GetNodes() != &rNd
.GetNodes())
168 m_pNode
= const_cast<SwNode
*>(&rNd
);
172 m_pNode
= const_cast<SwNode
*>(&rNd
);
176 SwNodeIndex
& SwNodeIndex::Assign( const SwNode
& rNd
, SwNodeOffset nOffset
)
181 m_pNode
= GetNodes()[ GetIndex() + nOffset
];
188 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */