xref: /AOO41X/main/sw/source/core/fields/chpfld.cxx (revision 8809db7a87f97847b57a57f4cd2b0104b2b83182)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_sw.hxx"
26 
27 
28 #include <com/sun/star/text/ChapterFormat.hpp>
29 #include <doc.hxx>
30 #include <frame.hxx>        // SwChapterFieldType::ChangeExpansion()
31 #include <pam.hxx>          // fuer GetBodyTxtNode
32 #include <ndtxt.hxx>
33 #include <chpfld.hxx>
34 #include <expfld.hxx>       // fuer GetBodyTxtNode
35 #ifndef _UNOFLDMID_H
36 #include <unofldmid.h>
37 #endif
38 #include <numrule.hxx>
39 
40 using namespace ::com::sun::star;
41 
42 /*--------------------------------------------------------------------
43     Beschreibung: SwChapterFieldType
44  --------------------------------------------------------------------*/
45 
46 
47 SwChapterFieldType::SwChapterFieldType()
48     : SwFieldType( RES_CHAPTERFLD )
49 {
50 }
51 
52 
53 SwFieldType* SwChapterFieldType::Copy() const
54 {
55     return new SwChapterFieldType();
56 }
57 
58 
59 /*--------------------------------------------------------------------
60     Beschreibung: Kapittelfeld
61  --------------------------------------------------------------------*/
62 
63 
64 SwChapterField::SwChapterField(SwChapterFieldType* pTyp, sal_uInt32 nFmt)
65     : SwField(pTyp, nFmt), nLevel( 0 )
66 {}
67 
68 
69 String SwChapterField::Expand() const
70 {
71     String sStr( sNumber );
72     switch( GetFormat() )
73     {
74         case CF_TITLE:      sStr = sTitle;  break;
75 
76         case CF_NUMBER:
77         case CF_NUM_TITLE:  sStr.Insert( sPre, 0 );
78                             sStr += sPost;
79                             if( CF_NUM_TITLE == GetFormat() )
80                                 sStr += sTitle;
81                             break;
82 
83         case CF_NUM_NOPREPST_TITLE: sStr += sTitle; break;
84     }
85     return sStr;
86 }
87 
88 
89 SwField* SwChapterField::Copy() const
90 {
91     SwChapterField *pTmp =
92         new SwChapterField((SwChapterFieldType*)GetTyp(), GetFormat());
93     pTmp->nLevel = nLevel;
94     pTmp->sTitle = sTitle;
95     pTmp->sNumber = sNumber;
96     pTmp->sPost = sPost;
97     pTmp->sPre = sPre;
98 
99     return pTmp;
100 }
101 
102 // --> OD 2008-02-14 #i53420#
103 //void SwChapterField::ChangeExpansion( const SwFrm* pFrm,
104 //                                      const SwTxtNode* pTxtNd,
105 //                                      sal_Bool bSrchNum )
106 //{
107 //    ASSERT( pFrm, "in welchem Frame stehe ich denn?" )
108 //    SwDoc* pDoc = (SwDoc*)pTxtNd->GetDoc();
109 //    SwPosition aPos( pDoc->GetNodes().GetEndOfContent() );
110 
111 //    if( pFrm->IsInDocBody() )
112 //        aPos.nNode = *pTxtNd;
113 //    else if( 0 == (pTxtNd = GetBodyTxtNode( *pDoc, aPos, *pFrm )) )
114 //        // kein TxtNode (Formatierung Kopf/Fusszeile)
115 //        return;
116 //    ChangeExpansion(*pTxtNd, bSrchNum);
117 //}
118 void SwChapterField::ChangeExpansion(const SwFrm* pFrm,
119                                       const SwCntntNode* pCntntNode,
120                                       sal_Bool bSrchNum )
121 {
122     ASSERT( pFrm, "in welchem Frame stehe ich denn?" )
123     SwDoc* pDoc = (SwDoc*)pCntntNode->GetDoc();
124 
125     const SwTxtNode* pTxtNode = dynamic_cast<const SwTxtNode*>(pCntntNode);
126     if ( !pTxtNode || !pFrm->IsInDocBody() )
127     {
128         SwPosition aDummyPos( pDoc->GetNodes().GetEndOfContent() );
129         pTxtNode = GetBodyTxtNode( *pDoc, aDummyPos, *pFrm );
130     }
131 
132     if ( pTxtNode )
133     {
134         ChangeExpansion( *pTxtNode, bSrchNum );
135     }
136 }
137 // <--
138 
139 void SwChapterField::ChangeExpansion(const SwTxtNode &rTxtNd, sal_Bool bSrchNum)
140 {
141     SwDoc* pDoc = (SwDoc*)rTxtNd.GetDoc();
142     const SwTxtNode *pTxtNd = rTxtNd.FindOutlineNodeOfLevel( nLevel );
143     if( pTxtNd )
144     {
145         if( bSrchNum )
146         {
147             const SwTxtNode* pONd = pTxtNd;
148             do {
149                 if( pONd && pONd->GetTxtColl() )
150                 {
151                     sal_uInt8 nPrevLvl = nLevel;
152 
153                     // --> OD 2008-04-02 #refactorlists#
154 //                    nLevel = GetRealLevel( pONd->GetTxtColl()->
155 //                                            GetOutlineLevel() );
156                     //ASSERT( pONd->GetOutlineLevel() >= 0 && pONd->GetOutlineLevel() < MAXLEVEL,   //#outline level,zhaojianwei
157                     //        "<SwChapterField::ChangeExpansion(..)> - outline node with inconsistent outline level. Serious defect -> please inform OD." );
158                     //nLevel = static_cast<sal_uInt8>(pONd->GetOutlineLevel());
159                     ASSERT( pONd->GetAttrOutlineLevel() >= 0 && pONd->GetAttrOutlineLevel() <= MAXLEVEL,
160                             "<SwChapterField::ChangeExpansion(..)> - outline node with inconsistent outline level. Serious defect -> please inform OD." );
161                     nLevel = static_cast<sal_uInt8>(pONd->GetAttrOutlineLevel());                           //<-end,zhaojianwei
162                     // <--
163 
164                     if( nPrevLvl < nLevel )
165                         nLevel = nPrevLvl;
166                     else if( SVX_NUM_NUMBER_NONE != pDoc->GetOutlineNumRule()
167                             ->Get( nLevel ).GetNumberingType() )
168                     {
169                         pTxtNd = pONd;
170                         break;
171                     }
172 
173                     if( !nLevel-- )
174                         break;
175                     pONd = pTxtNd->FindOutlineNodeOfLevel( nLevel );
176                 }
177                 else
178                     break;
179             } while( sal_True );
180         }
181 
182         // nur die Nummer besorgen, ohne Pre-/Post-fixstrings
183 
184         if ( pTxtNd->IsOutline() )
185         {
186             // --> OD 2005-11-17 #128041#
187             // correction of refactoring done by cws swnumtree:
188             // retrieve numbering string without prefix and suffix strings
189             // as stated in the above german comment.
190             sNumber = pTxtNd->GetNumString( false );
191             // <--
192 
193             SwNumRule* pRule( pTxtNd->GetNumRule() );
194             if ( pTxtNd->IsCountedInList() && pRule )
195             {
196                 const SwNumFmt& rNFmt = pRule->Get( static_cast<sal_uInt16>(pTxtNd->GetActualListLevel()) );
197                 sPost = rNFmt.GetSuffix();
198                 sPre = rNFmt.GetPrefix();
199             }
200             else
201                 sPost = aEmptyStr, sPre = aEmptyStr;
202         }
203         else
204         {
205             sPost = aEmptyStr;
206             sPre = aEmptyStr;
207             sNumber = String("??", RTL_TEXTENCODING_ASCII_US);
208         }
209 
210         sTitle = pTxtNd->GetExpandTxt();
211 
212         for( xub_StrLen i = 0; i < sTitle.Len(); ++i )
213             if( ' ' > sTitle.GetChar( i ) )
214                 sTitle.Erase( i--, 1 );
215     }
216     else
217     {
218         sNumber = aEmptyStr;
219         sTitle = aEmptyStr;
220         sPost = aEmptyStr;
221         sPre = aEmptyStr;
222     }
223 }
224 
225 /*-----------------05.03.98 16:19-------------------
226 
227 --------------------------------------------------*/
228 sal_Bool SwChapterField::QueryValue( uno::Any& rAny, sal_uInt16 nWhichId ) const
229 {
230     switch( nWhichId )
231     {
232     case FIELD_PROP_BYTE1:
233         rAny <<= (sal_Int8)nLevel;
234         break;
235 
236     case FIELD_PROP_USHORT1:
237         {
238             sal_Int16 nRet;
239             switch( GetFormat() )
240             {
241                 case CF_NUMBER: nRet = text::ChapterFormat::NUMBER; break;
242                 case CF_TITLE:  nRet = text::ChapterFormat::NAME; break;
243                 case CF_NUMBER_NOPREPST:
244                     nRet = text::ChapterFormat::DIGIT;
245                 break;
246                 case CF_NUM_NOPREPST_TITLE:
247                     nRet = text::ChapterFormat::NO_PREFIX_SUFFIX;
248                 break;
249                 case CF_NUM_TITLE:
250                 default:        nRet = text::ChapterFormat::NAME_NUMBER;
251             }
252             rAny <<= nRet;
253         }
254         break;
255 
256     default:
257         DBG_ERROR("illegal property");
258     }
259     return sal_True;
260 }
261 /*-----------------05.03.98 16:19-------------------
262 
263 --------------------------------------------------*/
264 sal_Bool SwChapterField::PutValue( const uno::Any& rAny, sal_uInt16 nWhichId )
265 {
266     sal_Bool bRet = sal_True;
267     switch( nWhichId )
268     {
269     case FIELD_PROP_BYTE1:
270     {
271         sal_Int8 nTmp = 0;
272         rAny >>= nTmp;
273         if(nTmp >= 0 && nTmp < MAXLEVEL)
274             nLevel = nTmp;
275         else
276             bRet = sal_False;
277         break;
278     }
279 
280     case FIELD_PROP_USHORT1:
281         {
282             sal_Int16 nVal = 0;
283             rAny >>= nVal;
284             switch( nVal )
285             {
286                 case text::ChapterFormat::NAME: SetFormat(CF_TITLE); break;
287                 case text::ChapterFormat::NUMBER:  SetFormat(CF_NUMBER); break;
288                 case text::ChapterFormat::NO_PREFIX_SUFFIX:
289                             SetFormat(CF_NUM_NOPREPST_TITLE);
290                 break;
291                 case text::ChapterFormat::DIGIT:
292                         SetFormat(CF_NUMBER_NOPREPST);
293                 break;
294                 //case text::ChapterFormat::NAME_NUMBER:
295                 default:        SetFormat(CF_NUM_TITLE);
296             }
297         }
298         break;
299 
300     default:
301         DBG_ERROR("illegal property");
302         bRet = sal_False;
303     }
304     return bRet;
305 }
306