sfx2/source/dialog/filedlghelper.cxx | 31 +++++++++++++- vcl/unx/gtk3/fpicker/SalGtkFilePicker.cxx | 58 +++++++++++++++------------- vcl/unx/gtk3/fpicker/SalGtkFilePicker.hxx | 1 vcl/unx/gtk3/fpicker/SalGtkFolderPicker.cxx | 15 ++++++- vcl/unx/gtk3/fpicker/SalGtkFolderPicker.hxx | 6 ++ vcl/unx/gtk3/fpicker/SalGtkPicker.cxx | 4 + vcl/unx/gtk3/fpicker/SalGtkPicker.hxx | 3 + 7 files changed, 85 insertions(+), 33 deletions(-)
New commits: commit 203d96787969f707c78101be18d51b44ace98f93 Author: Caolán McNamara <caol...@redhat.com> AuthorDate: Mon Jun 21 13:01:52 2021 +0100 Commit: Caolán McNamara <caol...@redhat.com> CommitDate: Mon Jun 21 16:06:56 2021 +0200 give folderpicker an optional parent so, like a file picker, it can make its parent modal while its operating. Otherwise its possible to interact with the parent dialog in undesirable ways, e.g. file, export as, export as epub, the folder picker of 'media directory' Change-Id: Ib61f8e630e176b6d81e80798fd0d282d16e8c086 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/117582 Tested-by: Jenkins Reviewed-by: Caolán McNamara <caol...@redhat.com> diff --git a/sfx2/source/dialog/filedlghelper.cxx b/sfx2/source/dialog/filedlghelper.cxx index 482b2146afdf..b9750c142967 100644 --- a/sfx2/source/dialog/filedlghelper.cxx +++ b/sfx2/source/dialog/filedlghelper.cxx @@ -785,7 +785,7 @@ ErrCode FileDialogHelper_Impl::getGraphic( Graphic& rGraphic ) const return nRet; } -static bool lcl_isSystemFilePicker( const uno::Reference< XFilePicker3 >& _rxFP ) +static bool lcl_isSystemFilePicker( const uno::Reference< XExecutableDialog >& _rxFP ) { try { @@ -1132,9 +1132,34 @@ FileDialogHelper_Impl::FileDialogHelper_Impl( mxFileDlg->addFilePickerListener( this ); } -css::uno::Reference<css::ui::dialogs::XFolderPicker2> createFolderPicker(const css::uno::Reference<css::uno::XComponentContext>& rContext, weld::Window* /*pPreferredParent*/) +css::uno::Reference<css::ui::dialogs::XFolderPicker2> createFolderPicker(const css::uno::Reference<css::uno::XComponentContext>& rContext, weld::Window* pPreferredParent) { - return css::ui::dialogs::FolderPicker::create(rContext); + auto xRet = css::ui::dialogs::FolderPicker::create(rContext); + + // see FileDialogHelper_Impl::FileDialogHelper_Impl (above) for args to FilePicker + // reuse the same arguments for FolderPicker + if (pPreferredParent && lcl_isSystemFilePicker(xRet)) + { + uno::Reference< XInitialization > xInit(xRet, UNO_QUERY); + if (xInit.is()) + { + Sequence<Any> aInitArguments(2); + + aInitArguments[0] <<= sal_Int32(0); + aInitArguments[1] <<= pPreferredParent->GetXWindow(); + + try + { + xInit->initialize(aInitArguments); + } + catch (const Exception&) + { + OSL_FAIL( "createFolderPicker: could not initialize the picker!" ); + } + } + } + + return xRet; } FileDialogHelper_Impl::~FileDialogHelper_Impl() diff --git a/vcl/unx/gtk3/fpicker/SalGtkFilePicker.cxx b/vcl/unx/gtk3/fpicker/SalGtkFilePicker.cxx index d2d5c6ea7642..cb73a86c3af3 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkFilePicker.cxx +++ b/vcl/unx/gtk3/fpicker/SalGtkFilePicker.cxx @@ -83,7 +83,6 @@ void SalGtkFilePicker::InitialMapping() SalGtkFilePicker::SalGtkFilePicker( const uno::Reference< uno::XComponentContext >& xContext ) : SalGtkPicker( xContext ), SalGtkFilePicker_Base( m_rbHelperMtx ), - m_pParentWidget ( nullptr ), m_pVBox ( nullptr ), mnHID_FolderChange( 0 ), mnHID_SelectionChange( 0 ), @@ -1589,6 +1588,38 @@ sal_Bool SAL_CALL SalGtkFilePicker::getShowState() return mbPreviewState; } +GtkWidget* SalGtkPicker::GetParentWidget(const uno::Sequence<uno::Any>& rArguments) +{ + GtkWidget* pParentWidget = nullptr; + + css::uno::Reference<css::awt::XWindow> xParentWindow; + if (rArguments.getLength() > 1) + { + rArguments[1] >>= xParentWindow; + } + + if (xParentWindow.is()) + { + if (SalGtkXWindow* pGtkXWindow = dynamic_cast<SalGtkXWindow*>(xParentWindow.get())) + pParentWidget = pGtkXWindow->getGtkWidget(); + else + { + css::uno::Reference<css::awt::XSystemDependentWindowPeer> xSysDepWin(xParentWindow, css::uno::UNO_QUERY); + if (xSysDepWin.is()) + { + css::uno::Sequence<sal_Int8> aProcessIdent(16); + rtl_getGlobalProcessId(reinterpret_cast<sal_uInt8*>(aProcessIdent.getArray())); + uno::Any aAny = xSysDepWin->getWindowHandle(aProcessIdent, css::lang::SystemDependent::SYSTEM_XWINDOW); + css::awt::SystemDependentXWindow tmp; + aAny >>= tmp; + pParentWidget = GetGtkSalData()->GetGtkDisplay()->findGtkWidgetForNativeHandle(tmp.WindowHandle); + } + } + } + + return pParentWidget; +} + // XInitialization void SAL_CALL SalGtkFilePicker::initialize( const uno::Sequence<uno::Any>& aArguments ) @@ -1611,30 +1642,7 @@ void SAL_CALL SalGtkFilePicker::initialize( const uno::Sequence<uno::Any>& aArgu sal_Int16 templateId = -1; aAny >>= templateId; - css::uno::Reference<css::awt::XWindow> xParentWindow; - if (aArguments.getLength() > 1) - { - aArguments[1] >>= xParentWindow; - } - - if (xParentWindow.is()) - { - if (SalGtkXWindow* pGtkXWindow = dynamic_cast<SalGtkXWindow*>(xParentWindow.get())) - m_pParentWidget = pGtkXWindow->getGtkWidget(); - else - { - css::uno::Reference<css::awt::XSystemDependentWindowPeer> xSysDepWin(xParentWindow, css::uno::UNO_QUERY); - if (xSysDepWin.is()) - { - css::uno::Sequence<sal_Int8> aProcessIdent(16); - rtl_getGlobalProcessId(reinterpret_cast<sal_uInt8*>(aProcessIdent.getArray())); - aAny = xSysDepWin->getWindowHandle(aProcessIdent, css::lang::SystemDependent::SYSTEM_XWINDOW); - css::awt::SystemDependentXWindow tmp; - aAny >>= tmp; - m_pParentWidget = GetGtkSalData()->GetGtkDisplay()->findGtkWidgetForNativeHandle(tmp.WindowHandle); - } - } - } + m_pParentWidget = GetParentWidget(aArguments); GtkFileChooserAction eAction = GTK_FILE_CHOOSER_ACTION_OPEN; OString sOpen = getOpenText(); diff --git a/vcl/unx/gtk3/fpicker/SalGtkFilePicker.hxx b/vcl/unx/gtk3/fpicker/SalGtkFilePicker.hxx index 5797a7a04e19..4c07f1b9cc16 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkFilePicker.hxx +++ b/vcl/unx/gtk3/fpicker/SalGtkFilePicker.hxx @@ -147,7 +147,6 @@ class SalGtkFilePicker : public SalGtkPicker, public SalGtkFilePicker_Base css::uno::Reference< css::ui::dialogs::XFilePickerListener > m_xListener; std::unique_ptr<std::vector<FilterEntry>> m_pFilterVector; - GtkWidget *m_pParentWidget; GtkWidget *m_pVBox; GtkWidget *m_pFilterExpander; GtkWidget *m_pFilterView; diff --git a/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.cxx b/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.cxx index 21ac1b533d9b..ae617d5af181 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.cxx +++ b/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.cxx @@ -156,8 +156,12 @@ sal_Int16 SAL_CALL SalGtkFolderPicker::execute() uno::Reference<frame::XDesktop> xDesktop = frame::Desktop::create(m_xContext); - GtkWindow *pParent = RunDialog::GetTransientFor(); - fprintf(stderr, "transient is %p\n", pParent); + GtkWindow *pParent = GTK_WINDOW(m_pParentWidget); + if (!pParent) + { + SAL_WARN( "vcl.gtk", "no parent widget set"); + pParent = RunDialog::GetTransientFor(); + } if (pParent) gtk_window_set_transient_for(GTK_WINDOW(m_pDialog), pParent); rtl::Reference<RunDialog> pRunDialog = new RunDialog(m_pDialog, xToolkit, xDesktop); @@ -179,6 +183,13 @@ sal_Int16 SAL_CALL SalGtkFolderPicker::execute() return retVal; } +// XInitialization + +void SAL_CALL SalGtkFolderPicker::initialize(const uno::Sequence<uno::Any>& aArguments) +{ + m_pParentWidget = GetParentWidget(aArguments); +} + // XCancellable void SAL_CALL SalGtkFolderPicker::cancel() diff --git a/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.hxx b/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.hxx index a7425d683f64..5b1d8dcebf72 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.hxx +++ b/vcl/unx/gtk3/fpicker/SalGtkFolderPicker.hxx @@ -27,7 +27,7 @@ class SalGtkFolderPicker : public SalGtkPicker, - public cppu::WeakImplHelper< css::ui::dialogs::XFolderPicker2 > + public cppu::WeakImplHelper<css::ui::dialogs::XFolderPicker2, css::lang::XInitialization> { public: @@ -50,6 +50,10 @@ class SalGtkFolderPicker : virtual void SAL_CALL setDescription( const OUString& rDescription ) override; + // XInitialization + + virtual void SAL_CALL initialize( const css::uno::Sequence< css::uno::Any >& aArguments ) override; + // XCancellable virtual void SAL_CALL cancel( ) override; diff --git a/vcl/unx/gtk3/fpicker/SalGtkPicker.cxx b/vcl/unx/gtk3/fpicker/SalGtkPicker.cxx index a14582bc2b20..6f7a927c3e84 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkPicker.cxx +++ b/vcl/unx/gtk3/fpicker/SalGtkPicker.cxx @@ -226,7 +226,9 @@ IMPL_STATIC_LINK(RunDialog, TerminateDesktop, void*, p, void) } SalGtkPicker::SalGtkPicker( const uno::Reference<uno::XComponentContext>& xContext ) - : m_pDialog( nullptr ), m_xContext( xContext ) + : m_pParentWidget(nullptr) + , m_pDialog(nullptr) + , m_xContext(xContext) { } diff --git a/vcl/unx/gtk3/fpicker/SalGtkPicker.hxx b/vcl/unx/gtk3/fpicker/SalGtkPicker.hxx index 36cab844df52..8ebdcfdd4630 100644 --- a/vcl/unx/gtk3/fpicker/SalGtkPicker.hxx +++ b/vcl/unx/gtk3/fpicker/SalGtkPicker.hxx @@ -55,6 +55,7 @@ class SalGtkPicker virtual ~SalGtkPicker(); protected: osl::Mutex m_rbHelperMtx; + GtkWidget *m_pParentWidget; GtkWidget *m_pDialog; protected: /// @throws css::uno::RuntimeException @@ -72,6 +73,8 @@ class SalGtkPicker // to instantiate own services css::uno::Reference< css::uno::XComponentContext > m_xContext; + static GtkWidget* GetParentWidget(const css::uno::Sequence<css::uno::Any>& rArguments); + static OUString getResString( sal_Int32 aId ); }; _______________________________________________ Libreoffice-commits mailing list libreoffice-comm...@lists.freedesktop.org https://lists.freedesktop.org/mailman/listinfo/libreoffice-commits