[Libreoffice-commits] core.git: offapi/com sw/inc sw/source

Jan-Marek Glogowski glogow at fbihome.de
Wed Feb 12 02:23:32 PST 2014


 offapi/com/sun/star/text/MailMerge.idl |    7 +++++++
 sw/inc/dbmgr.hxx                       |    4 ++--
 sw/source/ui/dbui/dbmgr.cxx            |    7 ++++++-
 sw/source/ui/inc/unomailmerge.hxx      |   15 +++++++++++++--
 sw/source/ui/uno/unomailmerge.cxx      |   33 ++++++++++++++++++++++++++++++++-
 5 files changed, 60 insertions(+), 6 deletions(-)

New commits:
commit 1a12777f46954045afbe8fffa6dd199b4b338762
Author: Jan-Marek Glogowski <glogow at fbihome.de>
Date:   Sun Dec 22 17:42:20 2013 +0100

    Export MailMerge cancel functionality via UNO.
    
    If you start a mail merge jobs via UNO, there is no way to cancel
    it. But the functionality is already implemented and used by the
    LO internal mail merge dialogs.
    
    This patch adds an optional XCancellable interface to the MailMerge
    service and implements it in the SwXMailMerge class.
    
    As the XJob::execute function already uses the SolarMutex to
    prevent parallel runs, XCancellable::cancel can be implemented by
    storing the SwNewDBMgr in the private variable m_pMgr, protected by
    a mutex.
    
    The bCancel member has to be converted from a bitfield value to a
    real boolean, because otherwise all bitfield values would have to
    be protected by a mutex. Bitfield assignments aren't atomic as you
    always have to replace at least a byte.
    
    Change-Id: I007cc23fdf04ccfca7d3cd6180b0e17e99f53061
    Reviewed-on: https://gerrit.libreoffice.org/7190
    Reviewed-by: Michael Stahl <mstahl at redhat.com>
    Tested-by: Michael Stahl <mstahl at redhat.com>

diff --git a/offapi/com/sun/star/text/MailMerge.idl b/offapi/com/sun/star/text/MailMerge.idl
index f669d71..9741182 100644
--- a/offapi/com/sun/star/text/MailMerge.idl
+++ b/offapi/com/sun/star/text/MailMerge.idl
@@ -26,6 +26,7 @@
 #include <com/sun/star/beans/XPropertySet.idl>
 #include <com/sun/star/text/XMailMergeBroadcaster.idl>
 #include <com/sun/star/sdb/DataAccessDescriptor.idl>
+#include <com/sun/star/util/XCancellable.idl>
 
 
  module com {  module sun {  module star {  module text {
@@ -51,6 +52,12 @@ published service MailMerge
      */
     interface com::sun::star::task::XJob;
 
+    /** interface to cancel the current mail merge job.
+
+        @since LibreOffice 4.3
+     */
+    [optional] interface com::sun::star::util::XCancellable;
+
     /** interface to access the services properties.
      */
     interface com::sun::star::beans::XPropertySet;
diff --git a/sw/inc/dbmgr.hxx b/sw/inc/dbmgr.hxx
index 009584f..e5ab96e 100644
--- a/sw/inc/dbmgr.hxx
+++ b/sw/inc/dbmgr.hxx
@@ -190,10 +190,9 @@ friend class SwConnectionDisposedListener_Impl;
     OUString            sEMailAddrFld;      ///< Mailing: Column name of email address.
     OUString            sSubject;           ///< Mailing: Subject
     OUString            sAttached;          ///< Mailing: Attached Files.
+    sal_Bool            bCancel;            ///< Mail merge canceled.
     sal_Bool            bInitDBFields : 1;
     sal_Bool            bSingleJobs : 1;    ///< Printing job when called from Basic.
-    sal_Bool            bCancel : 1;        ///< Mail merge save canceled.
-
     sal_Bool            bInMerge    : 1;    ///< merge process active
     sal_Bool            bMergeSilent : 1;   ///< suppress display of dialogs/boxes (used when called over API)
     sal_Bool            bMergeLock : 1;     /**< prevent update of database fields while document is
@@ -233,6 +232,7 @@ public:
     /// Merging of data records into fields.
     sal_Bool            MergeNew( const SwMergeDescriptor& rMergeDesc );
     sal_Bool            Merge(SwWrtShell* pSh);
+    void                MergeCancel();
 
     /// Initialize data fields that lack name of database.
     inline sal_Bool     IsInitDBFields() const  { return bInitDBFields; }
diff --git a/sw/source/ui/dbui/dbmgr.cxx b/sw/source/ui/dbui/dbmgr.cxx
index 63d70d1..192d29e 100644
--- a/sw/source/ui/dbui/dbmgr.cxx
+++ b/sw/source/ui/dbui/dbmgr.cxx
@@ -1355,10 +1355,15 @@ sal_Bool SwNewDBMgr::MergeMailFiles(SwWrtShell* pSourceShell,
     return bNoError;
 }
 
+void SwNewDBMgr::MergeCancel()
+{
+    bCancel = sal_True;
+}
+
 IMPL_LINK_INLINE_START( SwNewDBMgr, PrtCancelHdl, Button *, pButton )
 {
     pButton->GetParent()->Hide();
-    bCancel = sal_True;
+    MergeCancel();
     return 0;
 }
 IMPL_LINK_INLINE_END( SwNewDBMgr, PrtCancelHdl, Button *, pButton )
diff --git a/sw/source/ui/inc/unomailmerge.hxx b/sw/source/ui/inc/unomailmerge.hxx
index 2be74c6..09d4beb 100644
--- a/sw/source/ui/inc/unomailmerge.hxx
+++ b/sw/source/ui/inc/unomailmerge.hxx
@@ -20,7 +20,7 @@
 #ifndef INCLUDED_SW_SOURCE_UI_INC_UNOMAILMERGE_HXX
 #define INCLUDED_SW_SOURCE_UI_INC_UNOMAILMERGE_HXX
 
-#include <cppuhelper/implbase5.hxx>
+#include <cppuhelper/implbase6.hxx>
 #include <cppuhelper/interfacecontainer.hxx>
 #include <unotools/configitem.hxx>
 
@@ -31,6 +31,7 @@
 #include <com/sun/star/lang/XServiceInfo.hpp>
 #include <com/sun/star/beans/PropertyChangeEvent.hpp>
 #include <com/sun/star/text/XMailMergeBroadcaster.hpp>
+#include <com/sun/star/util/XCancellable.hpp>
 #include <svl/itemprop.hxx>
 #include <sfx2/objsh.hxx>
 
@@ -76,16 +77,22 @@ typedef cppu::OMultiTypeInterfaceContainerHelperVar
 
 ////////////////////////////////////////////////////////////
 
+class SwNewDBMgr;
+class MailMergeExecuteFinalizer;
+
 class SwXMailMerge :
-    public cppu::WeakImplHelper5
+    public cppu::WeakImplHelper6
     <
         com::sun::star::task::XJob,
+        com::sun::star::util::XCancellable,
         com::sun::star::beans::XPropertySet,
         com::sun::star::text::XMailMergeBroadcaster,
         com::sun::star::lang::XComponent,
         com::sun::star::lang::XServiceInfo
     >
 {
+    friend class MailMergeExecuteFinalizer;
+
     cppu::OInterfaceContainerHelper     aEvtListeners;
     cppu::OInterfaceContainerHelper     aMergeListeners;
     OPropertyListenerContainerHelper    aPropListeners;
@@ -133,6 +140,7 @@ class SwXMailMerge :
     com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyValue > aSaveFilterData;
 
     sal_Bool        bDisposing;
+    SwNewDBMgr     *m_pMgr;
 
     void    launchEvent( const com::sun::star::beans::PropertyChangeEvent &rEvt ) const;
 
@@ -150,6 +158,9 @@ public:
     // XJob
     virtual ::com::sun::star::uno::Any SAL_CALL execute( const ::com::sun::star::uno::Sequence< ::com::sun::star::beans::NamedValue >& Arguments ) throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException);
 
+    // XCancellable
+    virtual void SAL_CALL cancel() throw (com::sun::star::uno::RuntimeException);
+
     // XPropertySet
     virtual ::com::sun::star::uno::Reference< ::com::sun::star::beans::XPropertySetInfo > SAL_CALL getPropertySetInfo(  ) throw (::com::sun::star::uno::RuntimeException);
     virtual void SAL_CALL setPropertyValue( const OUString& aPropertyName, const ::com::sun::star::uno::Any& aValue ) throw (::com::sun::star::beans::UnknownPropertyException, ::com::sun::star::beans::PropertyVetoException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::lang::WrappedTargetException, ::com::sun::star::uno::RuntimeException);
diff --git a/sw/source/ui/uno/unomailmerge.cxx b/sw/source/ui/uno/unomailmerge.cxx
index b6c93a0..2e839d7 100644
--- a/sw/source/ui/uno/unomailmerge.cxx
+++ b/sw/source/ui/uno/unomailmerge.cxx
@@ -382,7 +382,8 @@ SwXMailMerge::SwXMailMerge() :
     bSendAsHTML(sal_False),
     bSendAsAttachment(sal_False),
     bSaveAsSingleFile(sal_False),
-    bDisposing(sal_False)
+    bDisposing(sal_False),
+    m_pMgr(0)
 {
     // create empty document
     // like in: SwModule::InsertEnv (appenv.cxx)
@@ -411,11 +412,31 @@ SwXMailMerge::~SwXMailMerge()
     }
 }
 
+// Guarantee object consistence in case of an exception
+class MailMergeExecuteFinalizer {
+public:
+    MailMergeExecuteFinalizer(SwXMailMerge *mailmerge) {
+        OSL_ENSURE( mailmerge, "mailmerge object missing" );
+        this->m_aMailMerge = mailmerge;
+    }
+    ~MailMergeExecuteFinalizer() {
+        osl::MutexGuard pMgrGuard( GetMailMergeMutex() );
+        m_aMailMerge->m_pMgr = 0;
+    }
+
+private:
+    // Disallow copy
+    MailMergeExecuteFinalizer(const MailMergeExecuteFinalizer&) {}
+
+    SwXMailMerge *m_aMailMerge;
+};
+
 uno::Any SAL_CALL SwXMailMerge::execute(
         const uno::Sequence< beans::NamedValue >& rArguments )
     throw (IllegalArgumentException, Exception, RuntimeException)
 {
     SolarMutexGuard aGuard;
+    MailMergeExecuteFinalizer aFinalizer(this);
 
     // get property values to be used
     // (use values from the service as default and override them with
@@ -655,6 +676,7 @@ uno::Any SAL_CALL SwXMailMerge::execute(
     //force layout creation
     rSh.CalcLayout();
     OSL_ENSURE( pMgr, "database manager missing" );
+    m_pMgr = pMgr;
 
     SwMergeDescriptor aMergeDesc( nMergeType, rSh, aDescriptor );
 
@@ -798,6 +820,15 @@ uno::Any SAL_CALL SwXMailMerge::execute(
     return makeAny( sal_True );
 }
 
+void SAL_CALL SwXMailMerge::cancel() throw (com::sun::star::uno::RuntimeException)
+{
+    // Cancel may be called from a second thread, so this protects from m_pMgr
+    /// cleanup in the execute function.
+    osl::MutexGuard pMgrGuard( GetMailMergeMutex() );
+    if (m_pMgr)
+        m_pMgr->MergeCancel();
+}
+
 void SwXMailMerge::LaunchMailMergeEvent( const MailMergeEvent &rEvt ) const
 {
     cppu::OInterfaceIteratorHelper aIt( ((SwXMailMerge *) this)->aMergeListeners );


More information about the Libreoffice-commits mailing list