[Libreoffice-commits] .: 6 commits - offapi/com offapi/UnoApi_offapi.mk sc/source sd/source sfx2/inc sfx2/Library_sfx.mk sfx2/Package_inc.mk sfx2/source sw/source ucb/source

Libreoffice Gerrit user logerrit at kemper.freedesktop.org
Thu Oct 11 08:46:45 PDT 2012


 offapi/UnoApi_offapi.mk                        |    1 
 offapi/com/sun/star/document/XCmisDocument.idl |   40 +++
 sc/source/ui/view/tabvwsh.cxx                  |    2 
 sd/source/ui/slideshow/slideshowimpl.cxx       |    4 
 sd/source/ui/view/drvwshrg.cxx                 |    2 
 sd/source/ui/view/outlnvsh.cxx                 |    2 
 sfx2/Library_sfx.mk                            |    1 
 sfx2/Package_inc.mk                            |    1 
 sfx2/inc/sfx2/infobar.hxx                      |   77 ++++++
 sfx2/inc/sfx2/sfx.hrc                          |    2 
 sfx2/inc/sfx2/sfxbasecontroller.hxx            |    5 
 sfx2/inc/sfx2/sfxbasemodel.hxx                 |   30 ++
 sfx2/inc/sfx2/sfxsids.hrc                      |    1 
 sfx2/inc/sfx2/viewfrm.hxx                      |   10 
 sfx2/source/appl/appreg.cxx                    |    2 
 sfx2/source/dialog/infobar.cxx                 |  283 +++++++++++++++++++++++++
 sfx2/source/doc/sfxbasemodel.cxx               |   99 ++++++++
 sfx2/source/view/sfxbasecontroller.cxx         |   64 +++++
 sfx2/source/view/view.src                      |   12 +
 sfx2/source/view/viewfrm.cxx                   |   33 ++
 sw/source/core/crsr/crstrvl.cxx                |    2 
 sw/source/ui/uiview/view0.cxx                  |    2 
 sw/source/ui/web/wview.cxx                     |    2 
 ucb/source/ucp/cmis/cmis_content.cxx           |  224 +++++++++++++++++++
 ucb/source/ucp/cmis/cmis_url.cxx               |    6 
 ucb/source/ucp/cmis/cmis_url.hxx               |    1 
 26 files changed, 901 insertions(+), 7 deletions(-)

New commits:
commit d45feee6148ed947cae41ae1742361dd50b7c9c4
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Thu Oct 11 14:31:09 2012 +0200

    CMIS UCP: fixed crash when cancelling authentication dialog
    
    Change-Id: Ic7d8382df31e7489497a6bdb14bfa8c6317f11f4

diff --git a/ucb/source/ucp/cmis/cmis_content.cxx b/ucb/source/ucp/cmis/cmis_content.cxx
index 0baee4f..ae448ed 100644
--- a/ucb/source/ucp/cmis/cmis_content.cxx
+++ b/ucb/source/ucp/cmis/cmis_content.cxx
@@ -274,6 +274,11 @@ namespace cmis
                         rUsername, rPassword, OUSTR_TO_STDSTR( m_aURL.getRepositoryId( ) ) );
                 m_pProvider->registerSession( sSessionId, m_pSession );
             }
+            else
+            {
+                // Silently fail as the user cancelled the authentication
+                throw uno::RuntimeException( );
+            }
         }
         return m_pSession;
     }
@@ -322,7 +327,7 @@ namespace cmis
                                 ucb::IOErrorCode_GENERAL,
                                 uno::Sequence< uno::Any >( 0 ),
                                 xEnv,
-                                rtl::OUString::createFromAscii( e.what() ) );
+                                rtl::OUString::createFromAscii( e.what( ) ) );
         }
         return bIsFolder;
     }
commit c767f82403635221af58998a3265e38e8d19e76d
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Thu Oct 11 14:14:48 2012 +0200

    CMIS: Implemented the CheckOut button of the InfoBar
    
    Implementing it needed:
     + Adding XCmisDocument::checkOut method and implement it in SfxBaseModel
     + Moving the CMIS properties loading into a SfxBaseModel private method to
    factorize code.
     + Adding the SfxInfoBarContainerChild registration in all modules
    
    Change-Id: I35bcb53cd2feff354aa5d9245897d0631cc924a0

