2012-09-10 23:05:00 -07:00
|
|
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
|
|
|
/* 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 "TimeChangeObserver.h"
|
|
|
|
#include "mozilla/ClearOnShutdown.h"
|
2012-12-11 07:45:51 -08:00
|
|
|
#include "mozilla/Services.h"
|
2012-09-10 23:05:00 -07:00
|
|
|
#include "mozilla/StaticPtr.h"
|
|
|
|
#include "nsPIDOMWindow.h"
|
|
|
|
#include "nsDOMEvent.h"
|
|
|
|
#include "nsContentUtils.h"
|
2012-10-23 00:15:43 -07:00
|
|
|
#include "nsIObserverService.h"
|
2012-09-10 23:05:00 -07:00
|
|
|
|
|
|
|
using namespace mozilla;
|
2012-10-23 00:15:43 -07:00
|
|
|
using namespace mozilla::hal;
|
|
|
|
using namespace mozilla::services;
|
2012-09-10 23:05:00 -07:00
|
|
|
|
|
|
|
StaticAutoPtr<nsSystemTimeChangeObserver> sObserver;
|
|
|
|
|
|
|
|
nsSystemTimeChangeObserver* nsSystemTimeChangeObserver::GetInstance()
|
|
|
|
{
|
|
|
|
if (!sObserver) {
|
|
|
|
sObserver = new nsSystemTimeChangeObserver();
|
|
|
|
ClearOnShutdown(&sObserver);
|
|
|
|
}
|
|
|
|
return sObserver;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsSystemTimeChangeObserver::~nsSystemTimeChangeObserver()
|
|
|
|
{
|
2012-10-23 00:15:43 -07:00
|
|
|
UnregisterSystemClockChangeObserver(this);
|
|
|
|
UnregisterSystemTimezoneChangeObserver(this);
|
2012-09-10 23:05:00 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
2012-10-23 00:15:43 -07:00
|
|
|
nsSystemTimeChangeObserver::FireMozTimeChangeEvent()
|
2012-09-10 23:05:00 -07:00
|
|
|
{
|
2013-02-15 13:57:18 -08:00
|
|
|
ListenerArray::ForwardIterator iter(mWindowListeners);
|
|
|
|
while (iter.HasMore()) {
|
|
|
|
nsWeakPtr weakWindow = iter.GetNext();
|
|
|
|
nsCOMPtr<nsPIDOMWindow> window = do_QueryReferent(weakWindow);
|
|
|
|
nsCOMPtr<nsIDocument> document;
|
|
|
|
if (!window || !(document = window->GetDoc())) {
|
|
|
|
mWindowListeners.RemoveElement(weakWindow);
|
|
|
|
continue;
|
2012-09-10 23:05:00 -07:00
|
|
|
}
|
|
|
|
|
2012-09-17 01:35:55 -07:00
|
|
|
nsContentUtils::DispatchTrustedEvent(document, window,
|
2012-09-10 23:05:00 -07:00
|
|
|
NS_LITERAL_STRING("moztimechange"), /* bubbles = */ true,
|
|
|
|
/* canceable = */ false);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2012-10-23 00:15:43 -07:00
|
|
|
void
|
|
|
|
nsSystemTimeChangeObserver::Notify(const int64_t& aClockDeltaMS)
|
|
|
|
{
|
|
|
|
// Notify observers that the system clock has been adjusted.
|
|
|
|
nsCOMPtr<nsIObserverService> observerService = GetObserverService();
|
|
|
|
if (observerService) {
|
|
|
|
nsString dataStr;
|
|
|
|
dataStr.AppendFloat(static_cast<double>(aClockDeltaMS));
|
|
|
|
observerService->NotifyObservers(
|
|
|
|
nullptr, "system-clock-change", dataStr.get());
|
|
|
|
}
|
|
|
|
|
|
|
|
FireMozTimeChangeEvent();
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
nsSystemTimeChangeObserver::Notify(
|
|
|
|
const SystemTimezoneChangeInformation& aSystemTimezoneChangeInfo)
|
|
|
|
{
|
|
|
|
FireMozTimeChangeEvent();
|
|
|
|
}
|
|
|
|
|
2012-09-10 23:05:00 -07:00
|
|
|
nsresult
|
|
|
|
nsSystemTimeChangeObserver::AddWindowListener(nsIDOMWindow* aWindow)
|
|
|
|
{
|
|
|
|
return GetInstance()->AddWindowListenerImpl(aWindow);
|
|
|
|
}
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsSystemTimeChangeObserver::AddWindowListenerImpl(nsIDOMWindow* aWindow)
|
|
|
|
{
|
|
|
|
if (!aWindow) {
|
|
|
|
return NS_ERROR_ILLEGAL_VALUE;
|
|
|
|
}
|
|
|
|
|
2013-02-15 13:57:18 -08:00
|
|
|
nsWeakPtr windowWeakRef = do_GetWeakReference(aWindow);
|
2012-10-03 02:38:46 -07:00
|
|
|
NS_ASSERTION(windowWeakRef, "nsIDOMWindow implementations shuld support weak ref");
|
|
|
|
|
|
|
|
if (mWindowListeners.IndexOf(windowWeakRef) !=
|
2013-02-15 13:57:18 -08:00
|
|
|
ListenerArray::array_type::NoIndex) {
|
2012-09-10 23:05:00 -07:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
2013-02-15 13:57:18 -08:00
|
|
|
if (mWindowListeners.IsEmpty()) {
|
2012-10-23 00:15:43 -07:00
|
|
|
RegisterSystemClockChangeObserver(sObserver);
|
|
|
|
RegisterSystemTimezoneChangeObserver(sObserver);
|
2012-09-10 23:05:00 -07:00
|
|
|
}
|
|
|
|
|
2012-10-03 02:38:46 -07:00
|
|
|
mWindowListeners.AppendElement(windowWeakRef);
|
2012-09-10 23:05:00 -07:00
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsSystemTimeChangeObserver::RemoveWindowListener(nsIDOMWindow* aWindow)
|
|
|
|
{
|
|
|
|
if (!sObserver) {
|
|
|
|
return NS_OK;
|
|
|
|
}
|
|
|
|
|
|
|
|
return GetInstance()->RemoveWindowListenerImpl(aWindow);
|
|
|
|
}
|
|
|
|
|
|
|
|
nsresult
|
|
|
|
nsSystemTimeChangeObserver::RemoveWindowListenerImpl(nsIDOMWindow* aWindow)
|
|
|
|
{
|
|
|
|
mWindowListeners.RemoveElement(NS_GetWeakReference(aWindow));
|
|
|
|
|
2013-02-15 13:57:18 -08:00
|
|
|
if (mWindowListeners.IsEmpty()) {
|
2012-10-23 00:15:43 -07:00
|
|
|
UnregisterSystemClockChangeObserver(sObserver);
|
|
|
|
UnregisterSystemTimezoneChangeObserver(sObserver);
|
2012-09-10 23:05:00 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
return NS_OK;
|
|
|
|
}
|