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
29
30 #include <doc.hxx>
31 #include <docsh.hxx>
32 #include <com/sun/star/uno/Reference.hxx>
33 #include <com/sun/star/container/XNameContainer.hpp>
34 #include <com/sun/star/lang/XMultiServiceFactory.hpp>
35 #include <com/sun/star/frame/XModule.hpp>
36 #include <com/sun/star/xforms/XModel.hpp>
37 #include <com/sun/star/xforms/XFormsUIHelper1.hpp>
38 #include <unotools/processfactory.hxx>
39 #include <tools/diagnose_ex.h>
40 #include <com/sun/star/container/XIndexAccess.hpp>
41
42 using namespace ::com::sun::star;
43
44 using uno::Reference;
45 using uno::XInterface;
46 using uno::UNO_QUERY;
47 using uno::makeAny;
48 using uno::Exception;
49 using container::XNameContainer;
50 using xforms::XModel;
51 using frame::XModule;
52 using xforms::XFormsUIHelper1;
53 using rtl::OUString;
54 using com::sun::star::container::XIndexAccess;
55
getXForms() const56 Reference<XNameContainer> SwDoc::getXForms() const
57 {
58 return xXForms;
59 }
60
isXForms() const61 bool SwDoc::isXForms() const
62 {
63 return xXForms.is();
64 }
65
lcl_createInstance(const sal_Char * pServiceName)66 Reference<XInterface> lcl_createInstance( const sal_Char* pServiceName )
67 {
68 DBG_ASSERT( pServiceName != NULL, "no service name" );
69 return utl::getProcessServiceFactory()->createInstance(
70 OUString::createFromAscii( pServiceName ) );
71 }
72
initXForms(bool bCreateDefaultModel)73 void SwDoc::initXForms( bool bCreateDefaultModel )
74 {
75 DBG_ASSERT( ! isXForms(), "please initialize only once" );
76
77 try
78 {
79 // create XForms components
80 xXForms.set( lcl_createInstance( "com.sun.star.xforms.XForms" ),
81 UNO_QUERY );
82 DBG_ASSERT( xXForms.is(), "can't create XForms container" );
83
84 // change our module identifier, to be able to have a dedicated UI
85 Reference< XModule > xModule;
86 SwDocShell* pShell( GetDocShell() );
87 if ( pShell )
88 xModule = xModule.query( pShell->GetModel() );
89 DBG_ASSERT( xModule.is(), "SwDoc::initXForms: no XModule at the document!" );
90 if ( xModule.is() )
91 xModule->setIdentifier( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "com.sun.star.xforms.XMLFormDocument" ) ) );
92
93 // create default model
94 if( bCreateDefaultModel && xXForms.is() )
95 {
96 OUString sName(RTL_CONSTASCII_USTRINGPARAM("Model 1"));
97 Reference<XModel> xModel(
98 lcl_createInstance( "com.sun.star.xforms.Model" ),
99 UNO_QUERY );
100 DBG_ASSERT( xModel.is(), "no model?" );
101 if( xModel.is() )
102 {
103 xModel->setID( sName );
104 Reference<XFormsUIHelper1>( xModel, UNO_QUERY )->newInstance(
105 OUString(RTL_CONSTASCII_USTRINGPARAM("Instance 1")),
106 OUString(), sal_True );
107 xModel->initialize();
108 xXForms->insertByName( sName, makeAny( xModel ) );
109 }
110 DBG_ASSERT( xXForms->hasElements(), "can't create XForms model" );
111 }
112
113 DBG_ASSERT( isXForms(), "initialization failed" );
114 }
115 catch( const Exception& )
116 {
117 DBG_UNHANDLED_EXCEPTION();
118 }
119 }
120
121 //
122 // #i113606#, to release the cyclic reference between XFormModel and bindings/submissions.
123 //
disposeXForms()124 void SwDoc::disposeXForms( )
125 {
126 // get XForms models
127 if( xXForms.is() )
128 {
129 // iterate over all models
130 uno::Sequence<OUString> aNames = xXForms->getElementNames();
131 const OUString* pNames = aNames.getConstArray();
132 sal_Int32 nNames = aNames.getLength();
133 for( sal_Int32 n = 0; (n < nNames); n++ )
134 {
135 Reference< xforms::XModel > xModel(
136 xXForms->getByName( pNames[n] ), UNO_QUERY );
137
138 if( xModel.is() )
139 {
140 // ask model for bindings
141 Reference< XIndexAccess > xBindings(
142 xModel->getBindings(), UNO_QUERY );
143
144 //
145 // Then release them one by one
146 //
147 int nCount = xBindings->getCount();
148 for( int i = nCount-1; i >= 0; i-- )
149 {
150 xModel->getBindings()->remove(xBindings->getByIndex( i ));
151 }
152
153 // ask model for Submissions
154 Reference< XIndexAccess > xSubmissions(
155 xModel->getSubmissions(), UNO_QUERY );
156
157 //
158 // Then release them one by one
159 //
160 nCount = xSubmissions->getCount();
161 for( int i = nCount-1; i >= 0; i-- )
162 {
163 xModel->getSubmissions()->remove(xSubmissions->getByIndex( i ));
164 }
165 }
166 }
167 }
168 }
169