diff --git a/offapi/com/sun/star/document/XCmisDocument.idl b/offapi/com/sun/star/document/XCmisDocument.idl
index 246a1b7..82ac4ff 100644
--- a/offapi/com/sun/star/document/XCmisDocument.idl
+++ b/offapi/com/sun/star/document/XCmisDocument.idl
@@ -19,6 +19,11 @@ module com {   module sun {   module star {   module document {
   */
 interface XCmisDocument : com::sun::star::uno::XInterface
 {
+    /** Check out the document into a private working copy on the
+        server, and update the loaded document to reflect this change.
+     */
+    void checkOut( );
+
     /** Contains the properties values named after their CMIS ID.
      */
     [attribute] com::sun::star::beans::PropertyValues CmisPropertiesValues;
diff --git a/sc/source/ui/view/tabvwsh.cxx b/sc/source/ui/view/tabvwsh.cxx
index 4e744a0..06f6dd4 100644
--- a/sc/source/ui/view/tabvwsh.cxx
+++ b/sc/source/ui/view/tabvwsh.cxx
@@ -35,6 +35,7 @@
 #include <sfx2/viewfrm.hxx>
 #include <sfx2/bindings.hxx>
 #include <sfx2/app.hxx>
+#include <sfx2/infobar.hxx>
 
 #include "tabvwsh.hxx"
 #include "docsh.hxx"
@@ -59,6 +60,7 @@ SFX_IMPL_INTERFACE(ScTabViewShell,SfxViewShell,ScResId(SCSTR_TABVIEWSHELL))
 
     SFX_CHILDWINDOW_REGISTRATION(FID_INPUTLINE_STATUS);
     SFX_CHILDWINDOW_REGISTRATION(SfxTemplateDialogWrapper::GetChildWindowId());
+    SFX_CHILDWINDOW_REGISTRATION(SfxInfoBarContainerChild::GetChildWindowId());
     SFX_CHILDWINDOW_CONTEXT_REGISTRATION(SID_NAVIGATOR);
     SFX_CHILDWINDOW_REGISTRATION(SID_TASKPANE);
     SFX_CHILDWINDOW_REGISTRATION(ScNameDlgWrapper::GetChildWindowId());
diff --git a/sd/source/ui/slideshow/slideshowimpl.cxx b/sd/source/ui/slideshow/slideshowimpl.cxx
index e085f47..2cc9d30 100644
--- a/sd/source/ui/slideshow/slideshowimpl.cxx
+++ b/sd/source/ui/slideshow/slideshowimpl.cxx
@@ -44,6 +44,7 @@
 
 #include <toolkit/unohlp.hxx>
 
+#include <sfx2/infobar.hxx>
 #include <sfx2/imagemgr.hxx>
 #include <sfx2/request.hxx>
 #include <sfx2/docfile.hxx>
@@ -2570,7 +2571,8 @@ FncGetChildWindowId aShowChildren[] =
     &SvxIMapDlgChildWindow::GetChildWindowId,
     &SvxHlinkDlgWrapper::GetChildWindowId,
     &SfxTemplateDialogWrapper::GetChildWindowId,
-    &GalleryChildWindow::GetChildWindowId
+    &GalleryChildWindow::GetChildWindowId,
+    &SfxInfoBarContainerChild::GetChildWindowId
 };
 
 #define NAVIGATOR_CHILD_MASK        0x80000000UL
diff --git a/sd/source/ui/view/drvwshrg.cxx b/sd/source/ui/view/drvwshrg.cxx
index 6f21afe..51b9e27 100644
--- a/sd/source/ui/view/drvwshrg.cxx
+++ b/sd/source/ui/view/drvwshrg.cxx
@@ -29,6 +29,7 @@
 
 #include "DrawViewShell.hxx"
 #include <sfx2/templdlg.hxx>
+#include <sfx2/infobar.hxx>
 
 #include <svx/fontwork.hxx>
 #include <svx/bmpmask.hxx>
@@ -77,6 +78,7 @@ SFX_IMPL_INTERFACE(DrawViewShell, SfxShell, SdResId(STR_DRAWVIEWSHELL))
     SFX_POPUPMENU_REGISTRATION( SdResId(RID_DRAW_TEXTOBJ_INSIDE_POPUP) );
     SFX_CHILDWINDOW_CONTEXT_REGISTRATION( SID_NAVIGATOR );
     SFX_CHILDWINDOW_REGISTRATION( SfxTemplateDialogWrapper::GetChildWindowId() );
+    SFX_CHILDWINDOW_REGISTRATION( SfxInfoBarContainerChild::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( SvxFontWorkChildWindow::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( SvxColorChildWindow::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( AnimationChildWindow::GetChildWindowId() );
diff --git a/sd/source/ui/view/outlnvsh.cxx b/sd/source/ui/view/outlnvsh.cxx
index fbf2b18..2b93ed6 100644
--- a/sd/source/ui/view/outlnvsh.cxx
+++ b/sd/source/ui/view/outlnvsh.cxx
@@ -36,6 +36,7 @@
 #include <svx/hyperdlg.hxx>
 #include <svx/zoomslideritem.hxx>
 
+#include <sfx2/infobar.hxx>
 #include <sfx2/objface.hxx>
 #include <sot/exchange.hxx>
 #include <svx/ruler.hxx>
@@ -126,6 +127,7 @@ SFX_IMPL_INTERFACE(OutlineViewShell, SfxShell, SdResId(STR_OUTLINEVIEWSHELL))
     SFX_OBJECTBAR_REGISTRATION( SFX_OBJECTBAR_APPLICATION | SFX_VISIBILITY_DESKTOP | SFX_VISIBILITY_STANDARD | SFX_VISIBILITY_CLIENT | SFX_VISIBILITY_VIEWER | SFX_VISIBILITY_READONLYDOC,
                                 SdResId(RID_DRAW_VIEWER_TOOLBOX) );
     SFX_CHILDWINDOW_REGISTRATION( SfxTemplateDialogWrapper::GetChildWindowId() );
+    SFX_CHILDWINDOW_REGISTRATION( SfxInfoBarContainerChild::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( SvxHlinkDlgWrapper::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( ::sd::SpellDialogChildWindow::GetChildWindowId() );
     SFX_CHILDWINDOW_REGISTRATION( SID_SEARCH_DLG );
diff --git a/sfx2/inc/sfx2/sfxbasecontroller.hxx b/sfx2/inc/sfx2/sfxbasecontroller.hxx
index cf26530..b8daf8b 100644
--- a/sfx2/inc/sfx2/sfxbasecontroller.hxx
+++ b/sfx2/inc/sfx2/sfxbasecontroller.hxx
@@ -44,6 +44,8 @@
 #include <com/sun/star/awt/XMouseClickHandler.hpp>
 #include <com/sun/star/awt/XKeyHandler.hpp>
 #include <com/sun/star/awt/XUserInputInterception.hpp>
+#include <tools/link.hxx>
+#include <vcl/button.hxx>
 
 #include <sfx2/viewsh.hxx>
 #include <sfx2/sfxuno.hxx>
@@ -385,6 +387,8 @@ private:
     SAL_DLLPRIVATE SfxViewFrame& GetViewFrame_Impl() const;
     SAL_DLLPRIVATE void ShowInfoBars( );
 
+    DECL_LINK( CheckOutHandler, PushButton * );
+
 //________________________________________________________________________________________________________
 //  private variables
 //________________________________________________________________________________________________________
diff --git a/sfx2/inc/sfx2/sfxbasemodel.hxx b/sfx2/inc/sfx2/sfxbasemodel.hxx
index 8b7097f..7a3b4a5 100644
--- a/sfx2/inc/sfx2/sfxbasemodel.hxx
+++ b/sfx2/inc/sfx2/sfxbasemodel.hxx
@@ -1421,6 +1421,7 @@ public:
                 ::com::sun::star::beans::PropertyValue >& _cmispropertiesdisplaynames )
         throw (::com::sun::star::uno::RuntimeException);
 
+    virtual void SAL_CALL checkOut(  ) throw ( ::com::sun::star::uno::RuntimeException );
 
     //____________________________________________________________________________________________________
     //  SfxListener
@@ -1542,6 +1543,8 @@ private:
 
     SAL_DLLPRIVATE void NotifyModifyListeners_Impl() const;
 
+    SAL_DLLPRIVATE void loadCmisProperties();
+
 //________________________________________________________________________________________________________
 //  private variables and methods
 //________________________________________________________________________________________________________
diff --git a/sfx2/inc/sfx2/viewfrm.hxx b/sfx2/inc/sfx2/viewfrm.hxx
index 26b5e47..c3d8893 100644
--- a/sfx2/inc/sfx2/viewfrm.hxx
+++ b/sfx2/inc/sfx2/viewfrm.hxx
@@ -23,6 +23,7 @@
 #include "sfx2/dllapi.h"
 #include "sal/types.h"
 #include <svl/lstner.hxx>
+#include <sfx2/infobar.hxx>
 #include <sfx2/module.hxx>
 #include <sfx2/frame.hxx>
 #include <sfx2/shell.hxx>
@@ -191,6 +192,7 @@ public:
         and position of each button will be changed: only the width will remain unchanged.
       */
     void                    AppendInfoBar( const rtl::OUString& sMessage, std::vector< PushButton* > aButtons );
+    void                    RemoveInfoBar( SfxInfoBarWindow* pInfoBar );
 
     SAL_DLLPRIVATE void SetDowning_Impl();
     SAL_DLLPRIVATE void GetDocNumber_Impl();
diff --git a/sfx2/source/doc/objstor.cxx b/sfx2/source/doc/objstor.cxx
index fa4116b..b9b5f04 100644
--- a/sfx2/source/doc/objstor.cxx
+++ b/sfx2/source/doc/objstor.cxx
@@ -29,7 +29,6 @@
 #include <com/sun/star/frame/XStorable.hpp>
 #include <com/sun/star/frame/XModel.hpp>
 #include <com/sun/star/frame/XFrame.hpp>
-#include <com/sun/star/document/XCmisDocument.hpp>
 #include <com/sun/star/document/XFilter.hpp>
 #include <com/sun/star/document/XImporter.hpp>
 #include <com/sun/star/document/XExporter.hpp>
@@ -745,23 +744,6 @@ sal_Bool SfxObjectShell::DoLoad( SfxMedium *pMed )
             com::sun::star::uno::Reference < XPropertySetInfo > xProps = aContent.getProperties();
             if ( xProps.is() )
             {
-                // Copy all the CMIS properties to the document (if there is any)
-                ::rtl::OUString aCmisPropsValues( "CmisPropertiesValues" );
-                ::rtl::OUString aCmisPropsNames( "CmisPropertiesDisplayNames" );
-                uno::Reference< document::XCmisDocument > xCmisDoc( GetModel( ), uno::UNO_QUERY_THROW );
-                if ( xProps->hasPropertyByName( aCmisPropsValues ) )
-                {
-                    beans::PropertyValues aCmisValues;
-                    aContent.getPropertyValue( aCmisPropsValues ) >>= aCmisValues;
-                    xCmisDoc->setCmisPropertiesValues( aCmisValues );
-                }
-                if ( xProps->hasPropertyByName( aCmisPropsNames ) )
-                {
-                    beans::PropertyValues aPropNames;
-                    aContent.getPropertyValue( aCmisPropsNames ) >>= aPropNames;
-                    xCmisDoc->setCmisPropertiesDisplayNames( aPropNames );
-                }
-
                 ::rtl::OUString aAuthor( "Author" );
                 ::rtl::OUString aKeywords( "Keywords" );
                 ::rtl::OUString aSubject( "Subject" );
diff --git a/sfx2/source/doc/sfxbasemodel.cxx b/sfx2/source/doc/sfxbasemodel.cxx
index ea8fdfa..872bdbc 100644
--- a/sfx2/source/doc/sfxbasemodel.cxx
+++ b/sfx2/source/doc/sfxbasemodel.cxx
@@ -2001,6 +2001,8 @@ void SAL_CALL SfxBaseModel::load(   const uno::Sequence< beans::PropertyValue >&
             }
         }
 
+        loadCmisProperties( );
+
         sal_Bool bHidden = sal_False;
         SFX_ITEMSET_ARG( pMedium->GetItemSet(), pHidItem, SfxBoolItem, SID_HIDDEN, sal_False);
         if ( pHidItem )
@@ -2542,6 +2544,74 @@ void SAL_CALL SfxBaseModel::setCmisPropertiesDisplayNames( const uno::Sequence<
     m_pData->m_cmisPropertiesDisplayNames = _cmispropertiesdisplaynames;
 }
 
+void SAL_CALL SfxBaseModel::checkOut(  ) throw ( uno::RuntimeException )
+{
+    SfxMedium* pMedium = m_pData->m_pObjectShell->GetMedium();
+    if ( pMedium )
+    {
+        try
+        {
+            ::ucbhelper::Content aContent( pMedium->GetName(),
+                uno::Reference<ucb::XCommandEnvironment>(),
+                comphelper::getProcessComponentContext() );
+
+            uno::Any aResult = aContent.executeCommand( "checkout", uno::Any( ) );
+            rtl::OUString sURL;
+            aResult >>= sURL;
+
+            m_pData->m_pObjectShell->GetMedium( )->SwitchDocumentToFile( sURL );
+            m_pData->m_xDocumentProperties->setTitle( getTitle( ) );
+            uno::Sequence< beans::PropertyValue > aSequence ;
+            TransformItems( SID_OPENDOC, *pMedium->GetItemSet(), aSequence );
+            attachResource( sURL, aSequence );
+
+            // Reload the CMIS properties
+            loadCmisProperties( );
+        }
+        catch (const ucb::ContentCreationException &)
+        {
+        }
+        catch (const ucb::CommandAbortedException &)
+        {
+        }
+    }
+}
+
+void SfxBaseModel::loadCmisProperties( )
+{
+    SfxMedium* pMedium = m_pData->m_pObjectShell->GetMedium();
+    if ( pMedium )
+    {
+        try
+        {
+            ::ucbhelper::Content aContent( pMedium->GetName( ),
+                uno::Reference<ucb::XCommandEnvironment>(),
+                comphelper::getProcessComponentContext() );
+            com::sun::star::uno::Reference < beans::XPropertySetInfo > xProps = aContent.getProperties();
+            ::rtl::OUString aCmisPropsValues( "CmisPropertiesValues" );
+            ::rtl::OUString aCmisPropsNames( "CmisPropertiesDisplayNames" );
+            if ( xProps->hasPropertyByName( aCmisPropsValues ) )
+            {
+                beans::PropertyValues aCmisValues;
+                aContent.getPropertyValue( aCmisPropsValues ) >>= aCmisValues;
+                setCmisPropertiesValues( aCmisValues );
+            }
+            if ( xProps->hasPropertyByName( aCmisPropsNames ) )
+            {
+                beans::PropertyValues aPropNames;
+                aContent.getPropertyValue( aCmisPropsNames ) >>= aPropNames;
+                setCmisPropertiesDisplayNames( aPropNames );
+            }
+        }
+        catch (const ucb::ContentCreationException &)
+        {
+        }
+        catch (const ucb::CommandAbortedException &)
+        {
+        }
+    }
+}
+
 //________________________________________________________________________________________________________
 //  SfxListener
 //________________________________________________________________________________________________________
@@ -3587,6 +3657,7 @@ void SAL_CALL SfxBaseModel::loadFromStorage( const uno::Reference< XSTORAGE >& x
                                             uno::Reference< uno::XInterface >(),
                                             nError ? nError : ERRCODE_IO_CANTREAD );
     }
+    loadCmisProperties( );
 }
 
 void SAL_CALL SfxBaseModel::storeToStorage( const uno::Reference< XSTORAGE >& xStorage,
diff --git a/sfx2/source/view/sfxbasecontroller.cxx b/sfx2/source/view/sfxbasecontroller.cxx
index 89ead63..7b315a6 100644
--- a/sfx2/source/view/sfxbasecontroller.cxx
+++ b/sfx2/source/view/sfxbasecontroller.cxx
@@ -63,6 +63,7 @@
 #include <sfx2/sfxresid.hxx>
 #include <workwin.hxx>
 #include <sfx2/objface.hxx>
+#include <sfx2/infobar.hxx>
 
 #include <osl/mutex.hxx>
 #include <tools/diagnose_ex.h>
@@ -1460,7 +1461,7 @@ void SfxBaseController::ShowInfoBars( )
                 SfxViewFrame* pViewFrame = m_pData->m_pViewShell->GetFrame();
                 std::vector< PushButton* > aButtons;
                 PushButton* pBtn = new PushButton( &pViewFrame->GetWindow(), SfxResId( BT_CHECKOUT ) );
-                // TODO Set the handler
+                pBtn->SetClickHdl( LINK( this, SfxBaseController, CheckOutHandler ) );
                 aButtons.push_back( pBtn );
                 pViewFrame->AppendInfoBar( SfxResId( STR_NONCHECKEDOUT_DOCUMENT ), aButtons );
             }
@@ -1468,6 +1469,28 @@ void SfxBaseController::ShowInfoBars( )
     }
 }
 
+IMPL_LINK( SfxBaseController, CheckOutHandler, PushButton*, pBtn )
+{
+    if ( m_pData->m_pViewShell )
+    {
+        try
+        {
+            REFERENCE< document::XCmisDocument > xCmisDoc( m_pData->m_pViewShell->GetObjectShell()->GetModel(), uno::UNO_QUERY_THROW );
+            xCmisDoc->checkOut( );
+
+            // Remove the info bar
+            SfxInfoBarWindow* pInfoBar = ( SfxInfoBarWindow* )pBtn->GetParent( );
+            SfxViewFrame* pViewFrame = m_pData->m_pViewShell->GetFrame();
+            pViewFrame->RemoveInfoBar( pInfoBar );
+        }
+        catch ( const uno::RuntimeException& )
+        {
+            // TODO Handle the problem in some way?
+        }
+    }
+    return 0;
+}
+
 
 //=============================================================================
 css::uno::Reference< css::frame::XTitle > SfxBaseController::impl_getTitleHelper ()
diff --git a/sfx2/source/view/viewfrm.cxx b/sfx2/source/view/viewfrm.cxx
index 9d459c6..d9ed893 100644
--- a/sfx2/source/view/viewfrm.cxx
+++ b/sfx2/source/view/viewfrm.cxx
@@ -3358,9 +3358,28 @@ void SfxViewFrame::AppendInfoBar( const rtl::OUString& sMessage, std::vector< Pu
     if ( !HasChildWindow( nId ) )
         ToggleChildWindow( nId );
     SfxChildWindow* pChild = GetChildWindow( nId );
-    SfxInfoBarContainerWindow* pInfoBars = ( SfxInfoBarContainerWindow* )pChild->GetWindow();
-    pInfoBars->appendInfoBar( sMessage, aButtons );
-    ShowChildWindow( nId );
+    if ( pChild )
+    {
+        SfxInfoBarContainerWindow* pInfoBars = ( SfxInfoBarContainerWindow* )pChild->GetWindow();
+        pInfoBars->appendInfoBar( sMessage, aButtons );
+        ShowChildWindow( nId );
+    }
+}
+
+void SfxViewFrame::RemoveInfoBar( SfxInfoBarWindow* pInfoBar )
+{
+    const sal_uInt16 nId = SfxInfoBarContainerChild::GetChildWindowId();
+
+    // Make sure the InfoBar container is visible
+    if ( !HasChildWindow( nId ) )
+        ToggleChildWindow( nId );
+    SfxChildWindow* pChild = GetChildWindow( nId );
+    if ( pChild )
+    {
+        SfxInfoBarContainerWindow* pInfoBars = ( SfxInfoBarContainerWindow* )pChild->GetWindow();
+        pInfoBars->removeInfoBar( pInfoBar );
+        ShowChildWindow( nId );
+    }
 }
 
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sw/source/ui/uiview/view0.cxx b/sw/source/ui/uiview/view0.cxx
index 8e212c5..3d171ca 100644
--- a/sw/source/ui/uiview/view0.cxx
+++ b/sw/source/ui/uiview/view0.cxx
@@ -29,6 +29,7 @@
 #include <viewopt.hxx>
 #include <globals.h>
 #include <sfx2/app.hxx>
+#include <sfx2/infobar.hxx>
 #include <sfx2/request.hxx>
 #include <svl/whiter.hxx>
 #include <svx/srchdlg.hxx>
@@ -100,6 +101,7 @@ SFX_IMPL_INTERFACE( SwView, SfxViewShell, SW_RES(RID_TOOLS_TOOLBOX) )
     SFX_CHILDWINDOW_CONTEXT_REGISTRATION(SID_NAVIGATOR);
     SFX_CHILDWINDOW_REGISTRATION(SID_TASKPANE);
     SFX_CHILDWINDOW_REGISTRATION(SfxTemplateDialogWrapper::GetChildWindowId());
+    SFX_CHILDWINDOW_REGISTRATION(SfxInfoBarContainerChild::GetChildWindowId());
     SFX_CHILDWINDOW_REGISTRATION(SvxSearchDialogWrapper::GetChildWindowId());
     SFX_CHILDWINDOW_REGISTRATION(SwSpellDialogChildWindow::GetChildWindowId());
     SFX_CHILDWINDOW_REGISTRATION(FN_REDLINE_ACCEPT);
diff --git a/sw/source/ui/web/wview.cxx b/sw/source/ui/web/wview.cxx
index d480847..d6541a2 100644
--- a/sw/source/ui/web/wview.cxx
+++ b/sw/source/ui/web/wview.cxx
@@ -20,6 +20,7 @@
 #include <sfx2/msg.hxx>
 #include <svl/srchitem.hxx>
 #include <sfx2/dispatch.hxx>
+#include <sfx2/infobar.hxx>
 #include <sfx2/templdlg.hxx>
 #include <svx/srchdlg.hxx>
 #include <basic/sbxobj.hxx>
@@ -84,6 +85,7 @@ SFX_IMPL_INTERFACE( SwWebView, SwView, SW_RES(RID_WEBTOOLS_TOOLBOX) )
 {
     SFX_CHILDWINDOW_REGISTRATION(SfxTemplateDialogWrapper::GetChildWindowId());
     SFX_CHILDWINDOW_REGISTRATION(SvxSearchDialogWrapper::GetChildWindowId());
+    SFX_CHILDWINDOW_REGISTRATION(SfxInfoBarContainerChild::GetChildWindowId());
     SFX_OBJECTBAR_REGISTRATION( SFX_OBJECTBAR_TOOLS|
                                 SFX_VISIBILITY_STANDARD|SFX_VISIBILITY_SERVER,
                                 SW_RES(RID_WEBTOOLS_TOOLBOX) );
diff --git a/ucb/source/ucp/cmis/cmis_content.cxx b/ucb/source/ucp/cmis/cmis_content.cxx
index fbfa83b..0baee4f 100644
--- a/ucb/source/ucp/cmis/cmis_content.cxx
+++ b/ucb/source/ucp/cmis/cmis_content.cxx
@@ -1005,6 +1005,9 @@ namespace cmis
             ( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "open" ) ),
               -1, getCppuType( static_cast<ucb::OpenCommandArgument2 * >( 0 ) ) ),
 
+            // Mandatory CMIS-only commands
+            ucb::CommandInfo ( rtl::OUString( "checkout" ), -1, getCppuVoidType() ),
+
             // Folder Only, omitted if not a folder
             ucb::CommandInfo
             ( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "transfer" ) ),
@@ -1187,6 +1190,49 @@ namespace cmis
                                     rtl::OUString::createFromAscii( e.what() ) );
             }
         }
