Bug 1348738 - (Part 2) Make nsRepeatService use InitWithFuncCallback instead of InitWithCallback. r?dholbert
This patch makes nsRepeatService stop inheriting from nsITimerCallback.
We needed that inheritance for InitWithCallback, but we do not need it
for InitWithFuncCallback.
This patch also makes nsRepeatService singly-owned instead of being
refcounted, since we're left with only a single owning pointer.
MozReview-Commit-ID: Fl8beVC8kGH
--- a/layout/xul/nsRepeatService.cpp
+++ b/layout/xul/nsRepeatService.cpp
@@ -6,21 +6,22 @@
//
// Eric Vaughan
// Netscape Communications
//
// See documentation in associated header file
//
#include "nsRepeatService.h"
+#include "mozilla/StaticPtr.h"
#include "nsIServiceManager.h"
using namespace mozilla;
-static StaticRefPtr<nsRepeatService> gRepeatService;
+static StaticAutoPtr<nsRepeatService> gRepeatService;
nsRepeatService::nsRepeatService()
: mCallback(nullptr), mCallbackData(nullptr)
{
}
nsRepeatService::~nsRepeatService()
{
@@ -66,28 +67,32 @@ void nsRepeatService::Stop(Callback aCal
if (mRepeatTimer) {
mRepeatTimer->Cancel();
mRepeatTimer = nullptr;
}
mCallback = nullptr;
mCallbackData = nullptr;
}
-NS_IMETHODIMP nsRepeatService::Notify(nsITimer *timer)
-{
- // do callback
- if (mCallback)
- mCallback(mCallbackData);
-
- // start timer again.
- InitTimerCallback(REPEAT_DELAY);
- return NS_OK;
-}
-
void
nsRepeatService::InitTimerCallback(uint32_t aInitialDelay)
{
- if (mRepeatTimer) {
- mRepeatTimer->InitWithCallback(this, aInitialDelay, nsITimer::TYPE_ONE_SHOT);
+ if (!mRepeatTimer) {
+ return;
}
-}
-NS_IMPL_ISUPPORTS(nsRepeatService, nsITimerCallback)
+ mRepeatTimer->InitWithFuncCallback([](nsITimer* aTimer, void* aClosure) {
+ // Use gRepeatService instead of nsRepeatService::GetInstance() (because
+ // we don't want nsRepeatService::GetInstance() to re-create a new instance
+ // for us, if we happen to get invoked after nsRepeatService::Shutdown() has
+ // nulled out gRepeatService).
+ nsRepeatService* rs = gRepeatService;
+ if (!rs) {
+ return;
+ }
+
+ if (rs->mCallback) {
+ rs->mCallback(rs->mCallbackData);
+ }
+
+ rs->InitTimerCallback(REPEAT_DELAY);
+ }, nullptr, aInitialDelay, nsITimer::TYPE_ONE_SHOT);
+}
--- a/layout/xul/nsRepeatService.h
+++ b/layout/xul/nsRepeatService.h
@@ -17,42 +17,38 @@
#ifdef XP_MACOSX
#define REPEAT_DELAY 25
#else
#define REPEAT_DELAY 50
#endif
class nsITimer;
-class nsRepeatService final : public nsITimerCallback
+class nsRepeatService final
{
public:
+ typedef void (* Callback)(void* aData);
- typedef void (* Callback)(void* aData);
-
- NS_DECL_NSITIMERCALLBACK
+ ~nsRepeatService();
// Start dispatching timer events to the callback. There is no memory
// management of aData here; it is the caller's responsibility to call
// Stop() before aData's memory is released.
void Start(Callback aCallback, void* aData,
uint32_t aInitialDelay = INITAL_REPEAT_DELAY);
// Stop dispatching timer events to the callback. If the repeat service
// is not currently configured with the given callback and data, this
// is just ignored.
void Stop(Callback aCallback, void* aData);
static nsRepeatService* GetInstance();
static void Shutdown();
- NS_DECL_ISUPPORTS
-
protected:
nsRepeatService();
- virtual ~nsRepeatService();
private:
// helper function to initialize callback function to mRepeatTimer
void InitTimerCallback(uint32_t aInitialDelay);
Callback mCallback;
void* mCallbackData;
nsCOMPtr<nsITimer> mRepeatTimer;