xref: /AOO41X/main/sc/source/filter/xml/xmlsorti.cxx (revision b3f79822e811ac3493b185030a72c3c5a51f32d8)
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_sc.hxx"
26 
27 
28 
29 // INCLUDE ---------------------------------------------------------------
30 
31 #include "xmlsorti.hxx"
32 #include "xmlimprt.hxx"
33 #include "docuno.hxx"
34 #include "convuno.hxx"
35 #include "XMLConverter.hxx"
36 #include "unonames.hxx"
37 #include "rangeutl.hxx"
38 
39 #include <xmloff/xmltkmap.hxx>
40 #include <xmloff/nmspmap.hxx>
41 #include <comphelper/extract.hxx>
42 #include <xmloff/xmltoken.hxx>
43 
44 #define SC_USERLIST "UserList"
45 
46 using namespace com::sun::star;
47 using namespace xmloff::token;
48 
49 //------------------------------------------------------------------
50 
ScXMLSortContext(ScXMLImport & rImport,sal_uInt16 nPrfx,const::rtl::OUString & rLName,const::com::sun::star::uno::Reference<::com::sun::star::xml::sax::XAttributeList> & xAttrList,ScXMLDatabaseRangeContext * pTempDatabaseRangeContext)51 ScXMLSortContext::ScXMLSortContext( ScXMLImport& rImport,
52                                       sal_uInt16 nPrfx,
53                                       const ::rtl::OUString& rLName,
54                                       const ::com::sun::star::uno::Reference<
55                                       ::com::sun::star::xml::sax::XAttributeList>& xAttrList,
56                                         ScXMLDatabaseRangeContext* pTempDatabaseRangeContext) :
57     SvXMLImportContext( rImport, nPrfx, rLName ),
58     pDatabaseRangeContext(pTempDatabaseRangeContext),
59     sCountry(),
60     sLanguage(),
61     sAlgorithm(),
62     nUserListIndex(0),
63     bCopyOutputData(sal_False),
64     bBindFormatsToContent(sal_True),
65     bIsCaseSensitive(sal_False),
66     bEnabledUserList(sal_False)
67 {
68     sal_Int16 nAttrCount(xAttrList.is() ? xAttrList->getLength() : 0);
69     const SvXMLTokenMap& rAttrTokenMap(GetScImport().GetSortAttrTokenMap());
70     for( sal_Int16 i=0; i < nAttrCount; ++i )
71     {
72         const rtl::OUString& sAttrName(xAttrList->getNameByIndex( i ));
73         rtl::OUString aLocalName;
74         sal_uInt16 nPrefix(GetScImport().GetNamespaceMap().GetKeyByAttrName(
75                                             sAttrName, &aLocalName ));
76         const rtl::OUString& sValue(xAttrList->getValueByIndex( i ));
77 
78         switch( rAttrTokenMap.Get( nPrefix, aLocalName ) )
79         {
80             case XML_TOK_SORT_ATTR_BIND_STYLES_TO_CONTENT :
81             {
82                 bBindFormatsToContent = IsXMLToken(sValue, XML_TRUE);
83             }
84             break;
85             case XML_TOK_SORT_ATTR_TARGET_RANGE_ADDRESS :
86             {
87                 ScRange aScRange;
88                 sal_Int32 nOffset(0);
89                 if (ScRangeStringConverter::GetRangeFromString( aScRange, sValue, GetScImport().GetDocument(), ::formula::FormulaGrammar::CONV_OOO, nOffset ))
90                 {
91                     ScUnoConversion::FillApiAddress( aOutputPosition, aScRange.aStart );
92                     bCopyOutputData = sal_True;
93                 }
94             }
95             break;
96             case XML_TOK_SORT_ATTR_CASE_SENSITIVE :
97             {
98                 bIsCaseSensitive = IsXMLToken(sValue, XML_TRUE);
99             }
100             break;
101             case XML_TOK_SORT_ATTR_LANGUAGE :
102                 sLanguage = sValue;
103             break;
104             case XML_TOK_SORT_ATTR_COUNTRY :
105                 sCountry = sValue;
106             break;
107             case XML_TOK_SORT_ATTR_ALGORITHM :
108                 sAlgorithm = sValue;
109             break;
110         }
111     }
112 }
113 
~ScXMLSortContext()114 ScXMLSortContext::~ScXMLSortContext()
115 {
116 }
117 
CreateChildContext(sal_uInt16 nPrefix,const::rtl::OUString & rLName,const::com::sun::star::uno::Reference<::com::sun::star::xml::sax::XAttributeList> & xAttrList)118 SvXMLImportContext *ScXMLSortContext::CreateChildContext( sal_uInt16 nPrefix,
119                                             const ::rtl::OUString& rLName,
120                                             const ::com::sun::star::uno::Reference<
121                                         ::com::sun::star::xml::sax::XAttributeList>& xAttrList )
122 {
123     SvXMLImportContext *pContext(0);
124 
125     const SvXMLTokenMap& rTokenMap(GetScImport().GetSortElemTokenMap());
126     switch( rTokenMap.Get( nPrefix, rLName ) )
127     {
128         case XML_TOK_SORT_SORT_BY :
129         {
130             pContext = new ScXMLSortByContext( GetScImport(), nPrefix,
131                                                         rLName, xAttrList, this);
132         }
133         break;
134     }
135 
136     if( !pContext )
137         pContext = new SvXMLImportContext( GetImport(), nPrefix, rLName );
138 
139     return pContext;
140 }
141 
EndElement()142 void ScXMLSortContext::EndElement()
143 {
144     sal_Int32 nLangLength(sLanguage.getLength());
145     sal_Int32 nCountryLength(sCountry.getLength());
146     sal_Int32 nAlgoLength(sAlgorithm.getLength());
147     sal_uInt8 i (0);
148     if (nLangLength || nCountryLength)
149         ++i;
150     if (nAlgoLength)
151         ++i;
152     uno::Sequence <beans::PropertyValue> aSortDescriptor(7 + i);
153     aSortDescriptor[0].Name = rtl::OUString::createFromAscii(SC_UNONAME_BINDFMT);
154     aSortDescriptor[0].Value = ::cppu::bool2any(bBindFormatsToContent);
155     aSortDescriptor[1].Name = rtl::OUString::createFromAscii(SC_UNONAME_COPYOUT);
156     aSortDescriptor[1].Value = ::cppu::bool2any(bCopyOutputData);
157     aSortDescriptor[2].Name = rtl::OUString::createFromAscii(SC_UNONAME_ISCASE);
158     aSortDescriptor[2].Value = ::cppu::bool2any(bIsCaseSensitive);
159     aSortDescriptor[3].Name = rtl::OUString::createFromAscii(SC_UNONAME_ISULIST);
160     aSortDescriptor[3].Value = ::cppu::bool2any(bEnabledUserList);
161     aSortDescriptor[4].Name = rtl::OUString::createFromAscii(SC_UNONAME_OUTPOS);
162     aSortDescriptor[4].Value <<= aOutputPosition;
163     aSortDescriptor[5].Name = rtl::OUString::createFromAscii(SC_UNONAME_UINDEX);
164     aSortDescriptor[5].Value <<= nUserListIndex;
165     aSortDescriptor[6].Name = rtl::OUString::createFromAscii(SC_UNONAME_SORTFLD);
166     aSortDescriptor[6].Value <<= aSortFields;
167     if (nLangLength || nCountryLength)
168     {
169         lang::Locale aLocale;
170         aLocale.Language = sLanguage;
171         aLocale.Country = sCountry;
172         aSortDescriptor[7].Name = rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_COLLLOC));
173         aSortDescriptor[7].Value <<= aLocale;
174     }
175     if (nAlgoLength)
176     {
177         aSortDescriptor[6 + i].Name = rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(SC_UNONAME_COLLALG));
178         aSortDescriptor[6 + i].Value <<= sAlgorithm;
179     }
180     pDatabaseRangeContext->SetSortSequence(aSortDescriptor);
181 }
182 
AddSortField(const rtl::OUString & sFieldNumber,const rtl::OUString & sDataType,const rtl::OUString & sOrder)183 void ScXMLSortContext::AddSortField(const rtl::OUString& sFieldNumber, const rtl::OUString& sDataType, const rtl::OUString& sOrder)
184 {
185     util::SortField aSortField;
186     aSortField.Field = sFieldNumber.toInt32();
187     if (IsXMLToken(sOrder, XML_ASCENDING))
188         aSortField.SortAscending = sal_True;
189     else
190         aSortField.SortAscending = sal_False;
191     if (sDataType.getLength() > 8)
192     {
193         rtl::OUString sTemp = sDataType.copy(0, 8);
194         if (sTemp.compareToAscii(SC_USERLIST) == 0)
195         {
196             bEnabledUserList = sal_True;
197             sTemp = sDataType.copy(8);
198             nUserListIndex = static_cast<sal_Int16>(sTemp.toInt32());
199         }
200         else
201         {
202             if (IsXMLToken(sDataType, XML_AUTOMATIC))
203                 aSortField.FieldType = util::SortFieldType_AUTOMATIC;
204         }
205     }
206     else
207     {
208         if (IsXMLToken(sDataType, XML_TEXT))
209             aSortField.FieldType = util::SortFieldType_ALPHANUMERIC;
210         else if (IsXMLToken(sDataType, XML_NUMBER))
211             aSortField.FieldType = util::SortFieldType_NUMERIC;
212     }
213     aSortFields.realloc(aSortFields.getLength() + 1);
214     aSortFields[aSortFields.getLength() - 1] = aSortField;
215 }
216 
ScXMLSortByContext(ScXMLImport & rImport,sal_uInt16 nPrfx,const::rtl::OUString & rLName,const::com::sun::star::uno::Reference<::com::sun::star::xml::sax::XAttributeList> & xAttrList,ScXMLSortContext * pTempSortContext)217 ScXMLSortByContext::ScXMLSortByContext( ScXMLImport& rImport,
218                                       sal_uInt16 nPrfx,
219                                       const ::rtl::OUString& rLName,
220                                       const ::com::sun::star::uno::Reference<
221                                       ::com::sun::star::xml::sax::XAttributeList>& xAttrList,
222                                         ScXMLSortContext* pTempSortContext) :
223     SvXMLImportContext( rImport, nPrfx, rLName ),
224     pSortContext(pTempSortContext),
225     sDataType(GetXMLToken(XML_AUTOMATIC)),
226     sOrder(GetXMLToken(XML_ASCENDING))
227 {
228     sal_Int16 nAttrCount(xAttrList.is() ? xAttrList->getLength() : 0);
229     const SvXMLTokenMap& rAttrTokenMap(GetScImport().GetSortSortByAttrTokenMap());
230     for( sal_Int16 i=0; i < nAttrCount; ++i )
231     {
232         const rtl::OUString& sAttrName(xAttrList->getNameByIndex( i ));
233         rtl::OUString aLocalName;
234         sal_uInt16 nPrefix(GetScImport().GetNamespaceMap().GetKeyByAttrName(
235                                             sAttrName, &aLocalName ));
236         const rtl::OUString& sValue(xAttrList->getValueByIndex( i ));
237 
238         switch( rAttrTokenMap.Get( nPrefix, aLocalName ) )
239         {
240             case XML_TOK_SORT_BY_ATTR_FIELD_NUMBER :
241             {
242                 sFieldNumber = sValue;
243             }
244             break;
245             case XML_TOK_SORT_BY_ATTR_DATA_TYPE :
246             {
247                 sDataType = sValue;
248             }
249             break;
250             case XML_TOK_SORT_BY_ATTR_ORDER :
251             {
252                 sOrder = sValue;
253             }
254             break;
255         }
256     }
257 }
258 
~ScXMLSortByContext()259 ScXMLSortByContext::~ScXMLSortByContext()
260 {
261 }
262 
CreateChildContext(sal_uInt16 nPrefix,const::rtl::OUString & rLName,const::com::sun::star::uno::Reference<::com::sun::star::xml::sax::XAttributeList> &)263 SvXMLImportContext *ScXMLSortByContext::CreateChildContext( sal_uInt16 nPrefix,
264                                             const ::rtl::OUString& rLName,
265                                             const ::com::sun::star::uno::Reference<
266                                         ::com::sun::star::xml::sax::XAttributeList>& /* xAttrList */ )
267 {
268     return new SvXMLImportContext( GetImport(), nPrefix, rLName );
269 }
270 
EndElement()271 void ScXMLSortByContext::EndElement()
272 {
273     pSortContext->AddSortField(sFieldNumber, sDataType, sOrder);
274 }
275 
276