+        else if ( aCommand.Name == "checkout" )
+        {
+            try
+            {
+                // Checkout the document if possible
+                libcmis::DocumentPtr pDoc = boost::dynamic_pointer_cast< libcmis::Document >( getObject( xEnv ) );
+                if ( pDoc.get( ) == NULL )
+                {
+                    ucbhelper::cancelCommandExecution(
+                                        ucb::IOErrorCode_GENERAL,
+                                        uno::Sequence< uno::Any >( 0 ),
+                                        xEnv,
+                                        "Checkout only supported by documents" );
+                }
+                libcmis::DocumentPtr pPwc = pDoc->checkOut( );
+
+                // Compute the URL of the Private Working Copy (PWC)
+                URL aCmisUrl( m_sURL );
+                vector< string > aPaths = pPwc->getPaths( );
+                if ( !aPaths.empty() )
+                {
+                    string sPath = aPaths.front( );
+                    aCmisUrl.setObjectPath( STD_TO_OUSTR( sPath ) );
+                }
+                else
+                {
+                    // We may have unfiled PWC depending on the server, those
+                    // won't have any path, use their ID instead
+                    string sId = pPwc->getId( );
+                    aCmisUrl.setObjectId( STD_TO_OUSTR( sId ) );
+                }
+                aRet <<= aCmisUrl.asString( );
+            }
+            catch ( const libcmis::Exception& e )
+            {
+                SAL_INFO( "cmisucp", "Unexpected libcmis exception: " << e.what( ) );
+                ucbhelper::cancelCommandExecution(
+                                    ucb::IOErrorCode_GENERAL,
+                                    uno::Sequence< uno::Any >( 0 ),
+                                    xEnv,
+                                    rtl::OUString::createFromAscii( e.what() ) );
+            }
+        }
         else
         {
             SAL_INFO( "cmisucp", "Unknown command to execute" );
diff --git a/ucb/source/ucp/cmis/cmis_url.cxx b/ucb/source/ucp/cmis/cmis_url.cxx
index e184d70..dfd0cc7 100644
--- a/ucb/source/ucp/cmis/cmis_url.cxx
+++ b/ucb/source/ucp/cmis/cmis_url.cxx
@@ -89,6 +89,12 @@ namespace cmis
         m_sId = rtl::OUString( );
     }
 
+    void URL::setObjectId( rtl::OUString sId )
+    {
+        m_sPath = rtl::OUString( );
+        m_sId = sId;
+    }
+
     rtl::OUString URL::asString( )
     {
         rtl::OUString sUrl;
diff --git a/ucb/source/ucp/cmis/cmis_url.hxx b/ucb/source/ucp/cmis/cmis_url.hxx
index 6283d7a..e2912d4 100644
--- a/ucb/source/ucp/cmis/cmis_url.hxx
+++ b/ucb/source/ucp/cmis/cmis_url.hxx
@@ -56,6 +56,7 @@ namespace cmis
             rtl::OUString& getUsername( ) { return m_sUser; }
             rtl::OUString& getPassword( ) { return m_sPass; }
             void setObjectPath( rtl::OUString sPath );
+            void setObjectId( rtl::OUString sId );
 
             rtl::OUString asString( );
     };
