Commit 31562bab authored by Mounir Lamouri's avatar Mounir Lamouri
Browse files

Bug 720794 - Part 2 (DOM) - Implement reading and event parts of Screen...

Bug 720794 - Part 2 (DOM) - Implement reading and event parts of Screen Orientation API. r=jst sr=sicking
parent aa389d8a
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -2466,6 +2466,7 @@ nsDOMClassInfo::Init()

  DOM_CLASSINFO_MAP_BEGIN(Screen, nsIDOMScreen)
    DOM_CLASSINFO_MAP_ENTRY(nsIDOMScreen)
    DOM_CLASSINFO_MAP_ENTRY(nsIDOMEventTarget)
  DOM_CLASSINFO_MAP_END

  DOM_CLASSINFO_MAP_BEGIN_NO_CLASS_IF(DOMPrototype, nsIDOMDOMConstructor)
+9 −6
Original line number Diff line number Diff line
@@ -1312,6 +1312,11 @@ nsGlobalWindow::FreeInnerObjects(bool aClearScope)
    mNavigator = nsnull;
  }

  if (mScreen) {
    mScreen->Invalidate();
    mScreen = nsnull;
  }

  if (mDocument) {
    NS_ASSERTION(mDoc, "Why is mDoc null?");

@@ -2492,8 +2497,6 @@ nsGlobalWindow::SetDocShell(nsIDocShell* aDocShell)

  if (mFrames)
    mFrames->SetDocShell(aDocShell);
  if (mScreen)
    mScreen->SetDocShell(aDocShell);

  if (!mDocShell) {
    MaybeForgiveSpamCount();
@@ -3001,14 +3004,14 @@ nsGlobalWindow::GetNavigator(nsIDOMNavigator** aNavigator)
NS_IMETHODIMP
nsGlobalWindow::GetScreen(nsIDOMScreen** aScreen)
{
  FORWARD_TO_OUTER(GetScreen, (aScreen), NS_ERROR_NOT_INITIALIZED);
  FORWARD_TO_INNER(GetScreen, (aScreen), NS_ERROR_NOT_INITIALIZED);

  *aScreen = nsnull;

  if (!mScreen && mDocShell) {
    mScreen = new nsScreen(mDocShell);
  if (!mScreen) {
      return NS_ERROR_OUT_OF_MEMORY;
    mScreen = nsScreen::Create(this);
    if (!mScreen) {
      return NS_ERROR_UNEXPECTED;
    }
  }

+114 −19
Original line number Diff line number Diff line
@@ -46,8 +46,10 @@
#include "nsIDocShellTreeItem.h"
#include "nsLayoutUtils.h"
#include "mozilla/Preferences.h"
#include "nsDOMEvent.h"

using namespace mozilla;
using namespace mozilla::dom;

/* static */ bool nsScreen::sInitialized = false;
/* static */ bool nsScreen::sAllowScreenEnabledProperty = false;
@@ -64,42 +66,75 @@ nsScreen::Initialize()
                               "dom.screenBrightnessProperty.enabled");
}

//
//  Screen class implementation
//
nsScreen::nsScreen(nsIDocShell* aDocShell)
  : mDocShell(aDocShell)
void
nsScreen::Invalidate()
{
  hal::UnregisterScreenOrientationObserver(this);
}

/* static */ already_AddRefed<nsScreen>
nsScreen::Create(nsPIDOMWindow* aWindow)
{
  if (!sInitialized) {
    Initialize();
  }

  if (!aWindow->GetDocShell()) {
    return nsnull;
  }

nsScreen::~nsScreen()
  nsRefPtr<nsScreen> screen = new nsScreen();

  nsCOMPtr<nsIScriptGlobalObject> sgo = do_QueryInterface(aWindow);
  NS_ENSURE_TRUE(sgo, nsnull);

  nsCOMPtr<nsIScriptContext> scriptContext = sgo->GetContext();
  NS_ENSURE_TRUE(scriptContext, nsnull);

  screen->mOwner = aWindow;
  screen->mScriptContext.swap(scriptContext);
  screen->mDocShell = aWindow->GetDocShell();

  hal::RegisterScreenOrientationObserver(screen);
  hal::GetCurrentScreenOrientation(&(screen->mOrientation));

  return screen.forget();
}

nsScreen::nsScreen()
{
}

nsScreen::~nsScreen()
{
  Invalidate();
}

DOMCI_DATA(Screen, nsScreen)

NS_IMPL_CYCLE_COLLECTION_CLASS(nsScreen)

NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsScreen,
                                                  nsDOMEventTargetHelper)
  NS_CYCLE_COLLECTION_TRAVERSE_EVENT_HANDLER(mozorientationchange)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END

NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsScreen,
                                                nsDOMEventTargetHelper)
  NS_CYCLE_COLLECTION_UNLINK_EVENT_HANDLER(mozorientationchange)
NS_IMPL_CYCLE_COLLECTION_UNLINK_END

// QueryInterface implementation for nsScreen
NS_INTERFACE_MAP_BEGIN(nsScreen)
  NS_INTERFACE_MAP_ENTRY(nsISupports)
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsScreen)
  NS_INTERFACE_MAP_ENTRY(nsIDOMScreen)
  NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIDOMScreen)
  NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(Screen)
