summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/svl/broadcast.hxx14
-rw-r--r--svl/source/notify/broadcast.cxx30
2 files changed, 35 insertions, 9 deletions
diff --git a/include/svl/broadcast.hxx b/include/svl/broadcast.hxx
index 80d9568b6392..6a6bc03c6fd6 100644
--- a/include/svl/broadcast.hxx
+++ b/include/svl/broadcast.hxx
@@ -21,7 +21,7 @@
#include <svl/svldllapi.h>
-#include <boost/unordered_set.hpp>
+#include <vector>
class SvtListener;
class SfxHint;
@@ -31,11 +31,18 @@ class SVL_DLLPUBLIC SvtBroadcaster
public:
friend class SvtListener;
- typedef boost::unordered_set<SvtListener*> ListenersType;
+ typedef std::vector<SvtListener*> ListenersType;
private:
const SvtBroadcaster& operator=(const SvtBroadcaster &); // verboten
+ /**
+ * Ensure that the container doesn't contain any duplicated listener
+ * entries. As a side effect, the listeners get sorted by pointer values
+ * after this call.
+ */
+ void Normalize();
+
void Add( SvtListener* p );
void Remove( SvtListener* p );
@@ -55,7 +62,8 @@ public:
private:
ListenersType maListeners;
- bool mbDying;
+ bool mbDisposing:1;
+ bool mbNormalized:1;
};
diff --git a/svl/source/notify/broadcast.cxx b/svl/source/notify/broadcast.cxx
index 7e59e36e2ec7..96d34a7f6ced 100644
--- a/svl/source/notify/broadcast.cxx
+++ b/svl/source/notify/broadcast.cxx
@@ -62,32 +62,49 @@ public:
}
+void SvtBroadcaster::Normalize()
+{
+ if (mbNormalized)
+ return;
+
+ std::sort(maListeners.begin(), maListeners.end());
+ ListenersType::iterator itUniqueEnd = std::unique(maListeners.begin(), maListeners.end());
+ maListeners.erase(itUniqueEnd, maListeners.end());
+ mbNormalized = true;
+}
+
void SvtBroadcaster::Add( SvtListener* p )
{
- maListeners.insert(p);
+ maListeners.push_back(p);
+ mbNormalized = false;
}
void SvtBroadcaster::Remove( SvtListener* p )
{
- if (mbDying)
+ if (mbDisposing)
return;
- maListeners.erase(p);
+ Normalize();
+ std::pair<ListenersType::iterator,ListenersType::iterator> r =
+ std::equal_range(maListeners.begin(), maListeners.end(), p);
+
+ if (r.first != r.second)
+ maListeners.erase(r.first, r.second);
if (maListeners.empty())
ListenersGone();
}
-SvtBroadcaster::SvtBroadcaster() : mbDying(false) {}
+SvtBroadcaster::SvtBroadcaster() : mbDisposing(false), mbNormalized(false) {}
SvtBroadcaster::SvtBroadcaster( const SvtBroadcaster &rBC ) :
- maListeners(rBC.maListeners), mbDying(false)
+ maListeners(rBC.maListeners), mbDisposing(false), mbNormalized(rBC.mbNormalized)
{
std::for_each(maListeners.begin(), maListeners.end(), StartListeningHandler(*this));
}
SvtBroadcaster::~SvtBroadcaster()
{
- mbDying = true;
+ mbDisposing = true;
Broadcast( SfxSimpleHint(SFX_HINT_DYING) );
// unregister all listeners.
@@ -96,6 +113,7 @@ SvtBroadcaster::~SvtBroadcaster()
void SvtBroadcaster::Broadcast( const SfxHint &rHint )
{
+ Normalize();
std::for_each(maListeners.begin(), maListeners.end(), NotifyHandler(*this, rHint));
}