diff options
author | Ivo Hinkelmann <ihi@openoffice.org> | 2011-04-01 09:34:55 +0200 |
---|---|---|
committer | Ivo Hinkelmann <ihi@openoffice.org> | 2011-04-01 09:34:55 +0200 |
commit | 605ebc1399566686085c98c5698903af31b97607 (patch) | |
tree | 87a9cb9cb3299ba6f3009f055d49fdf4a7cdad68 | |
parent | 6b4d26b6823ff962b5aaca278b996f99313ddb93 (diff) | |
parent | fc6b149ea291a21960448e13c70c6a981924d417 (diff) |
CWS-TOOLING: integrate CWS calcvba
Notes
split repo tag: calc_ooo/DEV300_m106
-rw-r--r-- | sc/source/ui/docshell/docsh.cxx | 65 | ||||
-rw-r--r-- | sc/source/ui/unoobj/docuno.cxx | 13 | ||||
-rw-r--r-- | sc/source/ui/vba/excelvbahelper.cxx | 5 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaapplication.cxx | 120 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaapplication.hxx | 12 | ||||
-rwxr-xr-x | sc/source/ui/vba/vbaeventshelper.cxx | 590 | ||||
-rwxr-xr-x | sc/source/ui/vba/vbaeventshelper.hxx | 17 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaformat.cxx | 4 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaformat.hxx | 2 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaglobals.cxx | 6 | ||||
-rwxr-xr-x | sc/source/ui/vba/vbarange.cxx | 22 | ||||
-rw-r--r-- | sc/source/ui/vba/vbawindow.cxx | 198 | ||||
-rw-r--r-- | sc/source/ui/vba/vbawindow.hxx | 26 | ||||
-rw-r--r-- | sc/source/ui/vba/vbawindows.cxx | 8 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaworkbook.cxx | 11 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaworkbooks.cxx | 27 | ||||
-rw-r--r-- | sc/source/ui/vba/vbaworksheets.cxx | 27 | ||||
-rw-r--r-- | sc/util/makefile.mk | 1 |
18 files changed, 624 insertions, 530 deletions
diff --git a/sc/source/ui/docshell/docsh.cxx b/sc/source/ui/docshell/docsh.cxx index 4d989158952b..fc854e63ecbb 100644 --- a/sc/source/ui/docshell/docsh.cxx +++ b/sc/source/ui/docshell/docsh.cxx @@ -499,74 +499,23 @@ sal_Bool __EXPORT ScDocShell::Load( SfxMedium& rMedium ) void __EXPORT ScDocShell::Notify( SfxBroadcaster&, const SfxHint& rHint ) { - uno::Reference< script::vba::XVBAEventProcessor > xVbaEvents = aDocument.GetVbaEventProcessor(); - if ( xVbaEvents.is() ) try + if (rHint.ISA(ScTablesHint) ) { - using namespace ::com::sun::star::script::vba::VBAEventId; - if (rHint.ISA(ScTablesHint) ) + const ScTablesHint& rScHint = static_cast< const ScTablesHint& >( rHint ); + if (rScHint.GetId() == SC_TAB_INSERTED) { - const ScTablesHint& rScHint = static_cast< const ScTablesHint& >( rHint ); - if (rScHint.GetId() == SC_TAB_INSERTED) + uno::Reference< script::vba::XVBAEventProcessor > xVbaEvents = aDocument.GetVbaEventProcessor(); + if ( xVbaEvents.is() ) try { uno::Sequence< uno::Any > aArgs( 1 ); aArgs[0] <<= rScHint.GetTab1(); - xVbaEvents->processVbaEvent( WORKBOOK_NEWSHEET, aArgs ); + xVbaEvents->processVbaEvent( script::vba::VBAEventId::WORKBOOK_NEWSHEET, aArgs ); } - } - else if ( rHint.ISA( SfxEventHint ) ) - { - sal_uLong nEventId = static_cast< const SfxEventHint& >( rHint ).GetEventId(); - switch ( nEventId ) + catch( uno::Exception& ) { - case SFX_EVENT_ACTIVATEDOC: - { - uno::Sequence< uno::Any > aArgs; - xVbaEvents->processVbaEvent( WORKBOOK_ACTIVATE, aArgs ); - } - break; - case SFX_EVENT_DEACTIVATEDOC: - { - uno::Sequence< uno::Any > aArgs; - xVbaEvents->processVbaEvent( WORKBOOK_DEACTIVATE, aArgs ); - } - break; - case SFX_EVENT_OPENDOC: - { - uno::Sequence< uno::Any > aArgs; - xVbaEvents->processVbaEvent( WORKBOOK_OPEN, aArgs ); - } - break; - case SFX_EVENT_SAVEDOCDONE: - case SFX_EVENT_SAVEASDOCDONE: - case SFX_EVENT_SAVETODOCDONE: - { - uno::Sequence< uno::Any > aArgs( 1 ); - aArgs[ 0 ] <<= true; - xVbaEvents->processVbaEvent( WORKBOOK_AFTERSAVE, aArgs ); - } - break; - case SFX_EVENT_SAVEASDOCFAILED: - case SFX_EVENT_SAVEDOCFAILED: - case SFX_EVENT_SAVETODOCFAILED: - { - uno::Sequence< uno::Any > aArgs( 1 ); - aArgs[ 0 ] <<= false; - xVbaEvents->processVbaEvent( WORKBOOK_AFTERSAVE, aArgs ); - } - break; - case SFX_EVENT_CLOSEDOC: - { - // #163655# prevent event processing after model is disposed - aDocument.SetVbaEventProcessor( uno::Reference< script::vba::XVBAEventProcessor >() ); - uno::Reference< lang::XEventListener >( xVbaEvents, uno::UNO_QUERY_THROW )->disposing( lang::EventObject() ); - } - break; } } } - catch( uno::Exception& ) - { - } if (rHint.ISA(SfxSimpleHint)) // ohne Parameter { diff --git a/sc/source/ui/unoobj/docuno.cxx b/sc/source/ui/unoobj/docuno.cxx index d3ab32c66e81..daed78e09e82 100644 --- a/sc/source/ui/unoobj/docuno.cxx +++ b/sc/source/ui/unoobj/docuno.cxx @@ -104,6 +104,9 @@ using namespace com::sun::star; +// #i111553# provides the name of the VBA constant for this document type (e.g. 'ThisExcelDoc' for Calc) +#define SC_UNO_VBAGLOBNAME "VBAGlobalConstantName" + //------------------------------------------------------------------------ // alles ohne Which-ID, Map nur fuer PropertySetInfo @@ -118,6 +121,7 @@ const SfxItemPropertyMapEntry* lcl_GetDocOptPropertyMap() {MAP_CHAR_LEN(SC_UNO_AUTOCONTFOC), 0, &getBooleanCppuType(), 0, 0}, {MAP_CHAR_LEN(SC_UNO_BASICLIBRARIES), 0, &getCppuType((uno::Reference< script::XLibraryContainer >*)0), beans::PropertyAttribute::READONLY, 0}, {MAP_CHAR_LEN(SC_UNO_DIALOGLIBRARIES), 0, &getCppuType((uno::Reference< script::XLibraryContainer >*)0), beans::PropertyAttribute::READONLY, 0}, + {MAP_CHAR_LEN(SC_UNO_VBAGLOBNAME), 0, &getCppuType(static_cast< const rtl::OUString * >(0)), beans::PropertyAttribute::READONLY, 0}, {MAP_CHAR_LEN(SC_UNO_CALCASSHOWN), PROP_UNO_CALCASSHOWN, &getBooleanCppuType(), 0, 0}, {MAP_CHAR_LEN(SC_UNONAME_CLOCAL), 0, &getCppuType((lang::Locale*)0), 0, 0}, {MAP_CHAR_LEN(SC_UNO_CJK_CLOCAL), 0, &getCppuType((lang::Locale*)0), 0, 0}, @@ -1908,6 +1912,15 @@ uno::Any SAL_CALL ScModelObj::getPropertyValue( const rtl::OUString& aPropertyNa { aRet <<= pDocShell->GetDialogContainer(); } + else if ( aString.EqualsAscii( SC_UNO_VBAGLOBNAME ) ) + { + /* #i111553# This property provides the name of the constant that + will be used to store this model in the global Basic manager. + That constant will be equivelant to 'ThisComponent' but for + each application, so e.g. a 'ThisExcelDoc' and a 'ThisWordDoc' + constant can co-exist, as required by VBA. */ + aRet <<= rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ThisExcelDoc" ) ); + } else if ( aString.EqualsAscii( SC_UNO_RUNTIMEUID ) ) { aRet <<= getRuntimeUID(); diff --git a/sc/source/ui/vba/excelvbahelper.cxx b/sc/source/ui/vba/excelvbahelper.cxx index 04d88935acfc..50623610b5b3 100644 --- a/sc/source/ui/vba/excelvbahelper.cxx +++ b/sc/source/ui/vba/excelvbahelper.cxx @@ -247,7 +247,7 @@ getViewFrame( const uno::Reference< frame::XModel >& xModel ) return NULL; } -uno::Reference< vba::XHelperInterface > +uno::Reference< XHelperInterface > getUnoSheetModuleObj( const uno::Reference< sheet::XSpreadsheet >& xSheet ) throw ( uno::RuntimeException ) { uno::Reference< beans::XPropertySet > xProps( xSheet, uno::UNO_QUERY_THROW ); @@ -258,8 +258,7 @@ getUnoSheetModuleObj( const uno::Reference< sheet::XSpreadsheet >& xSheet ) thro // are *NO* special document module objects ( of course being able to switch between vba/non vba mode at // the document in the future could fix this, especially IF the switching of the vba mode takes care to // create the special document module objects if they don't exist. - uno::Reference< XHelperInterface > xParent( ov::getUnoDocModule( sCodeName, GetDocShellFromRange( xSheet ) ), uno::UNO_QUERY ); - return xParent; + return getUnoDocModule( sCodeName, GetDocShellFromRange( xSheet ) ); } uno::Reference< XHelperInterface > diff --git a/sc/source/ui/vba/vbaapplication.cxx b/sc/source/ui/vba/vbaapplication.cxx index 290b34a949ca..fa278e527d91 100644 --- a/sc/source/ui/vba/vbaapplication.cxx +++ b/sc/source/ui/vba/vbaapplication.cxx @@ -40,6 +40,7 @@ #include <ooo/vba/excel/XlMousePointer.hpp> #include <com/sun/star/sheet/XNamedRanges.hpp> #include <com/sun/star/sheet/XCellRangeAddressable.hpp> +#include <ooo/vba/XExecutableDialog.hpp> #include "vbaapplication.hxx" #include "vbaworkbooks.hxx" @@ -98,17 +99,6 @@ using namespace ::com::sun::star; uno::Any sbxToUnoValue( SbxVariable* pVar ); -class ActiveWorkbook : public ScVbaWorkbook -{ -protected: - virtual uno::Reference< frame::XModel > getModel() - { - return getCurrentExcelDoc(mxContext); - } -public: - ActiveWorkbook( const uno::Reference< XHelperInterface >& xParent, const uno::Reference< uno::XComponentContext >& xContext) : ScVbaWorkbook( xParent, xContext ){} -}; - // ============================================================================ /** Global application settings shared by all open workbooks. */ @@ -215,47 +205,15 @@ ScVbaApplication::hasProperty( const ::rtl::OUString& Name ) throw(uno::RuntimeE uno::Reference< excel::XWorkbook > ScVbaApplication::getActiveWorkbook() throw (uno::RuntimeException) { - uno::Reference< excel::XWorkbook > xWrkbk; - ScDocShell* pShell = excel::getDocShell( getCurrentExcelDoc( mxContext ) ); - if ( pShell ) - { - String aName; - if ( pShell->GetDocument() ) - { - aName = pShell->GetDocument()->GetCodeName(); - xWrkbk.set( getUnoDocModule( aName, pShell ), uno::UNO_QUERY ); - // fallback ( e.g. it's possible a new document was created via the api ) - // in that case the document will not have the appropriate Document Modules - // #TODO #FIXME ( needs to be fixes as part of providing support for an overall document - // vba mode etc. ) - if ( !xWrkbk.is() ) - return new ActiveWorkbook( this, mxContext ); - } - } - return xWrkbk; + // will throw if active document is not in VBA compatibility mode (no object for codename) + return uno::Reference< excel::XWorkbook >( getVBADocument( getCurrentExcelDoc( mxContext ) ), uno::UNO_QUERY_THROW ); } uno::Reference< excel::XWorkbook > SAL_CALL ScVbaApplication::getThisWorkbook() throw (uno::RuntimeException) { - uno::Reference< excel::XWorkbook > xWrkbk; - ScDocShell* pShell = excel::getDocShell( getThisExcelDoc( mxContext ) ); - if ( pShell ) - { - String aName; - if ( pShell->GetDocument() ) - { - aName = pShell->GetDocument()->GetCodeName(); - xWrkbk.set( getUnoDocModule( aName, pShell ), uno::UNO_QUERY ); - // fallback ( e.g. it's possible a new document was created via the api ) - // in that case the document will not have the appropriate Document Modules - // #TODO #FIXME ( needs to be fixes as part of providing support for an overall document - // vba mode etc. ) - if ( !xWrkbk.is() ) - return new ActiveWorkbook( this, mxContext ); - } - } - return xWrkbk; + // should never throw as this model is in VBA compatibility mode + return uno::Reference< excel::XWorkbook >( getVBADocument( getThisExcelDoc( mxContext ) ), uno::UNO_QUERY_THROW ); } uno::Reference< XAssistant > SAL_CALL @@ -343,17 +301,8 @@ ScVbaApplication::Workbooks( const uno::Any& aIndex ) throw (uno::RuntimeExcepti uno::Any SAL_CALL ScVbaApplication::Worksheets( const uno::Any& aIndex ) throw (uno::RuntimeException) { - uno::Reference< excel::XWorkbook > xWorkbook( getActiveWorkbook(), uno::UNO_QUERY ); - uno::Any result; - if ( xWorkbook.is() ) - result = xWorkbook->Worksheets( aIndex ); - - else - // Fixme - check if this is reasonable/desired behavior - throw uno::RuntimeException( rtl::OUString::createFromAscii( - "No ActiveWorkBook available" ), uno::Reference< uno::XInterface >() ); - - return result; + uno::Reference< excel::XWorkbook > xWorkbook( getActiveWorkbook(), uno::UNO_SET_THROW ); + return xWorkbook->Worksheets( aIndex ); } uno::Any SAL_CALL @@ -384,10 +333,10 @@ ScVbaApplication::Dialogs( const uno::Any &aIndex ) throw (uno::RuntimeException uno::Reference< excel::XWindow > SAL_CALL ScVbaApplication::getActiveWindow() throw (uno::RuntimeException) { - // #FIXME sofar can't determine Parent uno::Reference< frame::XModel > xModel = getCurrentDocument(); - ScVbaWindow* pWin = new ScVbaWindow( uno::Reference< XHelperInterface >(), mxContext, xModel ); - uno::Reference< excel::XWindow > xWin( pWin ); + uno::Reference< frame::XController > xController( xModel->getCurrentController(), uno::UNO_SET_THROW ); + uno::Reference< XHelperInterface > xParent( getActiveWorkbook(), uno::UNO_QUERY_THROW ); + uno::Reference< excel::XWindow > xWin( new ScVbaWindow( xParent, mxContext, xModel, xController ) ); return xWin; } @@ -792,37 +741,36 @@ rtl::OUString ScVbaApplication::getOfficePath( const rtl::OUString& _sPathType ) } return sRetPath; } + void SAL_CALL -ScVbaApplication::setDefaultFilePath( const ::rtl::OUString& DefaultFilePath ) throw (script::BasicErrorException, uno::RuntimeException) +ScVbaApplication::setDefaultFilePath( const ::rtl::OUString& DefaultFilePath ) throw (uno::RuntimeException) { uno::Reference< beans::XPropertySet > xProps = lcl_getPathSettingsService( mxContext ); rtl::OUString aURL; osl::FileBase::getFileURLFromSystemPath( DefaultFilePath, aURL ); - xProps->setPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Work")), uno::makeAny( aURL ) ); - - + xProps->setPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Work")), uno::Any( aURL ) ); } ::rtl::OUString SAL_CALL -ScVbaApplication::getDefaultFilePath( ) throw (script::BasicErrorException, uno::RuntimeException) +ScVbaApplication::getDefaultFilePath() throw (uno::RuntimeException) { return getOfficePath( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Work"))); } ::rtl::OUString SAL_CALL -ScVbaApplication::LibraryPath( ) throw (script::BasicErrorException, uno::RuntimeException) +ScVbaApplication::getLibraryPath() throw (uno::RuntimeException) { return getOfficePath( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Basic"))); } ::rtl::OUString SAL_CALL -ScVbaApplication::TemplatesPath( ) throw (script::BasicErrorException, uno::RuntimeException) +ScVbaApplication::getTemplatesPath() throw (uno::RuntimeException) { return getOfficePath( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM("Template"))); } ::rtl::OUString SAL_CALL -ScVbaApplication::PathSeparator( ) throw (script::BasicErrorException, uno::RuntimeException) +ScVbaApplication::getPathSeparator() throw (uno::RuntimeException) { static rtl::OUString sPathSep( RTL_CONSTASCII_USTRINGPARAM( FILE_PATH_SEPERATOR ) ); return sPathSep; @@ -1174,6 +1122,40 @@ ScVbaApplication::Caller( const uno::Any& /*aIndex*/ ) throw ( uno::RuntimeExcep return aRet; } +uno::Any SAL_CALL ScVbaApplication::GetOpenFilename( + const uno::Any& rFileFilter, const uno::Any& rFilterIndex, const uno::Any& rTitle, + const uno::Any& rButtonText, const uno::Any& rMultiSelect ) throw (uno::RuntimeException) +{ + uno::Sequence< uno::Any > aArgs( 6 ); + aArgs[ 0 ] <<= getThisExcelDoc( mxContext ); + aArgs[ 1 ] = rFileFilter; + aArgs[ 2 ] = rFilterIndex; + aArgs[ 3 ] = rTitle; + aArgs[ 4 ] = rButtonText; + aArgs[ 5 ] = rMultiSelect; + uno::Reference< lang::XMultiComponentFactory > xFactory( mxContext->getServiceManager(), uno::UNO_SET_THROW ); + uno::Reference< XExecutableDialog > xFilePicker( xFactory->createInstanceWithArgumentsAndContext( + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ooo.vba.OpenFilePicker" ) ), aArgs, mxContext ), uno::UNO_QUERY_THROW ); + return xFilePicker->execute(); +} + +uno::Any SAL_CALL ScVbaApplication::GetSaveAsFilename( + const uno::Any& rInitialFileName, const uno::Any& rFileFilter, const uno::Any& rFilterIndex, + const uno::Any& rTitle, const uno::Any& rButtonText ) throw (uno::RuntimeException) +{ + uno::Sequence< uno::Any > aArgs( 6 ); + aArgs[ 0 ] <<= getThisExcelDoc( mxContext ); + aArgs[ 1 ] = rInitialFileName; + aArgs[ 2 ] = rFileFilter; + aArgs[ 3 ] = rFilterIndex; + aArgs[ 4 ] = rTitle; + aArgs[ 5 ] = rButtonText; + uno::Reference< lang::XMultiComponentFactory > xFactory( mxContext->getServiceManager(), uno::UNO_SET_THROW ); + uno::Reference< XExecutableDialog > xFilePicker( xFactory->createInstanceWithArgumentsAndContext( + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ooo.vba.SaveAsFilePicker" ) ), aArgs, mxContext ), uno::UNO_QUERY_THROW ); + return xFilePicker->execute(); +} + uno::Reference< frame::XModel > ScVbaApplication::getCurrentDocument() throw (css::uno::RuntimeException) { diff --git a/sc/source/ui/vba/vbaapplication.hxx b/sc/source/ui/vba/vbaapplication.hxx index bb696c967a37..b09fb66a8f91 100644 --- a/sc/source/ui/vba/vbaapplication.hxx +++ b/sc/source/ui/vba/vbaapplication.hxx @@ -73,11 +73,11 @@ public: virtual sal_Bool SAL_CALL hasProperty(const rtl::OUString& Name) throw(css::uno::RuntimeException); // XApplication - virtual ::rtl::OUString SAL_CALL PathSeparator( ) throw (css::script::BasicErrorException, css::uno::RuntimeException); - virtual void SAL_CALL setDefaultFilePath( const ::rtl::OUString& DefaultFilePath ) throw (css::script::BasicErrorException, css::uno::RuntimeException); - virtual ::rtl::OUString SAL_CALL getDefaultFilePath( ) throw (css::script::BasicErrorException, css::uno::RuntimeException); - virtual ::rtl::OUString SAL_CALL LibraryPath( ) throw (css::script::BasicErrorException, css::uno::RuntimeException); - virtual ::rtl::OUString SAL_CALL TemplatesPath( ) throw (css::script::BasicErrorException, css::uno::RuntimeException); + virtual void SAL_CALL setDefaultFilePath( const ::rtl::OUString& DefaultFilePath ) throw (css::uno::RuntimeException); + virtual ::rtl::OUString SAL_CALL getDefaultFilePath() throw (css::uno::RuntimeException); + virtual ::rtl::OUString SAL_CALL getPathSeparator() throw (css::uno::RuntimeException); + virtual ::rtl::OUString SAL_CALL getLibraryPath() throw (css::uno::RuntimeException); + virtual ::rtl::OUString SAL_CALL getTemplatesPath() throw (css::uno::RuntimeException); virtual rtl::OUString SAL_CALL getName() throw (css::uno::RuntimeException); virtual sal_Bool SAL_CALL getDisplayAlerts() throw (css::uno::RuntimeException); @@ -120,6 +120,8 @@ public: virtual void SAL_CALL Volatile( const css::uno::Any& Volatile ) throw (css::uno::RuntimeException ); virtual void SAL_CALL DoEvents() throw (css::uno::RuntimeException); virtual css::uno::Any SAL_CALL Caller( const css::uno::Any& aIndex ) throw (css::uno::RuntimeException); + virtual css::uno::Any SAL_CALL GetOpenFilename( const css::uno::Any& rFileFilter, const css::uno::Any& rFilterIndex, const css::uno::Any& rTitle, const css::uno::Any& rButtonText, const css::uno::Any& rMultiSelect ) throw (css::uno::RuntimeException); + virtual css::uno::Any SAL_CALL GetSaveAsFilename( const css::uno::Any& rInitialFileName, const css::uno::Any& rFileFilter, const css::uno::Any& rFilterIndex, const css::uno::Any& rTitle, const css::uno::Any& rButtonText ) throw (css::uno::RuntimeException); // XHelperInterface virtual rtl::OUString& getServiceImplName(); virtual css::uno::Sequence<rtl::OUString> getServiceNames(); diff --git a/sc/source/ui/vba/vbaeventshelper.cxx b/sc/source/ui/vba/vbaeventshelper.cxx index 6ea807a16eae..e96b2d001e75 100755 --- a/sc/source/ui/vba/vbaeventshelper.cxx +++ b/sc/source/ui/vba/vbaeventshelper.cxx @@ -27,21 +27,22 @@ #include "vbaeventshelper.hxx" +#include <com/sun/star/awt/XTopWindow.hpp> +#include <com/sun/star/awt/XTopWindowListener.hpp> #include <com/sun/star/awt/XWindowListener.hpp> #include <com/sun/star/frame/XBorderResizeListener.hpp> #include <com/sun/star/frame/XControllerBorder.hpp> +#include <com/sun/star/script/ModuleType.hpp> #include <com/sun/star/script/vba/VBAEventId.hpp> #include <com/sun/star/sheet/XCellRangeAddressable.hpp> #include <com/sun/star/sheet/XSheetCellRangeContainer.hpp> #include <com/sun/star/table/XCellRange.hpp> #include <com/sun/star/util/XChangesListener.hpp> #include <com/sun/star/util/XChangesNotifier.hpp> -#include <com/sun/star/util/XCloseListener.hpp> - -#include <ooo/vba/excel/XApplication.hpp> #include <cppuhelper/implbase4.hxx> #include <toolkit/unohlp.hxx> +#include <unotools/eventcfg.hxx> #include <vbahelper/helperdecl.hxx> #include <vcl/svapp.hxx> #include <vcl/window.hxx> @@ -54,6 +55,8 @@ using namespace ::com::sun::star; using namespace ::com::sun::star::script::vba::VBAEventId; using namespace ::ooo::vba; +using ::rtl::OUString; + // ============================================================================ namespace { @@ -65,9 +68,13 @@ SCTAB lclGetTabFromArgs( const uno::Sequence< uno::Any >& rArgs, sal_Int32 nInde VbaEventsHelperBase::checkArgument( rArgs, nIndex ); // first try to extract a sheet index - SCTAB nTab = -1; + sal_Int32 nTab = -1; if( rArgs[ nIndex ] >>= nTab ) - return nTab; + { + if( (nTab < 0) || (nTab > MAXTAB) ) + throw lang::IllegalArgumentException(); + return static_cast< SCTAB >( nTab ); + } // try VBA Range object uno::Reference< excel::XRange > xVbaRange = getXSomethingFromArgs< excel::XRange >( rArgs, nIndex ); @@ -97,231 +104,271 @@ SCTAB lclGetTabFromArgs( const uno::Sequence< uno::Any >& rArgs, sal_Int32 nInde throw lang::IllegalArgumentException(); } +/** Returns the AWT container window of the passed controller. */ +uno::Reference< awt::XWindow > lclGetWindowForController( const uno::Reference< frame::XController >& rxController ) +{ + if( rxController.is() ) try + { + uno::Reference< frame::XFrame > xFrame( rxController->getFrame(), uno::UNO_SET_THROW ); + return xFrame->getContainerWindow(); + } + catch( uno::Exception& ) + { + } + return 0; +} + } // namespace // ============================================================================ -typedef ::cppu::WeakImplHelper4< - awt::XWindowListener, util::XCloseListener, frame::XBorderResizeListener, util::XChangesListener > ScVbaEventsListener_BASE; +typedef ::cppu::WeakImplHelper4< awt::XTopWindowListener, awt::XWindowListener, frame::XBorderResizeListener, util::XChangesListener > ScVbaEventListener_BASE; // This class is to process Workbook window related event -class ScVbaEventsListener : public ScVbaEventsListener_BASE +class ScVbaEventListener : public ScVbaEventListener_BASE { public : - ScVbaEventsListener( ScVbaEventsHelper& rVbaEvents, const uno::Reference< frame::XModel >& rxModel, ScDocShell* pDocShell ); - virtual ~ScVbaEventsListener(); - - void startListening(); - void stopListening(); + ScVbaEventListener( ScVbaEventsHelper& rVbaEvents, const uno::Reference< frame::XModel >& rxModel, ScDocShell* pDocShell ); + virtual ~ScVbaEventListener(); + + /** Starts listening to the passed document controller. */ + void startControllerListening( const uno::Reference< frame::XController >& rxController ); + /** Stops listening to the passed document controller. */ + void stopControllerListening( const uno::Reference< frame::XController >& rxController ); + + // XTopWindowListener + virtual void SAL_CALL windowOpened( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowClosing( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowClosed( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowMinimized( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowNormalized( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowActivated( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowDeactivated( const lang::EventObject& rEvent ) throw (uno::RuntimeException); // XWindowListener - virtual void SAL_CALL windowResized( const awt::WindowEvent& aEvent ) throw (uno::RuntimeException); - virtual void SAL_CALL windowMoved( const awt::WindowEvent& aEvent ) throw (uno::RuntimeException); - virtual void SAL_CALL windowShown( const lang::EventObject& aEvent ) throw (uno::RuntimeException); - virtual void SAL_CALL windowHidden( const lang::EventObject& aEvent ) throw (uno::RuntimeException); - virtual void SAL_CALL disposing( const lang::EventObject& aEvent ) throw (uno::RuntimeException); - - // XCloseListener - virtual void SAL_CALL queryClosing( const lang::EventObject& Source, ::sal_Bool GetsOwnership ) throw (util::CloseVetoException, uno::RuntimeException); - virtual void SAL_CALL notifyClosing( const lang::EventObject& Source ) throw (uno::RuntimeException); + virtual void SAL_CALL windowResized( const awt::WindowEvent& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowMoved( const awt::WindowEvent& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowShown( const lang::EventObject& rEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL windowHidden( const lang::EventObject& rEvent ) throw (uno::RuntimeException); // XBorderResizeListener - virtual void SAL_CALL borderWidthsChanged( const uno::Reference< uno::XInterface >& aObject, const frame::BorderWidths& aNewSize ) throw (uno::RuntimeException); + virtual void SAL_CALL borderWidthsChanged( const uno::Reference< uno::XInterface >& rSource, const frame::BorderWidths& aNewSize ) throw (uno::RuntimeException); // XChangesListener - virtual void SAL_CALL changesOccurred( const util::ChangesEvent& aEvent ) throw (uno::RuntimeException); + virtual void SAL_CALL changesOccurred( const util::ChangesEvent& rEvent ) throw (uno::RuntimeException); + + // XEventListener + virtual void SAL_CALL disposing( const lang::EventObject& rEvent ) throw (uno::RuntimeException); private: - uno::Reference< frame::XFrame > getFrame(); - uno::Reference< awt::XWindow > getContainerWindow(); - bool isMouseReleased(); - DECL_LINK( fireResizeMacro, void* ); + /** Starts listening to the document model. */ + void startModelListening(); + /** Stops listening to the document model. */ + void stopModelListening(); + + /** Returns the controller for the passed VCL window. */ + uno::Reference< frame::XController > getControllerForWindow( Window* pWindow ) const; + + /** Calls the Workbook_Window[Activate|Deactivate] event handler. */ + void processWindowActivateEvent( Window* pWindow, bool bActivate ); + /** Posts a Workbook_WindowResize user event. */ + void postWindowResizeEvent( Window* pWindow ); + /** Callback link for Application::PostUserEvent(). */ + DECL_LINK( processWindowResizeEvent, Window* ); private: - ::osl::Mutex maMutex; - ScVbaEventsHelper& mrVbaEvents; + typedef ::std::map< Window*, uno::Reference< frame::XController > > WindowControllerMap; + + ::osl::Mutex maMutex; + ScVbaEventsHelper& mrVbaEvents; uno::Reference< frame::XModel > mxModel; - ScDocShell* mpDocShell; - bool mbWindowResized; - bool mbBorderChanged; - bool mbDisposed; + ScDocShell* mpDocShell; + WindowControllerMap maControllers; /// Maps VCL top windows to their controllers. + Window* mpActiveWindow; /// Currently activated window, to prevent multiple (de)activation. + bool mbWindowResized; /// True = window resize system event processed. + bool mbBorderChanged; /// True = borders changed system event processed. + bool mbDisposed; }; // ---------------------------------------------------------------------------- -ScVbaEventsListener::ScVbaEventsListener( ScVbaEventsHelper& rVbaEvents, const uno::Reference< frame::XModel >& rxModel, ScDocShell* pDocShell ) : +ScVbaEventListener::ScVbaEventListener( ScVbaEventsHelper& rVbaEvents, const uno::Reference< frame::XModel >& rxModel, ScDocShell* pDocShell ) : mrVbaEvents( rVbaEvents ), mxModel( rxModel ), mpDocShell( pDocShell ), + mpActiveWindow( 0 ), mbWindowResized( false ), mbBorderChanged( false ), mbDisposed( !rxModel.is() ) { - OSL_TRACE( "ScVbaEventsListener::ScVbaEventsListener( 0x%x ) - ctor ", this ); + if( !mxModel.is() ) + return; + + startModelListening(); + try + { + uno::Reference< frame::XController > xController( mxModel->getCurrentController(), uno::UNO_QUERY_THROW ); + startControllerListening( xController ); + } + catch( uno::Exception& ) + { + } } -ScVbaEventsListener::~ScVbaEventsListener() +ScVbaEventListener::~ScVbaEventListener() { - OSL_TRACE( "ScVbaEventsListener::~ScVbaEventsListener( 0x%x ) - dtor ", this ); - stopListening(); } -void ScVbaEventsListener::startListening() +void ScVbaEventListener::startControllerListening( const uno::Reference< frame::XController >& rxController ) { - if( !mbDisposed ) + ::osl::MutexGuard aGuard( maMutex ); + + uno::Reference< awt::XWindow > xWindow = lclGetWindowForController( rxController ); + if( xWindow.is() ) + try { xWindow->addWindowListener( this ); } catch( uno::Exception& ) {} + + uno::Reference< awt::XTopWindow > xTopWindow( xWindow, uno::UNO_QUERY ); + if( xTopWindow.is() ) + try { xTopWindow->addTopWindowListener( this ); } catch( uno::Exception& ) {} + + uno::Reference< frame::XControllerBorder > xControllerBorder( rxController, uno::UNO_QUERY ); + if( xControllerBorder.is() ) + try { xControllerBorder->addBorderResizeListener( this ); } catch( uno::Exception& ) {} + + if( Window* pWindow = VCLUnoHelper::GetWindow( xWindow ) ) + maControllers[ pWindow ] = rxController; +} + +void ScVbaEventListener::stopControllerListening( const uno::Reference< frame::XController >& rxController ) +{ + ::osl::MutexGuard aGuard( maMutex ); + + uno::Reference< awt::XWindow > xWindow = lclGetWindowForController( rxController ); + if( xWindow.is() ) + try { xWindow->removeWindowListener( this ); } catch( uno::Exception& ) {} + + uno::Reference< awt::XTopWindow > xTopWindow( xWindow, uno::UNO_QUERY ); + if( xTopWindow.is() ) + try { xTopWindow->removeTopWindowListener( this ); } catch( uno::Exception& ) {} + + uno::Reference< frame::XControllerBorder > xControllerBorder( rxController, uno::UNO_QUERY ); + if( xControllerBorder.is() ) + try { xControllerBorder->removeBorderResizeListener( this ); } catch( uno::Exception& ) {} + + if( Window* pWindow = VCLUnoHelper::GetWindow( xWindow ) ) { - // add window listener - try - { - uno::Reference< awt::XWindow > xWindow( getContainerWindow(), uno::UNO_QUERY_THROW ); - xWindow->addWindowListener( this ); - } - catch( uno::Exception& ) - { - } - // add close listener - try - { - uno::Reference< util::XCloseBroadcaster > xCloseBroadcaster( mxModel, uno::UNO_QUERY_THROW ); - xCloseBroadcaster->addCloseListener( this ); - } - catch( uno::Exception& ) - { - } - // add Border resize listener - try - { - uno::Reference< frame::XControllerBorder > xControllerBorder( mxModel->getCurrentController(), uno::UNO_QUERY_THROW ); - xControllerBorder->addBorderResizeListener( this ); - } - catch( uno::Exception& ) - { - } - // add content change listener - try - { - uno::Reference< util::XChangesNotifier > xChangesNotifier( mxModel, uno::UNO_QUERY_THROW ); - xChangesNotifier->addChangesListener( this ); - } - catch( uno::Exception& ) - { - } + maControllers.erase( pWindow ); + if( pWindow == mpActiveWindow ) + mpActiveWindow = 0; } } -void ScVbaEventsListener::stopListening() +void SAL_CALL ScVbaEventListener::windowOpened( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) +{ +} + +void SAL_CALL ScVbaEventListener::windowClosing( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) { +} + +void SAL_CALL ScVbaEventListener::windowClosed( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) +{ +} + +void SAL_CALL ScVbaEventListener::windowMinimized( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) +{ +} + +void SAL_CALL ScVbaEventListener::windowNormalized( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) +{ +} + +void SAL_CALL ScVbaEventListener::windowActivated( const lang::EventObject& rEvent ) throw (uno::RuntimeException) +{ + ::osl::MutexGuard aGuard( maMutex ); + if( !mbDisposed ) { - try - { - uno::Reference< awt::XWindow > xWindow( getContainerWindow(), uno::UNO_QUERY_THROW ); - xWindow->removeWindowListener( this ); - } - catch( uno::Exception& ) - { - } - try - { - uno::Reference< util::XCloseBroadcaster > xCloseBroadcaster( mxModel, uno::UNO_QUERY_THROW ); - xCloseBroadcaster->removeCloseListener( this ); - } - catch( uno::Exception& ) - { - } - try - { - uno::Reference< frame::XControllerBorder > xControllerBorder( mxModel->getCurrentController(), uno::UNO_QUERY_THROW ); - xControllerBorder->removeBorderResizeListener( this ); - } - catch( uno::Exception& ) - { - } - try - { - uno::Reference< util::XChangesNotifier > xChangesNotifier( mxModel, uno::UNO_QUERY_THROW ); - xChangesNotifier->removeChangesListener( this ); - } - catch( uno::Exception& ) + uno::Reference< awt::XWindow > xWindow( rEvent.Source, uno::UNO_QUERY ); + Window* pWindow = VCLUnoHelper::GetWindow( xWindow ); + OSL_TRACE( "ScVbaEventListener::windowActivated - pWindow = 0x%x, mpActiveWindow = 0x%x", pWindow, mpActiveWindow ); + // do not fire activation event multiple time for the same window + if( pWindow && (pWindow != mpActiveWindow) ) { + // if another window is active, fire deactivation event first + if( mpActiveWindow ) + processWindowActivateEvent( mpActiveWindow, false ); + // fire activation event for the new window + processWindowActivateEvent( pWindow, true ); + mpActiveWindow = pWindow; } } - mbDisposed = true; } -void SAL_CALL ScVbaEventsListener::windowResized( const awt::WindowEvent& /*aEvent*/ ) throw ( uno::RuntimeException ) +void SAL_CALL ScVbaEventListener::windowDeactivated( const lang::EventObject& rEvent ) throw (uno::RuntimeException) { ::osl::MutexGuard aGuard( maMutex ); - // Workbook_window_resize event - mbWindowResized = true; - if( !mbDisposed && mbBorderChanged ) + + if( !mbDisposed ) { - if( /*Window* pWindow =*/ VCLUnoHelper::GetWindow( getContainerWindow() ) ) - { - mbBorderChanged = mbWindowResized = false; - acquire(); // ensure we don't get deleted before the event is handled - Application::PostUserEvent( LINK( this, ScVbaEventsListener, fireResizeMacro ), 0 ); - } + uno::Reference< awt::XWindow > xWindow( rEvent.Source, uno::UNO_QUERY ); + Window* pWindow = VCLUnoHelper::GetWindow( xWindow ); + OSL_TRACE( "ScVbaEventListener::windowDeactivated - pWindow = 0x%x, mpActiveWindow = 0x%x", pWindow, mpActiveWindow ); + // do not fire the deactivation event, if the window is not active (prevent multiple deactivation) + if( pWindow && (pWindow == mpActiveWindow) ) + processWindowActivateEvent( pWindow, false ); + // forget pointer to the active window + mpActiveWindow = 0; } } -void SAL_CALL ScVbaEventsListener::windowMoved( const awt::WindowEvent& /*aEvent*/ ) throw ( uno::RuntimeException ) +void SAL_CALL ScVbaEventListener::windowResized( const awt::WindowEvent& rEvent ) throw (uno::RuntimeException) { - // not interest this time -} + ::osl::MutexGuard aGuard( maMutex ); -void SAL_CALL ScVbaEventsListener::windowShown( const lang::EventObject& /*aEvent*/ ) throw ( uno::RuntimeException ) -{ - // not interest this time + mbWindowResized = true; + if( !mbDisposed && mbBorderChanged ) + { + uno::Reference< awt::XWindow > xWindow( rEvent.Source, uno::UNO_QUERY ); + postWindowResizeEvent( VCLUnoHelper::GetWindow( xWindow ) ); + } } -void SAL_CALL ScVbaEventsListener::windowHidden( const lang::EventObject& /*aEvent*/ ) throw ( uno::RuntimeException ) +void SAL_CALL ScVbaEventListener::windowMoved( const awt::WindowEvent& /*rEvent*/ ) throw (uno::RuntimeException) { - // not interest this time } -void SAL_CALL ScVbaEventsListener::disposing( const lang::EventObject& /*aEvent*/ ) throw ( uno::RuntimeException ) +void SAL_CALL ScVbaEventListener::windowShown( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) { - ::osl::MutexGuard aGuard( maMutex ); - OSL_TRACE( "ScVbaEventsListener::disposing( 0x%x )", this ); - mbDisposed = true; } -void SAL_CALL ScVbaEventsListener::queryClosing( const lang::EventObject& /*Source*/, sal_Bool /*GetsOwnership*/ ) throw (util::CloseVetoException, uno::RuntimeException) +void SAL_CALL ScVbaEventListener::windowHidden( const lang::EventObject& /*rEvent*/ ) throw (uno::RuntimeException) { - // it can cancel the close, but need to throw a CloseVetoException, and it will be transmit to caller. } -void SAL_CALL ScVbaEventsListener::notifyClosing( const lang::EventObject& /*Source*/ ) throw (uno::RuntimeException) +void SAL_CALL ScVbaEventListener::borderWidthsChanged( const uno::Reference< uno::XInterface >& rSource, const frame::BorderWidths& /*aNewSize*/ ) throw (uno::RuntimeException) { ::osl::MutexGuard aGuard( maMutex ); - stopListening(); -} -void SAL_CALL ScVbaEventsListener::borderWidthsChanged( const uno::Reference< uno::XInterface >& /*aObject*/, const frame::BorderWidths& /*aNewSize*/ ) throw (uno::RuntimeException) -{ - ::osl::MutexGuard aGuard( maMutex ); - // work with WindowResized event to guard Window Resize event. mbBorderChanged = true; if( !mbDisposed && mbWindowResized ) { - if( /*Window* pWindow =*/ VCLUnoHelper::GetWindow( getContainerWindow() ) ) - { - mbWindowResized = mbBorderChanged = false; - acquire(); // ensure we don't get deleted before the timer fires. - Application::PostUserEvent( LINK( this, ScVbaEventsListener, fireResizeMacro ), 0 ); - } + uno::Reference< frame::XController > xController( rSource, uno::UNO_QUERY ); + uno::Reference< awt::XWindow > xWindow = lclGetWindowForController( xController ); + postWindowResizeEvent( VCLUnoHelper::GetWindow( xWindow ) ); } } -void SAL_CALL ScVbaEventsListener::changesOccurred( const util::ChangesEvent& aEvent ) throw (uno::RuntimeException) +void SAL_CALL ScVbaEventListener::changesOccurred( const util::ChangesEvent& rEvent ) throw (uno::RuntimeException) { - sal_Int32 nCount = aEvent.Changes.getLength(); - if( nCount == 0 ) + ::osl::MutexGuard aGuard( maMutex ); + + sal_Int32 nCount = rEvent.Changes.getLength(); + if( mbDisposed || !mpDocShell || (nCount == 0) ) return; - util::ElementChange aChange = aEvent.Changes[ 0 ]; - rtl::OUString sOperation; + util::ElementChange aChange = rEvent.Changes[ 0 ]; + OUString sOperation; aChange.Accessor >>= sOperation; if( !sOperation.equalsIgnoreAsciiCaseAscii("cell-change") ) return; @@ -334,7 +381,7 @@ void SAL_CALL ScVbaEventsListener::changesOccurred( const util::ChangesEvent& aE { uno::Sequence< uno::Any > aArgs( 1 ); aArgs[0] <<= xRangeObj; - mrVbaEvents.processVbaEvent( WORKSHEET_CHANGE, aArgs ); + mrVbaEvents.processVbaEventNoThrow( WORKSHEET_CHANGE, aArgs ); } return; } @@ -342,7 +389,7 @@ void SAL_CALL ScVbaEventsListener::changesOccurred( const util::ChangesEvent& aE ScRangeList aRangeList; for( sal_Int32 nIndex = 0; nIndex < nCount; ++nIndex ) { - aChange = aEvent.Changes[ nIndex ]; + aChange = rEvent.Changes[ nIndex ]; aChange.Accessor >>= sOperation; uno::Reference< table::XCellRange > xRangeObj; aChange.ReplacedElement >>= xRangeObj; @@ -358,62 +405,117 @@ void SAL_CALL ScVbaEventsListener::changesOccurred( const util::ChangesEvent& aE } } - if( (aRangeList.Count() > 0) && mpDocShell ) + if( aRangeList.Count() > 0 ) { uno::Reference< sheet::XSheetCellRangeContainer > xRanges( new ScCellRangesObj( mpDocShell, aRangeList ) ); uno::Sequence< uno::Any > aArgs(1); aArgs[0] <<= xRanges; - mrVbaEvents.processVbaEvent( WORKSHEET_CHANGE, aArgs ); + mrVbaEvents.processVbaEventNoThrow( WORKSHEET_CHANGE, aArgs ); } } -// ---------------------------------------------------------------------------- +void SAL_CALL ScVbaEventListener::disposing( const lang::EventObject& rEvent ) throw (uno::RuntimeException) +{ + ::osl::MutexGuard aGuard( maMutex ); + + uno::Reference< frame::XModel > xModel( rEvent.Source, uno::UNO_QUERY ); + if( xModel.is() ) + { + OSL_ENSURE( xModel.get() == mxModel.get(), "ScVbaEventListener::disposing - disposing from unknown model" ); + stopModelListening(); + mbDisposed = true; + return; + } + + uno::Reference< frame::XController > xController( rEvent.Source, uno::UNO_QUERY ); + if( xController.is() ) + { + stopControllerListening( xController ); + return; + } +} -uno::Reference< frame::XFrame > ScVbaEventsListener::getFrame() +// private -------------------------------------------------------------------- + +void ScVbaEventListener::startModelListening() { - if( !mbDisposed && mxModel.is() ) try + try { - uno::Reference< frame::XController > xController( mxModel->getCurrentController(), uno::UNO_QUERY_THROW ); - return xController->getFrame(); + uno::Reference< util::XChangesNotifier > xChangesNotifier( mxModel, uno::UNO_QUERY_THROW ); + xChangesNotifier->addChangesListener( this ); } catch( uno::Exception& ) { } - return uno::Reference< frame::XFrame >(); } -uno::Reference< awt::XWindow > ScVbaEventsListener::getContainerWindow() +void ScVbaEventListener::stopModelListening() { try { - uno::Reference< frame::XFrame > xFrame( getFrame(), uno::UNO_SET_THROW ); - return xFrame->getContainerWindow(); + uno::Reference< util::XChangesNotifier > xChangesNotifier( mxModel, uno::UNO_QUERY_THROW ); + xChangesNotifier->removeChangesListener( this ); } catch( uno::Exception& ) { } - return uno::Reference< awt::XWindow >(); } -bool ScVbaEventsListener::isMouseReleased() +uno::Reference< frame::XController > ScVbaEventListener::getControllerForWindow( Window* pWindow ) const { - if( Window* pWindow = VCLUnoHelper::GetWindow( getContainerWindow() ) ) + WindowControllerMap::const_iterator aIt = maControllers.find( pWindow ); + return (aIt == maControllers.end()) ? uno::Reference< frame::XController >() : aIt->second; +} + +void ScVbaEventListener::processWindowActivateEvent( Window* pWindow, bool bActivate ) +{ + uno::Reference< frame::XController > xController = getControllerForWindow( pWindow ); + if( xController.is() ) { - Window::PointerState aPointerState = pWindow->GetPointerState(); - return (aPointerState.mnState & ( MOUSE_LEFT | MOUSE_MIDDLE | MOUSE_RIGHT )) == 0; + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= xController; + mrVbaEvents.processVbaEventNoThrow( bActivate ? WORKBOOK_WINDOWACTIVATE : WORKBOOK_WINDOWDEACTIVATE, aArgs ); } - return false; } -IMPL_LINK( ScVbaEventsListener, fireResizeMacro, void*, EMPTYARG ) +void ScVbaEventListener::postWindowResizeEvent( Window* pWindow ) { - if( !mbDisposed && isMouseReleased() ) try + // check that the passed window is still alive (it must be registered in maControllers) + if( pWindow && (maControllers.count( pWindow ) > 0) ) { - mrVbaEvents.processVbaEvent( WORKBOOK_WINDOWRESIZE, uno::Sequence< uno::Any >() ); + mbWindowResized = mbBorderChanged = false; + acquire(); // ensure we don't get deleted before the timer fires + Application::PostUserEvent( LINK( this, ScVbaEventListener, processWindowResizeEvent ), pWindow ); } - catch( uno::Exception& ) +} + +IMPL_LINK( ScVbaEventListener, processWindowResizeEvent, Window*, EMPTYARG pWindow ) +{ + ::osl::MutexGuard aGuard( maMutex ); + + /* Check that the passed window is still alive (it must be registered in + maControllers). While closing a document, postWindowResizeEvent() may + be called on the last window which posts a user event via + Application::PostUserEvent to call this event handler. VCL will trigger + the handler some time later. Sometimes, the window gets deleted before. + This is handled via the disposing() function which removes the window + pointer from the member maControllers. Thus, checking whether + maControllers contains pWindow ensures that the window is still alive. */ + if( !mbDisposed && pWindow && (maControllers.count( pWindow ) > 0) ) { - // #163419# do not throw exceptions into application core + // do not fire event unless all mouse buttons have been released + Window::PointerState aPointerState = pWindow->GetPointerState(); + if( (aPointerState.mnState & (MOUSE_LEFT | MOUSE_MIDDLE | MOUSE_RIGHT)) == 0 ) + { + uno::Reference< frame::XController > xController = getControllerForWindow( pWindow ); + if( xController.is() ) + { + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= xController; + // #163419# do not throw exceptions into application core + mrVbaEvents.processVbaEventNoThrow( WORKBOOK_WINDOWRESIZE, aArgs ); + } + } } release(); return 0; @@ -431,19 +533,19 @@ ScVbaEventsHelper::ScVbaEventsHelper( const uno::Sequence< uno::Any >& rArgs, co if( !mxModel.is() || !mpDocShell || !mpDoc ) return; -#define REGISTER_EVENT( eventid, eventname, type, cancelindex, worksheet ) \ - registerEventHandler( eventid, eventname, type, cancelindex, uno::Any( worksheet ) ) - +#define REGISTER_EVENT( eventid, moduletype, classname, eventname, cancelindex, worksheet ) \ + registerEventHandler( eventid, moduletype, classname "_" eventname, cancelindex, uno::Any( worksheet ) ) +#define REGISTER_AUTO_EVENT( eventid, eventname ) \ + REGISTER_EVENT( AUTO_##eventid, script::ModuleType::NORMAL, "Auto", eventname, -1, false ) #define REGISTER_WORKBOOK_EVENT( eventid, eventname, cancelindex ) \ - REGISTER_EVENT( WORKBOOK_##eventid, "Workbook_" eventname, EVENTHANDLER_DOCUMENT, cancelindex, false ) - + REGISTER_EVENT( WORKBOOK_##eventid, script::ModuleType::DOCUMENT, "Workbook", eventname, cancelindex, false ) #define REGISTER_WORKSHEET_EVENT( eventid, eventname, cancelindex ) \ - REGISTER_EVENT( WORKSHEET_##eventid, "Worksheet_" eventname, EVENTHANDLER_DOCUMENT, cancelindex, true ); \ - REGISTER_EVENT( (USERDEFINED_START + WORKSHEET_##eventid), "Workbook_Sheet" eventname, EVENTHANDLER_DOCUMENT, (((cancelindex) >= 0) ? ((cancelindex) + 1) : -1), false ) + REGISTER_EVENT( WORKSHEET_##eventid, script::ModuleType::DOCUMENT, "Worksheet", eventname, cancelindex, true ); \ + REGISTER_EVENT( (USERDEFINED_START + WORKSHEET_##eventid), script::ModuleType::DOCUMENT, "Workbook", "Sheet" eventname, (((cancelindex) >= 0) ? ((cancelindex) + 1) : -1), false ) // global - REGISTER_EVENT( AUTO_OPEN, "Auto_Open", EVENTHANDLER_GLOBAL, -1, false ); - REGISTER_EVENT( AUTO_CLOSE, "Auto_Close", EVENTHANDLER_GLOBAL, -1, false ); + REGISTER_AUTO_EVENT( OPEN, "Open" ); + REGISTER_AUTO_EVENT( CLOSE, "Close" ); // Workbook REGISTER_WORKBOOK_EVENT( ACTIVATE, "Activate", -1 ); @@ -468,19 +570,68 @@ ScVbaEventsHelper::ScVbaEventsHelper( const uno::Sequence< uno::Any >& rArgs, co REGISTER_WORKSHEET_EVENT( SELECTIONCHANGE, "SelectionChange", -1 ); REGISTER_WORKSHEET_EVENT( FOLLOWHYPERLINK, "FollowHyperlink", -1 ); -#undef REGISTER_EVENT -#undef REGISTER_WORKBOOK_EVENT #undef REGISTER_WORKSHEET_EVENT +#undef REGISTER_WORKBOOK_EVENT +#undef REGISTER_AUTO_EVENT +#undef REGISTER_EVENT } ScVbaEventsHelper::~ScVbaEventsHelper() { } -void SAL_CALL ScVbaEventsHelper::disposing( const lang::EventObject& rSource ) throw (uno::RuntimeException) +void SAL_CALL ScVbaEventsHelper::notifyEvent( const css::document::EventObject& rEvent ) throw (css::uno::RuntimeException) { - mxListener.clear(); - VbaEventsHelperBase::disposing( rSource ); + static const uno::Sequence< uno::Any > saEmptyArgs; + if( (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_OPENDOC )) || + (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_CREATEDOC )) ) // CREATEDOC triggered e.g. during VBA Workbooks.Add + { + processVbaEventNoThrow( WORKBOOK_OPEN, saEmptyArgs ); + } + else if( rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_ACTIVATEDOC ) ) + { + processVbaEventNoThrow( WORKBOOK_ACTIVATE, saEmptyArgs ); + } + else if( rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_DEACTIVATEDOC ) ) + { + processVbaEventNoThrow( WORKBOOK_DEACTIVATE, saEmptyArgs ); + } + else if( (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVEDOCDONE )) || + (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVEASDOCDONE )) || + (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVETODOCDONE )) ) + { + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= true; + processVbaEventNoThrow( WORKBOOK_AFTERSAVE, aArgs ); + } + else if( (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVEDOCFAILED )) || + (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVEASDOCFAILED )) || + (rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_SAVETODOCFAILED )) ) + { + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= false; + processVbaEventNoThrow( WORKBOOK_AFTERSAVE, aArgs ); + } + else if( rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_CLOSEDOC ) ) + { + /* Trigger the WORKBOOK_WINDOWDEACTIVATE and WORKBOOK_DEACTIVATE + events and stop listening to the model (done in base class). */ + uno::Reference< frame::XController > xController( mxModel->getCurrentController() ); + if( xController.is() ) + { + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= xController; + processVbaEventNoThrow( WORKBOOK_WINDOWDEACTIVATE, aArgs ); + } + processVbaEventNoThrow( WORKBOOK_DEACTIVATE, saEmptyArgs ); + } + else if( rEvent.EventName == GlobalEventConfig::GetEventName( STR_EVENT_VIEWCREATED ) ) + { + uno::Reference< frame::XController > xController( mxModel->getCurrentController() ); + if( mxListener.get() && xController.is() ) + mxListener->startControllerListening( xController ); + } + VbaEventsHelperBase::notifyEvent( rEvent ); } // protected ------------------------------------------------------------------ @@ -492,25 +643,35 @@ bool ScVbaEventsHelper::implPrepareEvent( EventQueue& rEventQueue, if( !mpShell || !mpDoc ) throw uno::RuntimeException(); - // framework and Calc fire a few events before 'opened', ignore them - bool bExecuteEvent = mbOpened; + /* For document events: check if events are enabled via the + Application.EnableEvents symbol (this is an Excel-only attribute). + Check this again for every event, as the event handler may change the + state of the EnableEvents symbol. Global events such as AUTO_OPEN and + AUTO_CLOSE are always enabled. */ + bool bExecuteEvent = (rInfo.mnModuleType != script::ModuleType::DOCUMENT) || ScVbaApplication::getDocumentEventsEnabled(); + + // framework and Calc fire a few events before 'OnLoad', ignore them + if( bExecuteEvent ) + bExecuteEvent = (rInfo.mnEventId == WORKBOOK_OPEN) ? !mbOpened : mbOpened; // special handling for some events - switch( rInfo.mnEventId ) + if( bExecuteEvent ) switch( rInfo.mnEventId ) { case WORKBOOK_OPEN: - bExecuteEvent = !mbOpened; - if( bExecuteEvent ) - { - // execute delayed Activate event too (see above) - rEventQueue.push_back( WORKBOOK_ACTIVATE ); - rEventQueue.push_back( WORKBOOK_WINDOWACTIVATE ); - rEventQueue.push_back( AUTO_OPEN ); - } + { + // execute delayed Activate event too (see above) + rEventQueue.push_back( WORKBOOK_ACTIVATE ); + uno::Sequence< uno::Any > aArgs( 1 ); + aArgs[ 0 ] <<= mxModel->getCurrentController(); + rEventQueue.push_back( EventQueueEntry( WORKBOOK_WINDOWACTIVATE, aArgs ) ); + rEventQueue.push_back( AUTO_OPEN ); + // remember initial selection + maOldSelection <<= mxModel->getCurrentSelection(); + } break; case WORKSHEET_SELECTIONCHANGE: // if selection is not changed, then do not fire the event - bExecuteEvent = bExecuteEvent && isSelectionChanged( rArgs, 0 ); + bExecuteEvent = isSelectionChanged( rArgs, 0 ); break; } @@ -520,14 +681,6 @@ bool ScVbaEventsHelper::implPrepareEvent( EventQueue& rEventQueue, bool bSheetEvent = false; if( (rInfo.maUserData >>= bSheetEvent) && bSheetEvent ) rEventQueue.push_back( EventQueueEntry( rInfo.mnEventId + USERDEFINED_START, rArgs ) ); - - /* For document events: check if events are enabled via the - Application.EnableEvents symbol (this is an Excel-only attribute). - Check this again for every event, as the event handler may change - the state of the EnableEvents symbol. Global events such as - AUTO_OPEN and AUTO_CLOSE are always enabled. */ - if( rInfo.meType == EVENTHANDLER_DOCUMENT ) - bExecuteEvent = ScVbaApplication::getDocumentEventsEnabled(); } return bExecuteEvent; @@ -574,7 +727,7 @@ uno::Sequence< uno::Any > ScVbaEventsHelper::implBuildArgumentList( const EventH case WORKBOOK_WINDOWDEACTIVATE: case WORKBOOK_WINDOWRESIZE: aVbaArgs.realloc( 1 ); - aVbaArgs[ 0 ] = createWindow(); + aVbaArgs[ 0 ] = createWindow( rArgs, 0 ); break; // 1 arg: worksheet case WORKBOOK_NEWSHEET: @@ -625,7 +778,7 @@ uno::Sequence< uno::Any > ScVbaEventsHelper::implBuildArgumentList( const EventH } void ScVbaEventsHelper::implPostProcessEvent( EventQueue& rEventQueue, - const EventHandlerInfo& rInfo, bool /*bSuccess*/, bool bCancel ) throw (uno::RuntimeException) + const EventHandlerInfo& rInfo, bool bCancel ) throw (uno::RuntimeException) { switch( rInfo.mnEventId ) { @@ -633,10 +786,7 @@ void ScVbaEventsHelper::implPostProcessEvent( EventQueue& rEventQueue, mbOpened = true; // register the listeners if( !mxListener.is() ) - { - mxListener = new ScVbaEventsListener( *this, mxModel, mpDocShell ); - mxListener->startListening(); - } + mxListener = new ScVbaEventListener( *this, mxModel, mpDocShell ); break; case WORKBOOK_BEFORECLOSE: /* Execute Auto_Close only if not cancelled by event handler, but @@ -647,7 +797,7 @@ void ScVbaEventsHelper::implPostProcessEvent( EventQueue& rEventQueue, } } -::rtl::OUString ScVbaEventsHelper::implGetDocumentModuleName( const EventHandlerInfo& rInfo, +OUString ScVbaEventsHelper::implGetDocumentModuleName( const EventHandlerInfo& rInfo, const uno::Sequence< uno::Any >& rArgs ) const throw (lang::IllegalArgumentException) { bool bSheetEvent = false; @@ -746,11 +896,13 @@ uno::Any ScVbaEventsHelper::createHyperlink( const uno::Sequence< uno::Any >& rA return uno::Any( xHyperlink ); } -uno::Any ScVbaEventsHelper::createWindow() const throw (uno::RuntimeException) +uno::Any ScVbaEventsHelper::createWindow( const uno::Sequence< uno::Any >& rArgs, sal_Int32 nIndex ) const + throw (lang::IllegalArgumentException, uno::RuntimeException) { - uno::Sequence< uno::Any > aArgs( 2 ); - aArgs[ 0 ] <<= createVBAUnoAPIService( mpShell, "ooo.vba.Application" ); + uno::Sequence< uno::Any > aArgs( 3 ); + aArgs[ 0 ] <<= getVBADocument( mxModel ); aArgs[ 1 ] <<= mxModel; + aArgs[ 2 ] <<= getXSomethingFromArgs< frame::XController >( rArgs, nIndex, false ); uno::Reference< uno::XInterface > xWindow( createVBAUnoAPIServiceWithArgs( mpShell, "ooo.vba.excel.Window", aArgs ), uno::UNO_SET_THROW ); return uno::Any( xWindow ); } diff --git a/sc/source/ui/vba/vbaeventshelper.hxx b/sc/source/ui/vba/vbaeventshelper.hxx index f1e8a4fb712d..4e7e3b52f610 100755 --- a/sc/source/ui/vba/vbaeventshelper.hxx +++ b/sc/source/ui/vba/vbaeventshelper.hxx @@ -25,15 +25,15 @@ * ************************************************************************/ -#ifndef SC_VBAEVENTS_HXX -#define SC_VBAEVENTS_HXX +#ifndef SC_VBAEVENTSHELPER_HXX +#define SC_VBAEVENTSHELPER_HXX #include <rtl/ref.hxx> #include <vbahelper/vbaeventshelperbase.hxx> #include "excelvbahelper.hxx" #include "rangelst.hxx" -class ScVbaEventsListener; +class ScVbaEventListener; // ============================================================================ @@ -45,13 +45,12 @@ public: const css::uno::Reference< css::uno::XComponentContext >& rxContext ); virtual ~ScVbaEventsHelper(); - // XEventListener - virtual void SAL_CALL disposing( const css::lang::EventObject& rSource ) throw (css::uno::RuntimeException); + virtual void SAL_CALL notifyEvent( const css::document::EventObject& rEvent ) throw (css::uno::RuntimeException); protected: virtual bool implPrepareEvent( EventQueue& rEventQueue, const EventHandlerInfo& rInfo, const css::uno::Sequence< css::uno::Any >& rArgs ) throw (css::uno::RuntimeException); virtual css::uno::Sequence< css::uno::Any > implBuildArgumentList( const EventHandlerInfo& rInfo, const css::uno::Sequence< css::uno::Any >& rArgs ) throw (css::lang::IllegalArgumentException); - virtual void implPostProcessEvent( EventQueue& rEventQueue, const EventHandlerInfo& rInfo, bool bSuccess, bool bCancel ) throw (css::uno::RuntimeException); + virtual void implPostProcessEvent( EventQueue& rEventQueue, const EventHandlerInfo& rInfo, bool bCancel ) throw (css::uno::RuntimeException); virtual ::rtl::OUString implGetDocumentModuleName( const EventHandlerInfo& rInfo, const css::uno::Sequence< css::uno::Any >& rArgs ) const throw (css::lang::IllegalArgumentException); private: @@ -65,11 +64,11 @@ private: css::uno::Any createRange( const css::uno::Sequence< css::uno::Any >& rArgs, sal_Int32 nIndex ) const throw (css::lang::IllegalArgumentException, css::uno::RuntimeException); /** Creates a VBA Hyperlink object (the argument must contain a UNO cell). */ css::uno::Any createHyperlink( const css::uno::Sequence< css::uno::Any >& rArgs, sal_Int32 nIndex ) const throw (css::lang::IllegalArgumentException, css::uno::RuntimeException); - /** Creates a VBA Window object. */ - css::uno::Any createWindow() const throw (css::uno::RuntimeException); + /** Creates a VBA Window object (the argument must contain a model controller). */ + css::uno::Any createWindow( const css::uno::Sequence< css::uno::Any >& rArgs, sal_Int32 nIndex ) const throw (css::lang::IllegalArgumentException, css::uno::RuntimeException); private: - ::rtl::Reference< ScVbaEventsListener > mxListener; + ::rtl::Reference< ScVbaEventListener > mxListener; css::uno::Any maOldSelection; ScDocShell* mpDocShell; ScDocument* mpDoc; diff --git a/sc/source/ui/vba/vbaformat.cxx b/sc/source/ui/vba/vbaformat.cxx index 3b0ba2367c1a..0186b5a78645 100644 --- a/sc/source/ui/vba/vbaformat.cxx +++ b/sc/source/ui/vba/vbaformat.cxx @@ -62,10 +62,10 @@ ScVbaFormat< Ifc1 >::ScVbaFormat( const uno::Reference< XHelperInterface >& xPar { try { - mxServiceInfo.set( mxPropertySet, uno::UNO_QUERY_THROW ); if ( !mxModel.is() ) DebugHelper::exception(SbERR_METHOD_FAILED, rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "XModel Interface could not be retrieved") ) ); - mxNumberFormatsSupplier.set( mxModel, uno::UNO_QUERY_THROW ); + // mxServiceInfo is unused, + // mxNumberFormatsSupplier is initialized when needed in initializeNumberFormats. } catch (uno::Exception& ) { diff --git a/sc/source/ui/vba/vbaformat.hxx b/sc/source/ui/vba/vbaformat.hxx index bfa88d6c7cb8..b875f84c69cd 100644 --- a/sc/source/ui/vba/vbaformat.hxx +++ b/sc/source/ui/vba/vbaformat.hxx @@ -52,7 +52,6 @@ protected: css::uno::Reference< css::util::XNumberFormats > xNumberFormats; css::uno::Reference< css::util::XNumberFormatTypes > xNumberFormatTypes; css::uno::Reference< css::frame::XModel > mxModel; - css::uno::Reference< css::lang::XServiceInfo > mxServiceInfo; css::uno::Reference< css::beans::XPropertyState > xPropertyState; sal_Bool mbCheckAmbiguoity; sal_Bool mbAddIndent; @@ -69,7 +68,6 @@ public: ScVbaFormat( const css::uno::Reference< ov::XHelperInterface >& xParent, const css::uno::Reference< css::uno::XComponentContext > & xContext, const css::uno::Reference< css::beans::XPropertySet >& _xPropertySet, const css::uno::Reference< css::frame::XModel >& xModel, bool bCheckAmbiguoity ) throw ( css::script::BasicErrorException ); virtual ~ScVbaFormat() {} virtual css::uno::Reference< ov::XHelperInterface > thisHelperIface() = 0; - css::uno::Reference< css::lang::XServiceInfo > getXServiceInfo() { return mxServiceInfo; } void SAL_CALL setAddIndent( const css::uno::Any& _BAddIndent) throw( css::uno::RuntimeException ) { _BAddIndent >>= mbAddIndent; } css::uno::Any SAL_CALL getAddIndent() throw( css::uno::RuntimeException ) { return css::uno::makeAny( mbAddIndent ); } // Interface Methods diff --git a/sc/source/ui/vba/vbaglobals.cxx b/sc/source/ui/vba/vbaglobals.cxx index c70a7f83726d..f9ab063937cf 100644 --- a/sc/source/ui/vba/vbaglobals.cxx +++ b/sc/source/ui/vba/vbaglobals.cxx @@ -234,11 +234,9 @@ ScVbaGlobals::getDebug() throw (uno::RuntimeException) { try // return empty object on error { - uno::Sequence< uno::Any > aArgs( 1 ); - aArgs[ 0 ] <<= uno::Reference< XHelperInterface >( this ); uno::Reference< lang::XMultiComponentFactory > xServiceManager( mxContext->getServiceManager(), uno::UNO_SET_THROW ); - uno::Reference< uno::XInterface > xVBADebug = xServiceManager->createInstanceWithArgumentsAndContext( - ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ooo.vba.Debug" ) ), aArgs, mxContext ); + uno::Reference< uno::XInterface > xVBADebug = xServiceManager->createInstanceWithContext( + ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ooo.vba.Debug" ) ), mxContext ); return uno::Any( xVBADebug ); } catch( uno::Exception& ) diff --git a/sc/source/ui/vba/vbarange.cxx b/sc/source/ui/vba/vbarange.cxx index 5cb6d44fc902..72f300d6463a 100755 --- a/sc/source/ui/vba/vbarange.cxx +++ b/sc/source/ui/vba/vbarange.cxx @@ -406,7 +406,7 @@ ScDocShell* getDocShellFromRange( const uno::Reference< table::XCellRange >& xRange ) throw ( uno::RuntimeException ) { // need the ScCellRangesBase to get docshell - uno::Reference< uno::XInterface > xIf( xRange, uno::UNO_QUERY_THROW ); + uno::Reference< uno::XInterface > xIf( xRange ); return getDocShellFromIf(xIf ); } @@ -414,7 +414,7 @@ ScDocShell* getDocShellFromRanges( const uno::Reference< sheet::XSheetCellRangeContainer >& xRanges ) throw ( uno::RuntimeException ) { // need the ScCellRangesBase to get docshell - uno::Reference< uno::XInterface > xIf( xRanges, uno::UNO_QUERY_THROW ); + uno::Reference< uno::XInterface > xIf( xRanges ); return getDocShellFromIf(xIf ); } @@ -426,7 +426,8 @@ uno::Reference< frame::XModel > getModelFromXIf( const uno::Reference< uno::XInt uno::Reference< frame::XModel > getModelFromRange( const uno::Reference< table::XCellRange >& xRange ) throw ( uno::RuntimeException ) { - uno::Reference< uno::XInterface > xIf( xRange, uno::UNO_QUERY_THROW ); + // the XInterface for getImplementation can be any derived interface, no need for queryInterface + uno::Reference< uno::XInterface > xIf( xRange ); return getModelFromXIf( xIf ); } @@ -1469,9 +1470,9 @@ uno::Reference< XCollection >& ScVbaRange::getBorders() void ScVbaRange::visitArray( ArrayVisitor& visitor ) { - uno::Reference< table::XColumnRowRange > xColumnRowRange(mxRange, uno::UNO_QUERY_THROW ); - sal_Int32 nRowCount = xColumnRowRange->getRows()->getCount(); - sal_Int32 nColCount = xColumnRowRange->getColumns()->getCount(); + table::CellRangeAddress aRangeAddr = lclGetRangeAddress( mxRange ); + sal_Int32 nRowCount = aRangeAddr.EndRow - aRangeAddr.StartRow + 1; + sal_Int32 nColCount = aRangeAddr.EndColumn - aRangeAddr.StartColumn + 1; for ( sal_Int32 i=0; i<nRowCount; ++i ) { for ( sal_Int32 j=0; j<nColCount; ++j ) @@ -3572,9 +3573,12 @@ ScVbaRange::End( ::sal_Int32 Direction ) throw (uno::RuntimeException) bool ScVbaRange::isSingleCellRange() { - uno::Reference< table::XColumnRowRange > xColumnRowRange(mxRange, uno::UNO_QUERY); - if ( xColumnRowRange.is() && xColumnRowRange->getRows()->getCount() == 1 && xColumnRowRange->getColumns()->getCount() == 1 ) - return true; + uno::Reference< sheet::XCellRangeAddressable > xAddressable( mxRange, uno::UNO_QUERY ); + if ( xAddressable.is() ) + { + table::CellRangeAddress aRangeAddr = xAddressable->getRangeAddress(); + return ( aRangeAddr.EndColumn == aRangeAddr.StartColumn && aRangeAddr.EndRow == aRangeAddr.StartRow ); + } return false; } diff --git a/sc/source/ui/vba/vbawindow.cxx b/sc/source/ui/vba/vbawindow.cxx index 5964fe98317c..ed10e52cca7a 100644 --- a/sc/source/ui/vba/vbawindow.cxx +++ b/sc/source/ui/vba/vbawindow.cxx @@ -59,11 +59,9 @@ typedef std::hash_map< rtl::OUString, SCTAB, ::rtl::OUStringHash, ::std::equal_to< ::rtl::OUString > > NameIndexHash; -typedef std::vector < uno::Reference< sheet::XSpreadsheet > > Sheets; +typedef std::vector< uno::Reference< sheet::XSpreadsheet > > Sheets; -typedef ::cppu::WeakImplHelper1< container::XEnumeration - -> Enumeration_BASE; +typedef ::cppu::WeakImplHelper1< container::XEnumeration > Enumeration_BASE; typedef ::cppu::WeakImplHelper3< container::XEnumerationAccess , com::sun::star::container::XIndexAccess @@ -200,13 +198,20 @@ public: }; -ScVbaWindow::ScVbaWindow( const uno::Reference< XHelperInterface >& xParent, const uno::Reference< uno::XComponentContext >& xContext, const uno::Reference< frame::XModel >& xModel ) : WindowImpl_BASE( xParent, xContext, xModel ) +ScVbaWindow::ScVbaWindow( + const uno::Reference< XHelperInterface >& xParent, + const uno::Reference< uno::XComponentContext >& xContext, + const uno::Reference< frame::XModel >& xModel, + const uno::Reference< frame::XController >& xController ) throw (uno::RuntimeException) : + WindowImpl_BASE( xParent, xContext, xModel, xController ) { init(); } -ScVbaWindow::ScVbaWindow( uno::Sequence< uno::Any > const & args, uno::Reference< uno::XComponentContext > const & xContext ) - : WindowImpl_BASE( args, xContext ) +ScVbaWindow::ScVbaWindow( + const uno::Sequence< uno::Any >& args, + const uno::Reference< uno::XComponentContext >& xContext ) throw (uno::RuntimeException) : + WindowImpl_BASE( args, xContext ) { init(); } @@ -218,20 +223,42 @@ ScVbaWindow::init() still zero. The implementation of ActivePane() uses a UNO reference of this (to set this window as parent of the pane obejct). This requires the own refcount to be non-zero, otherwise this instance will be - desctructed immediately! */ + desctructed immediately! Guard the call to ActivePane() in try/catch to + not miss the decrementation of the reference count on exception. */ osl_incrementInterlockedCount( &m_refCount ); - uno::Reference< frame::XController > xController( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); - m_xViewPane.set( xController, uno::UNO_QUERY_THROW ); - m_xViewFreezable.set( xController, uno::UNO_QUERY_THROW ); - m_xViewSplitable.set( xController, uno::UNO_QUERY_THROW ); - m_xPane.set( ActivePane(), uno::UNO_QUERY_THROW ); - m_xDevice.set( xController->getFrame()->getComponentWindow(), uno::UNO_QUERY_THROW ); + try + { + m_xPane = ActivePane(); + } + catch( uno::Exception& ) + { + } osl_decrementInterlockedCount( &m_refCount ); } +uno::Reference< beans::XPropertySet > +ScVbaWindow::getControllerProps() throw (uno::RuntimeException) +{ + return uno::Reference< beans::XPropertySet >( getController(), uno::UNO_QUERY_THROW ); +} + +uno::Reference< beans::XPropertySet > +ScVbaWindow::getFrameProps() throw (uno::RuntimeException) +{ + return uno::Reference< beans::XPropertySet >( getController()->getFrame(), uno::UNO_QUERY_THROW ); +} + +uno::Reference< awt::XDevice > +ScVbaWindow::getDevice() throw (uno::RuntimeException) +{ + return uno::Reference< awt::XDevice >( getWindow(), uno::UNO_QUERY_THROW ); +} + void ScVbaWindow::Scroll( const uno::Any& Down, const uno::Any& Up, const uno::Any& ToRight, const uno::Any& ToLeft, bool bLargeScroll ) throw (uno::RuntimeException) { + if( !m_xPane.is() ) + throw uno::RuntimeException(); if( bLargeScroll ) m_xPane->LargeScroll( Down, Up, ToRight, ToLeft ); else @@ -253,7 +280,7 @@ ScVbaWindow::LargeScroll( const uno::Any& Down, const uno::Any& Up, const uno::A uno::Any SAL_CALL ScVbaWindow::SelectedSheets( const uno::Any& aIndex ) throw (uno::RuntimeException) { - uno::Reference< container::XEnumerationAccess > xEnumAccess( new SelectedSheetsEnumAccess( mxContext, m_xModel ) ); + uno::Reference< container::XEnumerationAccess > xEnumAccess( new SelectedSheetsEnumAccess( mxContext, m_xModel ) ); // #FIXME needs a workbook as a parent uno::Reference< excel::XWorksheets > xSheets( new ScVbaWorksheets( uno::Reference< XHelperInterface >(), mxContext, xEnumAccess, m_xModel ) ); if ( aIndex.hasValue() ) @@ -283,16 +310,6 @@ ScVbaWindow::ScrollWorkbookTabs( const uno::Any& /*Sheets*/, const uno::Any& /*P */ } -uno::Reference< beans::XPropertySet > -getPropsFromModel( const uno::Reference< frame::XModel >& xModel ) -{ - uno::Reference< frame::XController > xController = xModel->getCurrentController(); - if ( !xController.is() ) - throw uno::RuntimeException( rtl::OUString( - RTL_CONSTASCII_USTRINGPARAM ("No controller for model") ), uno::Reference< uno::XInterface >() ); - return uno::Reference< beans::XPropertySet >( xController->getFrame(), uno::UNO_QUERY ); -} - uno::Any SAL_CALL ScVbaWindow::getCaption() throw (uno::RuntimeException) @@ -300,9 +317,8 @@ ScVbaWindow::getCaption() throw (uno::RuntimeException) static rtl::OUString sCrud(RTL_CONSTASCII_USTRINGPARAM(" - OpenOffice.org Calc" ) ); static sal_Int32 nCrudLen = sCrud.getLength(); - uno::Reference< beans::XPropertySet > xProps = getPropsFromModel( m_xModel ); rtl::OUString sTitle; - xProps->getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( SC_UNONAME_TITLE ) ) ) >>= sTitle; + getFrameProps()->getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM ( SC_UNONAME_TITLE ) ) ) >>= sTitle; sal_Int32 nCrudIndex = sTitle.indexOf( sCrud ); // adjust title ( by removing crud ) // sCrud string present @@ -338,16 +354,14 @@ ScVbaWindow::getCaption() throw (uno::RuntimeException) void SAL_CALL ScVbaWindow::setCaption( const uno::Any& _caption ) throw (uno::RuntimeException) { - - uno::Reference< beans::XPropertySet > xProps = getPropsFromModel( m_xModel ); - xProps->setPropertyValue( rtl::OUString( - RTL_CONSTASCII_USTRINGPARAM ( SC_UNONAME_TITLE ) ) , _caption ); + getFrameProps()->setPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( SC_UNONAME_TITLE ) ), _caption ); } uno::Any SAL_CALL ScVbaWindow::getScrollRow() throw (uno::RuntimeException) { sal_Int32 nValue = 0; + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); if ( pViewShell ) { @@ -361,6 +375,7 @@ ScVbaWindow::getScrollRow() throw (uno::RuntimeException) void SAL_CALL ScVbaWindow::setScrollRow( const uno::Any& _scrollrow ) throw (uno::RuntimeException) { + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); if ( pViewShell ) { @@ -376,6 +391,7 @@ uno::Any SAL_CALL ScVbaWindow::getScrollColumn() throw (uno::RuntimeException) { sal_Int32 nValue = 0; + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); if ( pViewShell ) { @@ -389,6 +405,7 @@ ScVbaWindow::getScrollColumn() throw (uno::RuntimeException) void SAL_CALL ScVbaWindow::setScrollColumn( const uno::Any& _scrollcolumn ) throw (uno::RuntimeException) { + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); if ( pViewShell ) { @@ -404,6 +421,7 @@ uno::Any SAL_CALL ScVbaWindow::getWindowState() throw (uno::RuntimeException) { sal_Int32 nwindowState = xlNormal; + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); SfxViewFrame* pViewFrame = pViewShell -> GetViewFrame(); WorkWindow* pWork = (WorkWindow*) pViewFrame->GetFrame().GetSystemWindow(); @@ -422,6 +440,7 @@ ScVbaWindow::setWindowState( const uno::Any& _windowstate ) throw (uno::RuntimeE { sal_Int32 nwindowState = xlMaximized; _windowstate >>= nwindowState; + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); SfxViewFrame* pViewFrame = pViewShell -> GetViewFrame(); WorkWindow* pWork = (WorkWindow*) pViewFrame->GetFrame().GetSystemWindow(); @@ -456,7 +475,8 @@ ScVbaWindow::Close( const uno::Any& SaveChanges, const uno::Any& FileName, const uno::Reference< excel::XPane > SAL_CALL ScVbaWindow::ActivePane() throw (script::BasicErrorException, uno::RuntimeException) { - return new ScVbaPane( this, mxContext, m_xModel, m_xViewPane ); + uno::Reference< sheet::XViewPane > xViewPane( getController(), uno::UNO_QUERY_THROW ); + return new ScVbaPane( this, mxContext, m_xModel, xViewPane ); } uno::Reference< excel::XRange > SAL_CALL @@ -484,10 +504,9 @@ ScVbaWindow::RangeSelection() throw (script::BasicErrorException, uno::RuntimeEx ::sal_Bool SAL_CALL ScVbaWindow::getDisplayGridlines() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_SHOWGRID ) ); sal_Bool bGrid = sal_True; - xProps->getPropertyValue( sName ) >>= bGrid; + getControllerProps()->getPropertyValue( sName ) >>= bGrid; return bGrid; } @@ -495,131 +514,125 @@ ScVbaWindow::getDisplayGridlines() throw (uno::RuntimeException) void SAL_CALL ScVbaWindow::setDisplayGridlines( ::sal_Bool _displaygridlines ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_SHOWGRID ) ); - xProps->setPropertyValue( sName, uno::makeAny( _displaygridlines )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _displaygridlines )); } ::sal_Bool SAL_CALL ScVbaWindow::getDisplayHeadings() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_COLROWHDR ) ); sal_Bool bHeading = sal_True; - xProps->getPropertyValue( sName ) >>= bHeading; + getControllerProps()->getPropertyValue( sName ) >>= bHeading; return bHeading; } void SAL_CALL ScVbaWindow::setDisplayHeadings( ::sal_Bool _bDisplayHeadings ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_COLROWHDR ) ); - xProps->setPropertyValue( sName, uno::makeAny( _bDisplayHeadings )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _bDisplayHeadings )); } ::sal_Bool SAL_CALL ScVbaWindow::getDisplayHorizontalScrollBar() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_HORSCROLL ) ); sal_Bool bHorizontalScrollBar = sal_True; - xProps->getPropertyValue( sName ) >>= bHorizontalScrollBar; + getControllerProps()->getPropertyValue( sName ) >>= bHorizontalScrollBar; return bHorizontalScrollBar; } void SAL_CALL ScVbaWindow::setDisplayHorizontalScrollBar( ::sal_Bool _bDisplayHorizontalScrollBar ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_HORSCROLL ) ); - xProps->setPropertyValue( sName, uno::makeAny( _bDisplayHorizontalScrollBar )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _bDisplayHorizontalScrollBar )); } ::sal_Bool SAL_CALL ScVbaWindow::getDisplayOutline() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_OUTLSYMB ) ); sal_Bool bOutline = sal_True; - xProps->getPropertyValue( sName ) >>= bOutline; + getControllerProps()->getPropertyValue( sName ) >>= bOutline; return bOutline; } void SAL_CALL ScVbaWindow::setDisplayOutline( ::sal_Bool _bDisplayOutline ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_OUTLSYMB ) ); - xProps->setPropertyValue( sName, uno::makeAny( _bDisplayOutline )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _bDisplayOutline )); } ::sal_Bool SAL_CALL ScVbaWindow::getDisplayVerticalScrollBar() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_VERTSCROLL ) ); sal_Bool bVerticalScrollBar = sal_True; - xProps->getPropertyValue( sName ) >>= bVerticalScrollBar; + getControllerProps()->getPropertyValue( sName ) >>= bVerticalScrollBar; return bVerticalScrollBar; } void SAL_CALL ScVbaWindow::setDisplayVerticalScrollBar( ::sal_Bool _bDisplayVerticalScrollBar ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_VERTSCROLL ) ); - xProps->setPropertyValue( sName, uno::makeAny( _bDisplayVerticalScrollBar )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _bDisplayVerticalScrollBar )); } ::sal_Bool SAL_CALL ScVbaWindow::getDisplayWorkbookTabs() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_SHEETTABS ) ); sal_Bool bWorkbookTabs = sal_True; - xProps->getPropertyValue( sName ) >>= bWorkbookTabs; + getControllerProps()->getPropertyValue( sName ) >>= bWorkbookTabs; return bWorkbookTabs; } void SAL_CALL ScVbaWindow::setDisplayWorkbookTabs( ::sal_Bool _bDisplayWorkbookTabs ) throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_SHEETTABS ) ); - xProps->setPropertyValue( sName, uno::makeAny( _bDisplayWorkbookTabs )); + getControllerProps()->setPropertyValue( sName, uno::makeAny( _bDisplayWorkbookTabs )); } ::sal_Bool SAL_CALL ScVbaWindow::getFreezePanes() throw (uno::RuntimeException) { - return m_xViewFreezable->hasFrozenPanes(); + uno::Reference< sheet::XViewFreezable > xViewFreezable( getController(), uno::UNO_QUERY_THROW ); + return xViewFreezable->hasFrozenPanes(); } void SAL_CALL ScVbaWindow::setFreezePanes( ::sal_Bool /*_bFreezePanes*/ ) throw (uno::RuntimeException) { - if( m_xViewSplitable->getIsWindowSplit() ) + uno::Reference< sheet::XViewPane > xViewPane( getController(), uno::UNO_QUERY_THROW ); + uno::Reference< sheet::XViewSplitable > xViewSplitable( xViewPane, uno::UNO_QUERY_THROW ); + uno::Reference< sheet::XViewFreezable > xViewFreezable( xViewPane, uno::UNO_QUERY_THROW ); + if( xViewSplitable->getIsWindowSplit() ) { // if there is a split we freeze at the split sal_Int32 nColumn = getSplitColumn(); sal_Int32 nRow = getSplitRow(); - m_xViewFreezable->freezeAtPosition( nColumn, nRow ); + xViewFreezable->freezeAtPosition( nColumn, nRow ); } else { // otherwise we freeze in the center of the visible sheet - table::CellRangeAddress aCellRangeAddress = m_xViewPane->getVisibleRange(); + table::CellRangeAddress aCellRangeAddress = xViewPane->getVisibleRange(); sal_Int32 nColumn = aCellRangeAddress.StartColumn + (( aCellRangeAddress.EndColumn - aCellRangeAddress.StartColumn )/2 ); sal_Int32 nRow = aCellRangeAddress.StartRow + (( aCellRangeAddress.EndRow - aCellRangeAddress.StartRow )/2 ); - m_xViewFreezable->freezeAtPosition( nColumn, nRow ); + xViewFreezable->freezeAtPosition( nColumn, nRow ); } } ::sal_Bool SAL_CALL ScVbaWindow::getSplit() throw (uno::RuntimeException) { - return m_xViewSplitable->getIsWindowSplit(); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + return xViewSplitable->getIsWindowSplit(); } void SAL_CALL @@ -627,14 +640,16 @@ ScVbaWindow::setSplit( ::sal_Bool _bSplit ) throw (uno::RuntimeException) { if( !_bSplit ) { - m_xViewSplitable->splitAtPosition(0,0); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + xViewSplitable->splitAtPosition(0,0); } else { + uno::Reference< sheet::XViewFreezable > xViewFreezable( getController(), uno::UNO_QUERY_THROW ); uno::Reference< excel::XRange > xRange = ActiveCell(); sal_Int32 nRow = xRange->getRow(); sal_Int32 nColumn = xRange->getColumn(); - m_xViewFreezable->freezeAtPosition( nColumn-1, nRow-1 ); + xViewFreezable->freezeAtPosition( nColumn-1, nRow-1 ); SplitAtDefinedPosition( sal_True ); } } @@ -642,7 +657,8 @@ ScVbaWindow::setSplit( ::sal_Bool _bSplit ) throw (uno::RuntimeException) sal_Int32 SAL_CALL ScVbaWindow::getSplitColumn() throw (uno::RuntimeException) { - return m_xViewSplitable->getSplitColumn(); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + return xViewSplitable->getSplitColumn(); } void SAL_CALL @@ -650,9 +666,10 @@ ScVbaWindow::setSplitColumn( sal_Int32 _splitcolumn ) throw (uno::RuntimeExcepti { if( getSplitColumn() != _splitcolumn ) { + uno::Reference< sheet::XViewFreezable > xViewFreezable( getController(), uno::UNO_QUERY_THROW ); sal_Bool bFrozen = getFreezePanes(); sal_Int32 nRow = getSplitRow(); - m_xViewFreezable->freezeAtPosition( _splitcolumn, nRow ); + xViewFreezable->freezeAtPosition( _splitcolumn, nRow ); SplitAtDefinedPosition( !bFrozen ); } } @@ -660,22 +677,23 @@ ScVbaWindow::setSplitColumn( sal_Int32 _splitcolumn ) throw (uno::RuntimeExcepti double SAL_CALL ScVbaWindow::getSplitHorizontal() throw (uno::RuntimeException) { - double fSplitHorizontal = m_xViewSplitable->getSplitHorizontal(); - double fHoriPoints = PixelsToPoints( m_xDevice, fSplitHorizontal, sal_True ); - return fHoriPoints; + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + return PixelsToPoints( getDevice(), xViewSplitable->getSplitHorizontal(), sal_True ); } void SAL_CALL ScVbaWindow::setSplitHorizontal( double _splithorizontal ) throw (uno::RuntimeException) { - double fHoriPixels = PointsToPixels( m_xDevice, _splithorizontal, sal_True ); - m_xViewSplitable->splitAtPosition( static_cast<sal_Int32>( fHoriPixels ), 0 ); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + double fHoriPixels = PointsToPixels( getDevice(), _splithorizontal, sal_True ); + xViewSplitable->splitAtPosition( static_cast< sal_Int32 >( fHoriPixels ), 0 ); } sal_Int32 SAL_CALL ScVbaWindow::getSplitRow() throw (uno::RuntimeException) { - sal_Int32 nValue = m_xViewSplitable->getSplitRow(); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + sal_Int32 nValue = xViewSplitable->getSplitRow(); return nValue ? nValue - 1 : nValue; } @@ -684,9 +702,10 @@ ScVbaWindow::setSplitRow( sal_Int32 _splitrow ) throw (uno::RuntimeException) { if( getSplitRow() != _splitrow ) { + uno::Reference< sheet::XViewFreezable > xViewFreezable( getController(), uno::UNO_QUERY_THROW ); sal_Bool bFrozen = getFreezePanes(); sal_Int32 nColumn = getSplitColumn(); - m_xViewFreezable->freezeAtPosition( nColumn , _splitrow ); + xViewFreezable->freezeAtPosition( nColumn , _splitrow ); SplitAtDefinedPosition( !bFrozen ); } } @@ -694,33 +713,33 @@ ScVbaWindow::setSplitRow( sal_Int32 _splitrow ) throw (uno::RuntimeException) double SAL_CALL ScVbaWindow::getSplitVertical() throw (uno::RuntimeException) { - double fSplitVertical = m_xViewSplitable->getSplitVertical(); - double fVertiPoints = PixelsToPoints( m_xDevice, fSplitVertical, sal_False ); - return fVertiPoints; + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + return PixelsToPoints( getDevice(), xViewSplitable->getSplitVertical(), sal_False ); } void SAL_CALL ScVbaWindow::setSplitVertical(double _splitvertical ) throw (uno::RuntimeException) { - double fVertiPixels = PointsToPixels( m_xDevice, _splitvertical, sal_False ); - m_xViewSplitable->splitAtPosition( 0, static_cast<sal_Int32>( fVertiPixels ) ); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + double fVertiPixels = PointsToPixels( getDevice(), _splitvertical, sal_False ); + xViewSplitable->splitAtPosition( 0, static_cast<sal_Int32>( fVertiPixels ) ); } void ScVbaWindow::SplitAtDefinedPosition(sal_Bool _bUnFreezePane) { - sal_Int32 nVertSplit = m_xViewSplitable->getSplitVertical(); - sal_Int32 nHoriSplit = m_xViewSplitable->getSplitHorizontal(); + uno::Reference< sheet::XViewSplitable > xViewSplitable( getController(), uno::UNO_QUERY_THROW ); + uno::Reference< sheet::XViewFreezable > xViewFreezable( xViewSplitable, uno::UNO_QUERY_THROW ); + sal_Int32 nVertSplit = xViewSplitable->getSplitVertical(); + sal_Int32 nHoriSplit = xViewSplitable->getSplitHorizontal(); if( _bUnFreezePane ) - { - m_xViewFreezable->freezeAtPosition(0,0); - } - m_xViewSplitable->splitAtPosition(nHoriSplit, nVertSplit); + xViewFreezable->freezeAtPosition(0,0); + xViewSplitable->splitAtPosition(nHoriSplit, nVertSplit); } uno::Any SAL_CALL ScVbaWindow::getZoom() throw (uno::RuntimeException) { - uno::Reference< beans::XPropertySet > xProps( m_xModel->getCurrentController(), uno::UNO_QUERY_THROW ); + uno::Reference< beans::XPropertySet > xProps = getControllerProps(); rtl::OUString sName( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_ZOOMTYPE ) ); sal_Int16 nZoomType = view::DocumentZoomType::PAGE_WIDTH; xProps->getPropertyValue( sName ) >>= nZoomType; @@ -785,6 +804,7 @@ ScVbaWindow::setView( const uno::Any& _view) throw (uno::RuntimeException) default: DebugHelper::exception(SbERR_BAD_PARAMETER, rtl::OUString() ); } + // !! TODO !! get view shell from controller ScTabViewShell* pViewShell = excel::getBestViewShell( m_xModel ); if ( pViewShell ) dispatchExecute( pViewShell, nSlot ); @@ -793,7 +813,7 @@ ScVbaWindow::setView( const uno::Any& _view) throw (uno::RuntimeException) uno::Reference< excel::XRange > SAL_CALL ScVbaWindow::getVisibleRange() throw (uno::RuntimeException) { - uno::Reference< container::XIndexAccess > xPanesIA( m_xViewPane, uno::UNO_QUERY_THROW ); + uno::Reference< container::XIndexAccess > xPanesIA( getController(), uno::UNO_QUERY_THROW ); uno::Reference< sheet::XViewPane > xTopLeftPane( xPanesIA->getByIndex( 0 ), uno::UNO_QUERY_THROW ); uno::Reference< excel::XPane > xPane( new ScVbaPane( this, mxContext, m_xModel, xTopLeftPane ) ); return xPane->getVisibleRange(); @@ -803,7 +823,7 @@ sal_Int32 SAL_CALL ScVbaWindow::PointsToScreenPixelsX(sal_Int32 _points) throw (css::script::BasicErrorException, css::uno::RuntimeException) { sal_Int32 nHundredthsofOneMillimeters = Millimeter::getInHundredthsOfOneMillimeter( _points ); - double fConvertFactor = (m_xDevice->getInfo().PixelPerMeterX/100000); + double fConvertFactor = (getDevice()->getInfo().PixelPerMeterX/100000); return static_cast<sal_Int32>(fConvertFactor * nHundredthsofOneMillimeters ); } @@ -811,7 +831,7 @@ sal_Int32 SAL_CALL ScVbaWindow::PointsToScreenPixelsY(sal_Int32 _points) throw (css::script::BasicErrorException, css::uno::RuntimeException) { sal_Int32 nHundredthsofOneMillimeters = Millimeter::getInHundredthsOfOneMillimeter( _points ); - double fConvertFactor = (m_xDevice->getInfo().PixelPerMeterY/100000); + double fConvertFactor = (getDevice()->getInfo().PixelPerMeterY/100000); return static_cast<sal_Int32>(fConvertFactor * nHundredthsofOneMillimeters ); } @@ -819,6 +839,7 @@ void SAL_CALL ScVbaWindow::PrintOut( const css::uno::Any& From, const css::uno::Any&To, const css::uno::Any& Copies, const css::uno::Any& Preview, const css::uno::Any& ActivePrinter, const css::uno::Any& PrintToFile, const css::uno::Any& Collate, const css::uno::Any& PrToFileName ) throw (css::script::BasicErrorException, css::uno::RuntimeException) { // need test, print current active sheet + // !! TODO !! get view shell from controller PrintOutHelper( excel::getBestViewShell( m_xModel ), From, To, Copies, Preview, ActivePrinter, PrintToFile, Collate, PrToFileName, sal_True ); } @@ -826,6 +847,7 @@ void SAL_CALL ScVbaWindow::PrintPreview( const css::uno::Any& EnableChanges ) throw (css::script::BasicErrorException, css::uno::RuntimeException) { // need test, print preview current active sheet + // !! TODO !! get view shell from controller PrintPreviewHelper( EnableChanges, excel::getBestViewShell( m_xModel ) ); } diff --git a/sc/source/ui/vba/vbawindow.hxx b/sc/source/ui/vba/vbawindow.hxx index d58d2a07cb4b..d183ee346185 100644 --- a/sc/source/ui/vba/vbawindow.hxx +++ b/sc/source/ui/vba/vbawindow.hxx @@ -27,7 +27,6 @@ #ifndef SC_VBA_WINDOW_HXX #define SC_VBA_WINDOW_HXX -#include <cppuhelper/implbase1.hxx> #include <ooo/vba/excel/XWindow.hpp> #include <com/sun/star/uno/XComponentContext.hpp> #include <com/sun/star/sheet/XViewPane.hpp> @@ -46,19 +45,30 @@ typedef cppu::ImplInheritanceHelper1< VbaWindowBase, ov::excel::XWindow > Window class ScVbaWindow : public WindowImpl_BASE { private: - css::uno::Reference< css::sheet::XViewPane > m_xViewPane; - css::uno::Reference< css::sheet::XViewFreezable > m_xViewFreezable; - css::uno::Reference< css::sheet::XViewSplitable > m_xViewSplitable; css::uno::Reference< ov::excel::XPane > m_xPane; - css::uno::Reference< css::awt::XDevice > m_xDevice; + void init(); + css::uno::Reference< css::beans::XPropertySet > getControllerProps() throw (css::uno::RuntimeException); + css::uno::Reference< css::beans::XPropertySet > getFrameProps() throw (css::uno::RuntimeException); + css::uno::Reference< css::awt::XDevice > getDevice() throw (css::uno::RuntimeException); + protected: void SplitAtDefinedPosition(sal_Bool _bUnFreezePane); + public: - void Scroll( const css::uno::Any& Down, const css::uno::Any& Up, const css::uno::Any& ToRight, const css::uno::Any& ToLeft, bool bLargeScroll = false ) throw (css::uno::RuntimeException); + void Scroll( const css::uno::Any& Down, const css::uno::Any& Up, const css::uno::Any& ToRight, const css::uno::Any& ToLeft, bool bLargeScroll = false ) throw (css::uno::RuntimeException); + public: - ScVbaWindow( const css::uno::Reference< ov::XHelperInterface >& xParent, const css::uno::Reference< css::uno::XComponentContext >& xContext, const css::uno::Reference< css::frame::XModel >& xModel ); - ScVbaWindow( css::uno::Sequence< css::uno::Any > const& aArgs, css::uno::Reference< css::uno::XComponentContext > const& xContext ); + ScVbaWindow( + const css::uno::Reference< ov::XHelperInterface >& xParent, + const css::uno::Reference< css::uno::XComponentContext >& xContext, + const css::uno::Reference< css::frame::XModel >& xModel, + const css::uno::Reference< css::frame::XController >& xController ) + throw (css::uno::RuntimeException); + ScVbaWindow( + const css::uno::Sequence< css::uno::Any >& aArgs, + const css::uno::Reference< css::uno::XComponentContext >& xContext ) + throw (css::uno::RuntimeException); // XWindow virtual css::uno::Reference< ov::excel::XRange > SAL_CALL ActiveCell( ) throw (css::script::BasicErrorException, css::uno::RuntimeException); diff --git a/sc/source/ui/vba/vbawindows.cxx b/sc/source/ui/vba/vbawindows.cxx index 3ddc5f5b3b45..80f215629126 100644 --- a/sc/source/ui/vba/vbawindows.cxx +++ b/sc/source/ui/vba/vbawindows.cxx @@ -53,7 +53,9 @@ uno::Reference< XHelperInterface > lcl_createWorkbookHIParent( const uno::Refere uno::Any ComponentToWindow( const uno::Any& aSource, uno::Reference< uno::XComponentContext > & xContext, const uno::Any& aApplication ) { uno::Reference< frame::XModel > xModel( aSource, uno::UNO_QUERY_THROW ); - uno::Reference< excel::XWindow > xWin( new ScVbaWindow( lcl_createWorkbookHIParent( xModel, xContext, aApplication ), xContext,xModel ) ); + // !! TODO !! iterate over all controllers + uno::Reference< frame::XController > xController( xModel->getCurrentController(), uno::UNO_SET_THROW ); + uno::Reference< excel::XWindow > xWin( new ScVbaWindow( lcl_createWorkbookHIParent( xModel, xContext, aApplication ), xContext, xModel, xController ) ); return uno::makeAny( xWin ); } @@ -138,8 +140,10 @@ public: { m_windows.push_back( xNext ); uno::Reference< frame::XModel > xModel( xNext, uno::UNO_QUERY_THROW ); // that the spreadsheetdocument is a xmodel is a given + // !! TODO !! iterate over all controllers + uno::Reference< frame::XController > xController( xModel->getCurrentController(), uno::UNO_SET_THROW ); uno::Reference< XHelperInterface > xTemp; // temporary needed for g++ 3.3.5 - ScVbaWindow window( xTemp, m_xContext, xModel ); + ScVbaWindow window( xTemp, m_xContext, xModel, xController ); rtl::OUString sCaption; window.getCaption() >>= sCaption; namesToIndices[ sCaption ] = nIndex++; diff --git a/sc/source/ui/vba/vbaworkbook.cxx b/sc/source/ui/vba/vbaworkbook.cxx index 1e2acd6252b8..e0d50c592e6c 100644 --- a/sc/source/ui/vba/vbaworkbook.cxx +++ b/sc/source/ui/vba/vbaworkbook.cxx @@ -218,14 +218,9 @@ ScVbaWorkbook::getActiveSheet() throw (uno::RuntimeException) { uno::Reference< frame::XModel > xModel( getCurrentExcelDoc( mxContext ), uno::UNO_SET_THROW ); uno::Reference< sheet::XSpreadsheetView > xView( xModel->getCurrentController(), uno::UNO_QUERY_THROW ); - uno::Reference< beans::XPropertySet > xSheetProps( xView->getActiveSheet(), uno::UNO_QUERY_THROW ); - // #162503# return the original document module wrapper object, instead of a new instance - ::rtl::OUString aCodeName; - xSheetProps->getPropertyValue( ::rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_CODENAME ) ) ) >>= aCodeName; - ScDocShell* pShell = excel::getDocShell( xModel ); - if( !pShell ) - throw uno::RuntimeException(); - return uno::Reference< excel::XWorksheet >( getUnoDocModule( aCodeName, pShell ), uno::UNO_QUERY_THROW ); + uno::Reference< sheet::XSpreadsheet > xSheet( xView->getActiveSheet(), uno::UNO_SET_THROW ); + // #162503# return the original sheet module wrapper object, instead of a new instance + return uno::Reference< excel::XWorksheet >( excel::getUnoSheetModuleObj( xSheet ), uno::UNO_QUERY_THROW ); } uno::Any SAL_CALL diff --git a/sc/source/ui/vba/vbaworkbooks.cxx b/sc/source/ui/vba/vbaworkbooks.cxx index a9f1970be34e..9fec863f5463 100644 --- a/sc/source/ui/vba/vbaworkbooks.cxx +++ b/sc/source/ui/vba/vbaworkbooks.cxx @@ -134,18 +134,6 @@ void setUpDocumentModules( const uno::Reference< sheet::XSpreadsheetDocument >& } } } - - /* Trigger the Workbook_Open event, event processor will register - itself as listener for specific events. */ - try - { - uno::Reference< script::vba::XVBAEventProcessor > xVbaEvents( pShell->GetDocument()->GetVbaEventProcessor(), uno::UNO_SET_THROW ); - uno::Sequence< uno::Any > aArgs; - xVbaEvents->processVbaEvent( script::vba::VBAEventId::WORKBOOK_OPEN, aArgs ); - } - catch( uno::Exception& ) - { - } } } @@ -157,19 +145,14 @@ getWorkbook( uno::Reference< uno::XComponentContext >& xContext, const uno::Refe if( !xModel.is() ) return uno::Any(); - ScDocShell* pShell = excel::getDocShell( xModel ); - if ( pShell ) + uno::Reference< excel::XWorkbook > xWb( getVBADocument( xModel ), uno::UNO_QUERY ); + if ( xWb.is() ) { - String sCodeName = pShell->GetDocument()->GetCodeName(); - uno::Reference< uno::XInterface > xIf = getUnoDocModule( sCodeName, pShell ); - if ( xIf.is() ) - { - OSL_TRACE(" *** Returning Module uno Object *** "); - return uno::makeAny( xIf ); - } + OSL_TRACE(" *** Returning Module uno Object *** "); + return uno::Any( xWb ); } - ScVbaWorkbook *pWb = new ScVbaWorkbook( xParent, xContext, xModel ); + ScVbaWorkbook *pWb = new ScVbaWorkbook( xParent, xContext, xModel ); return uno::Any( uno::Reference< excel::XWorkbook > (pWb) ); } diff --git a/sc/source/ui/vba/vbaworksheets.cxx b/sc/source/ui/vba/vbaworksheets.cxx index bd21cb396c66..cf74f90b5941 100644 --- a/sc/source/ui/vba/vbaworksheets.cxx +++ b/sc/source/ui/vba/vbaworksheets.cxx @@ -68,23 +68,6 @@ typedef std::vector< uno::Reference< sheet::XSpreadsheet > > SheetMap; // #FIXME #TODO the implementation of the Sheets collections sucks, // e.g. there is no support for tracking sheets added/removed from the collection -uno::Reference< uno::XInterface > -lcl_getModulAsUnoObject( const uno::Reference< sheet::XSpreadsheet >& xSheet, const uno::Reference< frame::XModel >& xModel ) throw ( uno::RuntimeException ) -{ - uno::Reference< uno::XInterface > xRet; - if ( !xSheet.is() ) - throw uno::RuntimeException(); - uno::Reference< beans::XPropertySet > xProps( xSheet, uno::UNO_QUERY_THROW ); - rtl::OUString sName; - xProps->getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( SC_UNO_CODENAME ) ) ) >>= sName; - - ScDocShell* pShell = excel::getDocShell( xModel ); - - if ( pShell ) - xRet = getUnoDocModule( sName, pShell ); - return xRet; -} - class WorkSheetsEnumeration : public SheetEnumeration_BASE { SheetMap mSheetMap; @@ -173,16 +156,16 @@ public: virtual uno::Any SAL_CALL nextElement( ) throw (container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException) { uno::Reference< sheet::XSpreadsheet > xSheet( m_xEnumeration->nextElement(), uno::UNO_QUERY_THROW ); - uno::Reference< uno::XInterface > xIf = lcl_getModulAsUnoObject( xSheet, m_xModel ); + uno::Reference< XHelperInterface > xIf = excel::getUnoSheetModuleObj( xSheet ); uno::Any aRet; if ( !xIf.is() ) - { + { // if the Sheet is in a document created by the api unfortunately ( at the // moment, it actually wont have the special Document modules uno::Reference< excel::XWorksheet > xNewSheet( new ScVbaWorksheet( m_xParent, m_xContext, xSheet, m_xModel ) ); aRet <<= xNewSheet; - } - else + } + else aRet <<= xIf; return aRet; } @@ -220,7 +203,7 @@ uno::Any ScVbaWorksheets::createCollectionObject( const uno::Any& aSource ) { uno::Reference< sheet::XSpreadsheet > xSheet( aSource, uno::UNO_QUERY ); - uno::Reference< XInterface > xIf = lcl_getModulAsUnoObject( xSheet, mxModel ); + uno::Reference< XHelperInterface > xIf = excel::getUnoSheetModuleObj( xSheet ); uno::Any aRet; if ( !xIf.is() ) { diff --git a/sc/util/makefile.mk b/sc/util/makefile.mk index dd0a6043c8fd..a7ce2f9407dc 100644 --- a/sc/util/makefile.mk +++ b/sc/util/makefile.mk @@ -311,6 +311,7 @@ SHL9STDLIBS= \ $(VCLLIB) \ $(TKLIB) \ $(MSFILTERLIB) \ + $(UNOTOOLSLIB) \ $(FORLIB) SHL9DEPN=$(SHL1TARGETN) $(SHL8TARGETN) |