NS_INTERFACE_MAP_END

NS_INTERFACE_MAP_END_INHERITING(nsDOMEventTargetHelper)

NS_IMPL_ADDREF(nsScreen)
NS_IMPL_RELEASE(nsScreen)
NS_IMPL_ADDREF_INHERITED(nsScreen, nsDOMEventTargetHelper)
NS_IMPL_RELEASE_INHERITED(nsScreen, nsDOMEventTargetHelper)


NS_IMETHODIMP
nsScreen::SetDocShell(nsIDocShell* aDocShell)
{
   mDocShell = aDocShell; // Weak Reference
   return NS_OK;
}
NS_IMPL_EVENT_HANDLER(nsScreen, mozorientationchange)

NS_IMETHODIMP
nsScreen::GetTop(PRInt32* aTop)
@@ -325,3 +360,63 @@ nsScreen::SetMozBrightness(double aBrightness)
  hal::SetScreenBrightness(aBrightness);
  return NS_OK;
}

void
nsScreen::Notify(const ScreenOrientationWrapper& aOrientation)
{
  ScreenOrientation previousOrientation = mOrientation;
  mOrientation = aOrientation.orientation;

  NS_ASSERTION(mOrientation != eScreenOrientation_Current &&
               mOrientation != eScreenOrientation_EndGuard &&
               mOrientation != eScreenOrientation_Portrait &&
               mOrientation != eScreenOrientation_Landscape,
               "Invalid orientation value passed to notify method!");

  if (mOrientation != previousOrientation) {
    // TODO: use an helper method, see bug 720768.
    nsRefPtr<nsDOMEvent> event = new nsDOMEvent(nsnull, nsnull);
    nsresult rv = event->InitEvent(NS_LITERAL_STRING("mozorientationchange"), false, false);
    if (NS_FAILED(rv)) {
      return;
    }

    rv = event->SetTrusted(true);
    if (NS_FAILED(rv)) {
      return;
    }

    bool dummy;
    rv = DispatchEvent(event, &dummy);
    if (NS_FAILED(rv)) {
      return;
    }
  }
}

NS_IMETHODIMP
nsScreen::GetMozOrientation(nsAString& aOrientation)
{
  switch (mOrientation) {
    case eScreenOrientation_Current:
    case eScreenOrientation_EndGuard:
    case eScreenOrientation_Portrait:
    case eScreenOrientation_Landscape:
      NS_ASSERTION(false, "Shouldn't be used when getting value!");
      return NS_ERROR_FAILURE;
    case eScreenOrientation_PortraitPrimary:
      aOrientation.AssignLiteral("portrait-primary");
      break;
    case eScreenOrientation_PortraitSecondary:
      aOrientation.AssignLiteral("portrait-secondary");
      break;
    case eScreenOrientation_LandscapePrimary:
      aOrientation.AssignLiteral("landscape-primary");
      break;
    case eScreenOrientation_LandscapeSecondary:
      aOrientation.AssignLiteral("landscape-secondary");
      break;
  }

  return NS_OK;
}
+22 −4
Original line number Diff line number Diff line
@@ -37,26 +37,37 @@
#ifndef nsScreen_h___
#define nsScreen_h___

#include "mozilla/Hal.h"
#include "nsIDOMScreen.h"
#include "nsISupports.h"
#include "nsIScriptContext.h"
#include "nsCOMPtr.h"
#include "mozilla/dom/ScreenOrientation.h"
#include "nsDOMEventTargetHelper.h"
#include "mozilla/Observer.h"

class nsIDocShell;
class nsDeviceContext;
struct nsRect;

// Script "screen" object
class nsScreen : public nsIDOMScreen
class nsScreen : public nsDOMEventTargetHelper
               , public nsIDOMScreen
               , public mozilla::hal::ScreenOrientationObserver
{
public:
  nsScreen(nsIDocShell* aDocShell);
  virtual ~nsScreen();
  static already_AddRefed<nsScreen> Create(nsPIDOMWindow* aWindow);

  NS_IMETHOD SetDocShell(nsIDocShell* aDocShell);
  void Invalidate();

  NS_DECL_ISUPPORTS
  NS_DECL_NSIDOMSCREEN
  NS_FORWARD_NSIDOMEVENTTARGET(nsDOMEventTargetHelper::)

  NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsScreen,
                                           nsDOMEventTargetHelper)

  void Notify(const mozilla::dom::ScreenOrientationWrapper& aOrientation);

protected:
  nsDeviceContext* GetDeviceContext();
@@ -65,12 +76,19 @@ protected:

  nsIDocShell* mDocShell; // Weak Reference

  mozilla::dom::ScreenOrientation mOrientation;

private:
  nsScreen();
  virtual ~nsScreen();

  static bool sInitialized;
  static bool sAllowScreenEnabledProperty;
  static bool sAllowScreenBrightnessProperty;

  static void Initialize();

  NS_DECL_EVENT_HANDLER(mozorientationchange)
};

#endif /* nsScreen_h___ */
+2 −0
Original line number Diff line number Diff line
@@ -91,3 +91,5 @@ XPIDLSRCS = \
	$(NULL)

include $(topsrcdir)/config/rules.mk

XPIDL_FLAGS += -I$(topsrcdir)/dom/interfaces/events/
Loading