xref: /AOO41X/main/forms/source/component/clickableimage.cxx (revision 24acc54625a85f778a4f966495e8f4cd9d7b247c)
1*24acc546SAndrew Rist /**************************************************************
2cdf0e10cSrcweir  *
3*24acc546SAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*24acc546SAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*24acc546SAndrew Rist  * distributed with this work for additional information
6*24acc546SAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*24acc546SAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*24acc546SAndrew Rist  * "License"); you may not use this file except in compliance
9*24acc546SAndrew Rist  * with the License.  You may obtain a copy of the License at
10cdf0e10cSrcweir  *
11*24acc546SAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12cdf0e10cSrcweir  *
13*24acc546SAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*24acc546SAndrew Rist  * software distributed under the License is distributed on an
15*24acc546SAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*24acc546SAndrew Rist  * KIND, either express or implied.  See the License for the
17*24acc546SAndrew Rist  * specific language governing permissions and limitations
18*24acc546SAndrew Rist  * under the License.
19cdf0e10cSrcweir  *
20*24acc546SAndrew Rist  *************************************************************/
21*24acc546SAndrew Rist 
22*24acc546SAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_forms.hxx"
26cdf0e10cSrcweir #include "clickableimage.hxx"
27cdf0e10cSrcweir #include "controlfeatureinterception.hxx"
28cdf0e10cSrcweir #include "urltransformer.hxx"
29cdf0e10cSrcweir #include "componenttools.hxx"
30cdf0e10cSrcweir #include <com/sun/star/form/XSubmit.hpp>
31cdf0e10cSrcweir #include <com/sun/star/awt/SystemPointer.hpp>
32cdf0e10cSrcweir #include <com/sun/star/form/FormComponentType.hpp>
33cdf0e10cSrcweir #include <com/sun/star/frame/XDispatch.hpp>
34cdf0e10cSrcweir #include <com/sun/star/frame/XDispatchProvider.hpp>
35cdf0e10cSrcweir #include <com/sun/star/frame/FrameSearchFlag.hpp>
36cdf0e10cSrcweir #include <com/sun/star/frame/XController.hpp>
37cdf0e10cSrcweir #include <com/sun/star/frame/XFrame.hpp>
38cdf0e10cSrcweir #include <com/sun/star/awt/ActionEvent.hpp>
39cdf0e10cSrcweir #include <com/sun/star/awt/XActionListener.hpp>
40cdf0e10cSrcweir #include <tools/urlobj.hxx>
41cdf0e10cSrcweir #include <tools/debug.hxx>
42cdf0e10cSrcweir #include <vcl/svapp.hxx>
43cdf0e10cSrcweir #include <sfx2/docfile.hxx>
44cdf0e10cSrcweir #include <sfx2/objsh.hxx>
45cdf0e10cSrcweir #include <vos/mutex.hxx>
46cdf0e10cSrcweir #include "services.hxx"
47cdf0e10cSrcweir #include <comphelper/container.hxx>
48cdf0e10cSrcweir #include <comphelper/listenernotification.hxx>
49cdf0e10cSrcweir #include <svtools/imageresourceaccess.hxx>
50cdf0e10cSrcweir #define LOCAL_URL_PREFIX	'#'
51cdf0e10cSrcweir 
52cdf0e10cSrcweir //.........................................................................
53cdf0e10cSrcweir namespace frm
54cdf0e10cSrcweir {
55cdf0e10cSrcweir //.........................................................................
56cdf0e10cSrcweir 
57cdf0e10cSrcweir     using namespace ::com::sun::star::uno;
58cdf0e10cSrcweir     using namespace ::com::sun::star::sdb;
59cdf0e10cSrcweir     using namespace ::com::sun::star::sdbc;
60cdf0e10cSrcweir     using namespace ::com::sun::star::sdbcx;
61cdf0e10cSrcweir     using namespace ::com::sun::star::beans;
62cdf0e10cSrcweir     using namespace ::com::sun::star::container;
63cdf0e10cSrcweir     using namespace ::com::sun::star::form;
64cdf0e10cSrcweir     using namespace ::com::sun::star::awt;
65cdf0e10cSrcweir     using namespace ::com::sun::star::io;
66cdf0e10cSrcweir     using namespace ::com::sun::star::lang;
67cdf0e10cSrcweir     using namespace ::com::sun::star::util;
68cdf0e10cSrcweir     using namespace ::com::sun::star::frame;
69cdf0e10cSrcweir     using namespace ::com::sun::star::form::submission;
70cdf0e10cSrcweir     using ::com::sun::star::awt::MouseEvent;
71cdf0e10cSrcweir     using ::com::sun::star::task::XInteractionHandler;
72cdf0e10cSrcweir 
73cdf0e10cSrcweir     //==================================================================
74cdf0e10cSrcweir     // OClickableImageBaseControl
75cdf0e10cSrcweir     //==================================================================
76cdf0e10cSrcweir     //------------------------------------------------------------------------------
_getTypes()77cdf0e10cSrcweir     Sequence<Type> OClickableImageBaseControl::_getTypes()
78cdf0e10cSrcweir     {
79cdf0e10cSrcweir         static Sequence<Type> aTypes;
80cdf0e10cSrcweir         if (!aTypes.getLength())
81cdf0e10cSrcweir             aTypes = concatSequences(OControl::_getTypes(), OClickableImageBaseControl_BASE::getTypes());
82cdf0e10cSrcweir         return aTypes;
83cdf0e10cSrcweir     }
84cdf0e10cSrcweir 
85cdf0e10cSrcweir     //------------------------------------------------------------------------------
OClickableImageBaseControl(const Reference<XMultiServiceFactory> & _rxFactory,const::rtl::OUString & _aService)86cdf0e10cSrcweir     OClickableImageBaseControl::OClickableImageBaseControl(const Reference<XMultiServiceFactory>& _rxFactory, const ::rtl::OUString& _aService)
87cdf0e10cSrcweir         :OControl(_rxFactory, _aService)
88cdf0e10cSrcweir         ,m_pThread(NULL)
89cdf0e10cSrcweir         ,m_aSubmissionVetoListeners( m_aMutex )
90cdf0e10cSrcweir         ,m_aApproveActionListeners( m_aMutex )
91cdf0e10cSrcweir         ,m_aActionListeners( m_aMutex )
92cdf0e10cSrcweir     {
93cdf0e10cSrcweir         m_pFeatureInterception.reset( new ControlFeatureInterception( _rxFactory ) );
94cdf0e10cSrcweir     }
95cdf0e10cSrcweir 
96cdf0e10cSrcweir     //------------------------------------------------------------------------------
~OClickableImageBaseControl()97cdf0e10cSrcweir     OClickableImageBaseControl::~OClickableImageBaseControl()
98cdf0e10cSrcweir     {
99cdf0e10cSrcweir         if (!OComponentHelper::rBHelper.bDisposed)
100cdf0e10cSrcweir         {
101cdf0e10cSrcweir             acquire();
102cdf0e10cSrcweir             dispose();
103cdf0e10cSrcweir         }
104cdf0e10cSrcweir     }
105cdf0e10cSrcweir 
106cdf0e10cSrcweir     // UNO Anbindung
107cdf0e10cSrcweir     //------------------------------------------------------------------------------
queryAggregation(const Type & _rType)108cdf0e10cSrcweir     Any SAL_CALL OClickableImageBaseControl::queryAggregation(const Type& _rType) throw (RuntimeException)
109cdf0e10cSrcweir     {
110cdf0e10cSrcweir         Any aReturn = OControl::queryAggregation(_rType);
111cdf0e10cSrcweir         if (!aReturn.hasValue())
112cdf0e10cSrcweir             aReturn = OClickableImageBaseControl_BASE::queryInterface(_rType);
113cdf0e10cSrcweir         return aReturn;
114cdf0e10cSrcweir     }
115cdf0e10cSrcweir 
116cdf0e10cSrcweir     // XApproveActionBroadcaster
117cdf0e10cSrcweir     //------------------------------------------------------------------------------
addApproveActionListener(const Reference<XApproveActionListener> & l)118cdf0e10cSrcweir     void OClickableImageBaseControl::addApproveActionListener(
119cdf0e10cSrcweir             const Reference<XApproveActionListener>& l) throw( RuntimeException )
120cdf0e10cSrcweir     {
121cdf0e10cSrcweir         m_aApproveActionListeners.addInterface(l);
122cdf0e10cSrcweir     }
123cdf0e10cSrcweir 
124cdf0e10cSrcweir     //------------------------------------------------------------------------------
removeApproveActionListener(const Reference<XApproveActionListener> & l)125cdf0e10cSrcweir     void OClickableImageBaseControl::removeApproveActionListener(
126cdf0e10cSrcweir             const Reference<XApproveActionListener>& l) throw( RuntimeException )
127cdf0e10cSrcweir     {
128cdf0e10cSrcweir         m_aApproveActionListeners.removeInterface(l);
129cdf0e10cSrcweir     }
130cdf0e10cSrcweir 
131cdf0e10cSrcweir     //--------------------------------------------------------------------
registerDispatchProviderInterceptor(const Reference<XDispatchProviderInterceptor> & _rxInterceptor)132cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::registerDispatchProviderInterceptor( const Reference< XDispatchProviderInterceptor >& _rxInterceptor ) throw (RuntimeException)
133cdf0e10cSrcweir     {
134cdf0e10cSrcweir         m_pFeatureInterception->registerDispatchProviderInterceptor( _rxInterceptor  );
135cdf0e10cSrcweir     }
136cdf0e10cSrcweir 
137cdf0e10cSrcweir     //--------------------------------------------------------------------
releaseDispatchProviderInterceptor(const Reference<XDispatchProviderInterceptor> & _rxInterceptor)138cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::releaseDispatchProviderInterceptor( const Reference< XDispatchProviderInterceptor >& _rxInterceptor ) throw (RuntimeException)
139cdf0e10cSrcweir     {
140cdf0e10cSrcweir         m_pFeatureInterception->releaseDispatchProviderInterceptor( _rxInterceptor  );
141cdf0e10cSrcweir     }
142cdf0e10cSrcweir 
143cdf0e10cSrcweir     // OComponentHelper
144cdf0e10cSrcweir     //------------------------------------------------------------------------------
disposing()145cdf0e10cSrcweir     void OClickableImageBaseControl::disposing()
146cdf0e10cSrcweir     {
147cdf0e10cSrcweir         EventObject aEvent( static_cast< XWeak* >( this ) );
148cdf0e10cSrcweir         m_aApproveActionListeners.disposeAndClear( aEvent );
149cdf0e10cSrcweir         m_aActionListeners.disposeAndClear( aEvent );
150cdf0e10cSrcweir         m_aSubmissionVetoListeners.disposeAndClear( aEvent );
151cdf0e10cSrcweir         m_pFeatureInterception->dispose();
152cdf0e10cSrcweir 
153cdf0e10cSrcweir         {
154cdf0e10cSrcweir             ::osl::MutexGuard aGuard( m_aMutex );
155cdf0e10cSrcweir             if( m_pThread )
156cdf0e10cSrcweir             {
157cdf0e10cSrcweir                 m_pThread->release();
158cdf0e10cSrcweir                 m_pThread = NULL;
159cdf0e10cSrcweir             }
160cdf0e10cSrcweir         }
161cdf0e10cSrcweir 
162cdf0e10cSrcweir         OControl::disposing();
163cdf0e10cSrcweir     }
164cdf0e10cSrcweir 
165cdf0e10cSrcweir     //------------------------------------------------------------------------------
getImageProducerThread()166cdf0e10cSrcweir     OImageProducerThread_Impl* OClickableImageBaseControl::getImageProducerThread()
167cdf0e10cSrcweir     {
168cdf0e10cSrcweir 	    if ( !m_pThread )
169cdf0e10cSrcweir 	    {
170cdf0e10cSrcweir 		    m_pThread = new OImageProducerThread_Impl( this );
171cdf0e10cSrcweir 		    m_pThread->acquire();
172cdf0e10cSrcweir 		    m_pThread->create();
173cdf0e10cSrcweir 	    }
174cdf0e10cSrcweir         return m_pThread;
175cdf0e10cSrcweir     }
176cdf0e10cSrcweir 
177cdf0e10cSrcweir     //------------------------------------------------------------------------------
approveAction()178cdf0e10cSrcweir     bool OClickableImageBaseControl::approveAction( )
179cdf0e10cSrcweir     {
180cdf0e10cSrcweir         sal_Bool bCancelled = sal_False;
181cdf0e10cSrcweir         EventObject aEvent( static_cast< XWeak* >( this ) );
182cdf0e10cSrcweir 
183cdf0e10cSrcweir         ::cppu::OInterfaceIteratorHelper aIter( m_aApproveActionListeners );
184cdf0e10cSrcweir         while( !bCancelled && aIter.hasMoreElements() )
185cdf0e10cSrcweir         {
186cdf0e10cSrcweir             // Jede approveAction-Methode muss thread-safe sein!!!
187cdf0e10cSrcweir             if( !static_cast< XApproveActionListener* >( aIter.next() )->approveAction( aEvent ) )
188cdf0e10cSrcweir                 bCancelled = sal_True;
189cdf0e10cSrcweir         }
190cdf0e10cSrcweir 
191cdf0e10cSrcweir         return !bCancelled;
192cdf0e10cSrcweir     }
193cdf0e10cSrcweir 
194cdf0e10cSrcweir     //------------------------------------------------------------------------------
195cdf0e10cSrcweir     // Diese Methode wird auch aus einem Thread gerufen und muss deshalb
196cdf0e10cSrcweir     // thread-safe sein.
actionPerformed_Impl(sal_Bool bNotifyListener,const MouseEvent & rEvt)197cdf0e10cSrcweir     void OClickableImageBaseControl::actionPerformed_Impl(sal_Bool bNotifyListener, const MouseEvent& rEvt)
198cdf0e10cSrcweir     {
199cdf0e10cSrcweir         if( bNotifyListener )
200cdf0e10cSrcweir         {
201cdf0e10cSrcweir             if ( !approveAction() )
202cdf0e10cSrcweir                 return;
203cdf0e10cSrcweir         }
204cdf0e10cSrcweir 
205cdf0e10cSrcweir         // Ob der Rest des Codes Thread-Safe ist weiss man nicht genau. Deshalb
206cdf0e10cSrcweir         // wird das meiste bei gelocktem Solar-Mutex erledigen.
207cdf0e10cSrcweir         Reference<XPropertySet>  xSet;
208cdf0e10cSrcweir         Reference< XInterface > xModelsParent;
209cdf0e10cSrcweir         FormButtonType eButtonType = FormButtonType_PUSH;
210cdf0e10cSrcweir         {
211cdf0e10cSrcweir             ::vos::OGuard aGuard( Application::GetSolarMutex() );
212cdf0e10cSrcweir 
213cdf0e10cSrcweir             // Parent holen
214cdf0e10cSrcweir             Reference<XFormComponent>  xComp(getModel(), UNO_QUERY);
215cdf0e10cSrcweir             if (!xComp.is())
216cdf0e10cSrcweir                 return;
217cdf0e10cSrcweir 
218cdf0e10cSrcweir             xModelsParent = xComp->getParent();
219cdf0e10cSrcweir             if (!xModelsParent.is())
220cdf0e10cSrcweir                 return;
221cdf0e10cSrcweir 
222cdf0e10cSrcweir             // which button type?
223cdf0e10cSrcweir             xSet = xSet.query( xComp );
224cdf0e10cSrcweir             if ( !xSet.is() )
225cdf0e10cSrcweir                 return;
226cdf0e10cSrcweir             xSet->getPropertyValue(PROPERTY_BUTTONTYPE) >>= eButtonType;
227cdf0e10cSrcweir         }
228cdf0e10cSrcweir 
229cdf0e10cSrcweir         switch (eButtonType)
230cdf0e10cSrcweir         {
231cdf0e10cSrcweir             case FormButtonType_RESET:
232cdf0e10cSrcweir             {
233cdf0e10cSrcweir                 // reset-Methoden muessen thread-safe sein!
234cdf0e10cSrcweir                 Reference<XReset>  xReset(xModelsParent, UNO_QUERY);
235cdf0e10cSrcweir                 if (!xReset.is())
236cdf0e10cSrcweir                     return;
237cdf0e10cSrcweir 
238cdf0e10cSrcweir                 xReset->reset();
239cdf0e10cSrcweir             }
240cdf0e10cSrcweir             break;
241cdf0e10cSrcweir 
242cdf0e10cSrcweir             case FormButtonType_SUBMIT:
243cdf0e10cSrcweir             {
244cdf0e10cSrcweir                 // if some outer component can provide an interaction handler, use it
245cdf0e10cSrcweir                 Reference< XInteractionHandler > xHandler( m_pFeatureInterception->queryDispatch( "private:/InteractionHandler" ), UNO_QUERY );
246cdf0e10cSrcweir                 try
247cdf0e10cSrcweir                 {
248cdf0e10cSrcweir                     implSubmit( rEvt, xHandler );
249cdf0e10cSrcweir                 }
250cdf0e10cSrcweir                 catch( const Exception& )
251cdf0e10cSrcweir                 {
252cdf0e10cSrcweir                     // ignore
253cdf0e10cSrcweir                 }
254cdf0e10cSrcweir             }
255cdf0e10cSrcweir             break;
256cdf0e10cSrcweir 
257cdf0e10cSrcweir             case FormButtonType_URL:
258cdf0e10cSrcweir             {
259cdf0e10cSrcweir                 ::vos::OGuard aGuard( Application::GetSolarMutex() );
260cdf0e10cSrcweir 
261cdf0e10cSrcweir                 Reference< XModel >  xModel = getXModel(xModelsParent);
262cdf0e10cSrcweir                 if (!xModel.is())
263cdf0e10cSrcweir                     return;
264cdf0e10cSrcweir 
265cdf0e10cSrcweir                 ///////////////////////////////////////////////////////////////////////
266cdf0e10cSrcweir                 // Jetzt URL ausfuehren
267cdf0e10cSrcweir                 Reference< XController >  xController = xModel->getCurrentController();
268cdf0e10cSrcweir                 if (!xController.is())
269cdf0e10cSrcweir                     return;
270cdf0e10cSrcweir 
271cdf0e10cSrcweir                 Reference< XFrame >  xFrame = xController->getFrame();
272cdf0e10cSrcweir                 if( !xFrame.is() )
273cdf0e10cSrcweir                     return;
274cdf0e10cSrcweir 
275cdf0e10cSrcweir                 URL aURL;
276cdf0e10cSrcweir                 aURL.Complete =
277cdf0e10cSrcweir                     getString(xSet->getPropertyValue(PROPERTY_TARGET_URL));
278cdf0e10cSrcweir 
279cdf0e10cSrcweir 			    if (aURL.Complete.getLength() && (LOCAL_URL_PREFIX == aURL.Complete.getStr()[0]))
280cdf0e10cSrcweir 			    {	// the URL contains a local URL only. Since the URLTransformer does not handle this case correctly
281cdf0e10cSrcweir 				    // (it can't: it does not know the document URL), we have to take care for this ourself.
282cdf0e10cSrcweir 				    // The real solution would be to not allow such relative URLs (there is a rule that at runtime, all
283cdf0e10cSrcweir 				    // URLs have to be absolute), but for compatibility reasons this is no option.
284cdf0e10cSrcweir 				    // The more as the user does not want to see a local URL as "file://<path>/<document>#mark" if it
285cdf0e10cSrcweir 				    // could be "#mark" as well.
286cdf0e10cSrcweir 				    // If we someday say that this hack (yes, it's kind of a hack) is not sustainable anymore, the complete
287cdf0e10cSrcweir 				    // solutiuon would be:
288cdf0e10cSrcweir 				    // * recognize URLs consisting of a mark only while _reading_ the document
289cdf0e10cSrcweir 				    // * for this, allow the INetURLObject (which at the moment is invoked when reading URLs) to
290cdf0e10cSrcweir 				    //   transform such mark-only URLs into correct absolute URLs
291cdf0e10cSrcweir 				    // * at the UI, show only the mark
292cdf0e10cSrcweir 				    // * !!!! recognize every SAVEAS on the document, so the absolute URL can be adjusted. This seems
293cdf0e10cSrcweir 				    // rather impossible !!!
294cdf0e10cSrcweir 				    // 89752 - 23.07.2001 - frank.schoenheit@sun.com
295cdf0e10cSrcweir 				    aURL.Mark = aURL.Complete;
296cdf0e10cSrcweir 				    aURL.Complete = xModel->getURL();
297cdf0e10cSrcweir 				    aURL.Complete += aURL.Mark;
298cdf0e10cSrcweir 			    }
299cdf0e10cSrcweir 
300cdf0e10cSrcweir 			    sal_Bool bDispatchUrlInternal = sal_False;
301cdf0e10cSrcweir 			    xSet->getPropertyValue(PROPERTY_DISPATCHURLINTERNAL) >>= bDispatchUrlInternal;
302cdf0e10cSrcweir 			    if ( bDispatchUrlInternal )
303cdf0e10cSrcweir 			    {
304cdf0e10cSrcweir                     m_pFeatureInterception->getTransformer().parseSmartWithAsciiProtocol( aURL, INET_FILE_SCHEME );
305cdf0e10cSrcweir 
306cdf0e10cSrcweir 				    ::rtl::OUString aTargetFrame;
307cdf0e10cSrcweir 				    xSet->getPropertyValue(PROPERTY_TARGET_FRAME) >>= aTargetFrame;
308cdf0e10cSrcweir 
309cdf0e10cSrcweir 				    Reference< XDispatch >  xDisp = Reference< XDispatchProvider > (xFrame,UNO_QUERY)->queryDispatch( aURL, aTargetFrame,
310cdf0e10cSrcweir 						    FrameSearchFlag::SELF | FrameSearchFlag::PARENT |
311cdf0e10cSrcweir 						    FrameSearchFlag::SIBLINGS | FrameSearchFlag::CREATE );
312cdf0e10cSrcweir 
313cdf0e10cSrcweir 				    Sequence<PropertyValue> aArgs(1);
314cdf0e10cSrcweir 				    PropertyValue& rProp = aArgs.getArray()[0];
315cdf0e10cSrcweir 				    rProp.Name = ::rtl::OUString::createFromAscii("Referer");
316cdf0e10cSrcweir 				    rProp.Value <<= xModel->getURL();
317cdf0e10cSrcweir 
318cdf0e10cSrcweir 				    if (xDisp.is())
319cdf0e10cSrcweir 					    xDisp->dispatch( aURL, aArgs );
320cdf0e10cSrcweir 			    }
321cdf0e10cSrcweir 			    else
322cdf0e10cSrcweir 			    {
323cdf0e10cSrcweir 				    URL aHyperLink = m_pFeatureInterception->getTransformer().getStrictURLFromAscii( ".uno:OpenHyperlink" );
324cdf0e10cSrcweir 
325cdf0e10cSrcweir 				    Reference< XDispatch >  xDisp = Reference< XDispatchProvider > (xFrame,UNO_QUERY)->queryDispatch(aHyperLink, ::rtl::OUString() , 0);
326cdf0e10cSrcweir 
327cdf0e10cSrcweir 				    if ( xDisp.is() )
328cdf0e10cSrcweir 				    {
329cdf0e10cSrcweir 					    Sequence<PropertyValue> aProps(3);
330cdf0e10cSrcweir 					    aProps[0].Name  = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("URL"));
331cdf0e10cSrcweir 					    aProps[0].Value <<= aURL.Complete;
332cdf0e10cSrcweir 
333cdf0e10cSrcweir 					    aProps[1].Name  = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("FrameName"));
334cdf0e10cSrcweir 					    aProps[1].Value = xSet->getPropertyValue(PROPERTY_TARGET_FRAME);
335cdf0e10cSrcweir 
336cdf0e10cSrcweir 					    aProps[2].Name  = ::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Referer"));
337cdf0e10cSrcweir 					    aProps[2].Value <<= xModel->getURL();
338cdf0e10cSrcweir 
339cdf0e10cSrcweir 					    xDisp->dispatch( aHyperLink, aProps );
340cdf0e10cSrcweir 				    }
341cdf0e10cSrcweir 			    }
342cdf0e10cSrcweir             }   break;
343cdf0e10cSrcweir             default:
344cdf0e10cSrcweir             {
345cdf0e10cSrcweir                     // notify the action listeners for a push button
346cdf0e10cSrcweir                 ActionEvent aEvt(static_cast<XWeak*>(this), m_aActionCommand);
347cdf0e10cSrcweir                 m_aActionListeners.notifyEach( &XActionListener::actionPerformed, aEvt );
348cdf0e10cSrcweir             }
349cdf0e10cSrcweir         }
350cdf0e10cSrcweir     }
351cdf0e10cSrcweir 
352cdf0e10cSrcweir 
353cdf0e10cSrcweir     //--------------------------------------------------------------------
addSubmissionVetoListener(const Reference<submission::XSubmissionVetoListener> & listener)354cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::addSubmissionVetoListener( const Reference< submission::XSubmissionVetoListener >& listener ) throw (NoSupportException, RuntimeException)
355cdf0e10cSrcweir     {
356cdf0e10cSrcweir         m_aSubmissionVetoListeners.addInterface( listener );
357cdf0e10cSrcweir     }
358cdf0e10cSrcweir 
359cdf0e10cSrcweir     //--------------------------------------------------------------------
removeSubmissionVetoListener(const Reference<submission::XSubmissionVetoListener> & listener)360cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::removeSubmissionVetoListener( const Reference< submission::XSubmissionVetoListener >& listener ) throw (NoSupportException, RuntimeException)
361cdf0e10cSrcweir     {
362cdf0e10cSrcweir         m_aSubmissionVetoListeners.removeInterface( listener );
363cdf0e10cSrcweir     }
364cdf0e10cSrcweir 
365cdf0e10cSrcweir     //--------------------------------------------------------------------
submitWithInteraction(const Reference<XInteractionHandler> & _rxHandler)366cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::submitWithInteraction( const Reference< XInteractionHandler >& _rxHandler ) throw (VetoException, WrappedTargetException, RuntimeException)
367cdf0e10cSrcweir     {
368cdf0e10cSrcweir         implSubmit( MouseEvent(), _rxHandler );
369cdf0e10cSrcweir     }
370cdf0e10cSrcweir 
371cdf0e10cSrcweir     //--------------------------------------------------------------------
submit()372cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseControl::submit(  ) throw (VetoException, WrappedTargetException, RuntimeException)
373cdf0e10cSrcweir     {
374cdf0e10cSrcweir         implSubmit( MouseEvent(), NULL );
375cdf0e10cSrcweir     }
376cdf0e10cSrcweir 
377cdf0e10cSrcweir     //--------------------------------------------------------------------
getSupportedServiceNames()378cdf0e10cSrcweir     Sequence< ::rtl::OUString > SAL_CALL OClickableImageBaseControl::getSupportedServiceNames(  ) throw (RuntimeException)
379cdf0e10cSrcweir     {
380cdf0e10cSrcweir 	    Sequence< ::rtl::OUString > aSupported = OControl::getSupportedServiceNames();
381cdf0e10cSrcweir 	    aSupported.realloc( aSupported.getLength() + 1 );
382cdf0e10cSrcweir 
383cdf0e10cSrcweir 	    ::rtl::OUString* pArray = aSupported.getArray();
384cdf0e10cSrcweir 	    pArray[ aSupported.getLength() - 1 ] = FRM_SUN_CONTROL_SUBMITBUTTON;
385cdf0e10cSrcweir 
386cdf0e10cSrcweir         return aSupported;
387cdf0e10cSrcweir     }
388cdf0e10cSrcweir 
389cdf0e10cSrcweir     //--------------------------------------------------------------------
implSubmit(const MouseEvent & _rEvent,const Reference<XInteractionHandler> & _rxHandler)390cdf0e10cSrcweir     void OClickableImageBaseControl::implSubmit( const MouseEvent& _rEvent, const Reference< XInteractionHandler >& _rxHandler ) SAL_THROW((VetoException, WrappedTargetException, RuntimeException))
391cdf0e10cSrcweir     {
392cdf0e10cSrcweir         try
393cdf0e10cSrcweir         {
394cdf0e10cSrcweir             // allow the veto listeners to join the game
395cdf0e10cSrcweir             m_aSubmissionVetoListeners.notifyEach( &XSubmissionVetoListener::submitting, EventObject( *this ) );
396cdf0e10cSrcweir 
397cdf0e10cSrcweir             // see whether there's an "submit interceptor" set at our model
398cdf0e10cSrcweir             Reference< submission::XSubmissionSupplier > xSubmissionSupp( getModel(), UNO_QUERY );
399cdf0e10cSrcweir             Reference< XSubmission > xSubmission;
400cdf0e10cSrcweir             if ( xSubmissionSupp.is() )
401cdf0e10cSrcweir                 xSubmission = xSubmissionSupp->getSubmission();
402cdf0e10cSrcweir 
403cdf0e10cSrcweir             if ( xSubmission.is() )
404cdf0e10cSrcweir             {
405cdf0e10cSrcweir                 if ( !_rxHandler.is() )
406cdf0e10cSrcweir                     xSubmission->submit();
407cdf0e10cSrcweir                 else
408cdf0e10cSrcweir                     xSubmission->submitWithInteraction( _rxHandler );
409cdf0e10cSrcweir             }
410cdf0e10cSrcweir             else
411cdf0e10cSrcweir             {
412cdf0e10cSrcweir                 // no "interceptor" -> ordinary (old-way) submission
413cdf0e10cSrcweir                 Reference< XChild > xChild( getModel(), UNO_QUERY );
414cdf0e10cSrcweir                 Reference< XSubmit > xParentSubmission;
415cdf0e10cSrcweir                 if ( xChild.is() )
416cdf0e10cSrcweir                     xParentSubmission = xParentSubmission.query( xChild->getParent() );
417cdf0e10cSrcweir                 if ( xParentSubmission.is() )
418cdf0e10cSrcweir                     xParentSubmission->submit( this, _rEvent );
419cdf0e10cSrcweir             }
420cdf0e10cSrcweir         }
421cdf0e10cSrcweir         catch( const VetoException& )
422cdf0e10cSrcweir         {
423cdf0e10cSrcweir             // allowed to leave
424cdf0e10cSrcweir             throw;
425cdf0e10cSrcweir         }
426cdf0e10cSrcweir         catch( const RuntimeException& )
427cdf0e10cSrcweir         {
428cdf0e10cSrcweir             // allowed to leave
429cdf0e10cSrcweir             throw;
430cdf0e10cSrcweir         }
431cdf0e10cSrcweir         catch( const WrappedTargetException& e )
432cdf0e10cSrcweir         {
433cdf0e10cSrcweir             // allowed to leave
434cdf0e10cSrcweir             throw;
435cdf0e10cSrcweir         }
436cdf0e10cSrcweir         catch( const Exception& e )
437cdf0e10cSrcweir         {
438cdf0e10cSrcweir             OSL_ENSURE( sal_False, "OClickableImageBaseControl::implSubmit: caught an unknown exception!" );
439cdf0e10cSrcweir             throw WrappedTargetException( ::rtl::OUString(), *this, makeAny( e ) );
440cdf0e10cSrcweir         }
441cdf0e10cSrcweir     }
442cdf0e10cSrcweir 
443cdf0e10cSrcweir     //==================================================================
444cdf0e10cSrcweir     // OClickableImageBaseModel
445cdf0e10cSrcweir     //==================================================================
446cdf0e10cSrcweir     //------------------------------------------------------------------------------
_getTypes()447cdf0e10cSrcweir     Sequence<Type> OClickableImageBaseModel::_getTypes()
448cdf0e10cSrcweir     {
449cdf0e10cSrcweir 	    return concatSequences(
450cdf0e10cSrcweir             OControlModel::_getTypes(),
451cdf0e10cSrcweir             OClickableImageBaseModel_Base::getTypes()
452cdf0e10cSrcweir         );
453cdf0e10cSrcweir     }
454cdf0e10cSrcweir 
455cdf0e10cSrcweir     //------------------------------------------------------------------
DBG_NAME(OClickableImageBaseModel)456cdf0e10cSrcweir     DBG_NAME( OClickableImageBaseModel )
457cdf0e10cSrcweir     //------------------------------------------------------------------
458cdf0e10cSrcweir     OClickableImageBaseModel::OClickableImageBaseModel( const Reference< XMultiServiceFactory >& _rxFactory, const ::rtl::OUString& _rUnoControlModelTypeName,
459cdf0e10cSrcweir 		    const ::rtl::OUString& rDefault )
460cdf0e10cSrcweir 	    :OControlModel( _rxFactory, _rUnoControlModelTypeName, rDefault )
461cdf0e10cSrcweir 	    ,OPropertyChangeListener(m_aMutex)
462cdf0e10cSrcweir 	    ,m_pMedium(NULL)
463cdf0e10cSrcweir 	    ,m_pProducer( NULL )
464cdf0e10cSrcweir 	    ,m_bDispatchUrlInternal(sal_False)
465cdf0e10cSrcweir 	    ,m_bDownloading(sal_False)
466cdf0e10cSrcweir 	    ,m_bProdStarted(sal_False)
467cdf0e10cSrcweir     {
468cdf0e10cSrcweir 	    DBG_CTOR( OClickableImageBaseModel, NULL );
469cdf0e10cSrcweir 	    implConstruct();
470cdf0e10cSrcweir 	    m_eButtonType = FormButtonType_PUSH;
471cdf0e10cSrcweir     }
472cdf0e10cSrcweir 
473cdf0e10cSrcweir     //------------------------------------------------------------------
OClickableImageBaseModel(const OClickableImageBaseModel * _pOriginal,const Reference<XMultiServiceFactory> & _rxFactory)474cdf0e10cSrcweir     OClickableImageBaseModel::OClickableImageBaseModel( const OClickableImageBaseModel* _pOriginal, const Reference<XMultiServiceFactory>& _rxFactory )
475cdf0e10cSrcweir 	    :OControlModel( _pOriginal, _rxFactory )
476cdf0e10cSrcweir 	    ,OPropertyChangeListener( m_aMutex )
477cdf0e10cSrcweir 	    ,m_pMedium( NULL )
478cdf0e10cSrcweir 	    ,m_pProducer( NULL )
479cdf0e10cSrcweir 	    ,m_bDispatchUrlInternal(sal_False)
480cdf0e10cSrcweir 	    ,m_bDownloading( sal_False )
481cdf0e10cSrcweir 	    ,m_bProdStarted( sal_False )
482cdf0e10cSrcweir     {
483cdf0e10cSrcweir 	    DBG_CTOR( OClickableImageBaseModel, NULL );
484cdf0e10cSrcweir 	    implConstruct();
485cdf0e10cSrcweir 
486cdf0e10cSrcweir 	    // copy properties
487cdf0e10cSrcweir 	    m_eButtonType			= _pOriginal->m_eButtonType;
488cdf0e10cSrcweir 	    m_sTargetURL			= _pOriginal->m_sTargetURL;
489cdf0e10cSrcweir 	    m_sTargetFrame			= _pOriginal->m_sTargetFrame;
490cdf0e10cSrcweir 	    m_bDispatchUrlInternal	= _pOriginal->m_bDispatchUrlInternal;
491cdf0e10cSrcweir     }
492cdf0e10cSrcweir 
493cdf0e10cSrcweir     //------------------------------------------------------------------------------
implInitializeImageURL()494cdf0e10cSrcweir     void OClickableImageBaseModel::implInitializeImageURL( )
495cdf0e10cSrcweir     {
496cdf0e10cSrcweir         osl_incrementInterlockedCount( &m_refCount );
497cdf0e10cSrcweir         {
498cdf0e10cSrcweir             // simulate a propertyChanged event for the ImageURL
499cdf0e10cSrcweir             // 2003-05-15 - #109591# - fs@openoffice.org
500cdf0e10cSrcweir             Any aImageURL;
501cdf0e10cSrcweir             getFastPropertyValue( aImageURL, PROPERTY_ID_IMAGE_URL );
502cdf0e10cSrcweir             _propertyChanged( PropertyChangeEvent( *this, PROPERTY_IMAGE_URL, sal_False, PROPERTY_ID_IMAGE_URL, Any( ), aImageURL ) );
503cdf0e10cSrcweir         }
504cdf0e10cSrcweir         osl_decrementInterlockedCount( &m_refCount );
505cdf0e10cSrcweir     }
506cdf0e10cSrcweir 
507cdf0e10cSrcweir     //------------------------------------------------------------------------------
implConstruct()508cdf0e10cSrcweir     void OClickableImageBaseModel::implConstruct()
509cdf0e10cSrcweir     {
510cdf0e10cSrcweir 	    m_pProducer = new ImageProducer;
511cdf0e10cSrcweir         increment( m_refCount );
512cdf0e10cSrcweir 	    {
513cdf0e10cSrcweir 		    m_xProducer = m_pProducer;
514cdf0e10cSrcweir 
515cdf0e10cSrcweir 		    if ( m_xAggregateSet.is() )
516cdf0e10cSrcweir 		    {
517cdf0e10cSrcweir 			    OPropertyChangeMultiplexer* pMultiplexer = new OPropertyChangeMultiplexer( this, m_xAggregateSet );
518cdf0e10cSrcweir 			    pMultiplexer->addProperty( PROPERTY_IMAGE_URL );
519cdf0e10cSrcweir 		    }
520cdf0e10cSrcweir 	    }
521cdf0e10cSrcweir         decrement(m_refCount);
522cdf0e10cSrcweir     }
523cdf0e10cSrcweir 
524cdf0e10cSrcweir     //------------------------------------------------------------------------------
~OClickableImageBaseModel()525cdf0e10cSrcweir     OClickableImageBaseModel::~OClickableImageBaseModel()
526cdf0e10cSrcweir     {
527cdf0e10cSrcweir         if (!OComponentHelper::rBHelper.bDisposed)
528cdf0e10cSrcweir         {
529cdf0e10cSrcweir             acquire();
530cdf0e10cSrcweir             dispose();
531cdf0e10cSrcweir         }
532cdf0e10cSrcweir         DBG_ASSERT(m_pMedium == NULL, "OClickableImageBaseModel::~OClickableImageBaseModel : leaving a memory leak ...");
533cdf0e10cSrcweir             // spaetestens im dispose sollte das aufgeraeumt worden sein
534cdf0e10cSrcweir 
535cdf0e10cSrcweir 	    DBG_DTOR( OClickableImageBaseModel, NULL );
536cdf0e10cSrcweir     }
537cdf0e10cSrcweir 
538cdf0e10cSrcweir     // XImageProducer
539cdf0e10cSrcweir     //--------------------------------------------------------------------
addConsumer(const Reference<XImageConsumer> & _rxConsumer)540cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseModel::addConsumer( const Reference< XImageConsumer >& _rxConsumer ) throw (RuntimeException)
541cdf0e10cSrcweir     {
542cdf0e10cSrcweir         ImageModelMethodGuard aGuard( *this );
543cdf0e10cSrcweir         GetImageProducer()->addConsumer( _rxConsumer );
544cdf0e10cSrcweir     }
545cdf0e10cSrcweir 
546cdf0e10cSrcweir     //--------------------------------------------------------------------
removeConsumer(const Reference<XImageConsumer> & _rxConsumer)547cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseModel::removeConsumer( const Reference< XImageConsumer >& _rxConsumer ) throw (RuntimeException)
548cdf0e10cSrcweir     {
549cdf0e10cSrcweir         ImageModelMethodGuard aGuard( *this );
550cdf0e10cSrcweir         GetImageProducer()->removeConsumer( _rxConsumer );
551cdf0e10cSrcweir     }
552cdf0e10cSrcweir 
553cdf0e10cSrcweir     //--------------------------------------------------------------------
startProduction()554cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseModel::startProduction(  ) throw (RuntimeException)
555cdf0e10cSrcweir     {
556cdf0e10cSrcweir         ImageModelMethodGuard aGuard( *this );
557cdf0e10cSrcweir         GetImageProducer()->startProduction();
558cdf0e10cSrcweir     }
559cdf0e10cSrcweir 
560cdf0e10cSrcweir     //--------------------------------------------------------------------
getSubmission()561cdf0e10cSrcweir     Reference< submission::XSubmission > SAL_CALL OClickableImageBaseModel::getSubmission() throw (RuntimeException)
562cdf0e10cSrcweir     {
563cdf0e10cSrcweir         return m_xSubmissionDelegate;
564cdf0e10cSrcweir     }
565cdf0e10cSrcweir 
566cdf0e10cSrcweir     //--------------------------------------------------------------------
setSubmission(const Reference<submission::XSubmission> & _submission)567cdf0e10cSrcweir     void SAL_CALL OClickableImageBaseModel::setSubmission( const Reference< submission::XSubmission >& _submission ) throw (RuntimeException)
568cdf0e10cSrcweir     {
569cdf0e10cSrcweir         m_xSubmissionDelegate = _submission;
570cdf0e10cSrcweir     }
571cdf0e10cSrcweir 
572cdf0e10cSrcweir     //--------------------------------------------------------------------
getSupportedServiceNames()573cdf0e10cSrcweir     Sequence< ::rtl::OUString > SAL_CALL OClickableImageBaseModel::getSupportedServiceNames(  ) throw (RuntimeException)
574cdf0e10cSrcweir     {
575cdf0e10cSrcweir 	    Sequence< ::rtl::OUString > aSupported = OControlModel::getSupportedServiceNames();
576cdf0e10cSrcweir 	    aSupported.realloc( aSupported.getLength() + 1 );
577cdf0e10cSrcweir 
578cdf0e10cSrcweir 	    ::rtl::OUString* pArray = aSupported.getArray();
579cdf0e10cSrcweir 	    pArray[ aSupported.getLength() - 1 ] = FRM_SUN_COMPONENT_SUBMITBUTTON;
580cdf0e10cSrcweir 
581cdf0e10cSrcweir         return aSupported;
582cdf0e10cSrcweir     }
583cdf0e10cSrcweir 
584cdf0e10cSrcweir     // OComponentHelper
585cdf0e10cSrcweir     //------------------------------------------------------------------------------
disposing()586cdf0e10cSrcweir     void OClickableImageBaseModel::disposing()
587cdf0e10cSrcweir     {
588cdf0e10cSrcweir         OControlModel::disposing();
589cdf0e10cSrcweir         if (m_pMedium)
590cdf0e10cSrcweir         {
591cdf0e10cSrcweir             delete m_pMedium;
592cdf0e10cSrcweir             m_pMedium = NULL;
593cdf0e10cSrcweir         }
594cdf0e10cSrcweir 
595cdf0e10cSrcweir         m_xProducer = NULL;
596cdf0e10cSrcweir         m_pProducer = NULL;
597cdf0e10cSrcweir     }
598cdf0e10cSrcweir 
599cdf0e10cSrcweir     //------------------------------------------------------------------------------
queryAggregation(const Type & _rType)600cdf0e10cSrcweir     Any SAL_CALL OClickableImageBaseModel::queryAggregation(const Type& _rType) throw (RuntimeException)
601cdf0e10cSrcweir     {
602cdf0e10cSrcweir         // order matters:
603cdf0e10cSrcweir         // we definately want to "overload" the XImageProducer interface of our aggregate,
604cdf0e10cSrcweir         // thus check OClickableImageBaseModel_Base (which provides this) first
605cdf0e10cSrcweir         Any aReturn = OClickableImageBaseModel_Base::queryInterface( _rType );
606cdf0e10cSrcweir 
607cdf0e10cSrcweir         // BUT: _don't_ let it feel responsible for the XTypeProvider interface
608cdf0e10cSrcweir         // (as this is implemented by our base class in the proper way)
609cdf0e10cSrcweir         if  (   _rType.equals( ::getCppuType( static_cast< Reference< XTypeProvider >* >( NULL ) ) )
610cdf0e10cSrcweir             ||  !aReturn.hasValue()
611cdf0e10cSrcweir             )
612cdf0e10cSrcweir             aReturn = OControlModel::queryAggregation( _rType );
613cdf0e10cSrcweir 
614cdf0e10cSrcweir         return aReturn;
615cdf0e10cSrcweir     }
616cdf0e10cSrcweir 
617cdf0e10cSrcweir     //------------------------------------------------------------------------------
getFastPropertyValue(Any & rValue,sal_Int32 nHandle) const618cdf0e10cSrcweir     void OClickableImageBaseModel::getFastPropertyValue(Any& rValue, sal_Int32 nHandle) const
619cdf0e10cSrcweir     {
620cdf0e10cSrcweir         switch (nHandle)
621cdf0e10cSrcweir         {
622cdf0e10cSrcweir             case PROPERTY_ID_BUTTONTYPE				: rValue <<= m_eButtonType; break;
623cdf0e10cSrcweir             case PROPERTY_ID_TARGET_URL				: rValue <<= m_sTargetURL; break;
624cdf0e10cSrcweir             case PROPERTY_ID_TARGET_FRAME			: rValue <<= m_sTargetFrame; break;
625cdf0e10cSrcweir 		    case PROPERTY_ID_DISPATCHURLINTERNAL	: rValue <<= m_bDispatchUrlInternal; break;
626cdf0e10cSrcweir             default:
627cdf0e10cSrcweir                 OControlModel::getFastPropertyValue(rValue, nHandle);
628cdf0e10cSrcweir         }
629cdf0e10cSrcweir     }
630cdf0e10cSrcweir 
631cdf0e10cSrcweir     //------------------------------------------------------------------------------
setFastPropertyValue_NoBroadcast(sal_Int32 nHandle,const Any & rValue)632cdf0e10cSrcweir     void OClickableImageBaseModel::setFastPropertyValue_NoBroadcast(sal_Int32 nHandle, const Any& rValue) throw ( Exception)
633cdf0e10cSrcweir     {
634cdf0e10cSrcweir         switch (nHandle)
635cdf0e10cSrcweir         {
636cdf0e10cSrcweir             case PROPERTY_ID_BUTTONTYPE :
637cdf0e10cSrcweir                 DBG_ASSERT(isA(rValue, static_cast<FormButtonType*>(NULL)), "OClickableImageBaseModel::setFastPropertyValue_NoBroadcast : invalid type !" );
638cdf0e10cSrcweir                 rValue >>= m_eButtonType;
639cdf0e10cSrcweir                 break;
640cdf0e10cSrcweir 
641cdf0e10cSrcweir             case PROPERTY_ID_TARGET_URL :
642cdf0e10cSrcweir                 DBG_ASSERT(rValue.getValueType().getTypeClass() == TypeClass_STRING, "OClickableImageBaseModel::setFastPropertyValue_NoBroadcast : invalid type !" );
643cdf0e10cSrcweir                 rValue >>= m_sTargetURL;
644cdf0e10cSrcweir                 break;
645cdf0e10cSrcweir 
646cdf0e10cSrcweir             case PROPERTY_ID_TARGET_FRAME :
647cdf0e10cSrcweir                 DBG_ASSERT(rValue.getValueType().getTypeClass() == TypeClass_STRING, "OClickableImageBaseModel::setFastPropertyValue_NoBroadcast : invalid type !" );
648cdf0e10cSrcweir                 rValue >>= m_sTargetFrame;
649cdf0e10cSrcweir                 break;
650cdf0e10cSrcweir 
651cdf0e10cSrcweir 		    case PROPERTY_ID_DISPATCHURLINTERNAL:
652cdf0e10cSrcweir 			    DBG_ASSERT(rValue.getValueType().getTypeClass() == TypeClass_BOOLEAN, "OClickableImageBaseModel::setFastPropertyValue_NoBroadcast : invalid type !" );
653cdf0e10cSrcweir                 rValue >>= m_bDispatchUrlInternal;
654cdf0e10cSrcweir 			    break;
655cdf0e10cSrcweir 
656cdf0e10cSrcweir             default:
657cdf0e10cSrcweir                 OControlModel::setFastPropertyValue_NoBroadcast(nHandle, rValue);
658cdf0e10cSrcweir         }
659cdf0e10cSrcweir     }
660cdf0e10cSrcweir 
661cdf0e10cSrcweir     //------------------------------------------------------------------------------
convertFastPropertyValue(Any & rConvertedValue,Any & rOldValue,sal_Int32 nHandle,const Any & rValue)662cdf0e10cSrcweir     sal_Bool OClickableImageBaseModel::convertFastPropertyValue(Any& rConvertedValue, Any& rOldValue, sal_Int32 nHandle, const Any& rValue)
663cdf0e10cSrcweir                                 throw( IllegalArgumentException )
664cdf0e10cSrcweir     {
665cdf0e10cSrcweir         switch (nHandle)
666cdf0e10cSrcweir         {
667cdf0e10cSrcweir             case PROPERTY_ID_BUTTONTYPE :
668cdf0e10cSrcweir 			    return tryPropertyValueEnum( rConvertedValue, rOldValue, rValue, m_eButtonType );
669cdf0e10cSrcweir 
670cdf0e10cSrcweir             case PROPERTY_ID_TARGET_URL :
671cdf0e10cSrcweir                 return tryPropertyValue(rConvertedValue, rOldValue, rValue, m_sTargetURL);
672cdf0e10cSrcweir 
673cdf0e10cSrcweir             case PROPERTY_ID_TARGET_FRAME :
674cdf0e10cSrcweir                 return tryPropertyValue(rConvertedValue, rOldValue, rValue, m_sTargetFrame);
675cdf0e10cSrcweir 
676cdf0e10cSrcweir 		    case PROPERTY_ID_DISPATCHURLINTERNAL :
677cdf0e10cSrcweir                 return tryPropertyValue(rConvertedValue, rOldValue, rValue, m_bDispatchUrlInternal);
678cdf0e10cSrcweir 
679cdf0e10cSrcweir             default:
680cdf0e10cSrcweir                 return OControlModel::convertFastPropertyValue(rConvertedValue, rOldValue, nHandle, rValue);
681cdf0e10cSrcweir         }
682cdf0e10cSrcweir     }
683cdf0e10cSrcweir 
684cdf0e10cSrcweir     //------------------------------------------------------------------------------
StartProduction()685cdf0e10cSrcweir     void OClickableImageBaseModel::StartProduction()
686cdf0e10cSrcweir     {
687cdf0e10cSrcweir         ImageProducer *pImgProd = GetImageProducer();
688cdf0e10cSrcweir         // grab the ImageURL
689cdf0e10cSrcweir         rtl::OUString sURL;
690cdf0e10cSrcweir         getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("ImageURL") ) ) >>= sURL;
691cdf0e10cSrcweir         if (!m_pMedium)
692cdf0e10cSrcweir         {
693cdf0e10cSrcweir             if ( ::svt::GraphicAccess::isSupportedURL( sURL )  )
694cdf0e10cSrcweir                 pImgProd->SetImage( sURL );
695cdf0e10cSrcweir             else
696cdf0e10cSrcweir                 // caution: the medium may be NULL if somebody gave us a invalid URL to work with
697cdf0e10cSrcweir                 // 11/24/2000 - 79667 - FS
698cdf0e10cSrcweir                 pImgProd->SetImage(String());
699cdf0e10cSrcweir             m_bDownloading = sal_False;
700cdf0e10cSrcweir             return;
701cdf0e10cSrcweir         }
702cdf0e10cSrcweir         if (m_pMedium->GetErrorCode()==0)
703cdf0e10cSrcweir         {
704cdf0e10cSrcweir             SvStream* pStream = m_pMedium->GetInStream();
705cdf0e10cSrcweir 
706cdf0e10cSrcweir             pImgProd->SetImage(*pStream);
707cdf0e10cSrcweir             pImgProd->startProduction();
708cdf0e10cSrcweir             m_bProdStarted = sal_True;
709cdf0e10cSrcweir         }
710cdf0e10cSrcweir         else
711cdf0e10cSrcweir         {
712cdf0e10cSrcweir             pImgProd->SetImage(String());
713cdf0e10cSrcweir             delete m_pMedium;
714cdf0e10cSrcweir             m_pMedium = 0;
715cdf0e10cSrcweir             m_bDownloading = sal_False;
716cdf0e10cSrcweir         }
717cdf0e10cSrcweir     }
718cdf0e10cSrcweir 
719cdf0e10cSrcweir     //------------------------------------------------------------------------------
SetURL(const::rtl::OUString & rURL)720cdf0e10cSrcweir     void OClickableImageBaseModel::SetURL( const ::rtl::OUString& rURL )
721cdf0e10cSrcweir     {
722cdf0e10cSrcweir         if (m_pMedium || !rURL.getLength())
723cdf0e10cSrcweir         {
724cdf0e10cSrcweir             // Den Stream am Producer freigeben, bevor das Medium geloscht wird.
725cdf0e10cSrcweir             GetImageProducer()->SetImage(String());
726cdf0e10cSrcweir             delete m_pMedium;
727cdf0e10cSrcweir             m_pMedium = NULL;
728cdf0e10cSrcweir         }
729cdf0e10cSrcweir 
730cdf0e10cSrcweir         // the SfxMedium is not allowed to be created with an invalid URL, so we have to check this first
731cdf0e10cSrcweir         // 23.01.2001 - 81927 - FS
732cdf0e10cSrcweir         INetURLObject aUrl(rURL);
733cdf0e10cSrcweir         if (INET_PROT_NOT_VALID == aUrl.GetProtocol())
734cdf0e10cSrcweir             // we treat an invalid URL like we would treat no URL
735cdf0e10cSrcweir             return;
736cdf0e10cSrcweir 
737cdf0e10cSrcweir         if (rURL.getLength() && !::svt::GraphicAccess::isSupportedURL( rURL ) )
738cdf0e10cSrcweir        {
739cdf0e10cSrcweir             if (m_pMedium)
740cdf0e10cSrcweir                 delete m_pMedium;
741cdf0e10cSrcweir 
742cdf0e10cSrcweir             m_pMedium = new SfxMedium(rURL, STREAM_STD_READ, sal_False);
743cdf0e10cSrcweir             m_pMedium->SetDataAvailableLink(
744cdf0e10cSrcweir                     STATIC_LINK(this, OClickableImageBaseModel, DataAvailableLink));
745cdf0e10cSrcweir 
746cdf0e10cSrcweir             // Das XModel suchen, um an die Object-Shell oder zumindest den
747cdf0e10cSrcweir             // Referer zu gelangen.
748cdf0e10cSrcweir             // Das Model findet man allerdings nur beim Laden von HTML-Dokumenten
749cdf0e10cSrcweir             // und dann, wenn die URL in einem bereits geladenen Dokument
750cdf0e10cSrcweir             // geaendert wird. Waehrend des Ladens kommt man nicht an das
751cdf0e10cSrcweir             // Model ran.
752cdf0e10cSrcweir             Reference< XModel >  xModel;
753cdf0e10cSrcweir             InterfaceRef  xIfc( *this );
754cdf0e10cSrcweir             while( !xModel.is() && xIfc.is() )
755cdf0e10cSrcweir             {
756cdf0e10cSrcweir                 Reference<XChild>  xChild( xIfc, UNO_QUERY );
757cdf0e10cSrcweir                 xIfc = xChild->getParent();
758cdf0e10cSrcweir                 query_interface(xIfc, xModel);
759cdf0e10cSrcweir             }
760cdf0e10cSrcweir 
761cdf0e10cSrcweir             // Die Object-Shell suchen, indem wir
762cdf0e10cSrcweir             // ueber alle Object-Shells iterieren und deren XModel mit dem
763cdf0e10cSrcweir             // eigenen vergleichen. Als Optimierung probieren wir aber erstmal
764cdf0e10cSrcweir             // die aktuelle Object-Shell.
765cdf0e10cSrcweir             // wir unser XModel mit dem aller Object
766cdf0e10cSrcweir             SfxObjectShell *pObjSh = 0;
767cdf0e10cSrcweir 
768cdf0e10cSrcweir             if( xModel.is() )
769cdf0e10cSrcweir             {
770cdf0e10cSrcweir                 SfxObjectShell *pTestObjSh = SfxObjectShell::Current();
771cdf0e10cSrcweir                 if( pTestObjSh )
772cdf0e10cSrcweir                 {
773cdf0e10cSrcweir                     Reference< XModel >  xTestModel = pTestObjSh->GetModel();
774cdf0e10cSrcweir                     if( xTestModel == xModel )
775cdf0e10cSrcweir                         pObjSh = pTestObjSh;
776cdf0e10cSrcweir                 }
777cdf0e10cSrcweir                 if( !pObjSh )
778cdf0e10cSrcweir                 {
779cdf0e10cSrcweir                     pTestObjSh = SfxObjectShell::GetFirst();
780cdf0e10cSrcweir                     while( !pObjSh && pTestObjSh )
781cdf0e10cSrcweir                     {
782cdf0e10cSrcweir                         Reference< XModel > xTestModel = pTestObjSh->GetModel();
783cdf0e10cSrcweir                         if( xTestModel == xModel )
784cdf0e10cSrcweir                             pObjSh = pTestObjSh;
785cdf0e10cSrcweir                         else
786cdf0e10cSrcweir                             pTestObjSh = SfxObjectShell::GetNext( *pTestObjSh );
787cdf0e10cSrcweir                     }
788cdf0e10cSrcweir                 }
789cdf0e10cSrcweir             }
790cdf0e10cSrcweir 
791cdf0e10cSrcweir     #ifdef USE_REGISTER_TRANSFER
792cdf0e10cSrcweir             if( pObjSh )
793cdf0e10cSrcweir             {
794cdf0e10cSrcweir                 // Medium registrieren, damit abgebrochen werden kann
795cdf0e10cSrcweir                 pObjSh->RegisterTransfer( *m_pMedium );
796cdf0e10cSrcweir 
797cdf0e10cSrcweir                 // Target-Frame uebertragen, damit auch javascript:-URLs
798cdf0e10cSrcweir                 // "geladen" werden koennen.
799cdf0e10cSrcweir                 const SfxMedium *pShMedium = pObjSh->GetMedium();
800cdf0e10cSrcweir                 if( pShMedium )
801cdf0e10cSrcweir                     m_pMedium->SetLoadTargetFrame(pShMedium->GetLoadTargetFrame());
802cdf0e10cSrcweir             }
803cdf0e10cSrcweir             else
804cdf0e10cSrcweir             {
805cdf0e10cSrcweir                 // Keine Object-Shell, aber ein Medium? Dann uebernehmen wir
806cdf0e10cSrcweir                 // zumindest den Referer.
807cdf0e10cSrcweir                 if( xModel.is() )
808cdf0e10cSrcweir                 {
809cdf0e10cSrcweir                     ::rtl::OUString sReferer( xModel->getURL() );
810cdf0e10cSrcweir                     if( sReferer.getLength() )
811cdf0e10cSrcweir                         m_pMedium->SetReferer( OUStringToString(sReferer, CHARSET_SYSTEM) );
812cdf0e10cSrcweir                 }
813cdf0e10cSrcweir             }
814cdf0e10cSrcweir     #else
815cdf0e10cSrcweir             if( pObjSh )
816cdf0e10cSrcweir             {
817cdf0e10cSrcweir                 // Target-Frame uebertragen, damit auch javascript:-URLs
818cdf0e10cSrcweir                 // "geladen" werden koennen.
819cdf0e10cSrcweir                 const SfxMedium *pShMedium = pObjSh->GetMedium();
820cdf0e10cSrcweir                 if( pShMedium )
821cdf0e10cSrcweir                     m_pMedium->SetLoadTargetFrame(pShMedium->GetLoadTargetFrame());
822cdf0e10cSrcweir             }
823cdf0e10cSrcweir 
824cdf0e10cSrcweir             if( xModel.is() )
825cdf0e10cSrcweir             {
826cdf0e10cSrcweir                 ::rtl::OUString sReferer( xModel->getURL() );
827cdf0e10cSrcweir                 if( sReferer.getLength() )
828cdf0e10cSrcweir                     m_pMedium->SetReferer( sReferer );
829cdf0e10cSrcweir             }
830cdf0e10cSrcweir     #endif
831cdf0e10cSrcweir 
832cdf0e10cSrcweir             // Downloading-Flag auf sal_True setzen. Es werden dann auch
833cdf0e10cSrcweir             // Data-Available-Links, wenn wir in den Pending-Staus gelangen.
834cdf0e10cSrcweir             m_bDownloading = sal_True;
835cdf0e10cSrcweir             m_bProdStarted = sal_False;
836cdf0e10cSrcweir 
837cdf0e10cSrcweir             // Download anstossen (Achtung: Kann auch synchron sein).
838cdf0e10cSrcweir             m_pMedium->DownLoad(STATIC_LINK(this, OClickableImageBaseModel, DownloadDoneLink));
839cdf0e10cSrcweir         }
840cdf0e10cSrcweir         else
841cdf0e10cSrcweir         {
842cdf0e10cSrcweir             if ( ::svt::GraphicAccess::isSupportedURL( rURL )  )
843cdf0e10cSrcweir                 GetImageProducer()->SetImage( rURL );
844cdf0e10cSrcweir             GetImageProducer()->startProduction();
845cdf0e10cSrcweir         }
846cdf0e10cSrcweir     }
847cdf0e10cSrcweir 
848cdf0e10cSrcweir     //------------------------------------------------------------------------------
DataAvailable()849cdf0e10cSrcweir     void OClickableImageBaseModel::DataAvailable()
850cdf0e10cSrcweir     {
851cdf0e10cSrcweir         if (!m_bProdStarted)
852cdf0e10cSrcweir             StartProduction();
853cdf0e10cSrcweir 
854cdf0e10cSrcweir         GetImageProducer()->NewDataAvailable();
855cdf0e10cSrcweir     }
856cdf0e10cSrcweir 
857cdf0e10cSrcweir     //------------------------------------------------------------------------------
DownloadDone()858cdf0e10cSrcweir     void OClickableImageBaseModel::DownloadDone()
859cdf0e10cSrcweir     {
860cdf0e10cSrcweir         DataAvailable();
861cdf0e10cSrcweir         m_bDownloading = sal_False;
862cdf0e10cSrcweir     }
863cdf0e10cSrcweir 
864cdf0e10cSrcweir     //------------------------------------------------------------------------------
IMPL_STATIC_LINK(OClickableImageBaseModel,DownloadDoneLink,void *,EMPTYARG)865cdf0e10cSrcweir     IMPL_STATIC_LINK( OClickableImageBaseModel, DownloadDoneLink, void*, EMPTYARG )
866cdf0e10cSrcweir     {
867cdf0e10cSrcweir         ::osl::MutexGuard aGuard( pThis->m_aMutex );
868cdf0e10cSrcweir         pThis->DownloadDone();
869cdf0e10cSrcweir         return 0;
870cdf0e10cSrcweir     }
871cdf0e10cSrcweir 
872cdf0e10cSrcweir     //------------------------------------------------------------------------------
IMPL_STATIC_LINK(OClickableImageBaseModel,DataAvailableLink,void *,EMPTYARG)873cdf0e10cSrcweir     IMPL_STATIC_LINK( OClickableImageBaseModel, DataAvailableLink, void*, EMPTYARG )
874cdf0e10cSrcweir     {
875cdf0e10cSrcweir         ::osl::MutexGuard aGuard( pThis->m_aMutex );
876cdf0e10cSrcweir         pThis->DataAvailable();
877cdf0e10cSrcweir         return 0;
878cdf0e10cSrcweir     }
879cdf0e10cSrcweir 
880cdf0e10cSrcweir     //------------------------------------------------------------------------------
_propertyChanged(const PropertyChangeEvent & rEvt)881cdf0e10cSrcweir     void OClickableImageBaseModel::_propertyChanged( const PropertyChangeEvent& rEvt )
882cdf0e10cSrcweir         throw( RuntimeException )
883cdf0e10cSrcweir     {
884cdf0e10cSrcweir         // Wenn eine URL gesetzt worden ist, muss die noch an den ImageProducer
885cdf0e10cSrcweir         // weitergereicht werden.
886cdf0e10cSrcweir         ::osl::MutexGuard aGuard(m_aMutex);
887cdf0e10cSrcweir         SetURL( getString(rEvt.NewValue) );
888cdf0e10cSrcweir     }
889cdf0e10cSrcweir 
890cdf0e10cSrcweir     // -----------------------------------------------------------------------------
getPropertyDefaultByHandle(sal_Int32 nHandle) const891cdf0e10cSrcweir     Any OClickableImageBaseModel::getPropertyDefaultByHandle( sal_Int32 nHandle ) const
892cdf0e10cSrcweir     {
893cdf0e10cSrcweir 	    switch (nHandle)
894cdf0e10cSrcweir 	    {
895cdf0e10cSrcweir             case PROPERTY_ID_BUTTONTYPE				: return makeAny( FormButtonType_PUSH );
896cdf0e10cSrcweir             case PROPERTY_ID_TARGET_URL				:
897cdf0e10cSrcweir             case PROPERTY_ID_TARGET_FRAME			: return makeAny( ::rtl::OUString() );
898cdf0e10cSrcweir 		    case PROPERTY_ID_DISPATCHURLINTERNAL	: return makeAny( sal_False );
899cdf0e10cSrcweir 		    default:
900cdf0e10cSrcweir 			    return OControlModel::getPropertyDefaultByHandle(nHandle);
901cdf0e10cSrcweir 	    }
902cdf0e10cSrcweir     }
903cdf0e10cSrcweir 
904cdf0e10cSrcweir     //==================================================================
905cdf0e10cSrcweir     // OImageProducerThread_Impl
906cdf0e10cSrcweir     //==================================================================
907cdf0e10cSrcweir     //------------------------------------------------------------------
cloneEvent(const EventObject * _pEvt) const908cdf0e10cSrcweir     EventObject* OImageProducerThread_Impl::cloneEvent( const EventObject* _pEvt ) const
909cdf0e10cSrcweir     {
910cdf0e10cSrcweir         return new EventObject( *_pEvt );
911cdf0e10cSrcweir     }
912cdf0e10cSrcweir 
913cdf0e10cSrcweir     //------------------------------------------------------------------
processEvent(::cppu::OComponentHelper * pCompImpl,const EventObject * pEvt,const Reference<XControl> &,sal_Bool)914cdf0e10cSrcweir     void OImageProducerThread_Impl::processEvent( ::cppu::OComponentHelper *pCompImpl,
915cdf0e10cSrcweir                                                 const EventObject* pEvt,
916cdf0e10cSrcweir                                                 const Reference<XControl>&,
917cdf0e10cSrcweir                                                 sal_Bool )
918cdf0e10cSrcweir     {
919cdf0e10cSrcweir         ((OClickableImageBaseControl *)pCompImpl)->actionPerformed_Impl( sal_True, *(MouseEvent *)pEvt );
920cdf0e10cSrcweir     }
921cdf0e10cSrcweir 
922cdf0e10cSrcweir //.........................................................................
923cdf0e10cSrcweir }   // namespace frm
924cdf0e10cSrcweir //.........................................................................
925cdf0e10cSrcweir 
926