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 .
21 #include "xformsapi.hxx"
23 #include <com/sun/star/frame/XModel.hpp>
24 #include <com/sun/star/uno/Reference.hxx>
25 #include <com/sun/star/beans/XPropertySet.hpp>
26 #include <com/sun/star/container/XNameAccess.hpp>
27 #include <com/sun/star/xforms/XFormsSupplier.hpp>
28 #include <com/sun/star/xforms/XDataTypeRepository.hpp>
29 #include <com/sun/star/xforms/Model.hpp>
30 #include <com/sun/star/xforms/XModel2.hpp>
31 #include <com/sun/star/container/XNameContainer.hpp>
32 #include <com/sun/star/xsd/DataTypeClass.hpp>
34 #include <comphelper/processfactory.hxx>
35 #include <sal/log.hxx>
36 #include <tools/diagnose_ex.h>
38 #include <xmloff/xmltoken.hxx>
39 #include <xmloff/namespacemap.hxx>
40 #include <xmloff/xmlnamespace.hxx>
41 #include <xmloff/xmltkmap.hxx>
43 using com::sun::star::uno::Reference
;
44 using com::sun::star::uno::Sequence
;
45 using com::sun::star::uno::UNO_QUERY
;
46 using com::sun::star::uno::UNO_QUERY_THROW
;
47 using com::sun::star::beans::XPropertySet
;
48 using com::sun::star::container::XNameAccess
;
49 using com::sun::star::xforms::XFormsSupplier
;
50 using com::sun::star::xforms::XDataTypeRepository
;
51 using com::sun::star::xforms::Model
;
52 using com::sun::star::xforms::XModel2
;
53 using com::sun::star::container::XNameContainer
;
54 using com::sun::star::uno::makeAny
;
55 using com::sun::star::uno::Any
;
56 using com::sun::star::uno::Exception
;
58 using namespace com::sun::star
;
59 using namespace xmloff::token
;
61 Reference
<XModel2
> xforms_createXFormsModel()
63 Reference
<XModel2
> xModel
= Model::create( comphelper::getProcessComponentContext() );
68 void xforms_addXFormsModel(
69 const Reference
<frame::XModel
>& xDocument
,
70 const Reference
<xforms::XModel2
>& xModel
)
72 bool bSuccess
= false;
75 Reference
<XFormsSupplier
> xSupplier( xDocument
, UNO_QUERY
);
78 Reference
<XNameContainer
> xForms
= xSupplier
->getXForms();
82 xModel
->getPropertyValue("ID") >>= sName
;
83 xForms
->insertByName( sName
, makeAny( xModel
) );
88 catch( const Exception
& )
93 // TODO: implement proper error handling
94 SAL_WARN_IF( !bSuccess
, "xmloff", "can't import model" );
97 static Reference
<XPropertySet
> lcl_findXFormsBindingOrSubmission(
98 Reference
<frame::XModel
> const & xDocument
,
99 const OUString
& rBindingID
,
102 // find binding by iterating over all models, and look for the
105 Reference
<XPropertySet
> xRet
;
109 Reference
<XFormsSupplier
> xSupplier( xDocument
, UNO_QUERY
);
113 Reference
<XNameContainer
> xForms
= xSupplier
->getXForms();
116 // iterate over all models
117 const Sequence
<OUString
> aNames
= xForms
->getElementNames();
118 for( const auto& rName
: aNames
)
120 Reference
<xforms::XModel2
> xModel(
121 xForms
->getByName( rName
), UNO_QUERY
);
124 // ask model for bindings
125 Reference
<XNameAccess
> xBindings(
127 ? xModel
->getBindings()
128 : xModel
->getSubmissions(),
131 // finally, ask binding for name
132 if( xBindings
->hasByName( rBindingID
) )
133 xRet
.set( xBindings
->getByName( rBindingID
),
143 catch( const Exception
& )
148 // TODO: if (!xRet.is()) rImport.SetError(...);
153 Reference
<XPropertySet
> xforms_findXFormsBinding(
154 Reference
<frame::XModel
> const & xDocument
,
155 const OUString
& rBindingID
)
157 return lcl_findXFormsBindingOrSubmission( xDocument
, rBindingID
, true );
160 Reference
<XPropertySet
> xforms_findXFormsSubmission(
161 Reference
<frame::XModel
> const & xDocument
,
162 const OUString
& rBindingID
)
164 return lcl_findXFormsBindingOrSubmission( xDocument
, rBindingID
, false );
167 void xforms_setValue( Reference
<XPropertySet
> const & xPropertySet
,
168 const OUString
& rName
,
171 xPropertySet
->setPropertyValue( rName
, rAny
);
174 #define TOKEN_MAP_ENTRY(NAMESPACE,TOKEN) { XML_NAMESPACE_##NAMESPACE, xmloff::token::XML_##TOKEN, xmloff::token::XML_##TOKEN }
175 const SvXMLTokenMapEntry aTypes
[] =
177 TOKEN_MAP_ENTRY( XSD
, STRING
),
178 TOKEN_MAP_ENTRY( XSD
, DECIMAL
),
179 TOKEN_MAP_ENTRY( XSD
, DOUBLE
),
180 TOKEN_MAP_ENTRY( XSD
, FLOAT
),
181 TOKEN_MAP_ENTRY( XSD
, BOOLEAN
),
182 TOKEN_MAP_ENTRY( XSD
, ANYURI
),
183 TOKEN_MAP_ENTRY( XSD
, DATETIME_XSD
),
184 TOKEN_MAP_ENTRY( XSD
, DATE
),
185 TOKEN_MAP_ENTRY( XSD
, TIME
),
186 TOKEN_MAP_ENTRY( XSD
, YEAR
),
187 TOKEN_MAP_ENTRY( XSD
, MONTH
),
188 TOKEN_MAP_ENTRY( XSD
, DAY
),
192 sal_uInt16
xforms_getTypeClass(
193 const Reference
<XDataTypeRepository
>& xRepository
,
194 const SvXMLNamespaceMap
& rNamespaceMap
,
195 const OUString
& rXMLName
)
197 // translate name into token for local name
199 sal_uInt16 nPrefix
= rNamespaceMap
.GetKeyByAttrValueQName(rXMLName
, &sLocalName
);
200 static const SvXMLTokenMap
aMap( aTypes
);
201 sal_uInt16 nToken
= aMap
.Get( nPrefix
, sLocalName
);
203 sal_uInt16 nTypeClass
= css::xsd::DataTypeClass::STRING
;
204 if( nToken
!= XML_TOK_UNKNOWN
)
206 // we found an XSD name: then get the proper API name for it
207 SAL_WARN_IF( !xRepository
.is(), "xmloff", "can't find type without repository");
211 nTypeClass
= css::xsd::DataTypeClass::STRING
;
214 nTypeClass
= css::xsd::DataTypeClass::anyURI
;
217 nTypeClass
= css::xsd::DataTypeClass::DECIMAL
;
220 nTypeClass
= css::xsd::DataTypeClass::DOUBLE
;
223 nTypeClass
= css::xsd::DataTypeClass::FLOAT
;
226 nTypeClass
= css::xsd::DataTypeClass::BOOLEAN
;
228 case XML_DATETIME_XSD
:
229 nTypeClass
= css::xsd::DataTypeClass::DATETIME
;
232 nTypeClass
= css::xsd::DataTypeClass::DATE
;
235 nTypeClass
= css::xsd::DataTypeClass::TIME
;
238 nTypeClass
= css::xsd::DataTypeClass::gYear
;
241 nTypeClass
= css::xsd::DataTypeClass::gDay
;
244 nTypeClass
= css::xsd::DataTypeClass::gMonth
;
247 /* data types not yet supported:
248 nTypeClass = css::xsd::DataTypeClass::DURATION;
249 nTypeClass = css::xsd::DataTypeClass::gYearMonth;
250 nTypeClass = css::xsd::DataTypeClass::gMonthDay;
251 nTypeClass = css::xsd::DataTypeClass::hexBinary;
252 nTypeClass = css::xsd::DataTypeClass::base64Binary;
253 nTypeClass = css::xsd::DataTypeClass::QName;
254 nTypeClass = css::xsd::DataTypeClass::NOTATION;
263 OUString
xforms_getTypeName(
264 const Reference
<XDataTypeRepository
>& xRepository
,
265 const SvXMLNamespaceMap
& rNamespaceMap
,
266 const OUString
& rXMLName
)
269 sal_uInt16 nPrefix
= rNamespaceMap
.GetKeyByAttrValueQName(rXMLName
, &sLocalName
);
270 static const SvXMLTokenMap
aMap( aTypes
);
271 sal_uInt16 nToken
= aMap
.Get( nPrefix
, sLocalName
);
272 return ( nToken
== XML_TOK_UNKNOWN
)
274 : xforms_getBasicTypeName( xRepository
, rNamespaceMap
, rXMLName
);
277 OUString
xforms_getBasicTypeName(
278 const Reference
<XDataTypeRepository
>& xRepository
,
279 const SvXMLNamespaceMap
& rNamespaceMap
,
280 const OUString
& rXMLName
)
282 OUString sTypeName
= rXMLName
;
286 xRepository
->getBasicDataType(
287 xforms_getTypeClass( xRepository
, rNamespaceMap
, rXMLName
) )
290 catch( const Exception
& )
292 TOOLS_WARN_EXCEPTION("xmloff", "exception during type creation");
297 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */