1*b1cdbd2cSJim Jagielski /**************************************************************
2*b1cdbd2cSJim Jagielski  *
3*b1cdbd2cSJim Jagielski  * Licensed to the Apache Software Foundation (ASF) under one
4*b1cdbd2cSJim Jagielski  * or more contributor license agreements.  See the NOTICE file
5*b1cdbd2cSJim Jagielski  * distributed with this work for additional information
6*b1cdbd2cSJim Jagielski  * regarding copyright ownership.  The ASF licenses this file
7*b1cdbd2cSJim Jagielski  * to you under the Apache License, Version 2.0 (the
8*b1cdbd2cSJim Jagielski  * "License"); you may not use this file except in compliance
9*b1cdbd2cSJim Jagielski  * with the License.  You may obtain a copy of the License at
10*b1cdbd2cSJim Jagielski  *
11*b1cdbd2cSJim Jagielski  *   http://www.apache.org/licenses/LICENSE-2.0
12*b1cdbd2cSJim Jagielski  *
13*b1cdbd2cSJim Jagielski  * Unless required by applicable law or agreed to in writing,
14*b1cdbd2cSJim Jagielski  * software distributed under the License is distributed on an
15*b1cdbd2cSJim Jagielski  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*b1cdbd2cSJim Jagielski  * KIND, either express or implied.  See the License for the
17*b1cdbd2cSJim Jagielski  * specific language governing permissions and limitations
18*b1cdbd2cSJim Jagielski  * under the License.
19*b1cdbd2cSJim Jagielski  *
20*b1cdbd2cSJim Jagielski  *************************************************************/
21*b1cdbd2cSJim Jagielski 
22*b1cdbd2cSJim Jagielski 
23*b1cdbd2cSJim Jagielski #include "precompiled_reportdesign.hxx"
24*b1cdbd2cSJim Jagielski #include "xmlGroup.hxx"
25*b1cdbd2cSJim Jagielski #include "xmlSection.hxx"
26*b1cdbd2cSJim Jagielski #include "xmlFunction.hxx"
27*b1cdbd2cSJim Jagielski #include "xmlfilter.hxx"
28*b1cdbd2cSJim Jagielski #include <xmloff/xmltoken.hxx>
29*b1cdbd2cSJim Jagielski #include <xmloff/xmlnmspe.hxx>
30*b1cdbd2cSJim Jagielski #include <xmloff/nmspmap.hxx>
31*b1cdbd2cSJim Jagielski #include <xmloff/xmluconv.hxx>
32*b1cdbd2cSJim Jagielski #include "xmlHelper.hxx"
33*b1cdbd2cSJim Jagielski #include "xmlEnums.hxx"
34*b1cdbd2cSJim Jagielski #include <ucbhelper/content.hxx>
35*b1cdbd2cSJim Jagielski #include <comphelper/namecontainer.hxx>
36*b1cdbd2cSJim Jagielski #include <com/sun/star/report/GroupOn.hpp>
37*b1cdbd2cSJim Jagielski #include <com/sun/star/report/KeepTogether.hpp>
38*b1cdbd2cSJim Jagielski #include <tools/debug.hxx>
39*b1cdbd2cSJim Jagielski 
40*b1cdbd2cSJim Jagielski namespace rptxml
41*b1cdbd2cSJim Jagielski {
42*b1cdbd2cSJim Jagielski 	using namespace ::com::sun::star;
43*b1cdbd2cSJim Jagielski 	using namespace ::com::sun::star::uno;
44*b1cdbd2cSJim Jagielski 	using namespace ::com::sun::star::report;
45*b1cdbd2cSJim Jagielski 	using namespace ::com::sun::star::xml::sax;
46*b1cdbd2cSJim Jagielski 
lcl_getKeepTogetherOption(const::rtl::OUString & _sValue)47*b1cdbd2cSJim Jagielski 	sal_uInt16 lcl_getKeepTogetherOption(const ::rtl::OUString& _sValue)
48*b1cdbd2cSJim Jagielski 	{
49*b1cdbd2cSJim Jagielski 		sal_uInt16 nRet = report::KeepTogether::NO;
50*b1cdbd2cSJim Jagielski 		const SvXMLEnumMapEntry* aXML_EnumMap = OXMLHelper::GetKeepTogetherOptions();
51*b1cdbd2cSJim Jagielski 		SvXMLUnitConverter::convertEnum( nRet, _sValue, aXML_EnumMap );
52*b1cdbd2cSJim Jagielski 		return nRet;
53*b1cdbd2cSJim Jagielski 	}
DBG_NAME(rpt_OXMLGroup)54*b1cdbd2cSJim Jagielski DBG_NAME( rpt_OXMLGroup )
55*b1cdbd2cSJim Jagielski 
56*b1cdbd2cSJim Jagielski OXMLGroup::OXMLGroup( ORptFilter& _rImport
57*b1cdbd2cSJim Jagielski 				,sal_uInt16 nPrfx
58*b1cdbd2cSJim Jagielski 				,const ::rtl::OUString& _sLocalName
59*b1cdbd2cSJim Jagielski 				,const Reference< XAttributeList > & _xAttrList
60*b1cdbd2cSJim Jagielski 				) :
61*b1cdbd2cSJim Jagielski 	SvXMLImportContext( _rImport, nPrfx, _sLocalName )
62*b1cdbd2cSJim Jagielski {
63*b1cdbd2cSJim Jagielski     DBG_CTOR( rpt_OXMLGroup,NULL);
64*b1cdbd2cSJim Jagielski 
65*b1cdbd2cSJim Jagielski 	m_xGroups = _rImport.getReportDefinition()->getGroups();
66*b1cdbd2cSJim Jagielski 	OSL_ENSURE(m_xGroups.is(),"Groups is NULL!");
67*b1cdbd2cSJim Jagielski 	m_xGroup = m_xGroups->createGroup();
68*b1cdbd2cSJim Jagielski 
69*b1cdbd2cSJim Jagielski 	OSL_ENSURE(_xAttrList.is(),"Attribute list is NULL!");
70*b1cdbd2cSJim Jagielski 
71*b1cdbd2cSJim Jagielski 	const SvXMLNamespaceMap& rMap = _rImport.GetNamespaceMap();
72*b1cdbd2cSJim Jagielski 	const SvXMLTokenMap& rTokenMap = _rImport.GetGroupElemTokenMap();
73*b1cdbd2cSJim Jagielski     m_xGroup->setSortAscending(sal_False);// the default value has to be set
74*b1cdbd2cSJim Jagielski 	const sal_Int16 nLength = (_xAttrList.is()) ? _xAttrList->getLength() : 0;
75*b1cdbd2cSJim Jagielski 	static const ::rtl::OUString s_sTRUE = ::xmloff::token::GetXMLToken(XML_TRUE);
76*b1cdbd2cSJim Jagielski 	for(sal_Int16 i = 0; i < nLength; ++i)
77*b1cdbd2cSJim Jagielski 	{
78*b1cdbd2cSJim Jagielski         ::rtl::OUString sLocalName;
79*b1cdbd2cSJim Jagielski 		const ::rtl::OUString sAttrName = _xAttrList->getNameByIndex( i );
80*b1cdbd2cSJim Jagielski 		const sal_uInt16 nPrefix = rMap.GetKeyByAttrName( sAttrName,&sLocalName );
81*b1cdbd2cSJim Jagielski 		::rtl::OUString sValue = _xAttrList->getValueByIndex( i );
82*b1cdbd2cSJim Jagielski 
83*b1cdbd2cSJim Jagielski 		try
84*b1cdbd2cSJim Jagielski 		{
85*b1cdbd2cSJim Jagielski 			switch( rTokenMap.Get( nPrefix, sLocalName ) )
86*b1cdbd2cSJim Jagielski 			{
87*b1cdbd2cSJim Jagielski 				case XML_TOK_START_NEW_COLUMN:
88*b1cdbd2cSJim Jagielski 					m_xGroup->setStartNewColumn(sValue == s_sTRUE);
89*b1cdbd2cSJim Jagielski 					break;
90*b1cdbd2cSJim Jagielski 				case XML_TOK_RESET_PAGE_NUMBER:
91*b1cdbd2cSJim Jagielski 					m_xGroup->setResetPageNumber(sValue == s_sTRUE);
92*b1cdbd2cSJim Jagielski 					break;
93*b1cdbd2cSJim Jagielski 				case XML_TOK_SORT_ASCENDING:
94*b1cdbd2cSJim Jagielski 					m_xGroup->setSortAscending(sValue == s_sTRUE);
95*b1cdbd2cSJim Jagielski 					break;
96*b1cdbd2cSJim Jagielski 				case XML_TOK_GROUP_EXPRESSION:
97*b1cdbd2cSJim Jagielski                     {
98*b1cdbd2cSJim Jagielski                         sal_Int32 nLen = sValue.getLength();
99*b1cdbd2cSJim Jagielski                         if ( nLen )
100*b1cdbd2cSJim Jagielski                         {
101*b1cdbd2cSJim Jagielski 
102*b1cdbd2cSJim Jagielski                             const static ::rtl::OUString s_sChanged(RTL_CONSTASCII_USTRINGPARAM("rpt:HASCHANGED(\""));
103*b1cdbd2cSJim Jagielski                             sal_Int32 nPos = sValue.indexOf(s_sChanged);
104*b1cdbd2cSJim Jagielski                             if ( nPos == -1 )
105*b1cdbd2cSJim Jagielski                                 nPos = 5;
106*b1cdbd2cSJim Jagielski                             else
107*b1cdbd2cSJim Jagielski                             {
108*b1cdbd2cSJim Jagielski                                 nPos = s_sChanged.getLength();
109*b1cdbd2cSJim Jagielski                                 static ::rtl::OUString s_sQuote(RTL_CONSTASCII_USTRINGPARAM("\"\""));
110*b1cdbd2cSJim Jagielski                                 static ::rtl::OUString s_sSingleQuote(RTL_CONSTASCII_USTRINGPARAM("\""));
111*b1cdbd2cSJim Jagielski                                 sal_Int32 nIndex = sValue.indexOf(s_sQuote,nPos);
112*b1cdbd2cSJim Jagielski                                 while ( nIndex > -1 )
113*b1cdbd2cSJim Jagielski                                 {
114*b1cdbd2cSJim Jagielski                                     sValue = sValue.replaceAt(nIndex,2,s_sSingleQuote);
115*b1cdbd2cSJim Jagielski                                     nIndex = sValue.indexOf(s_sQuote,nIndex+2);
116*b1cdbd2cSJim Jagielski                                 }
117*b1cdbd2cSJim Jagielski                                 nLen = sValue.getLength() - 1;
118*b1cdbd2cSJim Jagielski                             }
119*b1cdbd2cSJim Jagielski                             sValue = sValue.copy(nPos,nLen-nPos-1);
120*b1cdbd2cSJim Jagielski                             const ORptFilter::TGroupFunctionMap& aFunctions = _rImport.getFunctions();
121*b1cdbd2cSJim Jagielski                             ORptFilter::TGroupFunctionMap::const_iterator aFind = aFunctions.find(sValue);
122*b1cdbd2cSJim Jagielski                             if ( aFind != aFunctions.end() )
123*b1cdbd2cSJim Jagielski                             {
124*b1cdbd2cSJim Jagielski                                 sal_Int32 nIndex = 0;
125*b1cdbd2cSJim Jagielski                                 const ::rtl::OUString sCompleteFormula = aFind->second->getFormula();
126*b1cdbd2cSJim Jagielski                                 ::rtl::OUString sExpression = sCompleteFormula.getToken(1,'[',nIndex);
127*b1cdbd2cSJim Jagielski                                 nIndex = 0;
128*b1cdbd2cSJim Jagielski                                 sExpression = sExpression.getToken(0,']',nIndex);
129*b1cdbd2cSJim Jagielski                                 nIndex = 0;
130*b1cdbd2cSJim Jagielski                                 const ::rtl::OUString sFormula = sCompleteFormula.getToken(0,'(',nIndex);
131*b1cdbd2cSJim Jagielski                                 ::sal_Int16 nGroupOn = report::GroupOn::DEFAULT;
132*b1cdbd2cSJim Jagielski 
133*b1cdbd2cSJim Jagielski                                 if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:LEFT")))
134*b1cdbd2cSJim Jagielski                                 {
135*b1cdbd2cSJim Jagielski                                     nGroupOn = report::GroupOn::PREFIX_CHARACTERS;
136*b1cdbd2cSJim Jagielski                                     ::rtl::OUString sInterval = sCompleteFormula.getToken(1,';',nIndex);
137*b1cdbd2cSJim Jagielski                                     nIndex = 0;
138*b1cdbd2cSJim Jagielski                                     sInterval = sInterval.getToken(0,')',nIndex);
139*b1cdbd2cSJim Jagielski                                     m_xGroup->setGroupInterval(sInterval.toInt32());
140*b1cdbd2cSJim Jagielski                                 }
141*b1cdbd2cSJim Jagielski                                 else if ( sFormula == ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:YEAR")))
142*b1cdbd2cSJim Jagielski                                     nGroupOn = report::GroupOn::YEAR;
143*b1cdbd2cSJim Jagielski 	                            else if ( sFormula == ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:MONTH")))
144*b1cdbd2cSJim Jagielski                                 {
145*b1cdbd2cSJim Jagielski 	                                nGroupOn = report::GroupOn::MONTH;
146*b1cdbd2cSJim Jagielski                                 }
147*b1cdbd2cSJim Jagielski                                 else if ( sCompleteFormula.matchIgnoreAsciiCase(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:INT((MONTH")),0)
148*b1cdbd2cSJim Jagielski                                        && sCompleteFormula.endsWithIgnoreAsciiCaseAsciiL("-1)/3)+1",8) )
149*b1cdbd2cSJim Jagielski                                 {
150*b1cdbd2cSJim Jagielski                                     nGroupOn = report::GroupOn::QUARTAL;
151*b1cdbd2cSJim Jagielski                                 }
152*b1cdbd2cSJim Jagielski 	                            else if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:WEEK")))
153*b1cdbd2cSJim Jagielski 	                                nGroupOn = report::GroupOn::WEEK;
154*b1cdbd2cSJim Jagielski 	                            else if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:DAY")))
155*b1cdbd2cSJim Jagielski 	                                nGroupOn = report::GroupOn::DAY;
156*b1cdbd2cSJim Jagielski 	                            else if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:HOUR")))
157*b1cdbd2cSJim Jagielski 	                                nGroupOn = report::GroupOn::HOUR;
158*b1cdbd2cSJim Jagielski 	                            else if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:MINUTE")))
159*b1cdbd2cSJim Jagielski 	                                nGroupOn = report::GroupOn::MINUTE;
160*b1cdbd2cSJim Jagielski                                 else if ( sFormula ==::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("rpt:INT")))
161*b1cdbd2cSJim Jagielski                                 {
162*b1cdbd2cSJim Jagielski                                     nGroupOn = report::GroupOn::INTERVAL;
163*b1cdbd2cSJim Jagielski                                     _rImport.removeFunction(sExpression);
164*b1cdbd2cSJim Jagielski                                     sExpression = sExpression.copy(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("INT_count_")).getLength());
165*b1cdbd2cSJim Jagielski 
166*b1cdbd2cSJim Jagielski                                     nIndex = 0;
167*b1cdbd2cSJim Jagielski                                     ::rtl::OUString sInterval = sCompleteFormula.getToken(1,'/',nIndex);
168*b1cdbd2cSJim Jagielski                                     nIndex = 0;
169*b1cdbd2cSJim Jagielski                                     sInterval = sInterval.getToken(0,')',nIndex);
170*b1cdbd2cSJim Jagielski                                     m_xGroup->setGroupInterval(sInterval.toInt32());
171*b1cdbd2cSJim Jagielski                                 }
172*b1cdbd2cSJim Jagielski 
173*b1cdbd2cSJim Jagielski                                 m_xGroup->setGroupOn(nGroupOn);
174*b1cdbd2cSJim Jagielski 
175*b1cdbd2cSJim Jagielski                                 _rImport.removeFunction(sValue);
176*b1cdbd2cSJim Jagielski                                 sValue = sExpression;
177*b1cdbd2cSJim Jagielski                             }
178*b1cdbd2cSJim Jagielski                             m_xGroup->setExpression(sValue);
179*b1cdbd2cSJim Jagielski                         }
180*b1cdbd2cSJim Jagielski                     }
181*b1cdbd2cSJim Jagielski 					break;
182*b1cdbd2cSJim Jagielski 				case XML_TOK_GROUP_KEEP_TOGETHER:
183*b1cdbd2cSJim Jagielski 					m_xGroup->setKeepTogether(lcl_getKeepTogetherOption(sValue));
184*b1cdbd2cSJim Jagielski 					break;
185*b1cdbd2cSJim Jagielski                 default:
186*b1cdbd2cSJim Jagielski                     break;
187*b1cdbd2cSJim Jagielski 			}
188*b1cdbd2cSJim Jagielski 		}
189*b1cdbd2cSJim Jagielski 		catch(const Exception&)
190*b1cdbd2cSJim Jagielski 		{
191*b1cdbd2cSJim Jagielski 			OSL_ENSURE(0,"Exception catched while putting group props!");
192*b1cdbd2cSJim Jagielski 		}
193*b1cdbd2cSJim Jagielski 	}
194*b1cdbd2cSJim Jagielski }
195*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
196*b1cdbd2cSJim Jagielski 
~OXMLGroup()197*b1cdbd2cSJim Jagielski OXMLGroup::~OXMLGroup()
198*b1cdbd2cSJim Jagielski {
199*b1cdbd2cSJim Jagielski 
200*b1cdbd2cSJim Jagielski     DBG_DTOR( rpt_OXMLGroup,NULL);
201*b1cdbd2cSJim Jagielski }
202*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
CreateChildContext(sal_uInt16 nPrefix,const::rtl::OUString & rLocalName,const Reference<XAttributeList> & xAttrList)203*b1cdbd2cSJim Jagielski SvXMLImportContext* OXMLGroup::CreateChildContext(
204*b1cdbd2cSJim Jagielski 		sal_uInt16 nPrefix,
205*b1cdbd2cSJim Jagielski         const ::rtl::OUString& rLocalName,
206*b1cdbd2cSJim Jagielski 		const Reference< XAttributeList > & xAttrList )
207*b1cdbd2cSJim Jagielski {
208*b1cdbd2cSJim Jagielski 	SvXMLImportContext *pContext = 0;
209*b1cdbd2cSJim Jagielski     ORptFilter& rImport = GetOwnImport();
210*b1cdbd2cSJim Jagielski 	const SvXMLTokenMap&	rTokenMap	= rImport.GetGroupElemTokenMap();
211*b1cdbd2cSJim Jagielski 
212*b1cdbd2cSJim Jagielski 	switch( rTokenMap.Get( nPrefix, rLocalName ) )
213*b1cdbd2cSJim Jagielski 	{
214*b1cdbd2cSJim Jagielski         case XML_TOK_GROUP_FUNCTION:
215*b1cdbd2cSJim Jagielski 			{
216*b1cdbd2cSJim Jagielski 				rImport.GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
217*b1cdbd2cSJim Jagielski 				pContext = new OXMLFunction( rImport, nPrefix, rLocalName,xAttrList,m_xGroup.get());
218*b1cdbd2cSJim Jagielski 			}
219*b1cdbd2cSJim Jagielski 			break;
220*b1cdbd2cSJim Jagielski 		case XML_TOK_GROUP_HEADER:
221*b1cdbd2cSJim Jagielski 			{
222*b1cdbd2cSJim Jagielski 				rImport.GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
223*b1cdbd2cSJim Jagielski 				m_xGroup->setHeaderOn(sal_True);
224*b1cdbd2cSJim Jagielski 				pContext = new OXMLSection( rImport, nPrefix, rLocalName,xAttrList,m_xGroup->getHeader());
225*b1cdbd2cSJim Jagielski 			}
226*b1cdbd2cSJim Jagielski 			break;
227*b1cdbd2cSJim Jagielski         case XML_TOK_GROUP_GROUP:
228*b1cdbd2cSJim Jagielski 			rImport.GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
229*b1cdbd2cSJim Jagielski 			pContext = new OXMLGroup( rImport, nPrefix, rLocalName,xAttrList);
230*b1cdbd2cSJim Jagielski 			break;
231*b1cdbd2cSJim Jagielski 		case XML_TOK_GROUP_DETAIL:
232*b1cdbd2cSJim Jagielski 			{
233*b1cdbd2cSJim Jagielski 				rImport.GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
234*b1cdbd2cSJim Jagielski 				Reference<XReportDefinition> m_xComponent = rImport.getReportDefinition();
235*b1cdbd2cSJim Jagielski 				pContext = new OXMLSection( rImport, nPrefix, rLocalName,xAttrList ,m_xComponent->getDetail());
236*b1cdbd2cSJim Jagielski 			}
237*b1cdbd2cSJim Jagielski 			break;
238*b1cdbd2cSJim Jagielski 
239*b1cdbd2cSJim Jagielski 		case XML_TOK_GROUP_FOOTER:
240*b1cdbd2cSJim Jagielski 			{
241*b1cdbd2cSJim Jagielski 				rImport.GetProgressBarHelper()->Increment( PROGRESS_BAR_STEP );
242*b1cdbd2cSJim Jagielski 				m_xGroup->setFooterOn(sal_True);
243*b1cdbd2cSJim Jagielski 				pContext = new OXMLSection( rImport, nPrefix, rLocalName,xAttrList,m_xGroup->getFooter());
244*b1cdbd2cSJim Jagielski 			}
245*b1cdbd2cSJim Jagielski 			break;
246*b1cdbd2cSJim Jagielski         default:
247*b1cdbd2cSJim Jagielski             break;
248*b1cdbd2cSJim Jagielski 	}
249*b1cdbd2cSJim Jagielski 
250*b1cdbd2cSJim Jagielski 	if( !pContext )
251*b1cdbd2cSJim Jagielski 		pContext = new SvXMLImportContext( GetImport(), nPrefix, rLocalName );
252*b1cdbd2cSJim Jagielski 
253*b1cdbd2cSJim Jagielski 	return pContext;
254*b1cdbd2cSJim Jagielski }
255*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
GetOwnImport()256*b1cdbd2cSJim Jagielski ORptFilter& OXMLGroup::GetOwnImport()
257*b1cdbd2cSJim Jagielski {
258*b1cdbd2cSJim Jagielski 	return static_cast<ORptFilter&>(GetImport());
259*b1cdbd2cSJim Jagielski }
260*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
EndElement()261*b1cdbd2cSJim Jagielski void OXMLGroup::EndElement()
262*b1cdbd2cSJim Jagielski {
263*b1cdbd2cSJim Jagielski 	try
264*b1cdbd2cSJim Jagielski 	{
265*b1cdbd2cSJim Jagielski         // the group elements end in the reverse order
266*b1cdbd2cSJim Jagielski 		m_xGroups->insertByIndex(0,uno::makeAny(m_xGroup));
267*b1cdbd2cSJim Jagielski 	}catch(uno::Exception&)
268*b1cdbd2cSJim Jagielski 	{
269*b1cdbd2cSJim Jagielski 		OSL_ENSURE(0,"Exception catched!");
270*b1cdbd2cSJim Jagielski 	}
271*b1cdbd2cSJim Jagielski }
272*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
273*b1cdbd2cSJim Jagielski //----------------------------------------------------------------------------
274*b1cdbd2cSJim Jagielski } // namespace rptxml
275*b1cdbd2cSJim Jagielski // -----------------------------------------------------------------------------
276