commit 0c0e5c82c7d9fb790d0894c28af5cff99d71a910
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Wed Oct 10 15:27:57 2012 +0200

    fdo#54094: Add a space in sw outline tooltips
    
    Change-Id: I1f2046cc52261b717165a2f6838a826acefb7b09

diff --git a/sw/source/core/crsr/crstrvl.cxx b/sw/source/core/crsr/crstrvl.cxx
index 0b454ed..7a5218d 100644
--- a/sw/source/core/crsr/crstrvl.cxx
+++ b/sw/source/core/crsr/crstrvl.cxx
@@ -1026,7 +1026,7 @@ sal_Bool SwCrsrShell::GetContentAtPos( const Point& rPt,
             if( pONd )
             {
                 rCntntAtPos.eCntntAtPos = SwContentAtPos::SW_OUTLINE;
-                rCntntAtPos.sStr = pONd->GetExpandTxt( 0, STRING_LEN, true );
+                rCntntAtPos.sStr = pONd->GetExpandTxt( 0, STRING_LEN, true, true );
                 bRet = sal_True;
             }
         }
commit 9d9eb583f56ed494a8574a2e7677fe66aabfd6c7
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Tue Oct 9 17:52:40 2012 +0200

    CMIS: Show an infobar when the document isn't checked out
    
    Telling the user that the document isn't checked out is pretty important
    as it may cause troubles for the Save operation later (depending on the
    server policy)
    
    Change-Id: Ia101d37cc6266170914ae2cbd90accea1f377f60

diff --git a/sfx2/inc/sfx2/sfx.hrc b/sfx2/inc/sfx2/sfx.hrc
index 7971b85..cd1ecdc 100644
--- a/sfx2/inc/sfx2/sfx.hrc
+++ b/sfx2/inc/sfx2/sfx.hrc
@@ -172,6 +172,8 @@
 #define STR_PASSWD                          (RID_SFX_START+122)
 #define STR_PASSWD_EMPTY                    (RID_SFX_START+123)
 #define STR_PASSWD_MIN_LEN                  (RID_SFX_START+124)
+#define STR_NONCHECKEDOUT_DOCUMENT          (RID_SFX_START+125)
+#define BT_CHECKOUT                         (RID_SFX_START+126)
 #define STR_ACCTITLE_PRODUCTIVITYTOOLS      (RID_SFX_START+157)
 
 //=========================================================================
diff --git a/sfx2/inc/sfx2/sfxbasecontroller.hxx b/sfx2/inc/sfx2/sfxbasecontroller.hxx
index aa142f3..cf26530 100644
--- a/sfx2/inc/sfx2/sfxbasecontroller.hxx
+++ b/sfx2/inc/sfx2/sfxbasecontroller.hxx
@@ -383,6 +383,7 @@ private:
     };
     SAL_DLLPRIVATE void ConnectSfxFrame_Impl( const ConnectSfxFrame i_eConnect );
     SAL_DLLPRIVATE SfxViewFrame& GetViewFrame_Impl() const;
+    SAL_DLLPRIVATE void ShowInfoBars( );
 
 //________________________________________________________________________________________________________
 //  private variables
diff --git a/sfx2/source/doc/objstor.cxx b/sfx2/source/doc/objstor.cxx
index ec6b252..fa4116b 100644
--- a/sfx2/source/doc/objstor.cxx
+++ b/sfx2/source/doc/objstor.cxx
@@ -754,9 +754,6 @@ sal_Bool SfxObjectShell::DoLoad( SfxMedium *pMed )
                     beans::PropertyValues aCmisValues;
                     aContent.getPropertyValue( aCmisPropsValues ) >>= aCmisValues;
                     xCmisDoc->setCmisPropertiesValues( aCmisValues );
-
-                    // TODO For CMIS case, try to look for cmis:isVersionSeriesCheckedOut
-                    // If set to false, then show InfoBar to propose checkOut
                 }
                 if ( xProps->hasPropertyByName( aCmisPropsNames ) )
                 {
diff --git a/sfx2/source/view/sfxbasecontroller.cxx b/sfx2/source/view/sfxbasecontroller.cxx
index 33cc346..89ead63 100644
--- a/sfx2/source/view/sfxbasecontroller.cxx
+++ b/sfx2/source/view/sfxbasecontroller.cxx
@@ -28,6 +28,7 @@
 #include <com/sun/star/util/XCloseBroadcaster.hpp>
 #include <com/sun/star/util/XCloseListener.hpp>
 #include <com/sun/star/util/CloseVetoException.hpp>
+#include <com/sun/star/document/XCmisDocument.hpp>
 #include <com/sun/star/document/XViewDataSupplier.hpp>
 #include <cppuhelper/implbase1.hxx>
 #include <cppuhelper/implbase2.hxx>
@@ -58,6 +59,8 @@
 #include <sfx2/unoctitm.hxx>
 #include <sfx2/childwin.hxx>
 #include <sfx2/sfxsids.hrc>
+#include <sfx2/sfx.hrc>
+#include <sfx2/sfxresid.hxx>
 #include <workwin.hxx>
 #include <sfx2/objface.hxx>
 
@@ -581,6 +584,7 @@ void SAL_CALL SfxBaseController::attachFrame( const REFERENCE< XFRAME >& xFrame
         if ( m_pData->m_pViewShell )
         {
             ConnectSfxFrame_Impl( E_CONNECT );
+            ShowInfoBars( );
 
             // attaching the frame to the controller is the last step in the creation of a new view, so notify this
             SfxViewEventHint aHint( SFX_EVENT_VIEWCREATED, GlobalEventConfig::GetEventName( STR_EVENT_VIEWCREATED ), m_pData->m_pViewShell->GetObjectShell(), uno::Reference< frame::XController2 >( this ) );
@@ -1428,6 +1432,43 @@ void SfxBaseController::ConnectSfxFrame_Impl( const ConnectSfxFrame i_eConnect )
         pViewFrame->GetBindings().Invalidate( nViewNo + SID_VIEWSHELL0 );
 }
 
+void SfxBaseController::ShowInfoBars( )
+{
+    if ( m_pData->m_pViewShell )
+    {
+        // CMIS verifications
+        REFERENCE< document::XCmisDocument > xCmisDoc( m_pData->m_pViewShell->GetObjectShell()->GetModel(), uno::UNO_QUERY );
+        beans::PropertyValues aCmisProperties = xCmisDoc->getCmisPropertiesValues( );
+
+        if ( aCmisProperties.hasElements( ) )
+        {
+            // Loop over the CMIS Properties to find cmis:isVersionSeriesCheckedOut
+            bool bFoundCheckedout = false;
+            sal_Bool bCheckedOut = sal_False;
+            for ( sal_Int32 i = 0; i < aCmisProperties.getLength() && !bFoundCheckedout; ++i )
+            {
+                if ( aCmisProperties[i].Name == "cmis:isVersionSeriesCheckedOut" )
+                {
+                    bFoundCheckedout = true;
+                    aCmisProperties[i].Value >>= bCheckedOut;
+                }
+            }
+
+            if ( !bCheckedOut )
+            {
+                // Get the Frame and show the InfoBar if not checked out
+                SfxViewFrame* pViewFrame = m_pData->m_pViewShell->GetFrame();
+                std::vector< PushButton* > aButtons;
+                PushButton* pBtn = new PushButton( &pViewFrame->GetWindow(), SfxResId( BT_CHECKOUT ) );
+                // TODO Set the handler
+                aButtons.push_back( pBtn );
+                pViewFrame->AppendInfoBar( SfxResId( STR_NONCHECKEDOUT_DOCUMENT ), aButtons );
+            }
+        }
+    }
+}
+
+
 //=============================================================================
 css::uno::Reference< css::frame::XTitle > SfxBaseController::impl_getTitleHelper ()
 {
diff --git a/sfx2/source/view/view.src b/sfx2/source/view/view.src
index a4fa311..cc2ebbb 100644
--- a/sfx2/source/view/view.src
+++ b/sfx2/source/view/view.src
@@ -161,3 +161,15 @@ String STR_REPAIREDDOCUMENT
 {
     Text [ en-US ] = " (repaired document)" ;
 };
+
+String STR_NONCHECKEDOUT_DOCUMENT
+{
+    Text [ en-US ] = "Document is not checked out on server" ;
+};
+
+PushButton BT_CHECKOUT
+{
+    Pos = MAP_APPFONT( 0 , 0 );
+    Size = MAP_APPFONT( 30 , 0 );
+    Text[ en-US ] = "Check out";
+};
diff --git a/sfx2/source/view/viewfrm.cxx b/sfx2/source/view/viewfrm.cxx
index ad8dfc7..9d459c6 100644
--- a/sfx2/source/view/viewfrm.cxx
+++ b/sfx2/source/view/viewfrm.cxx
@@ -3353,7 +3353,10 @@ void SfxViewFrame::ActivateToolPanel_Impl( const ::rtl::OUString& i_rPanelURL )
 void SfxViewFrame::AppendInfoBar( const rtl::OUString& sMessage, std::vector< PushButton* > aButtons )
 {
     const sal_uInt16 nId = SfxInfoBarContainerChild::GetChildWindowId();
-    ShowChildWindow( nId );
+
+    // Make sure the InfoBar container is visible
+    if ( !HasChildWindow( nId ) )
+        ToggleChildWindow( nId );
     SfxChildWindow* pChild = GetChildWindow( nId );
     SfxInfoBarContainerWindow* pInfoBars = ( SfxInfoBarContainerWindow* )pChild->GetWindow();
     pInfoBars->appendInfoBar( sMessage, aButtons );
commit f5a84d8c1a44d82f2ca96a3d219a4cb05ab71a39
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Tue Oct 9 10:47:32 2012 +0200

    CMIS: Provide the CMIS properties in the UNO API of documents
    
    Change-Id: Ieb48f615a80e1fa2d49b4efada1f8f9fc4349c29

diff --git a/offapi/UnoApi_offapi.mk b/offapi/UnoApi_offapi.mk
index 442b4b7..a505169 100644
--- a/offapi/UnoApi_offapi.mk
+++ b/offapi/UnoApi_offapi.mk
@@ -2131,6 +2131,7 @@ $(eval $(call gb_UnoApi_add_idlfiles,offapi,offapi/com/sun/star/document,\
 	UpdateDocMode \
 	XActionLockable \
 	XBinaryStreamResolver \
+	XCmisDocument \
 	XCodeNameQuery \
 	XCompatWriterDocProperties \
 	XDocumentEventBroadcaster \
diff --git a/offapi/com/sun/star/document/XCmisDocument.idl b/offapi/com/sun/star/document/XCmisDocument.idl
new file mode 100644
index 0000000..246a1b7
--- /dev/null
+++ b/offapi/com/sun/star/document/XCmisDocument.idl
@@ -0,0 +1,35 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+#ifndef __com_sun_star_document_XCmisDataSupplier_idl__
+#define __com_sun_star_document_XCmisDataSupplier_idl__
+
+#include <com/sun/star/beans/PropertyValues.idl>
+#include <com/sun/star/uno/XInterface.idl>
+
+module com {   module sun {   module star {   module document {
+
+/** The document can provide access to CMIS properties and versions
+    through this interface.
+  */
+interface XCmisDocument : com::sun::star::uno::XInterface
+{
+    /** Contains the properties values named after their CMIS ID.
+     */
+    [attribute] com::sun::star::beans::PropertyValues CmisPropertiesValues;
+
+    /** Contains the property names to show to the user from their CMIS id.
+     */
+    [attribute] com::sun::star::beans::PropertyValues CmisPropertiesDisplayNames;
+};
+
+}; }; }; };
+
+#endif
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sfx2/inc/sfx2/sfxbasemodel.hxx b/sfx2/inc/sfx2/sfxbasemodel.hxx
index 0fae6b8..8b7097f 100644
--- a/sfx2/inc/sfx2/sfxbasemodel.hxx
+++ b/sfx2/inc/sfx2/sfxbasemodel.hxx
@@ -32,6 +32,7 @@
 #include <com/sun/star/container/XNameContainer.hpp>
 #include <com/sun/star/container/XNameReplace.hpp>
 #include <com/sun/star/frame/XController2.hpp>
+#include <com/sun/star/document/XCmisDocument.hpp>
 #include <com/sun/star/document/XDocumentInfo.hpp>
 #include <com/sun/star/document/XDocumentInfoSupplier.hpp>
 #include <com/sun/star/document/XDocumentPropertiesSupplier.hpp>
@@ -87,9 +88,9 @@
 #include <com/sun/star/task/XInteractionHandler.hpp>
 
 //________________________________________________________________________________________________________
-#ifndef INCLUDED_COMPHELPER_IMPLBASE_VAR_HXX_32
-#define INCLUDED_COMPHELPER_IMPLBASE_VAR_HXX_32
-#define COMPHELPER_IMPLBASE_INTERFACE_NUMBER 32
+#ifndef INCLUDED_COMPHELPER_IMPLBASE_VAR_HXX_33
+#define INCLUDED_COMPHELPER_IMPLBASE_VAR_HXX_33
+#define COMPHELPER_IMPLBASE_INTERFACE_NUMBER 33
 #include <comphelper/implbase_var.hxx>
 #endif
 
@@ -209,9 +210,10 @@ namespace sfx { namespace intern {
                  SfxListener
 */
 
-typedef ::comphelper::WeakImplHelper32  <   XCHILD
+typedef ::comphelper::WeakImplHelper33  <   XCHILD
                                         ,   XDOCUMENTINFOSUPPLIER
                                         ,   ::com::sun::star::document::XDocumentPropertiesSupplier
+                                        ,   ::com::sun::star::document::XCmisDocument
                                         ,   ::com::sun::star::rdf::XDocumentMetadataAccess
                                         ,   ::com::sun::star::document::XDocumentRecovery
                                         ,   ::com::sun::star::document::XUndoManagerSupplier
@@ -1402,6 +1404,23 @@ public:
             ::com::sun::star::lang::IllegalArgumentException,
             ::com::sun::star::lang::WrappedTargetException);
 
+    // XCmisDocument
+
+    virtual ::com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyValue >
+            SAL_CALL getCmisPropertiesValues()
+        throw (::com::sun::star::uno::RuntimeException);
+    virtual void SAL_CALL setCmisPropertiesValues(
+            const ::com::sun::star::uno::Sequence<
+                ::com::sun::star::beans::PropertyValue >& _cmispropertiesvalues )
+        throw (::com::sun::star::uno::RuntimeException);
+    virtual ::com::sun::star::uno::Sequence< ::com::sun::star::beans::PropertyValue >
+            SAL_CALL getCmisPropertiesDisplayNames()
+        throw (::com::sun::star::uno::RuntimeException);
+    virtual void SAL_CALL setCmisPropertiesDisplayNames(
+            const ::com::sun::star::uno::Sequence<
+                ::com::sun::star::beans::PropertyValue >& _cmispropertiesdisplaynames )
+        throw (::com::sun::star::uno::RuntimeException);
+
 
     //____________________________________________________________________________________________________
     //  SfxListener
diff --git a/sfx2/source/doc/objstor.cxx b/sfx2/source/doc/objstor.cxx
index b9b5f04..ec6b252 100644
--- a/sfx2/source/doc/objstor.cxx
+++ b/sfx2/source/doc/objstor.cxx
@@ -29,6 +29,7 @@
 #include <com/sun/star/frame/XStorable.hpp>
 #include <com/sun/star/frame/XModel.hpp>
 #include <com/sun/star/frame/XFrame.hpp>
+#include <com/sun/star/document/XCmisDocument.hpp>
 #include <com/sun/star/document/XFilter.hpp>
 #include <com/sun/star/document/XImporter.hpp>
 #include <com/sun/star/document/XExporter.hpp>
@@ -744,6 +745,26 @@ sal_Bool SfxObjectShell::DoLoad( SfxMedium *pMed )
             com::sun::star::uno::Reference < XPropertySetInfo > xProps = aContent.getProperties();
             if ( xProps.is() )
             {
+                // Copy all the CMIS properties to the document (if there is any)
+                ::rtl::OUString aCmisPropsValues( "CmisPropertiesValues" );
+                ::rtl::OUString aCmisPropsNames( "CmisPropertiesDisplayNames" );
+                uno::Reference< document::XCmisDocument > xCmisDoc( GetModel( ), uno::UNO_QUERY_THROW );
+                if ( xProps->hasPropertyByName( aCmisPropsValues ) )
+                {
+                    beans::PropertyValues aCmisValues;
+                    aContent.getPropertyValue( aCmisPropsValues ) >>= aCmisValues;
+                    xCmisDoc->setCmisPropertiesValues( aCmisValues );
+
+                    // TODO For CMIS case, try to look for cmis:isVersionSeriesCheckedOut
+                    // If set to false, then show InfoBar to propose checkOut
+                }
+                if ( xProps->hasPropertyByName( aCmisPropsNames ) )
+                {
+                    beans::PropertyValues aPropNames;
+                    aContent.getPropertyValue( aCmisPropsNames ) >>= aPropNames;
+                    xCmisDoc->setCmisPropertiesDisplayNames( aPropNames );
+                }
+
                 ::rtl::OUString aAuthor( "Author" );
                 ::rtl::OUString aKeywords( "Keywords" );
                 ::rtl::OUString aSubject( "Subject" );
diff --git a/sfx2/source/doc/sfxbasemodel.cxx b/sfx2/source/doc/sfxbasemodel.cxx
index f7c5f30..ea8fdfa 100644
--- a/sfx2/source/doc/sfxbasemodel.cxx
+++ b/sfx2/source/doc/sfxbasemodel.cxx
@@ -211,6 +211,8 @@ struct IMPL_SfxBaseModel_DataContainer : public ::sfx2::IModifiableDocument
     css::uno::Reference< css::frame::XUntitledNumbers >     m_xNumberedControllers;
     uno::Reference< rdf::XDocumentMetadataAccess>           m_xDocumentMetadata;
     ::rtl::Reference< ::sfx2::DocumentUndoManager >         m_pDocumentUndoManager;
+    uno::Sequence< beans::PropertyValue>                    m_cmisPropertiesValues;
+    uno::Sequence< beans::PropertyValue>                    m_cmisPropertiesDisplayNames;
 
 
     IMPL_SfxBaseModel_DataContainer( ::osl::Mutex& rMutex, SfxObjectShell* pObjectShell )
@@ -229,6 +231,8 @@ struct IMPL_SfxBaseModel_DataContainer : public ::sfx2::IModifiableDocument
             ,   m_xNumberedControllers  ()
             ,   m_xDocumentMetadata     () // lazy
             ,   m_pDocumentUndoManager  ()
+            ,   m_cmisPropertiesValues  ()
+            ,   m_cmisPropertiesDisplayNames ()
     {
         // increase global instance counter.
         ++g_nInstanceCounter;
@@ -2514,6 +2518,30 @@ void SAL_CALL SfxBaseModel::notifyDocumentEvent( const ::rtl::OUString&, const u
     throw lang::NoSupportException( ::rtl::OUString( "SfxBaseModel controlls all the sent notifications itself!"  ), uno::Reference< uno::XInterface >() );
 }
 
+uno::Sequence< beans::PropertyValue > SAL_CALL SfxBaseModel::getCmisPropertiesValues()
+    throw ( uno::RuntimeException )
+{
+    return m_pData->m_cmisPropertiesValues;
+}
+
+void SAL_CALL SfxBaseModel::setCmisPropertiesValues( const uno::Sequence< beans::PropertyValue >& _cmispropertiesvalues )
+    throw ( uno::RuntimeException )
+{
+    m_pData->m_cmisPropertiesValues = _cmispropertiesvalues;
+}
+
+uno::Sequence< beans::PropertyValue > SAL_CALL SfxBaseModel::getCmisPropertiesDisplayNames()
+    throw ( uno::RuntimeException )
+{
+    return m_pData->m_cmisPropertiesDisplayNames;
+}
+
+void SAL_CALL SfxBaseModel::setCmisPropertiesDisplayNames( const uno::Sequence< beans::PropertyValue >& _cmispropertiesdisplaynames )
+    throw ( uno::RuntimeException )
+{
+    m_pData->m_cmisPropertiesDisplayNames = _cmispropertiesdisplaynames;
+}
+
 //________________________________________________________________________________________________________
 //  SfxListener
 //________________________________________________________________________________________________________
diff --git a/ucb/source/ucp/cmis/cmis_content.cxx b/ucb/source/ucp/cmis/cmis_content.cxx
index afd04ae..fbfa83b 100644
--- a/ucb/source/ucp/cmis/cmis_content.cxx
+++ b/ucb/source/ucp/cmis/cmis_content.cxx
@@ -30,6 +30,7 @@
 
 #include <com/sun/star/beans/PropertyAttribute.hpp>
 #include <com/sun/star/beans/PropertyValue.hpp>
+#include <com/sun/star/beans/PropertyValues.hpp>
 #include <com/sun/star/beans/XPropertySetInfo.hpp>
 #include <com/sun/star/io/XActiveDataSink.hpp>
 #include <com/sun/star/io/XActiveDataStreamer.hpp>
@@ -89,6 +90,123 @@ namespace
 
         return unoTime;
     }
+
+    uno::Any lcl_cmisPropertyToUno( libcmis::PropertyPtr pProperty )
+    {
+        uno::Any aValue;
+        bool bMultiValued = pProperty->getPropertyType( )->isMultiValued( );
+        switch ( pProperty->getPropertyType( )->getType( ) )
+        {
+            default:
+            case libcmis::PropertyType::String:
+                {
+                    vector< string > aCmisStrings = pProperty->getStrings( );
+                    if ( bMultiValued )
+                    {
+                        uno::Sequence< rtl::OUString > aStrings( aCmisStrings.size( ) );
+                        rtl::OUString* aStringsArr = aStrings.getArray( );
+                        sal_Int32 i = 0;
+                        for ( vector< string >::iterator it = aCmisStrings.begin( );
+                                it != aCmisStrings.end( ); ++it, ++i )
+                        {
+                            string str = *it;
+                            aStringsArr[i] = STD_TO_OUSTR( str );
+                        }
+                        aValue <<= aStrings;
+                    }
+                    else if ( !aCmisStrings.empty( ) )
+                    {
+                        aValue <<= STD_TO_OUSTR( aCmisStrings.front( ) );
+                    }
+                }
+                break;
+            case libcmis::PropertyType::Integer:
+                {
+                    vector< long > aCmisLongs = pProperty->getLongs( );
+                    if ( bMultiValued )
+                    {
+                        uno::Sequence< sal_Int64 > aLongs( aCmisLongs.size( ) );
+                        sal_Int64* aLongsArr = aLongs.getArray( );
+                        sal_Int32 i = 0;
+                        for ( vector< long >::iterator it = aCmisLongs.begin( );
+                                it != aCmisLongs.end( ); ++it, ++i )
+                        {
+                            aLongsArr[i] = *it;
+                        }
+                        aValue <<= aLongs;
+                    }
+                    else if ( !aCmisLongs.empty( ) )
+                    {
+                        aValue <<= aCmisLongs.front( );
+                    }
+                }
+                break;
+            case libcmis::PropertyType::Decimal:
+                {
+                    vector< double > aCmisDoubles = pProperty->getDoubles( );
+                    if ( bMultiValued )
+                    {
+                        uno::Sequence< double > aDoubles( aCmisDoubles.size( ) );
+                        double* aDoublesArr = aDoubles.getArray( );
+                        sal_Int32 i = 0;
+                        for ( vector< double >::iterator it = aCmisDoubles.begin( );
+                                it != aCmisDoubles.end( ); ++it, ++i )
+                        {
+                            aDoublesArr[i] = *it;
+                        }
+                        aValue <<= aDoubles;
+                    }
+                    else if ( !aCmisDoubles.empty( ) )
+                    {
+                        aValue <<= aCmisDoubles.front( );
+                    }
+                }
+                break;
+            case libcmis::PropertyType::Bool:
+                {
+                    vector< bool > aCmisBools = pProperty->getBools( );
+                    if ( bMultiValued )
+                    {
+                        uno::Sequence< sal_Bool > aBools( aCmisBools.size( ) );
+                        sal_Bool* aBoolsArr = aBools.getArray( );
+                        sal_Int32 i = 0;
+                        for ( vector< bool >::iterator it = aCmisBools.begin( );
+                                it != aCmisBools.end( ); ++it, ++i )
+                        {
+                            aBoolsArr[i] = *it;
+                        }
+                        aValue <<= aBools;
+                    }
+                    else if ( !aCmisBools.empty( ) )
+                    {
+                        aValue <<= sal_Bool( aCmisBools.front( ) );
+                    }
+                }
+                break;
+            case libcmis::PropertyType::DateTime:
+                {
+                    vector< boost::posix_time::ptime > aCmisTimes = pProperty->getDateTimes( );
+                    if ( bMultiValued )
+                    {
+                        uno::Sequence< util::DateTime > aTimes( aCmisTimes.size( ) );
+                        util::DateTime* aTimesArr = aTimes.getArray( );
+                        sal_Int32 i = 0;
+                        for ( vector< boost::posix_time::ptime >::iterator it = aCmisTimes.begin( );
+                                it != aCmisTimes.end( ); ++it, ++i )
+                        {
+                            aTimesArr[i] = lcl_boostToUnoTime( *it );
+                        }
+                        aValue <<= aTimes;
+                    }
+                    else if ( !aCmisTimes.empty( ) )
+                    {
+                        aValue <<= lcl_boostToUnoTime( aCmisTimes.front( ) );
+                    }
+                }
+                break;
+        }
+        return aValue;
+    }
 }
 
 namespace cmis
@@ -374,6 +492,53 @@ namespace cmis
                         xRow->appendVoid( rProp );
                     }
                 }
+                else if ( rProp.Name == "CmisPropertiesValues" )
+                {
+                    try
+                    {
+                        libcmis::ObjectPtr object = getObject( xEnv );
+                        map< string, libcmis::PropertyPtr >& aProperties = object->getProperties( );
+                        beans::PropertyValues aCmisProperties( aProperties.size( ) );
+                        beans::PropertyValue* pCmisProps = aCmisProperties.getArray( );
+                        sal_Int32 i = 0;
+                        for ( map< string, libcmis::PropertyPtr >::iterator it = aProperties.begin();
+                                it != aProperties.end( ); ++it, ++i )
+                        {
+                            string name = it->first;
+                            pCmisProps[i].Name = STD_TO_OUSTR( name );
+                            pCmisProps[i].Value = lcl_cmisPropertyToUno( it->second );
+                        }
+                        xRow->appendObject( rProp.Name, uno::makeAny( aCmisProperties ) );
+                    }
+                    catch ( const libcmis::Exception& )
+                    {
+                        xRow->appendVoid( rProp );
+                    }
+                }
+                else if ( rProp.Name == "CmisPropertiesDisplayNames" )
+                {
+                    try
+                    {
+                        libcmis::ObjectPtr object = getObject( xEnv );
+                        map< string, libcmis::PropertyPtr >& aProperties = object->getProperties( );
+                        beans::PropertyValues aCmisProperties( aProperties.size( ) );
+                        beans::PropertyValue* pCmisProps = aCmisProperties.getArray( );
+                        sal_Int32 i = 0;
+                        for ( map< string, libcmis::PropertyPtr >::iterator it = aProperties.begin();
+                                it != aProperties.end( ); ++it, ++i )
+                        {
+                            string name = it->first;
+                            string displayName = it->second->getPropertyType()->getDisplayName( );
+                            pCmisProps[i].Name = STD_TO_OUSTR( name );
+                            pCmisProps[i].Value = uno::makeAny( STD_TO_OUSTR( displayName ) );
+                        }
+                        xRow->appendObject( rProp.Name, uno::makeAny( aCmisProperties ) );
+                    }
+                    catch ( const libcmis::Exception& )
+                    {
+                        xRow->appendVoid( rProp );
+                    }
+                }
                 else
                     SAL_INFO( "cmisucp", "Looking for unsupported property " << rProp.Name );
             }
@@ -798,6 +963,12 @@ namespace cmis
             beans::Property( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "MediaType" ) ),
                 -1, getCppuType( static_cast< const rtl::OUString * >( 0 ) ),
                 beans::PropertyAttribute::BOUND ),
+            beans::Property( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "CmisPropertiesValues" ) ),
+                -1, getCppuType( static_cast< const beans::PropertyValues * >( 0 ) ),
+                beans::PropertyAttribute::BOUND ),
+            beans::Property( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "CmisPropertiesDisplayNames" ) ),
+                -1, getCppuType( static_cast< const beans::PropertyValues * >( 0 ) ),
+                beans::PropertyAttribute::BOUND ),
         };
 
         const int nProps = SAL_N_ELEMENTS(aGenericProperties);
commit 97aa108f2b595145d63b00d515489030a849957e
Author: Cédric Bosdonnat <cedric.bosdonnat at free.fr>
Date:   Fri Oct 5 15:37:26 2012 +0200

    InfoBars: first implementation
    
    Change-Id: I4b18f19f5cf13d648a8d10cc31c63bb330a86b6f

diff --git a/sfx2/Library_sfx.mk b/sfx2/Library_sfx.mk
index baf7138..eae3511 100644
--- a/sfx2/Library_sfx.mk
+++ b/sfx2/Library_sfx.mk
@@ -153,6 +153,7 @@ $(eval $(call gb_Library_add_exception_objects,sfx,\
     sfx2/source/dialog/filedlghelper \
     sfx2/source/dialog/filtergrouping \
     sfx2/source/dialog/itemconnect \
+    sfx2/source/dialog/infobar \
     sfx2/source/dialog/inputdlg \
     sfx2/source/dialog/mailmodel \
     sfx2/source/dialog/bluthsnd \
diff --git a/sfx2/Package_inc.mk b/sfx2/Package_inc.mk
index 4156354..3292506 100644
--- a/sfx2/Package_inc.mk
+++ b/sfx2/Package_inc.mk
@@ -63,6 +63,7 @@ $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/htmlmode.hxx,sfx2/htmlmode.h
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/imagemgr.hxx,sfx2/imagemgr.hxx))
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/imgdef.hxx,sfx2/imgdef.hxx))
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/imgmgr.hxx,sfx2/imgmgr.hxx))
+$(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/infobar.hxx,sfx2/infobar.hxx))
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/ipclient.hxx,sfx2/ipclient.hxx))
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/itemconnect.hxx,sfx2/itemconnect.hxx))
 $(eval $(call gb_Package_add_file,sfx2_inc,inc/sfx2/itemwrapper.hxx,sfx2/itemwrapper.hxx))
diff --git a/sfx2/inc/sfx2/infobar.hxx b/sfx2/inc/sfx2/infobar.hxx
new file mode 100644
index 0000000..00d521f
--- /dev/null
+++ b/sfx2/inc/sfx2/infobar.hxx
@@ -0,0 +1,77 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+#ifndef _SFX2_MESSAGEBAR_HXX_
+#define _SFX2_MESSAGEBAR_HXX_
+
+#include <vector>
+
+#include <vcl/button.hxx>
+#include <vcl/fixed.hxx>
+
+#include <sfx2/dllapi.h>
+#include <sfx2/childwin.hxx>
+
+/** SfxChildWindow for positioning the InfoBar in the view.
+  */
+class SFX2_DLLPUBLIC SfxInfoBarContainerChild : public SfxChildWindow
+{
+    private:
+        SfxBindings* m_pBindings;
+
+    public:
+        SfxInfoBarContainerChild( Window* pParent,
+                                  sal_uInt16 nId,
+                                  SfxBindings* pBindings,
+                                  SfxChildWinInfo* pInfo );
+        virtual ~SfxInfoBarContainerChild();
+
+        SFX_DECL_CHILDWINDOW_WITHID( SfxInfoBarContainerChild );
+
+        void Update( );
+};
+
+/** Class representing a single InfoBar to be added in a SfxInfoBarContainerWindow.
+  */
+class SfxInfoBarWindow : public Window
+{
+    private:
+        FixedText*                  m_pMessage;
+        Button*                     m_pCloseBtn;
+        std::vector< PushButton* >  m_aActionBtns;
+
+    public:
+        SfxInfoBarWindow( Window* parent,
+                          const rtl::OUString& sMessage,
+                          std::vector< PushButton* > aButtons );
+        ~SfxInfoBarWindow( );
+
+        virtual void Paint( const Rectangle& );
+
+    private:
+        DECL_LINK( CloseHandler, void* );
+};
+
+class SfxInfoBarContainerWindow : public Window
+{
+    private:
+        SfxInfoBarContainerChild*        m_pChildWin;
+        std::vector< SfxInfoBarWindow* > m_pInfoBars;
+
+    public:
+        SfxInfoBarContainerWindow( SfxInfoBarContainerChild* pChildWin );
+        ~SfxInfoBarContainerWindow( );
+
+        void appendInfoBar( const rtl::OUString& sMessage, std::vector< PushButton* > aButtons );
+        void removeInfoBar( SfxInfoBarWindow* pInfoBar );
+};
+
+
+#endif
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sfx2/inc/sfx2/sfxsids.hrc b/sfx2/inc/sfx2/sfxsids.hrc
index 549ac0e..0d3522b 100644
--- a/sfx2/inc/sfx2/sfxsids.hrc
+++ b/sfx2/inc/sfx2/sfxsids.hrc
@@ -592,6 +592,7 @@
 #define SID_HYPERLINK_GETLINK               (SID_SVX_START + 361)
 #define SID_HYPERLINK_SETLINK               (SID_SVX_START + 362)
 #define SID_NAVIGATOR                       (SID_SVX_START + 366)
+#define SID_INFOBARCONTAINER                (SID_SVX_START + 367)
 #define SID_TASKPANE                        (SID_SVX_START + 370)
 #define SID_ZOOM_NEXT                       (SID_SVX_START + 402)
 #define SID_ZOOM_PREV                       (SID_SVX_START + 403)
diff --git a/sfx2/inc/sfx2/viewfrm.hxx b/sfx2/inc/sfx2/viewfrm.hxx
index ce8622e..26b5e47 100644
--- a/sfx2/inc/sfx2/viewfrm.hxx
+++ b/sfx2/inc/sfx2/viewfrm.hxx
@@ -28,6 +28,7 @@
 #include <sfx2/shell.hxx>
 #include <sfx2/sfxsids.hrc>
 #include <svl/poolitem.hxx>
+#include <vcl/button.hxx>
 #include <com/sun/star/frame/status/Verb.hpp>
 #include <com/sun/star/frame/XModel.hpp>
 #include <com/sun/star/frame/XController2.hpp>
@@ -184,6 +185,13 @@ public:
     void                        ChildWindowExecute(SfxRequest&);
     void                        ChildWindowState(SfxItemSet&);
 
+    /** Append a new InfoBar (see https://wiki.documentfoundation.org/Design/Whiteboards/Infobar).
+
+        The buttons will be added from Right to Left at the right of the info bar. The parent, size
+        and position of each button will be changed: only the width will remain unchanged.
+      */
+    void                    AppendInfoBar( const rtl::OUString& sMessage, std::vector< PushButton* > aButtons );
+
     SAL_DLLPRIVATE void SetDowning_Impl();
     SAL_DLLPRIVATE void GetDocNumber_Impl();
     SAL_DLLPRIVATE sal_Bool IsDowning_Impl() const;
diff --git a/sfx2/source/appl/appreg.cxx b/sfx2/source/appl/appreg.cxx
index c407d73..0c54aa8 100644
--- a/sfx2/source/appl/appreg.cxx
+++ b/sfx2/source/appl/appreg.cxx
@@ -27,6 +27,7 @@
 #include <sfx2/templdlg.hxx>
 #include "inettbc.hxx"
 #include "sfx2/stbitem.hxx"
+#include <sfx2/infobar.hxx>
 #include <sfx2/navigat.hxx>
 #include <sfx2/taskpane.hxx>
 #include <sfx2/module.hxx>
@@ -56,6 +57,7 @@ void SfxApplication::Registrations_Impl()
     SfxPartChildWnd_Impl::RegisterChildWindow();
     SfxTemplateDialogWrapper::RegisterChildWindow(sal_True);
     SfxDockingWrapper::RegisterChildWindow();
+    SfxInfoBarContainerChild::RegisterChildWindow( sal_True, NULL, SFX_CHILDWIN_NEVERHIDE );
 
     // Controller
     SfxToolBoxControl::RegisterControl(SID_REPEAT);
diff --git a/sfx2/source/dialog/infobar.cxx b/sfx2/source/dialog/infobar.cxx
new file mode 100644
index 0000000..e72468c
--- /dev/null
+++ b/sfx2/source/dialog/infobar.cxx
@@ -0,0 +1,283 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
+/*
+ * This file is part of the LibreOffice project.
+ *
+ * This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
+ */
+
+#include <basegfx/polygon/b2dpolygon.hxx>
+#include <drawinglayer/primitive2d/polygonprimitive2d.hxx>
+#include <drawinglayer/primitive2d/polypolygonprimitive2d.hxx>
+#include <drawinglayer/processor2d/baseprocessor2d.hxx>
+#include <drawinglayer/processor2d/processorfromoutputdevice.hxx>
+#include <sfx2/bindings.hxx>
+#include <sfx2/dispatch.hxx>
+#include <sfx2/infobar.hxx>
+#include <sfx2/objsh.hxx>
+#include <sfx2/sfx.hrc>
+#include <sfx2/viewsh.hxx>
+
+using namespace std;
+
+namespace
+{
+    class SfxCloseButton : public PushButton
+    {
+        public:
+            SfxCloseButton( Window* pParent ) : PushButton( pParent, 0 )
+            {
+            }
+
+            ~SfxCloseButton( ) { }
+
+            virtual void Paint( const Rectangle& rRect );
+    };
+
+    void SfxCloseButton::Paint( const Rectangle& )
+    {
+        const drawinglayer::geometry::ViewInformation2D aNewViewInfos;
+        drawinglayer::processor2d::BaseProcessor2D * pProcessor =
+            drawinglayer::processor2d::createBaseProcessor2DFromOutputDevice(
+                        *this, aNewViewInfos );
+
+        const Rectangle aRect( Rectangle( Point( 0, 0 ), PixelToLogic( GetSizePixel() ) ) );
+
+        drawinglayer::primitive2d::Primitive2DSequence aSeq( 2 );
+
+        basegfx::BColor aLightColor( 1.0, 1.0, 191.0 / 255.0 );
+        basegfx::BColor aDarkColor( 217.0 / 255.0, 217.0 / 255.0, 78.0 / 255.0 );
+
+        // Light background
+        basegfx::B2DPolygon aPolygon;
+        aPolygon.append( basegfx::B2DPoint( aRect.Left( ), aRect.Top( ) ) );
+        aPolygon.append( basegfx::B2DPoint( aRect.Right( ), aRect.Top( ) ) );
+        aPolygon.append( basegfx::B2DPoint( aRect.Right( ), aRect.Bottom( ) ) );
+        aPolygon.append( basegfx::B2DPoint( aRect.Left( ), aRect.Bottom( ) ) );
+        aPolygon.setClosed( true );
+        drawinglayer::primitive2d::PolyPolygonColorPrimitive2D* pBack =
+            new drawinglayer::primitive2d::PolyPolygonColorPrimitive2D(
+                    basegfx::B2DPolyPolygon( aPolygon ), aLightColor );
+        aSeq[0] = pBack;
+
+        drawinglayer::attribute::LineAttribute aLineAttribute( aDarkColor, 2.0 );
+
+        // Cross
+        basegfx::B2DPolyPolygon aCross;
+        basegfx::B2DPolygon aLine1;
+        aLine1.append( basegfx::B2DPoint( aRect.Left(), aRect.Top( ) ) );
+        aLine1.append( basegfx::B2DPoint( aRect.Right(), aRect.Bottom( ) ) );
+        aCross.append( aLine1 );
+        basegfx::B2DPolygon aLine2;
+        aLine2.append( basegfx::B2DPoint( aRect.Right(), aRect.Top( ) ) );
+        aLine2.append( basegfx::B2DPoint( aRect.Left(), aRect.Bottom( ) ) );
+        aCross.append( aLine2 );
+
+        drawinglayer::primitive2d::PolyPolygonStrokePrimitive2D * pCross =
+                new drawinglayer::primitive2d::PolyPolygonStrokePrimitive2D (
+                    aCross, aLineAttribute, drawinglayer::attribute::StrokeAttribute( ) );
+
+        aSeq[1] = pCross;
+
+        pProcessor->process( aSeq );
+        delete pProcessor;
+    }
+}
+
+SfxInfoBarWindow::SfxInfoBarWindow( Window* pParent, const rtl::OUString& sMessage,
+       vector< PushButton* > aButtons ) :
+    Window( pParent, 0 ),
+    m_pMessage( NULL ),
+    m_pCloseBtn( NULL ),
+    m_aActionBtns( aButtons )
+{
+    long nWidth = pParent->GetSizePixel().getWidth();
+    SetPosSizePixel( Point( 0, 0 ), Size( nWidth, 40 ) );
+    m_pMessage = new FixedText( this, 0 );
+    m_pMessage->SetText( sMessage );
+    m_pMessage->SetBackground( Wallpaper( Color(  255, 255, 191 ) ) );
+    m_pMessage->Show( );
+
+    m_pCloseBtn = new SfxCloseButton( this );
+    m_pCloseBtn->SetPosSizePixel( Point( nWidth - 25, 15 ), Size( 10, 10 ) );
+    m_pCloseBtn->SetClickHdl( LINK( this, SfxInfoBarWindow, CloseHandler ) );
+    m_pCloseBtn->Show( );
+
+    // Reparent the buttons and place them on the right of the bar
+    long nX = m_pCloseBtn->GetPosPixel( ).getX( ) - 15;
+    long nBtnGap = 5;
+    for ( vector< PushButton* >::iterator it = m_aActionBtns.begin( );
+            it != m_aActionBtns.end( ); ++it )
+    {
+        PushButton* pBtn = *it;
+        pBtn->SetParent( this );
+        long nBtnWidth = pBtn->GetSizePixel( ).getWidth();
+        nX -= nBtnWidth;
+        pBtn->SetPosSizePixel( Point( nX, 5 ), Size( nBtnWidth, 30 ) );
+        nX -= nBtnGap;
+        pBtn->Show( );
+    }
+
+    m_pMessage->SetPosSizePixel( Point( 10, 10 ), Size( nX - 20, 20 ) );
+}
+
+SfxInfoBarWindow::~SfxInfoBarWindow( )
+{
+    delete m_pMessage;
+    delete m_pCloseBtn;
+
+    for ( vector< PushButton* >::iterator it = m_aActionBtns.begin( );
+            it != m_aActionBtns.end( ); ++it )
+    {
+        delete *it;
+    }
+    m_aActionBtns.clear( );
+}
+
+void SfxInfoBarWindow::Paint( const Rectangle& rPaintRect )
+{
+    const drawinglayer::geometry::ViewInformation2D aNewViewInfos;
+    drawinglayer::processor2d::BaseProcessor2D * pProcessor =
+        drawinglayer::processor2d::createBaseProcessor2DFromOutputDevice(
+                    *this, aNewViewInfos );
+
+    const Rectangle aRect( Rectangle( Point( 0, 0 ), PixelToLogic( GetSizePixel() ) ) );
+
+    drawinglayer::primitive2d::Primitive2DSequence aSeq( 2 );
+
+    basegfx::BColor aLightColor( 1.0, 1.0, 191.0 / 255.0 );
+    basegfx::BColor aDarkColor( 217.0 / 255.0, 217.0 / 255.0, 78.0 / 255.0 );
+
+    // Light background
+    basegfx::B2DPolygon aPolygon;
+    aPolygon.append( basegfx::B2DPoint( aRect.Left( ), aRect.Top( ) ) );
+    aPolygon.append( basegfx::B2DPoint( aRect.Right( ), aRect.Top( ) ) );
+    aPolygon.append( basegfx::B2DPoint( aRect.Right( ), aRect.Bottom( ) ) );
+    aPolygon.append( basegfx::B2DPoint( aRect.Left( ), aRect.Bottom( ) ) );
+    aPolygon.setClosed( true );
+    drawinglayer::primitive2d::PolyPolygonColorPrimitive2D* pBack =
+        new drawinglayer::primitive2d::PolyPolygonColorPrimitive2D(
+                basegfx::B2DPolyPolygon( aPolygon ), aLightColor );
+    aSeq[0] = pBack;
+
+    drawinglayer::attribute::LineAttribute aLineAttribute( aDarkColor, 1.0 );
+
+    // Bottom dark line
+    basegfx::B2DPolygon aPolygonBottom;
+    aPolygonBottom.append( basegfx::B2DPoint( aRect.Left(), aRect.Bottom( ) ) );
+    aPolygonBottom.append( basegfx::B2DPoint( aRect.Right(), aRect.Bottom( ) ) );
+
+    drawinglayer::primitive2d::PolygonStrokePrimitive2D * pLineBottom =
+            new drawinglayer::primitive2d::PolygonStrokePrimitive2D (
+                aPolygonBottom, aLineAttribute );
+
+    aSeq[1] = pLineBottom;
+
+    pProcessor->process( aSeq );
+    delete pProcessor;
+
+    Window::Paint( rPaintRect );
+}
+
+IMPL_LINK_NOARG( SfxInfoBarWindow, CloseHandler )
+{
+    ((SfxInfoBarContainerWindow*)GetParent())->removeInfoBar( this );
+    return 0;
+}
+
+SfxInfoBarContainerWindow::SfxInfoBarContainerWindow( SfxInfoBarContainerChild* pChildWin ) :
+    Window( pChildWin->GetParent( ), 0 ),
+    m_pChildWin( pChildWin ),
+    m_pInfoBars( )
+{
+}
+
+SfxInfoBarContainerWindow::~SfxInfoBarContainerWindow( )
+{
+    for ( vector< SfxInfoBarWindow* >::iterator it = m_pInfoBars.begin( );
+            it != m_pInfoBars.end( ); ++it )
+    {
+        delete *it;
+    }
+    m_pInfoBars.clear( );
+}
+
+void SfxInfoBarContainerWindow::appendInfoBar( const rtl::OUString& sMessage, vector< PushButton* > aButtons )
+{
+    Size aSize = GetSizePixel( );
+
+    SfxInfoBarWindow* pInfoBar = new SfxInfoBarWindow( this, sMessage, aButtons );
+    pInfoBar->SetPosPixel( Point( 0, aSize.getHeight( ) ) );
+    m_pInfoBars.push_back( pInfoBar );
+    pInfoBar->Show( );
+
+    long nHeight = pInfoBar->GetSizePixel( ).getHeight( );
+    aSize.setHeight( aSize.getHeight() + nHeight );
+    SetSizePixel( aSize );
+}
+
+void SfxInfoBarContainerWindow::removeInfoBar( SfxInfoBarWindow* pInfoBar )
+{
+    for ( vector< SfxInfoBarWindow* >::iterator it = m_pInfoBars.begin( );
+            it != m_pInfoBars.end( ); ++it )
+    {
+        if ( pInfoBar == *it )
+        {
+            m_pInfoBars.erase( it );
+            break;
+        }
+    }
+    delete pInfoBar;
+
+    long nY = 0;
+    for ( vector< SfxInfoBarWindow* >::iterator it = m_pInfoBars.begin( ); it != m_pInfoBars.end( ); ++it )
+    {
+        SfxInfoBarWindow* pBar = *it;
+        pBar->SetPosPixel( Point( 0, nY ) );
+        nY += pBar->GetSizePixel( ).getHeight( );
+    }
+
+    Size aSize = GetSizePixel( );
+    aSize.setHeight( nY );
+    SetSizePixel( aSize );
+
+    m_pChildWin->Update( );
+}
+
+
+SFX_IMPL_POS_CHILDWINDOW_WITHID( SfxInfoBarContainerChild, SID_INFOBARCONTAINER, SFX_OBJECTBAR_OBJECT );
+
+SfxInfoBarContainerChild::SfxInfoBarContainerChild( Window* _pParent, sal_uInt16 nId, SfxBindings* pBindings, SfxChildWinInfo* ) :
+    SfxChildWindow( _pParent, nId ),
+    m_pBindings( pBindings )
+{
+    pWindow = new SfxInfoBarContainerWindow( this );
+    pWindow->SetPosSizePixel( Point( 0, 0 ), Size( _pParent->GetSizePixel( ).getWidth(), 0 ) );
+    pWindow->Show( );
+
+    eChildAlignment = SFX_ALIGN_LOWESTTOP;
+}
+
+SfxInfoBarContainerChild::~SfxInfoBarContainerChild( )
+{
+}
+
+SfxChildWinInfo SfxInfoBarContainerChild::GetInfo( ) const
+{
+    SfxChildWinInfo aInfo = SfxChildWindow::GetInfo();
+    return aInfo;
+}
+
+void SfxInfoBarContainerChild::Update( )
+{
+    // Refresh the frame to take the infobars container height change into account
+    const sal_uInt16 nId = GetChildWindowId();
+    SfxViewFrame* pVFrame = m_pBindings->GetDispatcher( )->GetFrame( );
+    pVFrame->ShowChildWindow( nId );
+
+    // Give the focus to the document view
+    pVFrame->GetWindow().GrabFocusToDocument();
+}
+
+/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
diff --git a/sfx2/source/view/viewfrm.cxx b/sfx2/source/view/viewfrm.cxx
index 83c10ea..ad8dfc7 100644
--- a/sfx2/source/view/viewfrm.cxx
+++ b/sfx2/source/view/viewfrm.cxx
@@ -20,6 +20,7 @@
 
 #include <stdio.h>
 
+#include <sfx2/infobar.hxx>
 #include <sfx2/viewfrm.hxx>
 #include <com/sun/star/document/MacroExecMode.hpp>
 #include <com/sun/star/frame/XLoadable.hpp>
@@ -3349,4 +3350,14 @@ void SfxViewFrame::ActivateToolPanel_Impl( const ::rtl::OUString& i_rPanelURL )
     pPanelAccess->ActivateToolPanel( i_rPanelURL );
 }
 
+void SfxViewFrame::AppendInfoBar( const rtl::OUString& sMessage, std::vector< PushButton* > aButtons )
+{
+    const sal_uInt16 nId = SfxInfoBarContainerChild::GetChildWindowId();
+    ShowChildWindow( nId );
+    SfxChildWindow* pChild = GetChildWindow( nId );
+    SfxInfoBarContainerWindow* pInfoBars = ( SfxInfoBarContainerWindow* )pChild->GetWindow();
+    pInfoBars->appendInfoBar( sMessage, aButtons );
+    ShowChildWindow( nId );
+}
+
 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */


More information about the Libreoffice-commits mailing list