Kaydet (Commit) 9be8c4f2 authored tarafından Michael Stahl's avatar Michael Stahl

sfx2: remove the global SidebarController::maSidebarControllerContainer

This global was crashing on exit, unsurprising as it contains UNO
services that reference VCL objects.

It turns out that there is already a UNO singleton
framework::ContextChangeEventMultiplexer that effectively contains this
mapping already, so try to hook that up without creating a public API of
it, which is made quite a bit harder by framework's inexplicable
multitude of libraries.

Change-Id: I4baf67b42c630191fa8879d650eeb62520c331a5
üst a792aa2c
......@@ -28,6 +28,7 @@
#include <com/sun/star/container/XContainerListener.hpp>
#include <com/sun/star/frame/XFrame.hpp>
#include <com/sun/star/uno/XComponentContext.hpp>
#include <com/sun/star/ui/XContextChangeEventListener.hpp>
#include <cppuhelper/implbase1.hxx>
......@@ -36,6 +37,7 @@
#include <rtl/ustring.hxx>
#include <fwidllapi.h>
#include <functional>
#include <set>
namespace framework
......@@ -304,6 +306,16 @@ class WeakDocumentEventListener : public ::cppu::WeakImplHelper1<com::sun::star:
}
};
FWI_DLLPUBLIC css::uno::Reference<css::ui::XContextChangeEventListener>
GetFirstListenerWith_Impl(
css::uno::Reference<css::uno::XInterface> const& xEventFocus,
std::function<bool (css::uno::Reference<css::ui::XContextChangeEventListener> const&)> const& rPredicate);
FWI_DLLPUBLIC extern auto (*g_pGetMultiplexerListener)(
css::uno::Reference<css::uno::XInterface> const&,
std::function<bool (css::uno::Reference<css::ui::XContextChangeEventListener> const&)> const&)
-> css::uno::Reference<css::ui::XContextChangeEventListener>;
} // namespace framework
#endif // INCLUDED_FRAMEWORK_INC_HELPER_MISCHELPER_HXX
......
......@@ -18,6 +18,8 @@
*/
#include <framework/sfxhelperfunctions.hxx>
#include <framework/ContextChangeEventMultiplexerTunnel.hxx>
#include <helper/mischelper.hxx>
#include <tools/diagnose_ex.h>
......@@ -163,6 +165,14 @@ void SAL_CALL ActivateToolPanel( const ::com::sun::star::uno::Reference< ::com::
(*pActivator)( i_rFrame, i_rPanelURL );
}
using namespace ::com::sun::star;
uno::Reference<ui::XContextChangeEventListener> GetFirstListenerWith(
uno::Reference<uno::XInterface> const& xEventFocus,
std::function<bool (uno::Reference<ui::XContextChangeEventListener> const&)> const& rPredicate)
{
return GetFirstListenerWith_Impl(xEventFocus, rPredicate);
}
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
......@@ -212,6 +212,21 @@ void FillLangItems( std::set< OUString > &rLangItems,
}
}
auto (*g_pGetMultiplexerListener)(
uno::Reference<uno::XInterface> const&,
std::function<bool (uno::Reference<ui::XContextChangeEventListener> const&)> const&)
-> uno::Reference<ui::XContextChangeEventListener> = nullptr;
uno::Reference<ui::XContextChangeEventListener>
GetFirstListenerWith_Impl(
uno::Reference<uno::XInterface> const& xEventFocus,
std::function<bool (uno::Reference<ui::XContextChangeEventListener> const&)> const& rPredicate)
{
assert(g_pGetMultiplexerListener != nullptr); // should not be called too early, nor too late
return g_pGetMultiplexerListener(xEventFocus, rPredicate);
}
} // namespace framework
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
......@@ -17,6 +17,8 @@
* the License at http://www.apache.org/licenses/LICENSE-2.0 .
*/
#include <helper/mischelper.hxx>
#include <com/sun/star/lang/XComponent.hpp>
#include <com/sun/star/lang/XEventListener.hpp>
#include <com/sun/star/lang/XServiceInfo.hpp>
......@@ -88,7 +90,6 @@ public:
const css::lang::EventObject& rEvent)
throw (cssu::RuntimeException, std::exception) SAL_OVERRIDE;
private:
typedef ::std::vector<cssu::Reference<css::ui::XContextChangeEventListener> > ListenerContainer;
class FocusDescriptor
{
......@@ -362,6 +363,50 @@ struct Singleton:
}
namespace framework {
// right now we assume there's one matching listener
uno::Reference<ui::XContextChangeEventListener> GetFirstListenerWith_ImplImpl(
uno::Reference<uno::XInterface> const& xEventFocus,
std::function<bool (uno::Reference<ui::XContextChangeEventListener> const&)> const& rPredicate)
{
assert(xEventFocus.is()); // in current usage it's a bug if the XController is null here
uno::Reference<ui::XContextChangeEventListener> xRet;
ContextChangeEventMultiplexer *const pMultiplexer(
dynamic_cast<ContextChangeEventMultiplexer *>(Singleton::get().instance.get()));
assert(pMultiplexer);
ContextChangeEventMultiplexer::FocusDescriptor const*const pFocusDescriptor(
pMultiplexer->GetFocusDescriptor(xEventFocus, false));
if (!pFocusDescriptor)
return xRet;
for (auto & xListener : pFocusDescriptor->maListeners)
{
if (rPredicate(xListener))
{
assert(!xRet.is()); // generalize this if it is used for more than 1:1 mapping?
xRet = xListener;
}
}
return xRet;
}
namespace {
struct Hook
{
Hook() { g_pGetMultiplexerListener = &GetFirstListenerWith_ImplImpl; }
~Hook() { g_pGetMultiplexerListener = nullptr; }
};
static Hook g_hook;
}
}
extern "C" SAL_DLLPUBLIC_EXPORT css::uno::XInterface * SAL_CALL
org_apache_openoffice_comp_framework_ContextChangeEventMultiplexer_get_implementation(
css::uno::XComponentContext *,
......
......@@ -21,8 +21,6 @@
#include <sal/config.h>
#include <map>
#include <sfx2/sidebar/AsynchronousCall.hxx>
#include <sfx2/sidebar/Context.hxx>
#include <sfx2/sidebar/FocusManager.hxx>
......@@ -43,8 +41,6 @@
#include <boost/optional.hpp>
#include <cppuhelper/compbase4.hxx>
#include <cppuhelper/basemutex.hxx>
#include <cppuhelper/weakref.hxx>
namespace
......@@ -161,11 +157,6 @@ public:
void notifyDeckTitle(const OUString& targetDeckId);
private:
typedef ::std::map<
const css::uno::Reference<css::frame::XController>,
css::uno::WeakReference<SidebarController>
> SidebarControllerContainer;
static SidebarControllerContainer maSidebarControllerContainer;
VclPtr<Deck> mpCurrentDeck;
VclPtr<SidebarDockingWindow> mpParentWindow;
......
......@@ -35,6 +35,7 @@
#include <sfx2/sfxsids.hrc>
#include <sfx2/titledockwin.hxx>
#include "sfxlocal.hrc"
#include <framework/ContextChangeEventMultiplexerTunnel.hxx>
#include <vcl/floatwin.hxx>
#include <vcl/fixed.hxx>
#include "splitwin.hxx"
......@@ -71,8 +72,6 @@ namespace
namespace sfx2 { namespace sidebar {
SidebarController::SidebarControllerContainer SidebarController::maSidebarControllerContainer;
namespace {
enum MenuId
{
......@@ -150,15 +149,13 @@ SidebarController::~SidebarController()
SidebarController* SidebarController::GetSidebarControllerForFrame (
const css::uno::Reference<css::frame::XFrame>& rxFrame)
{
SidebarControllerContainer::iterator iEntry (maSidebarControllerContainer.find(rxFrame->getController()));
if (iEntry == maSidebarControllerContainer.end())
return NULL;
css::uno::Reference<XInterface> xController (iEntry->second.get());
if ( ! xController.is())
return NULL;
uno::Reference<ui::XContextChangeEventListener> const xListener(
framework::GetFirstListenerWith(rxFrame->getController(),
[] (uno::Reference<uno::XInterface> const& xRef)
{ return nullptr != dynamic_cast<SidebarController*>(xRef.get()); }
));
return dynamic_cast<SidebarController*>(xController.get());
return dynamic_cast<SidebarController*>(xListener.get());
}
void SidebarController::registerSidebarForFrame(SidebarController* pController, css::uno::Reference<css::frame::XController> xController)
......@@ -171,20 +168,10 @@ void SidebarController::registerSidebarForFrame(SidebarController* pController,
xMultiplexer->addContextChangeEventListener(
static_cast<css::ui::XContextChangeEventListener*>(pController),
xController);
WeakReference<SidebarController> xWeakController (pController);
maSidebarControllerContainer.insert(
SidebarControllerContainer::value_type(
xController,
xWeakController));
}
void SidebarController::unregisterSidebarForFrame(SidebarController* pController, css::uno::Reference<css::frame::XController> xController)
{
SidebarControllerContainer::iterator iEntry (maSidebarControllerContainer.find(xController));
if (iEntry != maSidebarControllerContainer.end())
maSidebarControllerContainer.erase(iEntry);
css::uno::Reference<css::ui::XContextChangeEventMultiplexer> xMultiplexer (
css::ui::ContextChangeEventMultiplexer::get(
::comphelper::getProcessComponentContext()));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment