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 .
20 // SODispatchInterceptor.cpp : Implementation of CHelpApp and DLL registration.
22 #include <sal/config.h>
28 #include "SOActiveX.h"
29 #include "SODispatchInterceptor.h"
30 #include "com_uno_helper.h"
31 #include <sal/macros.h>
34 #pragma clang diagnostic push
35 #pragma clang diagnostic ignored "-Wnon-virtual-dtor"
37 #include "so_activex.h"
39 #pragma clang diagnostic pop
42 STDMETHODIMP
SODispatchInterceptor::InterfaceSupportsErrorInfo(REFIID riid
)
44 static const IID
* arr
[] =
46 &IID_ISODispatchInterceptor
,
49 for (std::size_t i
=0;i
<SAL_N_ELEMENTS(arr
);i
++)
52 if (InlineIsEqualGUID(*arr
[i
],riid
))
54 if (::ATL::InlineIsEqualGUID(*arr
[i
],riid
))
61 STDMETHODIMP
SODispatchInterceptor::queryDispatch( IDispatch FAR
* aURL
,
62 BSTR aTargetFrameName
,
64 IDispatch FAR
* FAR
* retVal
)
66 if ( !aURL
|| !retVal
) return E_FAIL
;
68 CComVariant aTargetUrl
;
69 OLECHAR
const * sURLMemberName
= L
"Complete";
71 HRESULT hr
= aURL
->GetIDsOfNames( IID_NULL
, const_cast<OLECHAR
**>(&sURLMemberName
), 1, LOCALE_USER_DEFAULT
, &nURLID
);
72 if( !SUCCEEDED( hr
) ) return hr
;
74 hr
= CComDispatchDriver::GetProperty( aURL
, nURLID
, &aTargetUrl
);
75 if( !SUCCEEDED( hr
) ) return hr
;
77 if( aTargetUrl
.vt
!= VT_BSTR
) return E_FAIL
;
80 if( !strncmp( OLE2T( aTargetUrl
.bstrVal
), ".uno:OpenHyperlink", 18 ) )
82 CComQIPtr
< IDispatch
, &IID_IDispatch
> pIDisp( this );
99 aArgs
[0] = CComVariant( nSearchFlags
);
100 aArgs
[1] = CComVariant( aTargetFrameName
);
101 aArgs
[2] = CComVariant( aURL
);
103 hr
= ExecuteFunc( m_xSlave
, L
"queryDispatch", aArgs
, 3, &aResult
);
104 if( !SUCCEEDED( hr
) || aResult
.vt
!= VT_DISPATCH
|| aResult
.pdispVal
== nullptr )
110 *retVal
= aResult
.pdispVal
;
112 CComQIPtr
< IUnknown
, &IID_IUnknown
> pIUnk( *retVal
);
120 STDMETHODIMP
SODispatchInterceptor::queryDispatches( SAFEARRAY FAR
* aDescripts
, SAFEARRAY FAR
* FAR
* retVal
)
122 if ( !aDescripts
|| !retVal
|| SafeArrayGetDim( aDescripts
) != 1 )
127 HRESULT hr
= SafeArrayGetLBound( aDescripts
, 1, &nLB
);
128 if( !SUCCEEDED( hr
) ) return hr
;
130 hr
= SafeArrayGetUBound( aDescripts
, 1, &nUB
);
131 if( !SUCCEEDED( hr
) ) return hr
;
132 if( nUB
< nLB
) return E_FAIL
;
134 *retVal
= SafeArrayCreateVector( VT_DISPATCH
, 0, nUB
- nLB
);
136 for ( long ind
= nLB
; ind
<= nUB
; ind
++ )
138 CComPtr
<IDispatch
> pElem
;
139 SafeArrayGetElement( aDescripts
, &ind
, pElem
);
142 OLECHAR
const * pMemberNames
[3] = { L
"FeatureURL", L
"FrameName", L
"SearchFlags" };
143 CComVariant pValues
[3];
144 hr
= GetPropertiesFromIDisp( pElem
, pMemberNames
, pValues
, 3 );
145 if( !SUCCEEDED( hr
) ) return hr
;
146 if( pValues
[0].vt
!= VT_DISPATCH
|| pValues
[0].pdispVal
== nullptr
147 || pValues
[1].vt
!= VT_BSTR
|| pValues
[2].vt
!= VT_I4
)
150 CComPtr
<IDispatch
> aRes
;
151 hr
= queryDispatch( pValues
[0].pdispVal
, pValues
[1].bstrVal
, pValues
[2].lVal
, &aRes
);
152 SafeArrayPutElement( *retVal
, &ind
, aRes
);
160 STDMETHODIMP
SODispatchInterceptor::dispatch( IDispatch FAR
* aURL
, SAFEARRAY FAR
* aArgs
)
163 OLECHAR
const * pUrlName
= L
"Complete";
165 HRESULT hr
= GetPropertiesFromIDisp( aURL
, &pUrlName
, &pValue
, 1 );
166 if( !SUCCEEDED( hr
) ) return hr
;
167 if( pValue
.vt
!= VT_BSTR
|| pValue
.bstrVal
== nullptr )
171 if( !strncmp( OLE2T( pValue
.bstrVal
), ".uno:OpenHyperlink", 18 ) )
173 long nLB
= 0, nUB
= 0;
174 // long nDim = SafeArrayGetDim( aArgs );
176 hr
= SafeArrayGetLBound( aArgs
, 1, &nLB
);
177 if( !SUCCEEDED( hr
) ) return hr
;
179 hr
= SafeArrayGetUBound( aArgs
, 1, &nUB
);
180 if( !SUCCEEDED( hr
) ) return hr
;
181 if( nUB
< nLB
) return E_FAIL
;
183 for ( long ind
= nLB
; ind
<= nUB
; ind
++ )
185 CComVariant pVarElem
;
186 SafeArrayGetElement( aArgs
, &ind
, &pVarElem
);
187 if( pVarElem
.vt
== VT_DISPATCH
&& pVarElem
.pdispVal
!= nullptr )
189 OLECHAR
const * pMemberNames
[2] = { L
"Name", L
"Value" };
190 CComVariant pValues
[2];
191 hr
= GetPropertiesFromIDisp( pVarElem
.pdispVal
, pMemberNames
, pValues
, 2 );
192 if( !SUCCEEDED( hr
) ) return hr
;
194 if( pValues
[0].vt
== VT_BSTR
&& pValues
[1].vt
== VT_BSTR
)
196 if( !strncmp( OLE2T( pValues
[0].bstrVal
), "URL", 3 ) )
198 EnterCriticalSection( &mMutex
);
199 if( m_xParentControl
)
201 // call GetUrl to the browser instance
202 m_xParentControl
->GetURL( pValues
[1].bstrVal
, L
"_self" );
204 LeaveCriticalSection( &mMutex
);
216 STDMETHODIMP
SODispatchInterceptor::addStatusListener( IDispatch FAR
* /*xControl*/, IDispatch FAR
* /*aURL*/)
222 STDMETHODIMP
SODispatchInterceptor::removeStatusListener( IDispatch FAR
* /*xControl*/, IDispatch FAR
* /*aURL*/)
228 STDMETHODIMP
SODispatchInterceptor::getInterceptedURLs( SAFEARRAY FAR
* FAR
* pVal
)
230 *pVal
= SafeArrayCreateVector( VT_BSTR
, 0, 3 );
236 CComBSTR
aPattern( OLESTR( "ftp://*" ) );
237 SafeArrayPutElement( *pVal
, &ix
, aPattern
);
240 aPattern
= CComBSTR( OLESTR( "http://*" ) );
241 SafeArrayPutElement( *pVal
, &ix
, aPattern
);
244 aPattern
= CComBSTR( OLESTR( "file://*" ) );
245 SafeArrayPutElement( *pVal
, &ix
, aPattern
);
251 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */