mirror of
https://repo.dactyloidae.xyz/Dactyloidae/UXP.git
synced 2026-09-30 20:37:31 +09:00
import FIREFOX_52_6_0esr_RELEASE from mozilla-esr52 hg repo
This commit is contained in:
commit
dcd9973243
150858 changed files with 23884658 additions and 0 deletions
42
xpfe/appshell/moz.build
Normal file
42
xpfe/appshell/moz.build
Normal file
|
|
@ -0,0 +1,42 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
MOCHITEST_CHROME_MANIFESTS += ['test/chrome.ini']
|
||||
|
||||
XPIDL_SOURCES += [
|
||||
'nsIAppShellService.idl',
|
||||
'nsIPopupWindowManager.idl',
|
||||
'nsIWindowlessBrowser.idl',
|
||||
'nsIWindowMediator.idl',
|
||||
'nsIWindowMediatorListener.idl',
|
||||
'nsIXULBrowserWindow.idl',
|
||||
'nsIXULWindow.idl',
|
||||
]
|
||||
|
||||
XPIDL_MODULE = 'appshell'
|
||||
|
||||
EXPORTS += [
|
||||
'nsAppShellCID.h',
|
||||
]
|
||||
|
||||
UNIFIED_SOURCES += [
|
||||
'nsAppShellFactory.cpp',
|
||||
'nsAppShellService.cpp',
|
||||
'nsAppShellWindowEnumerator.cpp',
|
||||
'nsChromeTreeOwner.cpp',
|
||||
'nsContentTreeOwner.cpp',
|
||||
'nsWebShellWindow.cpp',
|
||||
'nsWindowMediator.cpp',
|
||||
'nsXULWindow.cpp',
|
||||
]
|
||||
|
||||
LOCAL_INCLUDES += [
|
||||
'/dom/base',
|
||||
]
|
||||
|
||||
FINAL_LIBRARY = 'xul'
|
||||
|
||||
include('/ipc/chromium/chromium-config.mozbuild')
|
||||
10
xpfe/appshell/nsAppShellCID.h
Normal file
10
xpfe/appshell/nsAppShellCID.h
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
/* 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/. */
|
||||
|
||||
#ifndef nsAppShellCID_h__
|
||||
#define nsAppShellCID_h__
|
||||
|
||||
#define NS_APPSHELLSERVICE_CONTRACTID "@mozilla.org/appshell/appShellService;1"
|
||||
|
||||
#endif
|
||||
56
xpfe/appshell/nsAppShellFactory.cpp
Normal file
56
xpfe/appshell/nsAppShellFactory.cpp
Normal file
|
|
@ -0,0 +1,56 @@
|
|||
/* -*- 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 "mozilla/ModuleUtils.h"
|
||||
#include "nscore.h"
|
||||
#include "nsIWindowMediator.h"
|
||||
|
||||
#include "nsIAppShellService.h"
|
||||
#include "nsAppShellService.h"
|
||||
#include "nsWindowMediator.h"
|
||||
#include "nsChromeTreeOwner.h"
|
||||
#include "nsAppShellCID.h"
|
||||
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR(nsAppShellService)
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsWindowMediator, Init)
|
||||
|
||||
NS_DEFINE_NAMED_CID(NS_APPSHELLSERVICE_CID);
|
||||
NS_DEFINE_NAMED_CID(NS_WINDOWMEDIATOR_CID);
|
||||
|
||||
static const mozilla::Module::CIDEntry kAppShellCIDs[] = {
|
||||
{ &kNS_APPSHELLSERVICE_CID, false, nullptr, nsAppShellServiceConstructor },
|
||||
{ &kNS_WINDOWMEDIATOR_CID, false, nullptr, nsWindowMediatorConstructor },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module::ContractIDEntry kAppShellContracts[] = {
|
||||
{ NS_APPSHELLSERVICE_CONTRACTID, &kNS_APPSHELLSERVICE_CID },
|
||||
{ NS_WINDOWMEDIATOR_CONTRACTID, &kNS_WINDOWMEDIATOR_CID },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static nsresult
|
||||
nsAppShellModuleConstructor()
|
||||
{
|
||||
return nsChromeTreeOwner::InitGlobals();
|
||||
}
|
||||
|
||||
static void
|
||||
nsAppShellModuleDestructor()
|
||||
{
|
||||
nsChromeTreeOwner::FreeGlobals();
|
||||
}
|
||||
|
||||
static const mozilla::Module kAppShellModule = {
|
||||
mozilla::Module::kVersion,
|
||||
kAppShellCIDs,
|
||||
kAppShellContracts,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nsAppShellModuleConstructor,
|
||||
nsAppShellModuleDestructor
|
||||
};
|
||||
|
||||
NSMODULE_DEFN(appshell) = &kAppShellModule;
|
||||
1001
xpfe/appshell/nsAppShellService.cpp
Normal file
1001
xpfe/appshell/nsAppShellService.cpp
Normal file
File diff suppressed because it is too large
Load diff
58
xpfe/appshell/nsAppShellService.h
Normal file
58
xpfe/appshell/nsAppShellService.h
Normal file
|
|
@ -0,0 +1,58 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
#ifndef __nsAppShellService_h
|
||||
#define __nsAppShellService_h
|
||||
|
||||
#include "nsIAppShellService.h"
|
||||
#include "nsIObserver.h"
|
||||
|
||||
//Interfaces Needed
|
||||
#include "nsWebShellWindow.h"
|
||||
#include "nsStringFwd.h"
|
||||
#include "nsAutoPtr.h"
|
||||
#include "nsITabParent.h"
|
||||
#include "mozilla/Attributes.h"
|
||||
|
||||
// {0099907D-123C-4853-A46A-43098B5FB68C}
|
||||
#define NS_APPSHELLSERVICE_CID \
|
||||
{ 0x99907d, 0x123c, 0x4853, { 0xa4, 0x6a, 0x43, 0x9, 0x8b, 0x5f, 0xb6, 0x8c } }
|
||||
|
||||
class nsAppShellService final : public nsIAppShellService,
|
||||
public nsIObserver
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIAPPSHELLSERVICE
|
||||
NS_DECL_NSIOBSERVER
|
||||
|
||||
nsAppShellService();
|
||||
|
||||
protected:
|
||||
~nsAppShellService();
|
||||
|
||||
nsresult CreateHiddenWindowHelper(bool aIsPrivate);
|
||||
void EnsurePrivateHiddenWindow();
|
||||
|
||||
nsresult JustCreateTopWindow(nsIXULWindow *aParent,
|
||||
nsIURI *aUrl,
|
||||
uint32_t aChromeMask,
|
||||
int32_t aInitialWidth, int32_t aInitialHeight,
|
||||
bool aIsHiddenWindow,
|
||||
nsITabParent *aOpeningTab,
|
||||
mozIDOMWindowProxy *aOpenerWindow,
|
||||
nsWebShellWindow **aResult);
|
||||
uint32_t CalculateWindowZLevel(nsIXULWindow *aParent, uint32_t aChromeMask);
|
||||
|
||||
RefPtr<nsWebShellWindow> mHiddenWindow;
|
||||
RefPtr<nsWebShellWindow> mHiddenPrivateWindow;
|
||||
bool mXPCOMWillShutDown;
|
||||
bool mXPCOMShuttingDown;
|
||||
uint16_t mModalWindowCount;
|
||||
bool mApplicationProvidedHiddenWindow;
|
||||
uint32_t mScreenId;
|
||||
};
|
||||
|
||||
#endif
|
||||
495
xpfe/appshell/nsAppShellWindowEnumerator.cpp
Normal file
495
xpfe/appshell/nsAppShellWindowEnumerator.cpp
Normal file
|
|
@ -0,0 +1,495 @@
|
|||
/* -*- 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 "nsAppShellWindowEnumerator.h"
|
||||
|
||||
#include "nsIContentViewer.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIDOMDocument.h"
|
||||
#include "nsIDOMElement.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIFactory.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIXULWindow.h"
|
||||
|
||||
#include "nsWindowMediator.h"
|
||||
|
||||
//
|
||||
// static helper functions
|
||||
//
|
||||
|
||||
static nsCOMPtr<nsIDOMNode> GetDOMNodeFromDocShell(nsIDocShell *aShell);
|
||||
static void GetAttribute(nsIXULWindow *inWindow, const nsAString &inAttribute,
|
||||
nsAString &outValue);
|
||||
static void GetWindowType(nsIXULWindow* inWindow, nsString &outType);
|
||||
|
||||
nsCOMPtr<nsIDOMNode> GetDOMNodeFromDocShell(nsIDocShell *aShell)
|
||||
{
|
||||
nsCOMPtr<nsIDOMNode> node;
|
||||
|
||||
nsCOMPtr<nsIContentViewer> cv;
|
||||
aShell->GetContentViewer(getter_AddRefs(cv));
|
||||
if (cv) {
|
||||
nsCOMPtr<nsIDOMDocument> domdoc(do_QueryInterface(cv->GetDocument()));
|
||||
if (domdoc) {
|
||||
nsCOMPtr<nsIDOMElement> element;
|
||||
domdoc->GetDocumentElement(getter_AddRefs(element));
|
||||
if (element)
|
||||
node = element;
|
||||
}
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
// generic "retrieve the value of a XUL attribute" function
|
||||
void GetAttribute(nsIXULWindow *inWindow, const nsAString &inAttribute,
|
||||
nsAString &outValue)
|
||||
{
|
||||
nsCOMPtr<nsIDocShell> shell;
|
||||
if (inWindow && NS_SUCCEEDED(inWindow->GetDocShell(getter_AddRefs(shell)))) {
|
||||
nsCOMPtr<nsIDOMNode> node(GetDOMNodeFromDocShell(shell));
|
||||
if (node) {
|
||||
nsCOMPtr<nsIDOMElement> webshellElement(do_QueryInterface(node));
|
||||
if (webshellElement)
|
||||
webshellElement->GetAttribute(inAttribute, outValue);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// retrieve the window type, stored as the value of a particular
|
||||
// attribute in its XUL window tag
|
||||
void GetWindowType(nsIXULWindow* aWindow, nsString &outType)
|
||||
{
|
||||
GetAttribute(aWindow, NS_LITERAL_STRING("windowtype"), outType);
|
||||
}
|
||||
|
||||
//
|
||||
// nsWindowInfo
|
||||
//
|
||||
|
||||
nsWindowInfo::nsWindowInfo(nsIXULWindow* inWindow, int32_t inTimeStamp) :
|
||||
mWindow(inWindow),mTimeStamp(inTimeStamp),mZLevel(nsIXULWindow::normalZ)
|
||||
{
|
||||
ReferenceSelf(true, true);
|
||||
}
|
||||
|
||||
nsWindowInfo::~nsWindowInfo()
|
||||
{
|
||||
}
|
||||
|
||||
// return true if the window described by this WindowInfo has a type
|
||||
// equal to the given type
|
||||
bool nsWindowInfo::TypeEquals(const nsAString &aType)
|
||||
{
|
||||
nsAutoString rtnString;
|
||||
GetWindowType(mWindow, rtnString);
|
||||
return rtnString == aType;
|
||||
}
|
||||
|
||||
// insert the struct into their two linked lists, in position after the
|
||||
// given (independent) method arguments
|
||||
void nsWindowInfo::InsertAfter(nsWindowInfo *inOlder , nsWindowInfo *inHigher)
|
||||
{
|
||||
if (inOlder) {
|
||||
mOlder = inOlder;
|
||||
mYounger = inOlder->mYounger;
|
||||
mOlder->mYounger = this;
|
||||
if (mOlder->mOlder == mOlder)
|
||||
mOlder->mOlder = this;
|
||||
mYounger->mOlder = this;
|
||||
if (mYounger->mYounger == mYounger)
|
||||
mYounger->mYounger = this;
|
||||
}
|
||||
if (inHigher) {
|
||||
mHigher = inHigher;
|
||||
mLower = inHigher->mLower;
|
||||
mHigher->mLower = this;
|
||||
if (mHigher->mHigher == mHigher)
|
||||
mHigher->mHigher = this;
|
||||
mLower->mHigher = this;
|
||||
if (mLower->mLower == mLower)
|
||||
mLower->mLower = this;
|
||||
}
|
||||
}
|
||||
|
||||
// remove the struct from its linked lists
|
||||
void nsWindowInfo::Unlink(bool inAge, bool inZ)
|
||||
{
|
||||
if (inAge) {
|
||||
mOlder->mYounger = mYounger;
|
||||
mYounger->mOlder = mOlder;
|
||||
}
|
||||
if (inZ) {
|
||||
mLower->mHigher = mHigher;
|
||||
mHigher->mLower = mLower;
|
||||
}
|
||||
ReferenceSelf(inAge, inZ);
|
||||
}
|
||||
|
||||
// initialize the struct to be a valid linked list of one element
|
||||
void nsWindowInfo::ReferenceSelf(bool inAge, bool inZ)
|
||||
{
|
||||
if (inAge) {
|
||||
mYounger = this;
|
||||
mOlder = this;
|
||||
}
|
||||
if (inZ) {
|
||||
mLower = this;
|
||||
mHigher = this;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// nsAppShellWindowEnumerator
|
||||
//
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsAppShellWindowEnumerator, nsISimpleEnumerator)
|
||||
|
||||
nsAppShellWindowEnumerator::nsAppShellWindowEnumerator(
|
||||
const char16_t* aTypeString,
|
||||
nsWindowMediator& aMediator) :
|
||||
mWindowMediator(&aMediator), mType(aTypeString), mCurrentPosition(nullptr)
|
||||
{
|
||||
mWindowMediator->AddEnumerator(this);
|
||||
NS_ADDREF(mWindowMediator);
|
||||
}
|
||||
|
||||
nsAppShellWindowEnumerator::~nsAppShellWindowEnumerator()
|
||||
{
|
||||
mWindowMediator->RemoveEnumerator(this);
|
||||
NS_RELEASE(mWindowMediator);
|
||||
}
|
||||
|
||||
// after mCurrentPosition has been initialized to point to the beginning
|
||||
// of the appropriate list, adjust it if necessary
|
||||
void nsAppShellWindowEnumerator::AdjustInitialPosition()
|
||||
{
|
||||
if (!mType.IsEmpty() && mCurrentPosition && !mCurrentPosition->TypeEquals(mType))
|
||||
mCurrentPosition = FindNext();
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsAppShellWindowEnumerator::HasMoreElements(bool *retval)
|
||||
{
|
||||
if (!retval)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
|
||||
*retval = mCurrentPosition ? true : false;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// if a window is being removed adjust the iterator's current position
|
||||
void nsAppShellWindowEnumerator::WindowRemoved(nsWindowInfo *inInfo)
|
||||
{
|
||||
if (mCurrentPosition == inInfo)
|
||||
mCurrentPosition = FindNext();
|
||||
}
|
||||
|
||||
//
|
||||
// nsASDOMWindowEnumerator
|
||||
//
|
||||
|
||||
nsASDOMWindowEnumerator::nsASDOMWindowEnumerator(
|
||||
const char16_t* aTypeString,
|
||||
nsWindowMediator& aMediator) :
|
||||
nsAppShellWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
}
|
||||
|
||||
nsASDOMWindowEnumerator::~nsASDOMWindowEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsASDOMWindowEnumerator::GetNext(nsISupports **retval)
|
||||
{
|
||||
if (!retval)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
|
||||
*retval = nullptr;
|
||||
while (mCurrentPosition) {
|
||||
nsCOMPtr<nsPIDOMWindowOuter> domWindow;
|
||||
nsWindowMediator::GetDOMWindow(mCurrentPosition->mWindow, domWindow);
|
||||
mCurrentPosition = FindNext();
|
||||
if (domWindow)
|
||||
return CallQueryInterface(domWindow, retval);
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASXULWindowEnumerator
|
||||
//
|
||||
|
||||
nsASXULWindowEnumerator::nsASXULWindowEnumerator(
|
||||
const char16_t* aTypeString,
|
||||
nsWindowMediator& aMediator) :
|
||||
nsAppShellWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
}
|
||||
|
||||
nsASXULWindowEnumerator::~nsASXULWindowEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsASXULWindowEnumerator::GetNext(nsISupports **retval)
|
||||
{
|
||||
if (!retval)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
|
||||
*retval = nullptr;
|
||||
if (mCurrentPosition) {
|
||||
CallQueryInterface(mCurrentPosition->mWindow, retval);
|
||||
mCurrentPosition = FindNext();
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASDOMWindowEarlyToLateEnumerator
|
||||
//
|
||||
|
||||
nsASDOMWindowEarlyToLateEnumerator::nsASDOMWindowEarlyToLateEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASDOMWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mOldestWindow;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASDOMWindowEarlyToLateEnumerator::~nsASDOMWindowEarlyToLateEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASDOMWindowEarlyToLateEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
// see nsXULWindowEarlyToLateEnumerator::FindNext
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mYounger;
|
||||
listEnd = mWindowMediator->mOldestWindow;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mYounger;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASXULWindowEarlyToLateEnumerator
|
||||
//
|
||||
|
||||
nsASXULWindowEarlyToLateEnumerator::nsASXULWindowEarlyToLateEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASXULWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mOldestWindow;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASXULWindowEarlyToLateEnumerator::~nsASXULWindowEarlyToLateEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASXULWindowEarlyToLateEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
/* mCurrentPosition null is assumed to mean that the enumerator has run
|
||||
its course and is now basically useless. It could also be interpreted
|
||||
to mean that it was created at a time when there were no windows. In
|
||||
that case it would probably be more appropriate to check to see whether
|
||||
windows have subsequently been added. But it's not guaranteed that we'll
|
||||
pick up newly added windows anyway (if they occurred previous to our
|
||||
current position) so we just don't worry about that. */
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mYounger;
|
||||
listEnd = mWindowMediator->mOldestWindow;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mYounger;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASDOMWindowFrontToBackEnumerator
|
||||
//
|
||||
|
||||
nsASDOMWindowFrontToBackEnumerator::nsASDOMWindowFrontToBackEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASDOMWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mTopmostWindow;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASDOMWindowFrontToBackEnumerator::~nsASDOMWindowFrontToBackEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASDOMWindowFrontToBackEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
// see nsXULWindowEarlyToLateEnumerator::FindNext
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mLower;
|
||||
listEnd = mWindowMediator->mTopmostWindow;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mLower;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASXULWindowFrontToBackEnumerator
|
||||
//
|
||||
|
||||
nsASXULWindowFrontToBackEnumerator::nsASXULWindowFrontToBackEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASXULWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mTopmostWindow;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASXULWindowFrontToBackEnumerator::~nsASXULWindowFrontToBackEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASXULWindowFrontToBackEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
// see nsXULWindowEarlyToLateEnumerator::FindNext
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mLower;
|
||||
listEnd = mWindowMediator->mTopmostWindow;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mLower;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASDOMWindowBackToFrontEnumerator
|
||||
//
|
||||
|
||||
nsASDOMWindowBackToFrontEnumerator::nsASDOMWindowBackToFrontEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASDOMWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mTopmostWindow ?
|
||||
aMediator.mTopmostWindow->mHigher : nullptr;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASDOMWindowBackToFrontEnumerator::~nsASDOMWindowBackToFrontEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASDOMWindowBackToFrontEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
// see nsXULWindowEarlyToLateEnumerator::FindNext
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mHigher;
|
||||
listEnd = mWindowMediator->mTopmostWindow;
|
||||
if (listEnd)
|
||||
listEnd = listEnd->mHigher;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mHigher;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
//
|
||||
// nsASXULWindowBackToFrontEnumerator
|
||||
//
|
||||
|
||||
nsASXULWindowBackToFrontEnumerator::nsASXULWindowBackToFrontEnumerator(
|
||||
const char16_t *aTypeString,
|
||||
nsWindowMediator &aMediator) :
|
||||
nsASXULWindowEnumerator(aTypeString, aMediator)
|
||||
{
|
||||
mCurrentPosition = aMediator.mTopmostWindow ?
|
||||
aMediator.mTopmostWindow->mHigher : nullptr;
|
||||
AdjustInitialPosition();
|
||||
}
|
||||
|
||||
nsASXULWindowBackToFrontEnumerator::~nsASXULWindowBackToFrontEnumerator()
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowInfo *nsASXULWindowBackToFrontEnumerator::FindNext()
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
bool allWindows = mType.IsEmpty();
|
||||
|
||||
// see nsXULWindowEarlyToLateEnumerator::FindNext
|
||||
if (!mCurrentPosition)
|
||||
return nullptr;
|
||||
|
||||
info = mCurrentPosition->mHigher;
|
||||
listEnd = mWindowMediator->mTopmostWindow;
|
||||
if (listEnd)
|
||||
listEnd = listEnd->mHigher;
|
||||
|
||||
while (info != listEnd) {
|
||||
if (allWindows || info->TypeEquals(mType))
|
||||
return info;
|
||||
info = info->mHigher;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
166
xpfe/appshell/nsAppShellWindowEnumerator.h
Normal file
166
xpfe/appshell/nsAppShellWindowEnumerator.h
Normal file
|
|
@ -0,0 +1,166 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
#ifndef nsAppShellWindowEnumerator_h
|
||||
#define nsAppShellWindowEnumerator_h
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsString.h"
|
||||
|
||||
#include "nsISimpleEnumerator.h"
|
||||
#include "nsIXULWindow.h"
|
||||
|
||||
class nsWindowMediator;
|
||||
|
||||
//
|
||||
// nsWindowInfo
|
||||
//
|
||||
|
||||
struct nsWindowInfo
|
||||
{
|
||||
nsWindowInfo(nsIXULWindow* inWindow, int32_t inTimeStamp);
|
||||
~nsWindowInfo();
|
||||
|
||||
nsCOMPtr<nsIXULWindow> mWindow;
|
||||
int32_t mTimeStamp;
|
||||
uint32_t mZLevel;
|
||||
|
||||
// each struct is in two, independent, circular, doubly-linked lists
|
||||
nsWindowInfo *mYounger, // next younger in sequence
|
||||
*mOlder;
|
||||
nsWindowInfo *mLower, // next lower in z-order
|
||||
*mHigher;
|
||||
|
||||
bool TypeEquals(const nsAString &aType);
|
||||
void InsertAfter(nsWindowInfo *inOlder, nsWindowInfo *inHigher);
|
||||
void Unlink(bool inAge, bool inZ);
|
||||
void ReferenceSelf(bool inAge, bool inZ);
|
||||
};
|
||||
|
||||
//
|
||||
// virtual enumerators
|
||||
//
|
||||
|
||||
class nsAppShellWindowEnumerator : public nsISimpleEnumerator {
|
||||
|
||||
friend class nsWindowMediator;
|
||||
|
||||
public:
|
||||
nsAppShellWindowEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
NS_IMETHOD GetNext(nsISupports **retval) override = 0;
|
||||
NS_IMETHOD HasMoreElements(bool *retval) override;
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
protected:
|
||||
|
||||
virtual ~nsAppShellWindowEnumerator();
|
||||
|
||||
void AdjustInitialPosition();
|
||||
virtual nsWindowInfo *FindNext() = 0;
|
||||
|
||||
void WindowRemoved(nsWindowInfo *inInfo);
|
||||
|
||||
nsWindowMediator *mWindowMediator;
|
||||
nsString mType;
|
||||
nsWindowInfo *mCurrentPosition;
|
||||
};
|
||||
|
||||
class nsASDOMWindowEnumerator : public nsAppShellWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASDOMWindowEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
virtual ~nsASDOMWindowEnumerator();
|
||||
NS_IMETHOD GetNext(nsISupports **retval);
|
||||
};
|
||||
|
||||
class nsASXULWindowEnumerator : public nsAppShellWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASXULWindowEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
virtual ~nsASXULWindowEnumerator();
|
||||
NS_IMETHOD GetNext(nsISupports **retval);
|
||||
};
|
||||
|
||||
//
|
||||
// concrete enumerators
|
||||
//
|
||||
|
||||
class nsASDOMWindowEarlyToLateEnumerator : public nsASDOMWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASDOMWindowEarlyToLateEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASDOMWindowEarlyToLateEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
class nsASXULWindowEarlyToLateEnumerator : public nsASXULWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASXULWindowEarlyToLateEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASXULWindowEarlyToLateEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
class nsASDOMWindowFrontToBackEnumerator : public nsASDOMWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASDOMWindowFrontToBackEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASDOMWindowFrontToBackEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
class nsASXULWindowFrontToBackEnumerator : public nsASXULWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASXULWindowFrontToBackEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASXULWindowFrontToBackEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
class nsASDOMWindowBackToFrontEnumerator : public nsASDOMWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASDOMWindowBackToFrontEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASDOMWindowBackToFrontEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
class nsASXULWindowBackToFrontEnumerator : public nsASXULWindowEnumerator {
|
||||
|
||||
public:
|
||||
nsASXULWindowBackToFrontEnumerator(const char16_t* aTypeString,
|
||||
nsWindowMediator& inMediator);
|
||||
|
||||
virtual ~nsASXULWindowBackToFrontEnumerator();
|
||||
|
||||
protected:
|
||||
virtual nsWindowInfo *FindNext();
|
||||
};
|
||||
|
||||
#endif
|
||||
561
xpfe/appshell/nsChromeTreeOwner.cpp
Normal file
561
xpfe/appshell/nsChromeTreeOwner.cpp
Normal file
|
|
@ -0,0 +1,561 @@
|
|||
/* -*- Mode: C++; tab-width: 3; 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/. */
|
||||
|
||||
// Local Includes
|
||||
#include "nsChromeTreeOwner.h"
|
||||
#include "nsXULWindow.h"
|
||||
|
||||
// Helper Classes
|
||||
#include "nsString.h"
|
||||
#include "nsIEmbeddingSiteWindow.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsIDocShellTreeItem.h"
|
||||
|
||||
// Interfaces needed to include
|
||||
#include "nsIPrompt.h"
|
||||
#include "nsIAuthPrompt.h"
|
||||
#include "nsIBrowserDOMWindow.h"
|
||||
#include "nsIWebProgress.h"
|
||||
#include "nsIWidget.h"
|
||||
#include "nsIWindowMediator.h"
|
||||
#include "nsIDOMChromeWindow.h"
|
||||
#include "nsIDOMNode.h"
|
||||
#include "nsIDOMElement.h"
|
||||
#include "nsIDOMNodeList.h"
|
||||
#include "nsIDOMXULElement.h"
|
||||
#include "nsIXULBrowserWindow.h"
|
||||
#include "mozilla/dom/Element.h"
|
||||
|
||||
using namespace mozilla;
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner string literals
|
||||
//*****************************************************************************
|
||||
|
||||
struct nsChromeTreeOwnerLiterals
|
||||
{
|
||||
const nsLiteralString kPersist;
|
||||
const nsLiteralString kScreenX;
|
||||
const nsLiteralString kScreenY;
|
||||
const nsLiteralString kWidth;
|
||||
const nsLiteralString kHeight;
|
||||
const nsLiteralString kSizemode;
|
||||
const nsLiteralString kSpace;
|
||||
|
||||
nsChromeTreeOwnerLiterals()
|
||||
: NS_LITERAL_STRING_INIT(kPersist,"persist")
|
||||
, NS_LITERAL_STRING_INIT(kScreenX,"screenX")
|
||||
, NS_LITERAL_STRING_INIT(kScreenY,"screenY")
|
||||
, NS_LITERAL_STRING_INIT(kWidth,"width")
|
||||
, NS_LITERAL_STRING_INIT(kHeight,"height")
|
||||
, NS_LITERAL_STRING_INIT(kSizemode,"sizemode")
|
||||
, NS_LITERAL_STRING_INIT(kSpace," ")
|
||||
{}
|
||||
};
|
||||
|
||||
static nsChromeTreeOwnerLiterals *gLiterals;
|
||||
|
||||
nsresult
|
||||
nsChromeTreeOwner::InitGlobals()
|
||||
{
|
||||
NS_ASSERTION(gLiterals == nullptr, "already initialized");
|
||||
gLiterals = new nsChromeTreeOwnerLiterals();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
void
|
||||
nsChromeTreeOwner::FreeGlobals()
|
||||
{
|
||||
delete gLiterals;
|
||||
gLiterals = nullptr;
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
//*** nsChromeTreeOwner: Object Management
|
||||
//*****************************************************************************
|
||||
|
||||
nsChromeTreeOwner::nsChromeTreeOwner() : mXULWindow(nullptr)
|
||||
{
|
||||
}
|
||||
|
||||
nsChromeTreeOwner::~nsChromeTreeOwner()
|
||||
{
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner::nsISupports
|
||||
//*****************************************************************************
|
||||
|
||||
NS_IMPL_ADDREF(nsChromeTreeOwner)
|
||||
NS_IMPL_RELEASE(nsChromeTreeOwner)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN(nsChromeTreeOwner)
|
||||
NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIDocShellTreeOwner)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIDocShellTreeOwner)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIBaseWindow)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIWebProgressListener)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIInterfaceRequestor)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupportsWeakReference)
|
||||
NS_INTERFACE_MAP_END
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner::nsIInterfaceRequestor
|
||||
//*****************************************************************************
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetInterface(const nsIID& aIID, void** aSink)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aSink);
|
||||
|
||||
if(aIID.Equals(NS_GET_IID(nsIPrompt))) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetInterface(aIID, aSink);
|
||||
}
|
||||
if(aIID.Equals(NS_GET_IID(nsIAuthPrompt))) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetInterface(aIID, aSink);
|
||||
}
|
||||
if(aIID.Equals(NS_GET_IID(nsIWebBrowserChrome))) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetInterface(aIID, aSink);
|
||||
}
|
||||
if (aIID.Equals(NS_GET_IID(nsIEmbeddingSiteWindow))) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetInterface(aIID, aSink);
|
||||
}
|
||||
if (aIID.Equals(NS_GET_IID(nsIXULWindow))) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->QueryInterface(aIID, aSink);
|
||||
}
|
||||
|
||||
return QueryInterface(aIID, aSink);
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner::nsIDocShellTreeOwner
|
||||
//*****************************************************************************
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::ContentShellAdded(nsIDocShellTreeItem* aContentShell,
|
||||
bool aPrimary, bool aTargetable,
|
||||
const nsAString& aID)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->ContentShellAdded(aContentShell, aPrimary, aTargetable,
|
||||
aID);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::ContentShellRemoved(nsIDocShellTreeItem* aContentShell)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->ContentShellRemoved(aContentShell);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetPrimaryContentShell(nsIDocShellTreeItem** aShell)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetPrimaryContentShell(aShell);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::TabParentAdded(nsITabParent* aTab, bool aPrimary)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->TabParentAdded(aTab, aPrimary);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::TabParentRemoved(nsITabParent* aTab)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->TabParentRemoved(aTab);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetPrimaryTabParent(nsITabParent** aTab)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetPrimaryTabParent(aTab);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetPrimaryContentSize(int32_t* aWidth,
|
||||
int32_t* aHeight)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetPrimaryContentSize(aWidth, aHeight);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::SetPrimaryContentSize(int32_t aWidth,
|
||||
int32_t aHeight)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetPrimaryContentSize(aWidth, aHeight);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetRootShellSize(int32_t* aWidth,
|
||||
int32_t* aHeight)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetRootShellSize(aWidth, aHeight);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::SetRootShellSize(int32_t aWidth,
|
||||
int32_t aHeight)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetRootShellSize(aWidth, aHeight);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SizeShellTo(nsIDocShellTreeItem* aShellItem,
|
||||
int32_t aCX, int32_t aCY)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SizeShellTo(aShellItem, aCX, aCY);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::SetPersistence(bool aPersistPosition,
|
||||
bool aPersistSize,
|
||||
bool aPersistSizeMode)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
nsCOMPtr<dom::Element> docShellElement = mXULWindow->GetWindowDOMElement();
|
||||
if (!docShellElement)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
nsAutoString persistString;
|
||||
docShellElement->GetAttribute(gLiterals->kPersist, persistString);
|
||||
|
||||
bool saveString = false;
|
||||
int32_t index;
|
||||
|
||||
#define FIND_PERSIST_STRING(aString, aCond) \
|
||||
index = persistString.Find(aString); \
|
||||
if (!aCond && index > kNotFound) { \
|
||||
persistString.Cut(index, aString.Length()); \
|
||||
saveString = true; \
|
||||
} else if (aCond && index == kNotFound) { \
|
||||
persistString.Append(gLiterals->kSpace + aString); \
|
||||
saveString = true; \
|
||||
}
|
||||
FIND_PERSIST_STRING(gLiterals->kScreenX, aPersistPosition);
|
||||
FIND_PERSIST_STRING(gLiterals->kScreenY, aPersistPosition);
|
||||
FIND_PERSIST_STRING(gLiterals->kWidth, aPersistSize);
|
||||
FIND_PERSIST_STRING(gLiterals->kHeight, aPersistSize);
|
||||
FIND_PERSIST_STRING(gLiterals->kSizemode, aPersistSizeMode);
|
||||
|
||||
ErrorResult rv;
|
||||
if (saveString) {
|
||||
docShellElement->SetAttribute(gLiterals->kPersist, persistString, rv);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetPersistence(bool* aPersistPosition,
|
||||
bool* aPersistSize,
|
||||
bool* aPersistSizeMode)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
nsCOMPtr<dom::Element> docShellElement = mXULWindow->GetWindowDOMElement();
|
||||
if (!docShellElement)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
nsAutoString persistString;
|
||||
docShellElement->GetAttribute(gLiterals->kPersist, persistString);
|
||||
|
||||
// data structure doesn't quite match the question, but it's close enough
|
||||
// for what we want (since this method is never actually called...)
|
||||
if (aPersistPosition)
|
||||
*aPersistPosition = persistString.Find(gLiterals->kScreenX) > kNotFound ||
|
||||
persistString.Find(gLiterals->kScreenY) > kNotFound;
|
||||
if (aPersistSize)
|
||||
*aPersistSize = persistString.Find(gLiterals->kWidth) > kNotFound ||
|
||||
persistString.Find(gLiterals->kHeight) > kNotFound;
|
||||
if (aPersistSizeMode)
|
||||
*aPersistSizeMode = persistString.Find(gLiterals->kSizemode) > kNotFound;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetTargetableShellCount(uint32_t* aResult)
|
||||
{
|
||||
*aResult = 0;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::GetHasPrimaryContent(bool* aResult)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetHasPrimaryContent(aResult);
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner::nsIBaseWindow
|
||||
//*****************************************************************************
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::InitWindow(nativeWindow aParentNativeWindow,
|
||||
nsIWidget* parentWidget, int32_t x, int32_t y, int32_t cx, int32_t cy)
|
||||
{
|
||||
// Ignore widget parents for now. Don't think those are a vaild thing to call.
|
||||
NS_ENSURE_SUCCESS(SetPositionAndSize(x, y, cx, cy, 0), NS_ERROR_FAILURE);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::Create()
|
||||
{
|
||||
NS_ASSERTION(false, "You can't call this");
|
||||
return NS_ERROR_UNEXPECTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::Destroy()
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->Destroy();
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetUnscaledDevicePixelsPerCSSPixel(double *aScale)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetUnscaledDevicePixelsPerCSSPixel(aScale);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetDevicePixelsPerDesktopPixel(double *aScale)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetDevicePixelsPerDesktopPixel(aScale);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetPositionDesktopPix(int32_t x, int32_t y)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetPositionDesktopPix(x, y);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetPosition(int32_t x, int32_t y)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetPosition(x, y);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetPosition(int32_t* x, int32_t* y)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetPosition(x, y);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetSize(int32_t cx, int32_t cy, bool fRepaint)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetSize(cx, cy, fRepaint);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetSize(int32_t* cx, int32_t* cy)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetSize(cx, cy);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetPositionAndSize(int32_t x, int32_t y, int32_t cx,
|
||||
int32_t cy, uint32_t aFlags)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetPositionAndSize(x, y, cx, cy, aFlags);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetPositionAndSize(int32_t* x, int32_t* y, int32_t* cx,
|
||||
int32_t* cy)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetPositionAndSize(x, y, cx, cy);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::Repaint(bool aForce)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->Repaint(aForce);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetParentWidget(nsIWidget** aParentWidget)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetParentWidget(aParentWidget);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetParentWidget(nsIWidget* aParentWidget)
|
||||
{
|
||||
NS_ASSERTION(false, "You can't call this");
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetParentNativeWindow(nativeWindow* aParentNativeWindow)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetParentNativeWindow(aParentNativeWindow);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetParentNativeWindow(nativeWindow aParentNativeWindow)
|
||||
{
|
||||
NS_ASSERTION(false, "You can't call this");
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetNativeHandle(nsAString& aNativeHandle)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetNativeHandle(aNativeHandle);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetVisibility(bool* aVisibility)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetVisibility(aVisibility);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetVisibility(bool aVisibility)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetVisibility(aVisibility);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetEnabled(bool *aEnabled)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetEnabled(aEnabled);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetEnabled(bool aEnable)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetEnabled(aEnable);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetMainWidget(nsIWidget** aMainWidget)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aMainWidget);
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
|
||||
*aMainWidget = mXULWindow->mWindow;
|
||||
NS_IF_ADDREF(*aMainWidget);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetFocus()
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetFocus();
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::GetTitle(char16_t** aTitle)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->GetTitle(aTitle);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::SetTitle(const char16_t* aTitle)
|
||||
{
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
return mXULWindow->SetTitle(aTitle);
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner::nsIWebProgressListener
|
||||
//*****************************************************************************
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::OnProgressChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
int32_t aCurSelfProgress,
|
||||
int32_t aMaxSelfProgress,
|
||||
int32_t aCurTotalProgress,
|
||||
int32_t aMaxTotalProgress)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::OnStateChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
uint32_t aProgressStateFlags,
|
||||
nsresult aStatus)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsChromeTreeOwner::OnLocationChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsIURI* aLocation,
|
||||
uint32_t aFlags)
|
||||
{
|
||||
bool itsForYou = true;
|
||||
|
||||
if (aWebProgress) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
nsCOMPtr<mozIDOMWindowProxy> progressWin;
|
||||
aWebProgress->GetDOMWindow(getter_AddRefs(progressWin));
|
||||
|
||||
nsCOMPtr<nsIDocShell> docshell;
|
||||
mXULWindow->GetDocShell(getter_AddRefs(docshell));
|
||||
// XXXkhuey this is totally wrong, bug 1223303.
|
||||
nsCOMPtr<mozIDOMWindowProxy> ourWin(do_QueryInterface(docshell));
|
||||
|
||||
if (ourWin != progressWin)
|
||||
itsForYou = false;
|
||||
}
|
||||
|
||||
// If loading a new root .xul document, then redo chrome.
|
||||
if (itsForYou) {
|
||||
NS_ENSURE_STATE(mXULWindow);
|
||||
mXULWindow->mChromeLoaded = false;
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::OnStatusChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsresult aStatus,
|
||||
const char16_t* aMessage)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsChromeTreeOwner::OnSecurityChange(nsIWebProgress *aWebProgress,
|
||||
nsIRequest *aRequest,
|
||||
uint32_t state)
|
||||
{
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner: Helpers
|
||||
//*****************************************************************************
|
||||
|
||||
//*****************************************************************************
|
||||
// nsChromeTreeOwner: Accessors
|
||||
//*****************************************************************************
|
||||
|
||||
void nsChromeTreeOwner::XULWindow(nsXULWindow* aXULWindow)
|
||||
{
|
||||
mXULWindow = aXULWindow;
|
||||
}
|
||||
|
||||
nsXULWindow* nsChromeTreeOwner::XULWindow()
|
||||
{
|
||||
return mXULWindow;
|
||||
}
|
||||
53
xpfe/appshell/nsChromeTreeOwner.h
Normal file
53
xpfe/appshell/nsChromeTreeOwner.h
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
/* -*- Mode: C++; tab-width: 4; 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/. */
|
||||
|
||||
#ifndef nsChromeTreeOwner_h__
|
||||
#define nsChromeTreeOwner_h__
|
||||
|
||||
// Helper Classes
|
||||
#include "nsCOMPtr.h"
|
||||
|
||||
// Interfaces Needed
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIDocShellTreeOwner.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIWebProgressListener.h"
|
||||
#include "nsWeakReference.h"
|
||||
|
||||
class nsXULWindow;
|
||||
|
||||
class nsChromeTreeOwner : public nsIDocShellTreeOwner,
|
||||
public nsIBaseWindow,
|
||||
public nsIInterfaceRequestor,
|
||||
public nsIWebProgressListener,
|
||||
public nsSupportsWeakReference
|
||||
{
|
||||
friend class nsXULWindow;
|
||||
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
NS_DECL_NSIINTERFACEREQUESTOR
|
||||
NS_DECL_NSIBASEWINDOW
|
||||
NS_DECL_NSIDOCSHELLTREEOWNER
|
||||
NS_DECL_NSIWEBPROGRESSLISTENER
|
||||
|
||||
static nsresult InitGlobals();
|
||||
static void FreeGlobals();
|
||||
|
||||
protected:
|
||||
nsChromeTreeOwner();
|
||||
virtual ~nsChromeTreeOwner();
|
||||
|
||||
void XULWindow(nsXULWindow* aXULWindow);
|
||||
nsXULWindow* XULWindow();
|
||||
|
||||
protected:
|
||||
nsXULWindow* mXULWindow;
|
||||
};
|
||||
|
||||
#endif /* nsChromeTreeOwner_h__ */
|
||||
1131
xpfe/appshell/nsContentTreeOwner.cpp
Normal file
1131
xpfe/appshell/nsContentTreeOwner.cpp
Normal file
File diff suppressed because it is too large
Load diff
63
xpfe/appshell/nsContentTreeOwner.h
Normal file
63
xpfe/appshell/nsContentTreeOwner.h
Normal file
|
|
@ -0,0 +1,63 @@
|
|||
/* -*- Mode: IDL; tab-width: 4; 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/. */
|
||||
|
||||
#ifndef nsContentTreeOwner_h__
|
||||
#define nsContentTreeOwner_h__
|
||||
|
||||
// Helper Classes
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsString.h"
|
||||
|
||||
// Interfaces Needed
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIDocShellTreeOwner.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIWebBrowserChrome3.h"
|
||||
#include "nsIWindowProvider.h"
|
||||
|
||||
class nsXULWindow;
|
||||
class nsSiteWindow;
|
||||
|
||||
class nsContentTreeOwner final : public nsIDocShellTreeOwner,
|
||||
public nsIBaseWindow,
|
||||
public nsIInterfaceRequestor,
|
||||
public nsIWebBrowserChrome3,
|
||||
public nsIWindowProvider
|
||||
{
|
||||
friend class nsXULWindow;
|
||||
friend class nsSiteWindow;
|
||||
|
||||
public:
|
||||
NS_DECL_ISUPPORTS
|
||||
|
||||
NS_DECL_NSIBASEWINDOW
|
||||
NS_DECL_NSIDOCSHELLTREEOWNER
|
||||
NS_DECL_NSIINTERFACEREQUESTOR
|
||||
NS_DECL_NSIWEBBROWSERCHROME
|
||||
NS_DECL_NSIWEBBROWSERCHROME2
|
||||
NS_DECL_NSIWEBBROWSERCHROME3
|
||||
NS_DECL_NSIWINDOWPROVIDER
|
||||
|
||||
protected:
|
||||
explicit nsContentTreeOwner(bool fPrimary);
|
||||
virtual ~nsContentTreeOwner();
|
||||
|
||||
void XULWindow(nsXULWindow* aXULWindow);
|
||||
nsXULWindow* XULWindow();
|
||||
|
||||
protected:
|
||||
nsXULWindow *mXULWindow;
|
||||
nsSiteWindow *mSiteWindow;
|
||||
bool mPrimary;
|
||||
bool mContentTitleSetting;
|
||||
nsString mWindowTitleModifier;
|
||||
nsString mTitleSeparator;
|
||||
nsString mTitlePreface;
|
||||
nsString mTitleDefault;
|
||||
};
|
||||
|
||||
#endif /* nsContentTreeOwner_h__ */
|
||||
150
xpfe/appshell/nsIAppShellService.idl
Normal file
150
xpfe/appshell/nsIAppShellService.idl
Normal file
|
|
@ -0,0 +1,150 @@
|
|||
/* -*- 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 "nsISupports.idl"
|
||||
|
||||
interface nsIXULWindow;
|
||||
interface nsIWindowlessBrowser;
|
||||
interface nsIURI;
|
||||
interface mozIDOMWindowProxy;
|
||||
interface nsIAppShell;
|
||||
interface nsITabParent;
|
||||
|
||||
[ptr] native JSContext(JSContext);
|
||||
|
||||
%{C++
|
||||
#include "js/TypeDecls.h"
|
||||
%}
|
||||
|
||||
[scriptable, uuid(19266025-354c-4bb9-986b-3483b2b1cdef)]
|
||||
interface nsIAppShellService : nsISupports
|
||||
{
|
||||
/**
|
||||
* Create a window, which will be initially invisible.
|
||||
* @param aParent the parent window. Can be null.
|
||||
* @param aUrl the contents of the new window.
|
||||
* @param aChromeMask chrome flags affecting the kind of OS border
|
||||
* given to the window. see nsIBrowserWindow for
|
||||
* bit/flag definitions.
|
||||
* @param aCallbacks interface providing C++ hooks for window initialization
|
||||
* before the window is made visible. Can be null.
|
||||
* Deprecated.
|
||||
* @param aInitialWidth width, in pixels, of the window. Width of window
|
||||
* at creation. Can be overridden by the "width"
|
||||
* tag in the XUL. Set to NS_SIZETOCONTENT to force
|
||||
* the window to wrap to its contents.
|
||||
* @param aInitialHeight like aInitialWidth, but subtly different.
|
||||
* @param aOpeningTab The TabParent that requested that this window be opened.
|
||||
* Can be left null.
|
||||
* @param aOpenerWindow The Window Proxy which requested that this window be opened.
|
||||
* Can be left null.
|
||||
*/
|
||||
const long SIZE_TO_CONTENT = -1;
|
||||
nsIXULWindow createTopLevelWindow(in nsIXULWindow aParent,
|
||||
in nsIURI aUrl,
|
||||
in uint32_t aChromeMask,
|
||||
in long aInitialWidth,
|
||||
in long aInitialHeight,
|
||||
in nsITabParent aOpeningTab,
|
||||
in mozIDOMWindowProxy aOpenerWindow);
|
||||
|
||||
/**
|
||||
* This is the constructor for creating an invisible DocShell.
|
||||
* It is used to simulate DOM windows without an actual physical
|
||||
* representation.
|
||||
* @param aIsChrome Set true if you want to use it for chrome content.
|
||||
*/
|
||||
nsIWindowlessBrowser createWindowlessBrowser([optional] in bool aIsChrome);
|
||||
|
||||
[noscript]
|
||||
void createHiddenWindow();
|
||||
|
||||
void destroyHiddenWindow();
|
||||
|
||||
/**
|
||||
* B2G multi-screen support. When open another top-level window on b2g,
|
||||
* a screen ID is needed for identifying which screen this window is
|
||||
* opened to.
|
||||
* @param aScreenId Differentiate screens of windows. It is platform-
|
||||
* specific due to the hardware limitation for now.
|
||||
*/
|
||||
[noscript]
|
||||
void setScreenId(in uint32_t aScreenId);
|
||||
|
||||
/**
|
||||
* Return the (singleton) application hidden window, automatically created
|
||||
* and maintained by this AppShellService.
|
||||
* @param aResult the hidden window. Do not unhide hidden window.
|
||||
* Do not taunt hidden window.
|
||||
*/
|
||||
readonly attribute nsIXULWindow hiddenWindow;
|
||||
|
||||
/**
|
||||
* Return the (singleton) application hidden window, automatically created
|
||||
* and maintained by this AppShellService.
|
||||
* @param aResult the hidden window. Do not unhide hidden window.
|
||||
* Do not taunt hidden window.
|
||||
*/
|
||||
readonly attribute mozIDOMWindowProxy hiddenDOMWindow;
|
||||
|
||||
/**
|
||||
* Return the (singleton) application hidden private window, automatically
|
||||
* created and maintained by this AppShellService. This window is created
|
||||
* in private browsing mode.
|
||||
* @param aResult the hidden private window. Do not unhide hidden window.
|
||||
* Do not taunt hidden window.
|
||||
*/
|
||||
readonly attribute nsIXULWindow hiddenPrivateWindow;
|
||||
|
||||
/**
|
||||
* Return the (singleton) application hidden private window, automatically
|
||||
* created and maintained by this AppShellService. This window is created
|
||||
* in private browsing mode.
|
||||
* @param aResult the hidden private window. Do not unhide hidden window.
|
||||
* Do not taunt hidden window.
|
||||
*/
|
||||
readonly attribute mozIDOMWindowProxy hiddenPrivateDOMWindow;
|
||||
|
||||
/**
|
||||
* Return true if the application hidden window was provided by the
|
||||
* application. If it wasn't, the default hidden window was used. This will
|
||||
* usually be false on all non-mac platforms.
|
||||
*/
|
||||
readonly attribute boolean applicationProvidedHiddenWindow;
|
||||
|
||||
/**
|
||||
* Add a window to the application's registry of windows. These windows
|
||||
* are generally shown in the Windows taskbar, and the application
|
||||
* knows it can't quit until it's out of registered windows.
|
||||
* @param aWindow the window to register
|
||||
* @note When this method is successful, it fires the global notification
|
||||
* "xul-window-registered"
|
||||
*/
|
||||
void registerTopLevelWindow(in nsIXULWindow aWindow);
|
||||
|
||||
/**
|
||||
* Remove a window from the application's window registry. Note that
|
||||
* this method won't automatically attempt to quit the app when
|
||||
* the last window is unregistered. For that, see Quit().
|
||||
* @param aWindow you see the pattern
|
||||
*/
|
||||
void unregisterTopLevelWindow(in nsIXULWindow aWindow);
|
||||
|
||||
/**
|
||||
* Whether the hidden private window has been lazily created.
|
||||
*/
|
||||
[noscript]
|
||||
readonly attribute boolean hasHiddenPrivateWindow;
|
||||
|
||||
/**
|
||||
* Start/stop tracking lags in the event loop.
|
||||
* If the event loop gets unresponsive, a "event-loop-lag" notification
|
||||
* is sent. Note that calling `startEventLoopLagTracking` when tracking
|
||||
* is already enabled has no effect.
|
||||
* @return true if tracking succeeded.
|
||||
*/
|
||||
bool startEventLoopLagTracking();
|
||||
void stopEventLoopLagTracking();
|
||||
};
|
||||
35
xpfe/appshell/nsIPopupWindowManager.idl
Normal file
35
xpfe/appshell/nsIPopupWindowManager.idl
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
/**
|
||||
* This is the interface to the Popup Window Manager: an object which
|
||||
* maintains popup window permissions by website.
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
interface nsIPrincipal;
|
||||
|
||||
[scriptable, uuid(66386aa9-2088-4bae-82c7-9f58bc02be64)]
|
||||
interface nsIPopupWindowManager : nsISupports {
|
||||
|
||||
/**
|
||||
* These values are returned by the testPermission method
|
||||
*/
|
||||
const uint32_t ALLOW_POPUP = 1;
|
||||
const uint32_t DENY_POPUP = 2;
|
||||
const uint32_t ALLOW_POPUP_WITH_PREJUDICE = 3;
|
||||
|
||||
/**
|
||||
* Test whether a website has permission to show a popup window.
|
||||
* @param principal is the principal to be tested
|
||||
* @return one of the enumerated permission actions defined above
|
||||
*/
|
||||
uint32_t testPermission(in nsIPrincipal principal);
|
||||
};
|
||||
|
||||
%{ C++
|
||||
#define NS_POPUPWINDOWMANAGER_CONTRACTID "@mozilla.org/PopupWindowManager;1"
|
||||
%}
|
||||
206
xpfe/appshell/nsIWindowMediator.idl
Normal file
206
xpfe/appshell/nsIWindowMediator.idl
Normal file
|
|
@ -0,0 +1,206 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "nsISupports.idl"
|
||||
#include "nsISimpleEnumerator.idl"
|
||||
|
||||
%{C++
|
||||
#define NS_WINDOWMEDIATOR_CID \
|
||||
{ 0x79a2b7cc, 0xf05b, 0x4605, \
|
||||
{ 0xbf, 0xa0, 0xfa, 0xc5, 0x4f, 0x27, 0xee, 0xc8 } }
|
||||
|
||||
#define NS_WINDOWMEDIATOR_CONTRACTID \
|
||||
"@mozilla.org/appshell/window-mediator;1"
|
||||
%}
|
||||
|
||||
interface mozIDOMWindow;
|
||||
interface mozIDOMWindowProxy;
|
||||
interface nsIXULWindow;
|
||||
interface nsIWidget;
|
||||
interface nsIWindowMediatorListener;
|
||||
|
||||
[scriptable, uuid(df0da056-357d-427f-bafd-e6cbf19c9381)]
|
||||
interface nsIWindowMediator: nsISupports
|
||||
{
|
||||
/** Return an enumerator which iterates over all windows of type aWindowType
|
||||
* from the oldest window to the youngest.
|
||||
* @param aWindowType the returned enumerator will enumerate only
|
||||
* windows of this type. ("type" is the
|
||||
* |windowtype| attribute of the XML <window> element.)
|
||||
* If null, all windows will be enumerated.
|
||||
* @return an enumerator of nsIDOMWindows. Note that windows close
|
||||
* asynchronously in many cases, so windows returned from this
|
||||
* enumerator can have .closed set to true. Caveat enumerator!
|
||||
*/
|
||||
nsISimpleEnumerator getEnumerator(in wstring aWindowType);
|
||||
|
||||
/** Identical to getEnumerator except:
|
||||
* @return an enumerator of nsIXULWindows
|
||||
*/
|
||||
nsISimpleEnumerator getXULWindowEnumerator(in wstring aWindowType);
|
||||
|
||||
/** Return an enumerator which iterates over all windows of type aWindowType
|
||||
* in their z (front-to-back) order. Note this interface makes
|
||||
* no requirement that a window couldn't be revisited if windows
|
||||
* are re-ordered while z-order enumerators are active.
|
||||
* @param aWindowType the returned enumerator will enumerate only
|
||||
* windows of this type. ("type" is the
|
||||
* |windowtype| attribute of the XML <window> element.)
|
||||
* If null, all windows will be enumerated.
|
||||
* @param aFrontToBack if true, the enumerator enumerates windows in order
|
||||
* from front to back. back to front if false.
|
||||
* @return an enumerator of nsIDOMWindows
|
||||
*/
|
||||
nsISimpleEnumerator getZOrderDOMWindowEnumerator(in wstring aWindowType,
|
||||
in boolean aFrontToBack);
|
||||
|
||||
/** Identical to getZOrderDOMWindowEnumerator except:
|
||||
* @return an enumerator of nsIXULWindows
|
||||
*/
|
||||
nsISimpleEnumerator getZOrderXULWindowEnumerator(in wstring aWindowType,
|
||||
in boolean aFrontToBack);
|
||||
|
||||
/** This is a shortcut for simply fetching the first window in
|
||||
* front to back order.
|
||||
* @param aWindowType return the topmost window of this type.
|
||||
* ("type" is the |windowtype| attribute of
|
||||
* the XML <window> element.)
|
||||
* If null, return the topmost window of any type.
|
||||
* @return the topmost window
|
||||
*/
|
||||
mozIDOMWindowProxy getMostRecentWindow(in wstring aWindowType);
|
||||
|
||||
/**
|
||||
* Return the outer window with the given ID, if any. Can return null.
|
||||
*/
|
||||
mozIDOMWindowProxy getOuterWindowWithId(in unsigned long long aOuterWindowID);
|
||||
|
||||
/**
|
||||
* Return the inner window with the given current window ID, if any.
|
||||
* Can return null if no inner window with the ID exists or if it's not
|
||||
* a current inner anymore.
|
||||
*/
|
||||
mozIDOMWindow getCurrentInnerWindowWithId(in unsigned long long aInnerWindowID);
|
||||
|
||||
/** Add the window to the list of known windows. Listeners (see
|
||||
* addListener) will be notified through their onOpenWindow method.
|
||||
* @param aWindow the window to add
|
||||
*/
|
||||
[noscript] void registerWindow(in nsIXULWindow aWindow);
|
||||
|
||||
/** Remove the window from the list of known windows. Listeners (see
|
||||
* addListener) will be be notified through their onCloseWindow method.
|
||||
* @param aWindow the window to remove
|
||||
*/
|
||||
[noscript] void unregisterWindow(in nsIXULWindow aWindow);
|
||||
|
||||
/** Call this method when a window gains focus. It's a primitive means of
|
||||
* determining the most recent window. It's no longer necessary and it
|
||||
* really should be removed.
|
||||
* @param aWindow the window which has gained focus
|
||||
*/
|
||||
[noscript] void updateWindowTimeStamp(in nsIXULWindow aWindow);
|
||||
|
||||
/** Call this method when a window's title changes. Listeners (see
|
||||
* addListener) will be notified through their onWindowTitleChange method.
|
||||
* @param aWindow the window whose title has changed
|
||||
* @param inTitle the window's new title
|
||||
*/
|
||||
[noscript] void updateWindowTitle(in nsIXULWindow aWindow,
|
||||
in wstring inTitle );
|
||||
|
||||
/* z-ordering: */
|
||||
|
||||
const unsigned long zLevelTop = 1;
|
||||
const unsigned long zLevelBottom = 2;
|
||||
const unsigned long zLevelBelow = 3; // below some window
|
||||
|
||||
/** A window wants to be moved in z-order. Calculate whether and how
|
||||
* it should be constrained. Note this method is advisory only:
|
||||
* it changes nothing either in WindowMediator's internal state
|
||||
* or with the window.
|
||||
* Note it compares the nsIXULWindow to nsIWidgets. A pure interface
|
||||
* would use all nsIXULWindows. But we expect this to be called from
|
||||
* callbacks originating in native window code. They are expected to
|
||||
* hand us comparison values which are pulled from general storage
|
||||
* in the native widget, and may not correspond to an nsIWidget at all.
|
||||
* For that reason this interface requires only objects one step
|
||||
* removed from the native window (nsIWidgets), and its implementation
|
||||
* must be very understanding of what may be completely invalid
|
||||
* pointers in those parameters.
|
||||
*
|
||||
* @param inWindow the window in question
|
||||
* @param inPosition requested position
|
||||
* values: zLevelTop: topmost window. zLevelBottom: bottom.
|
||||
* zLevelBelow: below ioBelow. (the value of ioBelow will
|
||||
* be ignored for zLevelTop and Bottom.)
|
||||
* @param inBelow if inPosition==zLevelBelow, the window
|
||||
* below which inWindow wants to be placed. Otherwise this
|
||||
* variable is ignored.
|
||||
* @param outPosition constrained position, values like inPosition.
|
||||
* @param outBelow if outPosition==zLevelBelow, the window
|
||||
* below which inWindow should be placed. Otherwise this
|
||||
* this value will be null.
|
||||
* @return PR_TRUE if the position returned is different from
|
||||
* the position given.
|
||||
*/
|
||||
|
||||
[noscript] boolean calculateZPosition(in nsIXULWindow inWindow,
|
||||
in unsigned long inPosition,
|
||||
in nsIWidget inBelow,
|
||||
out unsigned long outPosition,
|
||||
out nsIWidget outBelow);
|
||||
|
||||
/** A window has been positioned behind another. Inform WindowMediator
|
||||
* @param inWindow the window in question
|
||||
* @param inPosition new position. values:
|
||||
* zLevelTop: topmost window.
|
||||
* zLevelBottom: bottom.
|
||||
* zLevelBelow: below inBelow. (inBelow is ignored
|
||||
* for other values of inPosition.)
|
||||
* @param inBelow the window inWindow is behind, if zLevelBelow
|
||||
*/
|
||||
[noscript] void setZPosition(in nsIXULWindow inWindow,
|
||||
in unsigned long inPosition,
|
||||
in nsIXULWindow inBelow);
|
||||
|
||||
/** Return the window's Z level (as defined in nsIXULWindow).
|
||||
* @param aWindow the window in question
|
||||
* @return aWindow's z level
|
||||
*/
|
||||
[noscript] uint32_t getZLevel(in nsIXULWindow aWindow);
|
||||
|
||||
/** Set the window's Z level (as defined in nsIXULWindow). The implementation
|
||||
* will reposition the window as necessary to match its new Z level.
|
||||
* The implementation will assume a window's Z level to be
|
||||
* nsIXULWindow::normalZ until it has been informed of a different level.
|
||||
* @param aWindow the window in question
|
||||
* @param aZLevel the window's new Z level
|
||||
*/
|
||||
[noscript] void setZLevel(in nsIXULWindow aWindow, in uint32_t aZLevel);
|
||||
|
||||
/** Register a listener for window status changes.
|
||||
* keeps strong ref? (to be decided)
|
||||
* @param aListener the listener to register
|
||||
*/
|
||||
void addListener(in nsIWindowMediatorListener aListener);
|
||||
|
||||
/** Unregister a listener of window status changes.
|
||||
* @param aListener the listener to unregister
|
||||
*/
|
||||
void removeListener(in nsIWindowMediatorListener aListener);
|
||||
};
|
||||
|
||||
// XXXcatalinb: This should be merged to nsIWindowMediator. Using this
|
||||
// to avoid UUID change in aurora.
|
||||
[scriptable, uuid(b9ed4063-39a2-4302-8e5c-7287eef021fe)]
|
||||
interface nsIWindowMediator_44 : nsIWindowMediator
|
||||
{
|
||||
/**
|
||||
* Same as getMostRecentWindow, but ignores private browsing
|
||||
* windows.
|
||||
*/
|
||||
mozIDOMWindowProxy getMostRecentNonPBWindow(in wstring aWindowType);
|
||||
};
|
||||
19
xpfe/appshell/nsIWindowMediatorListener.idl
Normal file
19
xpfe/appshell/nsIWindowMediatorListener.idl
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "nsISupports.idl"
|
||||
|
||||
interface nsIXULWindow;
|
||||
|
||||
[scriptable, uuid(2F276982-0D60-4377-A595-D350BA516395)]
|
||||
interface nsIWindowMediatorListener : nsISupports
|
||||
{
|
||||
void onWindowTitleChange(in nsIXULWindow window,
|
||||
in wstring newTitle);
|
||||
|
||||
void onOpenWindow(in nsIXULWindow window);
|
||||
void onCloseWindow(in nsIXULWindow window);
|
||||
};
|
||||
|
||||
27
xpfe/appshell/nsIWindowlessBrowser.idl
Normal file
27
xpfe/appshell/nsIWindowlessBrowser.idl
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
/* -*- Mode: IDL; tab-width: 4; 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 "nsIWebNavigation.idl"
|
||||
|
||||
/**
|
||||
* This interface represents a nsIWebBrowser instance with no associated OS
|
||||
* window. Its main function is to manage the lifetimes of those windows.
|
||||
* A strong reference to this object must be held until the window is
|
||||
* ready to be destroyed.
|
||||
*/
|
||||
[scriptable, uuid(abb46f48-abfc-41bf-aa9a-7feccefcf977)]
|
||||
interface nsIWindowlessBrowser : nsIWebNavigation
|
||||
{
|
||||
/**
|
||||
* "Closes" the windowless browser and destroys its associated nsIWebBrowser
|
||||
* and docshell.
|
||||
*
|
||||
* This method *must* be called for every windowless browser before its last
|
||||
* reference is released.
|
||||
*/
|
||||
void close();
|
||||
};
|
||||
|
||||
78
xpfe/appshell/nsIXULBrowserWindow.idl
Normal file
78
xpfe/appshell/nsIXULBrowserWindow.idl
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
/* -*- Mode: IDL; tab-width: 4; 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 "nsISupports.idl"
|
||||
#include "nsIURI.idl"
|
||||
#include "nsIDOMNode.idl"
|
||||
|
||||
interface nsIRequest;
|
||||
interface nsIDOMElement;
|
||||
interface nsIInputStream;
|
||||
interface nsIDocShell;
|
||||
interface nsITabParent;
|
||||
interface mozIDOMWindowProxy;
|
||||
|
||||
/**
|
||||
* The nsIXULBrowserWindow supplies the methods that may be called from the
|
||||
* internals of the browser area to tell the containing xul window to update
|
||||
* its ui.
|
||||
*/
|
||||
[scriptable, uuid(a8675fa9-c8b4-4350-9803-c38f344a9e38)]
|
||||
interface nsIXULBrowserWindow : nsISupports
|
||||
{
|
||||
/**
|
||||
* Sets the status according to JS' version of status.
|
||||
*/
|
||||
void setJSStatus(in AString status);
|
||||
|
||||
/**
|
||||
* Tells the object implementing this function what link we are currently
|
||||
* over.
|
||||
*/
|
||||
void setOverLink(in AString link, in nsIDOMElement element);
|
||||
|
||||
/**
|
||||
* Determines the appropriate target for a link.
|
||||
*/
|
||||
AString onBeforeLinkTraversal(in AString originalTarget,
|
||||
in nsIURI linkURI,
|
||||
in nsIDOMNode linkNode,
|
||||
in boolean isAppTab);
|
||||
|
||||
/**
|
||||
* Find the initial browser of the window and set its remote attribute.
|
||||
* This can be used to ensure that there is a remote browser in a new
|
||||
* window when it first spawns.
|
||||
*
|
||||
*/
|
||||
nsITabParent forceInitialBrowserRemote();
|
||||
void forceInitialBrowserNonRemote(in mozIDOMWindowProxy openerWindow);
|
||||
|
||||
/**
|
||||
* Determines whether a load should continue.
|
||||
*
|
||||
* @param aDocShell
|
||||
* The docshell performing the load.
|
||||
* @param aURI
|
||||
* The URI being loaded.
|
||||
* @param aReferrer
|
||||
* The referrer of the load.
|
||||
*/
|
||||
bool shouldLoadURI(in nsIDocShell aDocShell,
|
||||
in nsIURI aURI,
|
||||
in nsIURI aReferrer);
|
||||
/**
|
||||
* Show/hide a tooltip (when the user mouses over a link, say).
|
||||
*/
|
||||
void showTooltip(in long x, in long y, in AString tooltip, in AString direction);
|
||||
void hideTooltip();
|
||||
|
||||
/**
|
||||
* Return the number of tabs in this window.
|
||||
*/
|
||||
uint32_t getTabCount();
|
||||
};
|
||||
|
||||
168
xpfe/appshell/nsIXULWindow.idl
Normal file
168
xpfe/appshell/nsIXULWindow.idl
Normal file
|
|
@ -0,0 +1,168 @@
|
|||
/* -*- Mode: IDL; tab-width: 4; 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 "nsISupports.idl"
|
||||
|
||||
/**
|
||||
* The nsIXULWindow
|
||||
*
|
||||
* When the window is destroyed, it will fire a "xul-window-destroyed"
|
||||
* notification through the global observer service.
|
||||
*/
|
||||
|
||||
interface nsIDocShell;
|
||||
interface nsIDocShellTreeItem;
|
||||
interface nsIXULBrowserWindow;
|
||||
interface nsITabParent;
|
||||
interface mozIDOMWindowProxy;
|
||||
|
||||
[scriptable, uuid(d6d7a014-e28d-4c9d-8727-1cf6d870619b)]
|
||||
interface nsIXULWindow : nsISupports
|
||||
{
|
||||
/**
|
||||
* The docshell owning the XUL for this window.
|
||||
*/
|
||||
readonly attribute nsIDocShell docShell;
|
||||
|
||||
/**
|
||||
* Indicates if this window is instrinsically sized.
|
||||
*/
|
||||
attribute boolean intrinsicallySized;
|
||||
|
||||
/**
|
||||
* The primary content shell.
|
||||
*
|
||||
* Note that this is a docshell tree item and therefore can not be assured of
|
||||
* what object it is. It could be an editor, a docshell, or a browser object.
|
||||
* Or down the road any other object that supports being a DocShellTreeItem
|
||||
* Query accordingly to determine the capabilities.
|
||||
*/
|
||||
readonly attribute nsIDocShellTreeItem primaryContentShell;
|
||||
|
||||
/**
|
||||
* In multiprocess case we may not have primaryContentShell but
|
||||
* primaryTabParent.
|
||||
*/
|
||||
readonly attribute nsITabParent primaryTabParent;
|
||||
|
||||
void tabParentAdded(in nsITabParent aTab, in boolean aPrimary);
|
||||
void tabParentRemoved(in nsITabParent aTab);
|
||||
|
||||
/**
|
||||
* The content shell specified by the supplied id.
|
||||
*
|
||||
* Note that this is a docshell tree item and therefore can not be assured of
|
||||
* what object it is. It could be an editor, a docshell, or a browser object.
|
||||
* Or down the road any other object that supports being a DocShellTreeItem
|
||||
* Query accordingly to determine the capabilities.
|
||||
*/
|
||||
nsIDocShellTreeItem getContentShellById(in wstring ID);
|
||||
|
||||
/**
|
||||
* Tell this window that it has picked up a child XUL window
|
||||
* @param aChild the child window being added
|
||||
*/
|
||||
void addChildWindow(in nsIXULWindow aChild);
|
||||
|
||||
/**
|
||||
* Tell this window that it has lost a child XUL window
|
||||
* @param aChild the child window being removed
|
||||
*/
|
||||
void removeChildWindow(in nsIXULWindow aChild);
|
||||
|
||||
/**
|
||||
* Move the window to a centered position.
|
||||
* @param aRelative If not null, the window relative to which the window is
|
||||
* moved. See aScreen parameter for details.
|
||||
* @param aScreen PR_TRUE to center the window relative to the screen
|
||||
* containing aRelative if aRelative is not null. If
|
||||
* aRelative is null then relative to the screen of the
|
||||
* opener window if it was initialized by passing it to
|
||||
* nsWebShellWindow::Initialize. Failing that relative to
|
||||
* the main screen.
|
||||
* PR_FALSE to center it relative to aRelative itself.
|
||||
* @param aAlert PR_TRUE to move the window to an alert position,
|
||||
* generally centered horizontally and 1/3 down from the top.
|
||||
*/
|
||||
void center(in nsIXULWindow aRelative, in boolean aScreen, in boolean aAlert);
|
||||
|
||||
/**
|
||||
* Shows the window as a modal window. That is, ensures that it is visible
|
||||
* and runs a local event loop, exiting only once the window has been closed.
|
||||
*/
|
||||
void showModal();
|
||||
|
||||
const unsigned long lowestZ = 0;
|
||||
const unsigned long loweredZ = 4; /* "alwaysLowered" attribute */
|
||||
const unsigned long normalZ = 5;
|
||||
const unsigned long raisedZ = 6; /* "alwaysRaised" attribute */
|
||||
const unsigned long highestZ = 9;
|
||||
|
||||
attribute unsigned long zLevel;
|
||||
|
||||
/**
|
||||
* contextFlags are from nsIWindowCreator2
|
||||
*/
|
||||
attribute uint32_t contextFlags;
|
||||
|
||||
attribute uint32_t chromeFlags;
|
||||
|
||||
/**
|
||||
* Begin assuming |chromeFlags| don't change hereafter, and assert
|
||||
* if they do change. The state change is one-way and idempotent.
|
||||
*/
|
||||
void assumeChromeFlagsAreFrozen();
|
||||
|
||||
/**
|
||||
* Create a new window.
|
||||
* @param aChromeFlags see nsIWebBrowserChrome
|
||||
* @param aOpeningTab the TabParent that requested this new window be opened.
|
||||
* Can be left null.
|
||||
* @param aOpener The window which is requesting that this new window be opened.
|
||||
* @return the newly minted window
|
||||
*/
|
||||
nsIXULWindow createNewWindow(in int32_t aChromeFlags,
|
||||
in nsITabParent aOpeningTab,
|
||||
in mozIDOMWindowProxy aOpener);
|
||||
|
||||
attribute nsIXULBrowserWindow XULBrowserWindow;
|
||||
|
||||
/**
|
||||
* Back-door method to force application of chrome flags at a particular
|
||||
* time. Do NOT call this unless you know what you're doing! In particular,
|
||||
* calling this when this XUL window doesn't yet have a document in its
|
||||
* docshell could cause problems.
|
||||
*/
|
||||
[noscript] void applyChromeFlags();
|
||||
|
||||
/**
|
||||
* Given the dimensions of some content area held within this
|
||||
* XUL window, and assuming that that content area will change
|
||||
* its dimensions in linear proportion to the dimensions of this
|
||||
* XUL window, changes the size of the XUL window so that the
|
||||
* content area reaches a particular size.
|
||||
*
|
||||
* We need to supply the content area dimensions because sometimes
|
||||
* the child's nsDocShellTreeOwner needs to propagate a SizeShellTo
|
||||
* call to the parent. But the shellItem argument of the call will
|
||||
* not be available on the parent side.
|
||||
*
|
||||
* Note: this is an internal method, other consumers should never call this.
|
||||
*
|
||||
* @param aDesiredWidth
|
||||
* The desired width of the content area in device pixels.
|
||||
* @param aDesiredHeight
|
||||
* The desired height of the content area in device pixels.
|
||||
* @param shellItemWidth
|
||||
* The current width of the content area.
|
||||
* @param shellItemHeight
|
||||
* The current height of the content area.
|
||||
*/
|
||||
[noscript, notxpcom] void sizeShellToWithLimit(in int32_t aDesiredWidth,
|
||||
in int32_t aDesiredHeight,
|
||||
in int32_t shellItemWidth,
|
||||
in int32_t shellItemHeight);
|
||||
};
|
||||
911
xpfe/appshell/nsWebShellWindow.cpp
Normal file
911
xpfe/appshell/nsWebShellWindow.cpp
Normal file
|
|
@ -0,0 +1,911 @@
|
|||
/* -*- 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 "nsWebShellWindow.h"
|
||||
|
||||
#include "nsLayoutCID.h"
|
||||
#include "nsContentCID.h"
|
||||
#include "nsIWeakReference.h"
|
||||
#include "nsIContentViewer.h"
|
||||
#include "nsIComponentManager.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsIURL.h"
|
||||
#include "nsIIOService.h"
|
||||
#include "nsIURL.h"
|
||||
#include "nsNetCID.h"
|
||||
#include "nsIStringBundle.h"
|
||||
#include "nsReadableUtils.h"
|
||||
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsEscape.h"
|
||||
#include "nsPIDOMWindow.h"
|
||||
#include "nsIWebNavigation.h"
|
||||
#include "nsIWindowWatcher.h"
|
||||
|
||||
#include "nsIDOMXULElement.h"
|
||||
|
||||
#include "nsWidgetInitData.h"
|
||||
#include "nsWidgetsCID.h"
|
||||
#include "nsIWidget.h"
|
||||
#include "nsIWidgetListener.h"
|
||||
|
||||
#include "nsIDOMCharacterData.h"
|
||||
#include "nsIDOMNodeList.h"
|
||||
|
||||
#include "nsITimer.h"
|
||||
#include "nsXULPopupManager.h"
|
||||
|
||||
|
||||
#include "nsIDOMXULDocument.h"
|
||||
|
||||
#include "nsFocusManager.h"
|
||||
|
||||
#include "nsIWebProgress.h"
|
||||
#include "nsIWebProgressListener.h"
|
||||
|
||||
#include "nsIDocument.h"
|
||||
#include "nsIDOMDocument.h"
|
||||
#include "nsIDOMNode.h"
|
||||
#include "nsIDOMElement.h"
|
||||
#include "nsIDocumentLoaderFactory.h"
|
||||
#include "nsIObserverService.h"
|
||||
#include "prprf.h"
|
||||
|
||||
#include "nsIScreenManager.h"
|
||||
#include "nsIScreen.h"
|
||||
|
||||
#include "nsIContent.h" // for menus
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
|
||||
// For calculating size
|
||||
#include "nsIPresShell.h"
|
||||
#include "nsPresContext.h"
|
||||
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIDocShellTreeItem.h"
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "mozilla/DebugOnly.h"
|
||||
#include "mozilla/MouseEvents.h"
|
||||
|
||||
#include "nsPIWindowRoot.h"
|
||||
|
||||
#ifdef XP_MACOSX
|
||||
#include "nsINativeMenuService.h"
|
||||
#define USE_NATIVE_MENUS
|
||||
#endif
|
||||
|
||||
using namespace mozilla;
|
||||
using namespace mozilla::dom;
|
||||
|
||||
/* Define Class IDs */
|
||||
static NS_DEFINE_CID(kWindowCID, NS_WINDOW_CID);
|
||||
|
||||
#define SIZE_PERSISTENCE_TIMEOUT 500 // msec
|
||||
|
||||
nsWebShellWindow::nsWebShellWindow(uint32_t aChromeFlags)
|
||||
: nsXULWindow(aChromeFlags)
|
||||
, mSPTimerLock("nsWebShellWindow.mSPTimerLock")
|
||||
, mWidgetListenerDelegate(this)
|
||||
{
|
||||
}
|
||||
|
||||
nsWebShellWindow::~nsWebShellWindow()
|
||||
{
|
||||
MutexAutoLock lock(mSPTimerLock);
|
||||
if (mSPTimer)
|
||||
mSPTimer->Cancel();
|
||||
}
|
||||
|
||||
NS_IMPL_ADDREF_INHERITED(nsWebShellWindow, nsXULWindow)
|
||||
NS_IMPL_RELEASE_INHERITED(nsWebShellWindow, nsXULWindow)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN(nsWebShellWindow)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIWebProgressListener)
|
||||
NS_INTERFACE_MAP_END_INHERITING(nsXULWindow)
|
||||
|
||||
nsresult nsWebShellWindow::Initialize(nsIXULWindow* aParent,
|
||||
nsIXULWindow* aOpener,
|
||||
nsIURI* aUrl,
|
||||
int32_t aInitialWidth,
|
||||
int32_t aInitialHeight,
|
||||
bool aIsHiddenWindow,
|
||||
nsITabParent *aOpeningTab,
|
||||
mozIDOMWindowProxy *aOpenerWindow,
|
||||
nsWidgetInitData& widgetInitData)
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIWidget> parentWidget;
|
||||
|
||||
mIsHiddenWindow = aIsHiddenWindow;
|
||||
|
||||
int32_t initialX = 0, initialY = 0;
|
||||
nsCOMPtr<nsIBaseWindow> base(do_QueryInterface(aOpener));
|
||||
if (base) {
|
||||
rv = base->GetPositionAndSize(&mOpenerScreenRect.x,
|
||||
&mOpenerScreenRect.y,
|
||||
&mOpenerScreenRect.width,
|
||||
&mOpenerScreenRect.height);
|
||||
if (NS_FAILED(rv)) {
|
||||
mOpenerScreenRect.SetEmpty();
|
||||
} else {
|
||||
double scale;
|
||||
if (NS_SUCCEEDED(base->GetUnscaledDevicePixelsPerCSSPixel(&scale))) {
|
||||
mOpenerScreenRect.x = NSToIntRound(mOpenerScreenRect.x / scale);
|
||||
mOpenerScreenRect.y = NSToIntRound(mOpenerScreenRect.y / scale);
|
||||
mOpenerScreenRect.width = NSToIntRound(mOpenerScreenRect.width / scale);
|
||||
mOpenerScreenRect.height = NSToIntRound(mOpenerScreenRect.height / scale);
|
||||
}
|
||||
initialX = mOpenerScreenRect.x;
|
||||
initialY = mOpenerScreenRect.y;
|
||||
ConstrainToOpenerScreen(&initialX, &initialY);
|
||||
}
|
||||
}
|
||||
|
||||
// XXX: need to get the default window size from prefs...
|
||||
// Doesn't come from prefs... will come from CSS/XUL/RDF
|
||||
DesktopIntRect deskRect(initialX, initialY, aInitialWidth, aInitialHeight);
|
||||
|
||||
// Create top level window
|
||||
mWindow = do_CreateInstance(kWindowCID, &rv);
|
||||
if (NS_OK != rv) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* This next bit is troublesome. We carry two different versions of a pointer
|
||||
to our parent window. One is the parent window's widget, which is passed
|
||||
to our own widget. The other is a weak reference we keep here to our
|
||||
parent WebShellWindow. The former is useful to the widget, and we can't
|
||||
trust its treatment of the parent reference because they're platform-
|
||||
specific. The latter is useful to this class.
|
||||
A better implementation would be one in which the parent keeps strong
|
||||
references to its children and closes them before it allows itself
|
||||
to be closed. This would mimic the behaviour of OSes that support
|
||||
top-level child windows in OSes that do not. Later.
|
||||
*/
|
||||
nsCOMPtr<nsIBaseWindow> parentAsWin(do_QueryInterface(aParent));
|
||||
if (parentAsWin) {
|
||||
parentAsWin->GetMainWidget(getter_AddRefs(parentWidget));
|
||||
mParentWindow = do_GetWeakReference(aParent);
|
||||
}
|
||||
|
||||
mWindow->SetWidgetListener(&mWidgetListenerDelegate);
|
||||
rv = mWindow->Create((nsIWidget *)parentWidget, // Parent nsIWidget
|
||||
nullptr, // Native parent widget
|
||||
deskRect, // Widget dimensions
|
||||
&widgetInitData); // Widget initialization data
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
LayoutDeviceIntRect r = mWindow->GetClientBounds();
|
||||
// Match the default background color of content. Important on windows
|
||||
// since we no longer use content child widgets.
|
||||
mWindow->SetBackgroundColor(NS_RGB(255,255,255));
|
||||
|
||||
// Create web shell
|
||||
mDocShell = do_CreateInstance("@mozilla.org/docshell;1");
|
||||
NS_ENSURE_TRUE(mDocShell, NS_ERROR_FAILURE);
|
||||
|
||||
mDocShell->SetOpener(aOpeningTab);
|
||||
|
||||
// Make sure to set the item type on the docshell _before_ calling
|
||||
// Create() so it knows what type it is.
|
||||
nsCOMPtr<nsIDocShellTreeItem> docShellAsItem(do_QueryInterface(mDocShell));
|
||||
NS_ENSURE_TRUE(docShellAsItem, NS_ERROR_FAILURE);
|
||||
NS_ENSURE_SUCCESS(EnsureChromeTreeOwner(), NS_ERROR_FAILURE);
|
||||
|
||||
docShellAsItem->SetTreeOwner(mChromeTreeOwner);
|
||||
docShellAsItem->SetItemType(nsIDocShellTreeItem::typeChrome);
|
||||
|
||||
r.x = r.y = 0;
|
||||
nsCOMPtr<nsIBaseWindow> docShellAsWin(do_QueryInterface(mDocShell));
|
||||
NS_ENSURE_SUCCESS(docShellAsWin->InitWindow(nullptr, mWindow,
|
||||
r.x, r.y, r.width, r.height), NS_ERROR_FAILURE);
|
||||
NS_ENSURE_SUCCESS(docShellAsWin->Create(), NS_ERROR_FAILURE);
|
||||
|
||||
// Attach a WebProgress listener.during initialization...
|
||||
nsCOMPtr<nsIWebProgress> webProgress(do_GetInterface(mDocShell, &rv));
|
||||
if (webProgress) {
|
||||
webProgress->AddProgressListener(this, nsIWebProgress::NOTIFY_STATE_NETWORK);
|
||||
}
|
||||
|
||||
if (aOpenerWindow) {
|
||||
nsPIDOMWindowOuter* window = mDocShell->GetWindow();
|
||||
MOZ_ASSERT(window);
|
||||
window->SetOpenerWindow(nsPIDOMWindowOuter::From(aOpenerWindow), true);
|
||||
}
|
||||
|
||||
// Eagerly create an about:blank content viewer with the right principal here,
|
||||
// rather than letting it happening in the upcoming call to
|
||||
// SetInitialPrincipalToSubject. This avoids creating the about:blank document
|
||||
// and then blowing it away with a second one, which can cause problems for the
|
||||
// top-level chrome window case. See bug 789773.
|
||||
// Note that we don't accept expanded principals here, similar to
|
||||
// SetInitialPrincipalToSubject.
|
||||
if (nsContentUtils::IsInitialized()) { // Sometimes this happens really early See bug 793370.
|
||||
MOZ_ASSERT(mDocShell->ItemType() == nsIDocShellTreeItem::typeChrome);
|
||||
nsCOMPtr<nsIPrincipal> principal = nsContentUtils::SubjectPrincipalOrSystemIfNativeCaller();
|
||||
if (nsContentUtils::IsExpandedPrincipal(principal)) {
|
||||
principal = nullptr;
|
||||
}
|
||||
rv = mDocShell->CreateAboutBlankContentViewer(principal);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
nsCOMPtr<nsIDocument> doc = mDocShell->GetDocument();
|
||||
NS_ENSURE_TRUE(!!doc, NS_ERROR_FAILURE);
|
||||
doc->SetIsInitialDocument(true);
|
||||
}
|
||||
|
||||
if (nullptr != aUrl) {
|
||||
nsCString tmpStr;
|
||||
|
||||
rv = aUrl->GetSpec(tmpStr);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
NS_ConvertUTF8toUTF16 urlString(tmpStr);
|
||||
nsCOMPtr<nsIWebNavigation> webNav(do_QueryInterface(mDocShell));
|
||||
NS_ENSURE_TRUE(webNav, NS_ERROR_FAILURE);
|
||||
rv = webNav->LoadURI(urlString.get(),
|
||||
nsIWebNavigation::LOAD_FLAGS_NONE,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsIPresShell*
|
||||
nsWebShellWindow::GetPresShell()
|
||||
{
|
||||
if (!mDocShell)
|
||||
return nullptr;
|
||||
|
||||
return mDocShell->GetPresShell();
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WindowMoved(nsIWidget* aWidget, int32_t x, int32_t y)
|
||||
{
|
||||
nsXULPopupManager* pm = nsXULPopupManager::GetInstance();
|
||||
if (pm) {
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window =
|
||||
mDocShell ? mDocShell->GetWindow() : nullptr;
|
||||
pm->AdjustPopupsOnWindowChange(window);
|
||||
}
|
||||
|
||||
// Notify all tabs that the widget moved.
|
||||
if (mDocShell && mDocShell->GetWindow()) {
|
||||
nsCOMPtr<EventTarget> eventTarget = mDocShell->GetWindow()->GetTopWindowRoot();
|
||||
nsContentUtils::DispatchChromeEvent(mDocShell->GetDocument(),
|
||||
eventTarget,
|
||||
NS_LITERAL_STRING("MozUpdateWindowPos"),
|
||||
false, false, nullptr);
|
||||
}
|
||||
|
||||
// Persist position, but not immediately, in case this OS is firing
|
||||
// repeated move events as the user drags the window
|
||||
SetPersistenceTimer(PAD_POSITION);
|
||||
return false;
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WindowResized(nsIWidget* aWidget, int32_t aWidth, int32_t aHeight)
|
||||
{
|
||||
nsCOMPtr<nsIBaseWindow> shellAsWin(do_QueryInterface(mDocShell));
|
||||
if (shellAsWin) {
|
||||
shellAsWin->SetPositionAndSize(0, 0, aWidth, aHeight, 0);
|
||||
}
|
||||
// Persist size, but not immediately, in case this OS is firing
|
||||
// repeated size events as the user drags the sizing handle
|
||||
if (!IsLocked())
|
||||
SetPersistenceTimer(PAD_POSITION | PAD_SIZE | PAD_MISC);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::RequestWindowClose(nsIWidget* aWidget)
|
||||
{
|
||||
// Maintain a reference to this as it is about to get destroyed.
|
||||
nsCOMPtr<nsIXULWindow> xulWindow(this);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window(mDocShell ? mDocShell->GetWindow() : nullptr);
|
||||
nsCOMPtr<EventTarget> eventTarget = do_QueryInterface(window);
|
||||
|
||||
nsCOMPtr<nsIPresShell> presShell = mDocShell->GetPresShell();
|
||||
if (!presShell) {
|
||||
mozilla::DebugOnly<bool> dying;
|
||||
MOZ_ASSERT(NS_SUCCEEDED(mDocShell->IsBeingDestroyed(&dying)) && dying,
|
||||
"No presShell, but window is not being destroyed");
|
||||
} else if (eventTarget) {
|
||||
RefPtr<nsPresContext> presContext = presShell->GetPresContext();
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
WidgetMouseEvent event(true, eWindowClose, nullptr,
|
||||
WidgetMouseEvent::eReal);
|
||||
if (NS_SUCCEEDED(eventTarget->DispatchDOMEvent(&event, nullptr, presContext, &status)) &&
|
||||
status == nsEventStatus_eConsumeNoDefault)
|
||||
return false;
|
||||
}
|
||||
|
||||
Destroy();
|
||||
return false;
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::SizeModeChanged(nsSizeMode sizeMode)
|
||||
{
|
||||
// An alwaysRaised (or higher) window will hide any newly opened normal
|
||||
// browser windows, so here we just drop a raised window to the normal
|
||||
// zlevel if it's maximized. We make no provision for automatically
|
||||
// re-raising it when restored.
|
||||
if (sizeMode == nsSizeMode_Maximized || sizeMode == nsSizeMode_Fullscreen) {
|
||||
uint32_t zLevel;
|
||||
GetZLevel(&zLevel);
|
||||
if (zLevel > nsIXULWindow::normalZ)
|
||||
SetZLevel(nsIXULWindow::normalZ);
|
||||
}
|
||||
mWindow->SetSizeMode(sizeMode);
|
||||
|
||||
// Persist mode, but not immediately, because in many (all?)
|
||||
// cases this will merge with the similar call in NS_SIZE and
|
||||
// write the attribute values only once.
|
||||
SetPersistenceTimer(PAD_MISC);
|
||||
nsCOMPtr<nsPIDOMWindowOuter> ourWindow =
|
||||
mDocShell ? mDocShell->GetWindow() : nullptr;
|
||||
if (ourWindow) {
|
||||
MOZ_ASSERT(ourWindow->IsOuterWindow());
|
||||
|
||||
// Ensure that the fullscreen state is synchronized between
|
||||
// the widget and the outer window object.
|
||||
if (sizeMode == nsSizeMode_Fullscreen) {
|
||||
ourWindow->SetFullScreen(true);
|
||||
}
|
||||
else if (sizeMode != nsSizeMode_Minimized) {
|
||||
if (ourWindow->GetFullScreen()) {
|
||||
// The first SetFullscreenInternal call below ensures that we do
|
||||
// not trigger any fullscreen transition even if the window was
|
||||
// put in fullscreen only for the Fullscreen API. The second
|
||||
// SetFullScreen call ensures that the window really exit from
|
||||
// fullscreen even if it entered fullscreen for both Fullscreen
|
||||
// Mode and Fullscreen API.
|
||||
ourWindow->SetFullscreenInternal(FullscreenReason::ForForceExitFullscreen, false);
|
||||
ourWindow->SetFullScreen(false);
|
||||
}
|
||||
}
|
||||
|
||||
// And always fire a user-defined sizemodechange event on the window
|
||||
ourWindow->DispatchCustomEvent(NS_LITERAL_STRING("sizemodechange"));
|
||||
}
|
||||
|
||||
nsIPresShell* presShell;
|
||||
if ((presShell = GetPresShell())) {
|
||||
presShell->GetPresContext()->SizeModeChanged(sizeMode);
|
||||
}
|
||||
|
||||
// Note the current implementation of SetSizeMode just stores
|
||||
// the new state; it doesn't actually resize. So here we store
|
||||
// the state and pass the event on to the OS. The day is coming
|
||||
// when we'll handle the event here, and the return result will
|
||||
// then need to be different.
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::UIResolutionChanged()
|
||||
{
|
||||
nsCOMPtr<nsPIDOMWindowOuter> ourWindow =
|
||||
mDocShell ? mDocShell->GetWindow() : nullptr;
|
||||
if (ourWindow) {
|
||||
MOZ_ASSERT(ourWindow->IsOuterWindow());
|
||||
ourWindow->DispatchCustomEvent(NS_LITERAL_STRING("resolutionchange"));
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::FullscreenChanged(bool aInFullscreen)
|
||||
{
|
||||
if (mDocShell) {
|
||||
if (nsCOMPtr<nsPIDOMWindowOuter> ourWindow = mDocShell->GetWindow()) {
|
||||
ourWindow->FinishFullscreenChange(aInFullscreen);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::OSToolbarButtonPressed()
|
||||
{
|
||||
// Keep a reference as setting the chrome flags can fire events.
|
||||
nsCOMPtr<nsIXULWindow> xulWindow(this);
|
||||
|
||||
// rjc: don't use "nsIWebBrowserChrome::CHROME_EXTRA"
|
||||
// due to components with multiple sidebar components
|
||||
// (such as Mail/News, Addressbook, etc)... and frankly,
|
||||
// Mac IE, OmniWeb, and other Mac OS X apps all work this way
|
||||
uint32_t chromeMask = (nsIWebBrowserChrome::CHROME_TOOLBAR |
|
||||
nsIWebBrowserChrome::CHROME_LOCATIONBAR |
|
||||
nsIWebBrowserChrome::CHROME_PERSONAL_TOOLBAR);
|
||||
|
||||
nsCOMPtr<nsIWebBrowserChrome> wbc(do_GetInterface(xulWindow));
|
||||
if (!wbc)
|
||||
return;
|
||||
|
||||
uint32_t chromeFlags, newChromeFlags = 0;
|
||||
wbc->GetChromeFlags(&chromeFlags);
|
||||
newChromeFlags = chromeFlags & chromeMask;
|
||||
if (!newChromeFlags) chromeFlags |= chromeMask;
|
||||
else chromeFlags &= (~newChromeFlags);
|
||||
wbc->SetChromeFlags(chromeFlags);
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::ZLevelChanged(bool aImmediate, nsWindowZ *aPlacement,
|
||||
nsIWidget* aRequestBelow, nsIWidget** aActualBelow)
|
||||
{
|
||||
if (aActualBelow)
|
||||
*aActualBelow = nullptr;
|
||||
|
||||
return ConstrainToZLevel(aImmediate, aPlacement, aRequestBelow, aActualBelow);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WindowActivated()
|
||||
{
|
||||
nsCOMPtr<nsIXULWindow> xulWindow(this);
|
||||
|
||||
// focusing the window could cause it to close, so keep a reference to it
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window = mDocShell ? mDocShell->GetWindow() : nullptr;
|
||||
nsCOMPtr<nsIFocusManager> fm = do_GetService(FOCUSMANAGER_CONTRACTID);
|
||||
if (fm && window)
|
||||
fm->WindowRaised(window);
|
||||
|
||||
if (mChromeLoaded) {
|
||||
PersistentAttributesDirty(PAD_POSITION | PAD_SIZE | PAD_MISC);
|
||||
SavePersistentAttributes();
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WindowDeactivated()
|
||||
{
|
||||
nsCOMPtr<nsIXULWindow> xulWindow(this);
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> window =
|
||||
mDocShell ? mDocShell->GetWindow() : nullptr;
|
||||
nsCOMPtr<nsIFocusManager> fm = do_GetService(FOCUSMANAGER_CONTRACTID);
|
||||
if (fm && window)
|
||||
fm->WindowLowered(window);
|
||||
}
|
||||
|
||||
#ifdef USE_NATIVE_MENUS
|
||||
static void LoadNativeMenus(nsIDOMDocument *aDOMDoc, nsIWidget *aParentWindow)
|
||||
{
|
||||
nsCOMPtr<nsINativeMenuService> nms = do_GetService("@mozilla.org/widget/nativemenuservice;1");
|
||||
if (!nms) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Find the menubar tag (if there is more than one, we ignore all but
|
||||
// the first).
|
||||
nsCOMPtr<nsIDOMNodeList> menubarElements;
|
||||
aDOMDoc->GetElementsByTagNameNS(NS_LITERAL_STRING("http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"),
|
||||
NS_LITERAL_STRING("menubar"),
|
||||
getter_AddRefs(menubarElements));
|
||||
|
||||
nsCOMPtr<nsIDOMNode> menubarNode;
|
||||
if (menubarElements)
|
||||
menubarElements->Item(0, getter_AddRefs(menubarNode));
|
||||
|
||||
if (menubarNode) {
|
||||
nsCOMPtr<nsIContent> menubarContent(do_QueryInterface(menubarNode));
|
||||
nms->CreateNativeMenuBar(aParentWindow, menubarContent);
|
||||
} else {
|
||||
nms->CreateNativeMenuBar(aParentWindow, nullptr);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
class WebShellWindowTimerCallback final : public nsITimerCallback
|
||||
{
|
||||
public:
|
||||
explicit WebShellWindowTimerCallback(nsWebShellWindow* aWindow)
|
||||
: mWindow(aWindow)
|
||||
{}
|
||||
|
||||
NS_DECL_THREADSAFE_ISUPPORTS
|
||||
|
||||
NS_IMETHOD Notify(nsITimer* aTimer) override
|
||||
{
|
||||
// Although this object participates in a refcount cycle (this -> mWindow
|
||||
// -> mSPTimer -> this), mSPTimer is a one-shot timer and releases this
|
||||
// after it fires. So we don't need to release mWindow here.
|
||||
|
||||
mWindow->FirePersistenceTimer();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
private:
|
||||
~WebShellWindowTimerCallback() {}
|
||||
|
||||
RefPtr<nsWebShellWindow> mWindow;
|
||||
};
|
||||
|
||||
NS_IMPL_ISUPPORTS(WebShellWindowTimerCallback, nsITimerCallback)
|
||||
|
||||
} // namespace mozilla
|
||||
|
||||
void
|
||||
nsWebShellWindow::SetPersistenceTimer(uint32_t aDirtyFlags)
|
||||
{
|
||||
MutexAutoLock lock(mSPTimerLock);
|
||||
if (!mSPTimer) {
|
||||
mSPTimer = do_CreateInstance("@mozilla.org/timer;1");
|
||||
if (!mSPTimer) {
|
||||
NS_WARNING("Couldn't create @mozilla.org/timer;1 instance?");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
RefPtr<WebShellWindowTimerCallback> callback =
|
||||
new WebShellWindowTimerCallback(this);
|
||||
mSPTimer->InitWithCallback(callback, SIZE_PERSISTENCE_TIMEOUT,
|
||||
nsITimer::TYPE_ONE_SHOT);
|
||||
|
||||
PersistentAttributesDirty(aDirtyFlags);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::FirePersistenceTimer()
|
||||
{
|
||||
MutexAutoLock lock(mSPTimerLock);
|
||||
SavePersistentAttributes();
|
||||
}
|
||||
|
||||
|
||||
//----------------------------------------
|
||||
// nsIWebProgessListener implementation
|
||||
//----------------------------------------
|
||||
NS_IMETHODIMP
|
||||
nsWebShellWindow::OnProgressChange(nsIWebProgress *aProgress,
|
||||
nsIRequest *aRequest,
|
||||
int32_t aCurSelfProgress,
|
||||
int32_t aMaxSelfProgress,
|
||||
int32_t aCurTotalProgress,
|
||||
int32_t aMaxTotalProgress)
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWebShellWindow::OnStateChange(nsIWebProgress *aProgress,
|
||||
nsIRequest *aRequest,
|
||||
uint32_t aStateFlags,
|
||||
nsresult aStatus)
|
||||
{
|
||||
// If the notification is not about a document finishing, then just
|
||||
// ignore it...
|
||||
if (!(aStateFlags & nsIWebProgressListener::STATE_STOP) ||
|
||||
!(aStateFlags & nsIWebProgressListener::STATE_IS_NETWORK)) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (mChromeLoaded)
|
||||
return NS_OK;
|
||||
|
||||
// If this document notification is for a frame then ignore it...
|
||||
nsCOMPtr<mozIDOMWindowProxy> eventWin;
|
||||
aProgress->GetDOMWindow(getter_AddRefs(eventWin));
|
||||
auto* eventPWin = nsPIDOMWindowOuter::From(eventWin);
|
||||
if (eventPWin) {
|
||||
nsPIDOMWindowOuter *rootPWin = eventPWin->GetPrivateRoot();
|
||||
if (eventPWin != rootPWin)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
mChromeLoaded = true;
|
||||
mLockedUntilChromeLoad = false;
|
||||
|
||||
#ifdef USE_NATIVE_MENUS
|
||||
///////////////////////////////
|
||||
// Find the Menubar DOM and Load the menus, hooking them up to the loaded commands
|
||||
///////////////////////////////
|
||||
nsCOMPtr<nsIContentViewer> cv;
|
||||
mDocShell->GetContentViewer(getter_AddRefs(cv));
|
||||
if (cv) {
|
||||
nsCOMPtr<nsIDOMDocument> menubarDOMDoc(do_QueryInterface(cv->GetDocument()));
|
||||
if (menubarDOMDoc)
|
||||
LoadNativeMenus(menubarDOMDoc, mWindow);
|
||||
}
|
||||
#endif // USE_NATIVE_MENUS
|
||||
|
||||
OnChromeLoaded();
|
||||
LoadContentAreas();
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWebShellWindow::OnLocationChange(nsIWebProgress *aProgress,
|
||||
nsIRequest *aRequest,
|
||||
nsIURI *aURI,
|
||||
uint32_t aFlags)
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWebShellWindow::OnStatusChange(nsIWebProgress* aWebProgress,
|
||||
nsIRequest* aRequest,
|
||||
nsresult aStatus,
|
||||
const char16_t* aMessage)
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWebShellWindow::OnSecurityChange(nsIWebProgress *aWebProgress,
|
||||
nsIRequest *aRequest,
|
||||
uint32_t state)
|
||||
{
|
||||
NS_NOTREACHED("notification excluded in AddProgressListener(...)");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
//----------------------------------------
|
||||
|
||||
// if the main document URL specified URLs for any content areas, start them loading
|
||||
void nsWebShellWindow::LoadContentAreas() {
|
||||
|
||||
nsAutoString searchSpec;
|
||||
|
||||
// fetch the chrome document URL
|
||||
nsCOMPtr<nsIContentViewer> contentViewer;
|
||||
// yes, it's possible for the docshell to be null even this early
|
||||
// see bug 57514.
|
||||
if (mDocShell)
|
||||
mDocShell->GetContentViewer(getter_AddRefs(contentViewer));
|
||||
if (contentViewer) {
|
||||
nsIDocument* doc = contentViewer->GetDocument();
|
||||
if (doc) {
|
||||
nsIURI* mainURL = doc->GetDocumentURI();
|
||||
|
||||
nsCOMPtr<nsIURL> url = do_QueryInterface(mainURL);
|
||||
if (url) {
|
||||
nsAutoCString search;
|
||||
url->GetQuery(search);
|
||||
|
||||
AppendUTF8toUTF16(search, searchSpec);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// content URLs are specified in the search part of the URL
|
||||
// as <contentareaID>=<escapedURL>[;(repeat)]
|
||||
if (!searchSpec.IsEmpty()) {
|
||||
int32_t begPos,
|
||||
eqPos,
|
||||
endPos;
|
||||
nsString contentAreaID,
|
||||
contentURL;
|
||||
char *urlChar;
|
||||
nsresult rv;
|
||||
for (endPos = 0; endPos < (int32_t)searchSpec.Length(); ) {
|
||||
// extract contentAreaID and URL substrings
|
||||
begPos = endPos;
|
||||
eqPos = searchSpec.FindChar('=', begPos);
|
||||
if (eqPos < 0)
|
||||
break;
|
||||
|
||||
endPos = searchSpec.FindChar(';', eqPos);
|
||||
if (endPos < 0)
|
||||
endPos = searchSpec.Length();
|
||||
searchSpec.Mid(contentAreaID, begPos, eqPos-begPos);
|
||||
searchSpec.Mid(contentURL, eqPos+1, endPos-eqPos-1);
|
||||
endPos++;
|
||||
|
||||
// see if we have a docshell with a matching contentAreaID
|
||||
nsCOMPtr<nsIDocShellTreeItem> content;
|
||||
rv = GetContentShellById(contentAreaID.get(), getter_AddRefs(content));
|
||||
if (NS_SUCCEEDED(rv) && content) {
|
||||
nsCOMPtr<nsIWebNavigation> webNav(do_QueryInterface(content));
|
||||
if (webNav) {
|
||||
urlChar = ToNewCString(contentURL);
|
||||
if (urlChar) {
|
||||
nsUnescape(urlChar);
|
||||
contentURL.AssignWithConversion(urlChar);
|
||||
webNav->LoadURI(contentURL.get(),
|
||||
nsIWebNavigation::LOAD_FLAGS_NONE,
|
||||
nullptr,
|
||||
nullptr,
|
||||
nullptr);
|
||||
free(urlChar);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* ExecuteCloseHandler - Run the close handler, if any.
|
||||
* @return true iff we found a close handler to run.
|
||||
*/
|
||||
bool nsWebShellWindow::ExecuteCloseHandler()
|
||||
{
|
||||
/* If the event handler closes this window -- a likely scenario --
|
||||
things get deleted out of order without this death grip.
|
||||
(The problem may be the death grip in nsWindow::windowProc,
|
||||
which forces this window's widget to remain alive longer
|
||||
than it otherwise would.) */
|
||||
nsCOMPtr<nsIXULWindow> kungFuDeathGrip(this);
|
||||
|
||||
nsCOMPtr<EventTarget> eventTarget;
|
||||
if (mDocShell) {
|
||||
eventTarget = do_QueryInterface(mDocShell->GetWindow());
|
||||
}
|
||||
|
||||
if (eventTarget) {
|
||||
nsCOMPtr<nsIContentViewer> contentViewer;
|
||||
mDocShell->GetContentViewer(getter_AddRefs(contentViewer));
|
||||
if (contentViewer) {
|
||||
RefPtr<nsPresContext> presContext;
|
||||
contentViewer->GetPresContext(getter_AddRefs(presContext));
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
WidgetMouseEvent event(true, eWindowClose, nullptr,
|
||||
WidgetMouseEvent::eReal);
|
||||
|
||||
nsresult rv =
|
||||
eventTarget->DispatchDOMEvent(&event, nullptr, presContext, &status);
|
||||
if (NS_SUCCEEDED(rv) && status == nsEventStatus_eConsumeNoDefault)
|
||||
return true;
|
||||
// else fall through and return false
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
} // ExecuteCloseHandler
|
||||
|
||||
void nsWebShellWindow::ConstrainToOpenerScreen(int32_t* aX, int32_t* aY)
|
||||
{
|
||||
if (mOpenerScreenRect.IsEmpty()) {
|
||||
*aX = *aY = 0;
|
||||
return;
|
||||
}
|
||||
|
||||
int32_t left, top, width, height;
|
||||
// Constrain initial positions to the same screen as opener
|
||||
nsCOMPtr<nsIScreenManager> screenmgr = do_GetService("@mozilla.org/gfx/screenmanager;1");
|
||||
if (screenmgr) {
|
||||
nsCOMPtr<nsIScreen> screen;
|
||||
screenmgr->ScreenForRect(mOpenerScreenRect.x, mOpenerScreenRect.y,
|
||||
mOpenerScreenRect.width, mOpenerScreenRect.height,
|
||||
getter_AddRefs(screen));
|
||||
if (screen) {
|
||||
screen->GetAvailRectDisplayPix(&left, &top, &width, &height);
|
||||
if (*aX < left || *aX > left + width) {
|
||||
*aX = left;
|
||||
}
|
||||
if (*aY < top || *aY > top + height) {
|
||||
*aY = top;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// nsIBaseWindow
|
||||
NS_IMETHODIMP nsWebShellWindow::Destroy()
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIWebProgress> webProgress(do_GetInterface(mDocShell, &rv));
|
||||
if (webProgress) {
|
||||
webProgress->RemoveProgressListener(this);
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIXULWindow> kungFuDeathGrip(this);
|
||||
{
|
||||
MutexAutoLock lock(mSPTimerLock);
|
||||
if (mSPTimer) {
|
||||
mSPTimer->Cancel();
|
||||
SavePersistentAttributes();
|
||||
mSPTimer = nullptr;
|
||||
}
|
||||
}
|
||||
return nsXULWindow::Destroy();
|
||||
}
|
||||
|
||||
nsIXULWindow*
|
||||
nsWebShellWindow::WidgetListenerDelegate::GetXULWindow()
|
||||
{
|
||||
return mWebShellWindow->GetXULWindow();
|
||||
}
|
||||
|
||||
nsIPresShell*
|
||||
nsWebShellWindow::WidgetListenerDelegate::GetPresShell()
|
||||
{
|
||||
return mWebShellWindow->GetPresShell();
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WidgetListenerDelegate::WindowMoved(
|
||||
nsIWidget* aWidget, int32_t aX, int32_t aY)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
return holder->WindowMoved(aWidget, aX, aY);
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WidgetListenerDelegate::WindowResized(
|
||||
nsIWidget* aWidget, int32_t aWidth, int32_t aHeight)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
return holder->WindowResized(aWidget, aWidth, aHeight);
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WidgetListenerDelegate::RequestWindowClose(nsIWidget* aWidget)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
return holder->RequestWindowClose(aWidget);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::SizeModeChanged(nsSizeMode aSizeMode)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->SizeModeChanged(aSizeMode);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::UIResolutionChanged()
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->UIResolutionChanged();
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::FullscreenChanged(bool aInFullscreen)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->FullscreenChanged(aInFullscreen);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::OSToolbarButtonPressed()
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->OSToolbarButtonPressed();
|
||||
}
|
||||
|
||||
bool
|
||||
nsWebShellWindow::WidgetListenerDelegate::ZLevelChanged(
|
||||
bool aImmediate, nsWindowZ *aPlacement, nsIWidget* aRequestBelow,
|
||||
nsIWidget** aActualBelow)
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
return holder->ZLevelChanged(aImmediate,
|
||||
aPlacement,
|
||||
aRequestBelow,
|
||||
aActualBelow);
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::WindowActivated()
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->WindowActivated();
|
||||
}
|
||||
|
||||
void
|
||||
nsWebShellWindow::WidgetListenerDelegate::WindowDeactivated()
|
||||
{
|
||||
RefPtr<nsWebShellWindow> holder = mWebShellWindow;
|
||||
holder->WindowDeactivated();
|
||||
}
|
||||
116
xpfe/appshell/nsWebShellWindow.h
Normal file
116
xpfe/appshell/nsWebShellWindow.h
Normal file
|
|
@ -0,0 +1,116 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
#ifndef nsWebShellWindow_h__
|
||||
#define nsWebShellWindow_h__
|
||||
|
||||
#include "mozilla/Mutex.h"
|
||||
#include "nsIWebProgressListener.h"
|
||||
#include "nsITimer.h"
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsXULWindow.h"
|
||||
#include "nsIWidgetListener.h"
|
||||
#include "nsITabParent.h"
|
||||
|
||||
/* Forward declarations.... */
|
||||
class nsIURI;
|
||||
|
||||
struct nsWidgetInitData;
|
||||
|
||||
namespace mozilla {
|
||||
class WebShellWindowTimerCallback;
|
||||
} // namespace mozilla
|
||||
|
||||
class nsWebShellWindow final : public nsXULWindow,
|
||||
public nsIWebProgressListener
|
||||
{
|
||||
public:
|
||||
|
||||
// The implementation of non-refcounted nsIWidgetListener, which would hold a
|
||||
// strong reference on stack before calling nsWebShellWindow
|
||||
class WidgetListenerDelegate : public nsIWidgetListener
|
||||
{
|
||||
public:
|
||||
explicit WidgetListenerDelegate(nsWebShellWindow* aWebShellWindow)
|
||||
: mWebShellWindow(aWebShellWindow) {}
|
||||
|
||||
virtual nsIXULWindow* GetXULWindow() override;
|
||||
virtual nsIPresShell* GetPresShell() override;
|
||||
virtual bool WindowMoved(nsIWidget* aWidget, int32_t x, int32_t y) override;
|
||||
virtual bool WindowResized(nsIWidget* aWidget, int32_t aWidth, int32_t aHeight) override;
|
||||
virtual bool RequestWindowClose(nsIWidget* aWidget) override;
|
||||
virtual void SizeModeChanged(nsSizeMode sizeMode) override;
|
||||
virtual void UIResolutionChanged() override;
|
||||
virtual void FullscreenChanged(bool aInFullscreen) override;
|
||||
virtual void OSToolbarButtonPressed() override;
|
||||
virtual bool ZLevelChanged(bool aImmediate,
|
||||
nsWindowZ *aPlacement,
|
||||
nsIWidget* aRequestBelow,
|
||||
nsIWidget** aActualBelow) override;
|
||||
virtual void WindowActivated() override;
|
||||
virtual void WindowDeactivated() override;
|
||||
|
||||
private:
|
||||
// The lifetime of WidgetListenerDelegate is bound to nsWebShellWindow so
|
||||
// we just use a raw pointer here.
|
||||
nsWebShellWindow* mWebShellWindow;
|
||||
};
|
||||
|
||||
explicit nsWebShellWindow(uint32_t aChromeFlags);
|
||||
|
||||
// nsISupports interface...
|
||||
NS_DECL_ISUPPORTS_INHERITED
|
||||
|
||||
// nsWebShellWindow methods...
|
||||
nsresult Initialize(nsIXULWindow * aParent, nsIXULWindow * aOpener,
|
||||
nsIURI* aUrl,
|
||||
int32_t aInitialWidth, int32_t aInitialHeight,
|
||||
bool aIsHiddenWindow,
|
||||
nsITabParent *aOpeningTab,
|
||||
mozIDOMWindowProxy *aOpenerWIndow,
|
||||
nsWidgetInitData& widgetInitData);
|
||||
|
||||
nsresult Toolbar();
|
||||
|
||||
// nsIWebProgressListener
|
||||
NS_DECL_NSIWEBPROGRESSLISTENER
|
||||
|
||||
// nsIBaseWindow
|
||||
NS_IMETHOD Destroy() override;
|
||||
|
||||
// nsIWidgetListener
|
||||
nsIXULWindow* GetXULWindow() { return this; }
|
||||
nsIPresShell* GetPresShell();
|
||||
bool WindowMoved(nsIWidget* aWidget, int32_t x, int32_t y);
|
||||
bool WindowResized(nsIWidget* aWidget, int32_t aWidth, int32_t aHeight);
|
||||
bool RequestWindowClose(nsIWidget* aWidget);
|
||||
void SizeModeChanged(nsSizeMode sizeMode);
|
||||
void UIResolutionChanged();
|
||||
void FullscreenChanged(bool aInFullscreen);
|
||||
void OSToolbarButtonPressed();
|
||||
bool ZLevelChanged(bool aImmediate, nsWindowZ *aPlacement,
|
||||
nsIWidget* aRequestBelow, nsIWidget** aActualBelow);
|
||||
void WindowActivated();
|
||||
void WindowDeactivated();
|
||||
|
||||
protected:
|
||||
friend class mozilla::WebShellWindowTimerCallback;
|
||||
|
||||
virtual ~nsWebShellWindow();
|
||||
|
||||
void LoadContentAreas();
|
||||
bool ExecuteCloseHandler();
|
||||
void ConstrainToOpenerScreen(int32_t* aX, int32_t* aY);
|
||||
|
||||
nsCOMPtr<nsITimer> mSPTimer;
|
||||
mozilla::Mutex mSPTimerLock;
|
||||
WidgetListenerDelegate mWidgetListenerDelegate;
|
||||
|
||||
void SetPersistenceTimer(uint32_t aDirtyFlags);
|
||||
void FirePersistenceTimer();
|
||||
};
|
||||
|
||||
|
||||
#endif /* nsWebShellWindow_h__ */
|
||||
846
xpfe/appshell/nsWindowMediator.cpp
Normal file
846
xpfe/appshell/nsWindowMediator.cpp
Normal file
|
|
@ -0,0 +1,846 @@
|
|||
/* -*- 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 "nsCOMPtr.h"
|
||||
#include "nsString.h"
|
||||
#include "nsReadableUtils.h"
|
||||
#include "nsUnicharUtils.h"
|
||||
#include "nsTArray.h"
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIWidget.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIObserverService.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsISimpleEnumerator.h"
|
||||
#include "nsAppShellWindowEnumerator.h"
|
||||
#include "nsWindowMediator.h"
|
||||
#include "nsIWindowMediatorListener.h"
|
||||
#include "nsXPIDLString.h"
|
||||
#include "nsGlobalWindow.h"
|
||||
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIXULWindow.h"
|
||||
|
||||
using namespace mozilla;
|
||||
|
||||
static bool notifyOpenWindow(nsIWindowMediatorListener *aElement, void* aData);
|
||||
static bool notifyCloseWindow(nsIWindowMediatorListener *aElement, void* aData);
|
||||
static bool notifyWindowTitleChange(nsIWindowMediatorListener *aElement, void* aData);
|
||||
|
||||
// for notifyWindowTitleChange
|
||||
struct WindowTitleData {
|
||||
nsIXULWindow* mWindow;
|
||||
const char16_t *mTitle;
|
||||
};
|
||||
|
||||
nsresult
|
||||
nsWindowMediator::GetDOMWindow(nsIXULWindow* inWindow,
|
||||
nsCOMPtr<nsPIDOMWindowOuter>& outDOMWindow)
|
||||
{
|
||||
nsCOMPtr<nsIDocShell> docShell;
|
||||
|
||||
outDOMWindow = nullptr;
|
||||
inWindow->GetDocShell(getter_AddRefs(docShell));
|
||||
NS_ENSURE_TRUE(docShell, NS_ERROR_FAILURE);
|
||||
|
||||
outDOMWindow = docShell->GetWindow();
|
||||
return outDOMWindow ? NS_OK : NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsWindowMediator::nsWindowMediator() :
|
||||
mEnumeratorList(), mOldestWindow(nullptr), mTopmostWindow(nullptr),
|
||||
mTimeStamp(0), mSortingZOrder(false), mReady(false)
|
||||
{
|
||||
}
|
||||
|
||||
nsWindowMediator::~nsWindowMediator()
|
||||
{
|
||||
while (mOldestWindow)
|
||||
UnregisterWindow(mOldestWindow);
|
||||
}
|
||||
|
||||
nsresult nsWindowMediator::Init()
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIObserverService> obsSvc =
|
||||
do_GetService("@mozilla.org/observer-service;1", &rv);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
rv = obsSvc->AddObserver(this, "xpcom-shutdown", true);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
mReady = true;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowMediator::RegisterWindow(nsIXULWindow* inWindow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
if (GetInfoFor(inWindow)) {
|
||||
NS_ERROR("multiple window registration");
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
mTimeStamp++;
|
||||
|
||||
// Create window info struct and add to list of windows
|
||||
nsWindowInfo* windowInfo = new nsWindowInfo(inWindow, mTimeStamp);
|
||||
|
||||
WindowTitleData winData = { inWindow, nullptr };
|
||||
mListeners.EnumerateForwards(notifyOpenWindow, &winData);
|
||||
|
||||
if (mOldestWindow)
|
||||
windowInfo->InsertAfter(mOldestWindow->mOlder, nullptr);
|
||||
else
|
||||
mOldestWindow = windowInfo;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::UnregisterWindow(nsIXULWindow* inWindow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_STATE(mReady);
|
||||
nsWindowInfo *info = GetInfoFor(inWindow);
|
||||
if (info)
|
||||
return UnregisterWindow(info);
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsWindowMediator::UnregisterWindow(nsWindowInfo *inInfo)
|
||||
{
|
||||
// Inform the iterators
|
||||
uint32_t index = 0;
|
||||
while (index < mEnumeratorList.Length()) {
|
||||
mEnumeratorList[index]->WindowRemoved(inInfo);
|
||||
index++;
|
||||
}
|
||||
|
||||
WindowTitleData winData = { inInfo->mWindow.get(), nullptr };
|
||||
mListeners.EnumerateForwards(notifyCloseWindow, &winData);
|
||||
|
||||
// Remove from the lists and free up
|
||||
if (inInfo == mOldestWindow)
|
||||
mOldestWindow = inInfo->mYounger;
|
||||
if (inInfo == mTopmostWindow)
|
||||
mTopmostWindow = inInfo->mLower;
|
||||
inInfo->Unlink(true, true);
|
||||
if (inInfo == mOldestWindow)
|
||||
mOldestWindow = nullptr;
|
||||
if (inInfo == mTopmostWindow)
|
||||
mTopmostWindow = nullptr;
|
||||
delete inInfo;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsWindowInfo*
|
||||
nsWindowMediator::GetInfoFor(nsIXULWindow *aWindow)
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
|
||||
if (!aWindow)
|
||||
return nullptr;
|
||||
|
||||
info = mOldestWindow;
|
||||
listEnd = nullptr;
|
||||
while (info != listEnd) {
|
||||
if (info->mWindow.get() == aWindow)
|
||||
return info;
|
||||
info = info->mYounger;
|
||||
listEnd = mOldestWindow;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
nsWindowInfo*
|
||||
nsWindowMediator::GetInfoFor(nsIWidget *aWindow)
|
||||
{
|
||||
nsWindowInfo *info,
|
||||
*listEnd;
|
||||
|
||||
if (!aWindow)
|
||||
return nullptr;
|
||||
|
||||
info = mOldestWindow;
|
||||
listEnd = nullptr;
|
||||
|
||||
nsCOMPtr<nsIWidget> scanWidget;
|
||||
while (info != listEnd) {
|
||||
nsCOMPtr<nsIBaseWindow> base(do_QueryInterface(info->mWindow));
|
||||
if (base)
|
||||
base->GetMainWidget(getter_AddRefs(scanWidget));
|
||||
if (aWindow == scanWidget.get())
|
||||
return info;
|
||||
info = info->mYounger;
|
||||
listEnd = mOldestWindow;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetEnumerator(const char16_t* inType, nsISimpleEnumerator** outEnumerator)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(outEnumerator);
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
RefPtr<nsAppShellWindowEnumerator> enumerator = new nsASDOMWindowEarlyToLateEnumerator(inType, *this);
|
||||
enumerator.forget(outEnumerator);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetXULWindowEnumerator(const char16_t* inType, nsISimpleEnumerator** outEnumerator)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(outEnumerator);
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
RefPtr<nsAppShellWindowEnumerator> enumerator = new nsASXULWindowEarlyToLateEnumerator(inType, *this);
|
||||
enumerator.forget(outEnumerator);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetZOrderDOMWindowEnumerator(
|
||||
const char16_t *aWindowType, bool aFrontToBack,
|
||||
nsISimpleEnumerator **_retval)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
RefPtr<nsAppShellWindowEnumerator> enumerator;
|
||||
if (aFrontToBack)
|
||||
enumerator = new nsASDOMWindowFrontToBackEnumerator(aWindowType, *this);
|
||||
else
|
||||
enumerator = new nsASDOMWindowBackToFrontEnumerator(aWindowType, *this);
|
||||
|
||||
enumerator.forget(_retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetZOrderXULWindowEnumerator(
|
||||
const char16_t *aWindowType, bool aFrontToBack,
|
||||
nsISimpleEnumerator **_retval)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
RefPtr<nsAppShellWindowEnumerator> enumerator;
|
||||
if (aFrontToBack)
|
||||
enumerator = new nsASXULWindowFrontToBackEnumerator(aWindowType, *this);
|
||||
else
|
||||
enumerator = new nsASXULWindowBackToFrontEnumerator(aWindowType, *this);
|
||||
|
||||
enumerator.forget(_retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
int32_t
|
||||
nsWindowMediator::AddEnumerator(nsAppShellWindowEnumerator * inEnumerator)
|
||||
{
|
||||
return mEnumeratorList.AppendElement(inEnumerator) != nullptr;
|
||||
}
|
||||
|
||||
int32_t
|
||||
nsWindowMediator::RemoveEnumerator(nsAppShellWindowEnumerator * inEnumerator)
|
||||
{
|
||||
return mEnumeratorList.RemoveElement(inEnumerator);
|
||||
}
|
||||
|
||||
// Returns the window of type inType ( if null return any window type ) which has the most recent
|
||||
// time stamp
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetMostRecentWindow(const char16_t* inType,
|
||||
mozIDOMWindowProxy** outWindow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(outWindow);
|
||||
*outWindow = nullptr;
|
||||
if (!mReady)
|
||||
return NS_OK;
|
||||
|
||||
// Find the most window with the highest time stamp that matches
|
||||
// the requested type
|
||||
nsWindowInfo* info = MostRecentWindowInfo(inType, false);
|
||||
if (info && info->mWindow) {
|
||||
nsCOMPtr<nsPIDOMWindowOuter> DOMWindow;
|
||||
if (NS_SUCCEEDED(GetDOMWindow(info->mWindow, DOMWindow))) {
|
||||
DOMWindow.forget(outWindow);
|
||||
return NS_OK;
|
||||
}
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetMostRecentNonPBWindow(const char16_t* aType, mozIDOMWindowProxy** aWindow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(aWindow);
|
||||
*aWindow = nullptr;
|
||||
|
||||
nsWindowInfo *info = MostRecentWindowInfo(aType, true);
|
||||
nsCOMPtr<nsPIDOMWindowOuter> domWindow;
|
||||
if (info && info->mWindow) {
|
||||
GetDOMWindow(info->mWindow, domWindow);
|
||||
}
|
||||
|
||||
if (!domWindow) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
domWindow.forget(aWindow);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsWindowInfo*
|
||||
nsWindowMediator::MostRecentWindowInfo(const char16_t* inType,
|
||||
bool aSkipPrivateBrowsingOrClosed)
|
||||
{
|
||||
int32_t lastTimeStamp = -1;
|
||||
nsAutoString typeString(inType);
|
||||
bool allWindows = !inType || typeString.IsEmpty();
|
||||
|
||||
// Find the most recent window with the highest time stamp that matches
|
||||
// the requested type and has the correct browsing mode.
|
||||
nsWindowInfo* searchInfo = mOldestWindow;
|
||||
nsWindowInfo* listEnd = nullptr;
|
||||
nsWindowInfo* foundInfo = nullptr;
|
||||
for (; searchInfo != listEnd; searchInfo = searchInfo->mYounger) {
|
||||
listEnd = mOldestWindow;
|
||||
|
||||
if (!allWindows && !searchInfo->TypeEquals(typeString)) {
|
||||
continue;
|
||||
}
|
||||
if (searchInfo->mTimeStamp < lastTimeStamp) {
|
||||
continue;
|
||||
}
|
||||
if (!searchInfo->mWindow) {
|
||||
continue;
|
||||
}
|
||||
if (aSkipPrivateBrowsingOrClosed) {
|
||||
nsCOMPtr<nsIDocShell> docShell;
|
||||
searchInfo->mWindow->GetDocShell(getter_AddRefs(docShell));
|
||||
nsCOMPtr<nsILoadContext> loadContext = do_QueryInterface(docShell);
|
||||
if (!loadContext || loadContext->UsePrivateBrowsing()) {
|
||||
continue;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowOuter> piwindow = docShell->GetWindow();
|
||||
if (!piwindow || piwindow->Closed()) {
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
foundInfo = searchInfo;
|
||||
lastTimeStamp = searchInfo->mTimeStamp;
|
||||
}
|
||||
|
||||
return foundInfo;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetOuterWindowWithId(uint64_t aWindowID,
|
||||
mozIDOMWindowProxy** aWindow)
|
||||
{
|
||||
RefPtr<nsGlobalWindow> window = nsGlobalWindow::GetOuterWindowWithId(aWindowID);
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outer = window ? window->AsOuter() : nullptr;
|
||||
outer.forget(aWindow);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetCurrentInnerWindowWithId(uint64_t aWindowID,
|
||||
mozIDOMWindow** aWindow)
|
||||
{
|
||||
RefPtr<nsGlobalWindow> window = nsGlobalWindow::GetInnerWindowWithId(aWindowID);
|
||||
|
||||
// not found
|
||||
if (!window)
|
||||
return NS_OK;
|
||||
|
||||
nsCOMPtr<nsPIDOMWindowInner> inner = window->AsInner();
|
||||
nsCOMPtr<nsPIDOMWindowOuter> outer = inner->GetOuterWindow();
|
||||
NS_ENSURE_TRUE(outer, NS_ERROR_UNEXPECTED);
|
||||
|
||||
// outer is already using another inner, so it's same as not found
|
||||
if (outer->GetCurrentInnerWindow() != inner)
|
||||
return NS_OK;
|
||||
|
||||
inner.forget(aWindow);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::UpdateWindowTimeStamp(nsIXULWindow* inWindow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_STATE(mReady);
|
||||
nsWindowInfo *info = GetInfoFor(inWindow);
|
||||
if (info) {
|
||||
// increment the window's time stamp
|
||||
info->mTimeStamp = ++mTimeStamp;
|
||||
return NS_OK;
|
||||
}
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::UpdateWindowTitle(nsIXULWindow* inWindow,
|
||||
const char16_t* inTitle)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_STATE(mReady);
|
||||
if (GetInfoFor(inWindow)) {
|
||||
WindowTitleData winData = { inWindow, inTitle };
|
||||
mListeners.EnumerateForwards(notifyWindowTitleChange, &winData);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* This method's plan is to intervene only when absolutely necessary.
|
||||
We will get requests to place our windows behind unknown windows.
|
||||
For the most part, we need to leave those alone (turning them into
|
||||
explicit requests to be on top breaks Windows.) So generally we
|
||||
calculate a change as seldom as possible.
|
||||
*/
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::CalculateZPosition(
|
||||
nsIXULWindow *inWindow,
|
||||
uint32_t inPosition,
|
||||
nsIWidget *inBelow,
|
||||
uint32_t *outPosition,
|
||||
nsIWidget **outBelow,
|
||||
bool *outAltered)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_ARG_POINTER(outBelow);
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
*outBelow = nullptr;
|
||||
|
||||
if (!inWindow || !outPosition || !outAltered)
|
||||
return NS_ERROR_NULL_POINTER;
|
||||
|
||||
if (inPosition != nsIWindowMediator::zLevelTop &&
|
||||
inPosition != nsIWindowMediator::zLevelBottom &&
|
||||
inPosition != nsIWindowMediator::zLevelBelow)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
|
||||
nsWindowInfo *info = mTopmostWindow;
|
||||
nsIXULWindow *belowWindow = nullptr;
|
||||
bool found = false;
|
||||
nsresult result = NS_OK;
|
||||
|
||||
*outPosition = inPosition;
|
||||
*outAltered = false;
|
||||
|
||||
if (mSortingZOrder) { // don't fight SortZOrder()
|
||||
*outBelow = inBelow;
|
||||
NS_IF_ADDREF(*outBelow);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
uint32_t inZ;
|
||||
GetZLevel(inWindow, &inZ);
|
||||
|
||||
if (inPosition == nsIWindowMediator::zLevelBelow) {
|
||||
// locate inBelow. use topmost if it can't be found or isn't in the
|
||||
// z-order list
|
||||
info = GetInfoFor(inBelow);
|
||||
if (!info || (info->mYounger != info && info->mLower == info))
|
||||
info = mTopmostWindow;
|
||||
else
|
||||
found = true;
|
||||
|
||||
if (!found) {
|
||||
/* Treat unknown windows as a request to be on top.
|
||||
Not as it should be, but that's what Windows gives us.
|
||||
Note we change inPosition, but not *outPosition. This forces
|
||||
us to go through the "on top" calculation just below, without
|
||||
necessarily changing the output parameters. */
|
||||
inPosition = nsIWindowMediator::zLevelTop;
|
||||
}
|
||||
}
|
||||
|
||||
if (inPosition == nsIWindowMediator::zLevelTop) {
|
||||
if (mTopmostWindow && mTopmostWindow->mZLevel > inZ) {
|
||||
// asked for topmost, can't have it. locate highest allowed position.
|
||||
do {
|
||||
if (info->mZLevel <= inZ)
|
||||
break;
|
||||
info = info->mLower;
|
||||
} while (info != mTopmostWindow);
|
||||
|
||||
*outPosition = nsIWindowMediator::zLevelBelow;
|
||||
belowWindow = info->mHigher->mWindow;
|
||||
*outAltered = true;
|
||||
}
|
||||
} else if (inPosition == nsIWindowMediator::zLevelBottom) {
|
||||
if (mTopmostWindow && mTopmostWindow->mHigher->mZLevel < inZ) {
|
||||
// asked for bottommost, can't have it. locate lowest allowed position.
|
||||
do {
|
||||
info = info->mHigher;
|
||||
if (info->mZLevel >= inZ)
|
||||
break;
|
||||
} while (info != mTopmostWindow);
|
||||
|
||||
*outPosition = nsIWindowMediator::zLevelBelow;
|
||||
belowWindow = info->mWindow;
|
||||
*outAltered = true;
|
||||
}
|
||||
} else {
|
||||
unsigned long relativeZ;
|
||||
|
||||
// check that we're in the right z-plane
|
||||
if (found) {
|
||||
belowWindow = info->mWindow;
|
||||
relativeZ = info->mZLevel;
|
||||
if (relativeZ > inZ) {
|
||||
// might be OK. is lower window, if any, lower?
|
||||
if (info->mLower != info && info->mLower->mZLevel > inZ) {
|
||||
do {
|
||||
if (info->mZLevel <= inZ)
|
||||
break;
|
||||
info = info->mLower;
|
||||
} while (info != mTopmostWindow);
|
||||
|
||||
belowWindow = info->mHigher->mWindow;
|
||||
*outAltered = true;
|
||||
}
|
||||
} else if (relativeZ < inZ) {
|
||||
// nope. look for a higher window to be behind.
|
||||
do {
|
||||
info = info->mHigher;
|
||||
if (info->mZLevel >= inZ)
|
||||
break;
|
||||
} while (info != mTopmostWindow);
|
||||
|
||||
if (info->mZLevel >= inZ)
|
||||
belowWindow = info->mWindow;
|
||||
else
|
||||
*outPosition = nsIWindowMediator::zLevelTop;
|
||||
*outAltered = true;
|
||||
} // else they're equal, so it's OK
|
||||
}
|
||||
}
|
||||
|
||||
if (NS_SUCCEEDED(result) && belowWindow) {
|
||||
nsCOMPtr<nsIBaseWindow> base(do_QueryInterface(belowWindow));
|
||||
if (base)
|
||||
base->GetMainWidget(outBelow);
|
||||
else
|
||||
result = NS_ERROR_NO_INTERFACE;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::SetZPosition(
|
||||
nsIXULWindow *inWindow,
|
||||
uint32_t inPosition,
|
||||
nsIXULWindow *inBelow)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
nsWindowInfo *inInfo,
|
||||
*belowInfo;
|
||||
|
||||
if ((inPosition != nsIWindowMediator::zLevelTop &&
|
||||
inPosition != nsIWindowMediator::zLevelBottom &&
|
||||
inPosition != nsIWindowMediator::zLevelBelow) ||
|
||||
!inWindow) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
if (mSortingZOrder) // don't fight SortZOrder()
|
||||
return NS_OK;
|
||||
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
/* Locate inWindow and unlink it from the z-order list.
|
||||
It's important we look for it in the age list, not the z-order list.
|
||||
This is because the former is guaranteed complete, while
|
||||
now may be this window's first exposure to the latter. */
|
||||
inInfo = GetInfoFor(inWindow);
|
||||
if (!inInfo)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
|
||||
// locate inBelow, place inWindow behind it
|
||||
if (inPosition == nsIWindowMediator::zLevelBelow) {
|
||||
belowInfo = GetInfoFor(inBelow);
|
||||
// it had better also be in the z-order list
|
||||
if (belowInfo &&
|
||||
belowInfo->mYounger != belowInfo && belowInfo->mLower == belowInfo) {
|
||||
belowInfo = nullptr;
|
||||
}
|
||||
if (!belowInfo) {
|
||||
if (inBelow)
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
else
|
||||
inPosition = nsIWindowMediator::zLevelTop;
|
||||
}
|
||||
}
|
||||
if (inPosition == nsIWindowMediator::zLevelTop ||
|
||||
inPosition == nsIWindowMediator::zLevelBottom)
|
||||
belowInfo = mTopmostWindow ? mTopmostWindow->mHigher : nullptr;
|
||||
|
||||
if (inInfo != belowInfo) {
|
||||
inInfo->Unlink(false, true);
|
||||
inInfo->InsertAfter(nullptr, belowInfo);
|
||||
}
|
||||
if (inPosition == nsIWindowMediator::zLevelTop)
|
||||
mTopmostWindow = inInfo;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::GetZLevel(nsIXULWindow *aWindow, uint32_t *_retval)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
*_retval = nsIXULWindow::normalZ;
|
||||
nsWindowInfo *info = GetInfoFor(aWindow);
|
||||
if (info) {
|
||||
*_retval = info->mZLevel;
|
||||
} else {
|
||||
NS_WARNING("getting z level of unregistered window");
|
||||
// this goes off during window destruction
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::SetZLevel(nsIXULWindow *aWindow, uint32_t aZLevel)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
NS_ENSURE_STATE(mReady);
|
||||
|
||||
nsWindowInfo *info = GetInfoFor(aWindow);
|
||||
NS_ASSERTION(info, "setting z level of unregistered window");
|
||||
if (!info)
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
if (info->mZLevel != aZLevel) {
|
||||
bool lowered = info->mZLevel > aZLevel;
|
||||
info->mZLevel = aZLevel;
|
||||
if (lowered)
|
||||
SortZOrderFrontToBack();
|
||||
else
|
||||
SortZOrderBackToFront();
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
/* Fix potentially out-of-order windows by performing an insertion sort
|
||||
on the z-order list. The method will work no matter how broken the
|
||||
list, but its assumed usage is immediately after one window's z level
|
||||
has been changed, so one window is potentially out of place. Such a sort
|
||||
is most efficiently done in a particular direction. Use this one
|
||||
if a window's z level has just been reduced, so the sort is most efficiently
|
||||
done front to back.
|
||||
Note it's hardly worth going to all the trouble to write two versions
|
||||
of this method except that if we choose the inefficient sorting direction,
|
||||
on slow systems windows could visibly bubble around the window that
|
||||
was moved.
|
||||
*/
|
||||
void
|
||||
nsWindowMediator::SortZOrderFrontToBack()
|
||||
{
|
||||
nsWindowInfo *scan, // scans list looking for problems
|
||||
*search, // searches for correct placement for scan window
|
||||
*prev, // previous search element
|
||||
*lowest; // bottom-most window in list
|
||||
bool finished;
|
||||
|
||||
if (!mTopmostWindow) // early during program execution there's no z list yet
|
||||
return; // there's also only one window, so this is not dangerous
|
||||
|
||||
mSortingZOrder = true;
|
||||
|
||||
/* Step through the list from top to bottom. If we find a window which
|
||||
should be moved down in the list, move it to its highest legal position. */
|
||||
do {
|
||||
finished = true;
|
||||
lowest = mTopmostWindow->mHigher;
|
||||
scan = mTopmostWindow;
|
||||
while (scan != lowest) {
|
||||
uint32_t scanZ = scan->mZLevel;
|
||||
if (scanZ < scan->mLower->mZLevel) { // out of order
|
||||
search = scan->mLower;
|
||||
do {
|
||||
prev = search;
|
||||
search = search->mLower;
|
||||
} while (prev != lowest && scanZ < search->mZLevel);
|
||||
|
||||
// reposition |scan| within the list
|
||||
if (scan == mTopmostWindow)
|
||||
mTopmostWindow = scan->mLower;
|
||||
scan->Unlink(false, true);
|
||||
scan->InsertAfter(nullptr, prev);
|
||||
|
||||
// fix actual window order
|
||||
nsCOMPtr<nsIBaseWindow> base;
|
||||
nsCOMPtr<nsIWidget> scanWidget;
|
||||
nsCOMPtr<nsIWidget> prevWidget;
|
||||
base = do_QueryInterface(scan->mWindow);
|
||||
if (base)
|
||||
base->GetMainWidget(getter_AddRefs(scanWidget));
|
||||
base = do_QueryInterface(prev->mWindow);
|
||||
if (base)
|
||||
base->GetMainWidget(getter_AddRefs(prevWidget));
|
||||
if (scanWidget)
|
||||
scanWidget->PlaceBehind(eZPlacementBelow, prevWidget, false);
|
||||
|
||||
finished = false;
|
||||
break;
|
||||
}
|
||||
scan = scan->mLower;
|
||||
}
|
||||
} while (!finished);
|
||||
|
||||
mSortingZOrder = false;
|
||||
}
|
||||
|
||||
// see comment for SortZOrderFrontToBack
|
||||
void
|
||||
nsWindowMediator::SortZOrderBackToFront()
|
||||
{
|
||||
nsWindowInfo *scan, // scans list looking for problems
|
||||
*search, // searches for correct placement for scan window
|
||||
*lowest; // bottom-most window in list
|
||||
bool finished;
|
||||
|
||||
if (!mTopmostWindow) // early during program execution there's no z list yet
|
||||
return; // there's also only one window, so this is not dangerous
|
||||
|
||||
mSortingZOrder = true;
|
||||
|
||||
/* Step through the list from bottom to top. If we find a window which
|
||||
should be moved up in the list, move it to its lowest legal position. */
|
||||
do {
|
||||
finished = true;
|
||||
lowest = mTopmostWindow->mHigher;
|
||||
scan = lowest;
|
||||
while (scan != mTopmostWindow) {
|
||||
uint32_t scanZ = scan->mZLevel;
|
||||
if (scanZ > scan->mHigher->mZLevel) { // out of order
|
||||
search = scan;
|
||||
do {
|
||||
search = search->mHigher;
|
||||
} while (search != lowest && scanZ > search->mZLevel);
|
||||
|
||||
// reposition |scan| within the list
|
||||
if (scan != search && scan != search->mLower) {
|
||||
scan->Unlink(false, true);
|
||||
scan->InsertAfter(nullptr, search);
|
||||
}
|
||||
if (search == lowest)
|
||||
mTopmostWindow = scan;
|
||||
|
||||
// fix actual window order
|
||||
nsCOMPtr<nsIBaseWindow> base;
|
||||
nsCOMPtr<nsIWidget> scanWidget;
|
||||
nsCOMPtr<nsIWidget> searchWidget;
|
||||
base = do_QueryInterface(scan->mWindow);
|
||||
if (base)
|
||||
base->GetMainWidget(getter_AddRefs(scanWidget));
|
||||
if (mTopmostWindow != scan) {
|
||||
base = do_QueryInterface(search->mWindow);
|
||||
if (base)
|
||||
base->GetMainWidget(getter_AddRefs(searchWidget));
|
||||
}
|
||||
if (scanWidget)
|
||||
scanWidget->PlaceBehind(eZPlacementBelow, searchWidget, false);
|
||||
finished = false;
|
||||
break;
|
||||
}
|
||||
scan = scan->mHigher;
|
||||
}
|
||||
} while (!finished);
|
||||
|
||||
mSortingZOrder = false;
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS(nsWindowMediator,
|
||||
nsIWindowMediator_44,
|
||||
nsIWindowMediator,
|
||||
nsIObserver,
|
||||
nsISupportsWeakReference)
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::AddListener(nsIWindowMediatorListener* aListener)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aListener);
|
||||
|
||||
mListeners.AppendObject(aListener);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::RemoveListener(nsIWindowMediatorListener* aListener)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aListener);
|
||||
|
||||
mListeners.RemoveObject(aListener);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowMediator::Observe(nsISupports* aSubject,
|
||||
const char* aTopic,
|
||||
const char16_t* aData)
|
||||
{
|
||||
if (!strcmp(aTopic, "xpcom-shutdown") && mReady) {
|
||||
MOZ_RELEASE_ASSERT(NS_IsMainThread());
|
||||
while (mOldestWindow)
|
||||
UnregisterWindow(mOldestWindow);
|
||||
mReady = false;
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
bool
|
||||
notifyOpenWindow(nsIWindowMediatorListener *aListener, void* aData)
|
||||
{
|
||||
WindowTitleData* winData = static_cast<WindowTitleData*>(aData);
|
||||
aListener->OnOpenWindow(winData->mWindow);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
notifyCloseWindow(nsIWindowMediatorListener *aListener, void* aData)
|
||||
{
|
||||
WindowTitleData* winData = static_cast<WindowTitleData*>(aData);
|
||||
aListener->OnCloseWindow(winData->mWindow);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
notifyWindowTitleChange(nsIWindowMediatorListener *aListener, void* aData)
|
||||
{
|
||||
WindowTitleData* titleData = reinterpret_cast<WindowTitleData*>(aData);
|
||||
aListener->OnWindowTitleChange(titleData->mWindow, titleData->mTitle);
|
||||
|
||||
return true;
|
||||
}
|
||||
78
xpfe/appshell/nsWindowMediator.h
Normal file
78
xpfe/appshell/nsWindowMediator.h
Normal file
|
|
@ -0,0 +1,78 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
#ifndef nsWindowMediator_h_
|
||||
#define nsWindowMediator_h_
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIWindowMediator.h"
|
||||
#include "nsIObserver.h"
|
||||
#include "nsTArray.h"
|
||||
#include "nsXPIDLString.h"
|
||||
#include "nsWeakReference.h"
|
||||
#include "nsCOMArray.h"
|
||||
|
||||
class nsAppShellWindowEnumerator;
|
||||
class nsASXULWindowEarlyToLateEnumerator;
|
||||
class nsASDOMWindowEarlyToLateEnumerator;
|
||||
class nsASDOMWindowFrontToBackEnumerator;
|
||||
class nsASXULWindowFrontToBackEnumerator;
|
||||
class nsASDOMWindowBackToFrontEnumerator;
|
||||
class nsASXULWindowBackToFrontEnumerator;
|
||||
class nsIWindowMediatorListener;
|
||||
struct nsWindowInfo;
|
||||
|
||||
class nsWindowMediator :
|
||||
public nsIWindowMediator_44,
|
||||
public nsIObserver,
|
||||
public nsSupportsWeakReference
|
||||
{
|
||||
friend class nsAppShellWindowEnumerator;
|
||||
friend class nsASXULWindowEarlyToLateEnumerator;
|
||||
friend class nsASDOMWindowEarlyToLateEnumerator;
|
||||
friend class nsASDOMWindowFrontToBackEnumerator;
|
||||
friend class nsASXULWindowFrontToBackEnumerator;
|
||||
friend class nsASDOMWindowBackToFrontEnumerator;
|
||||
friend class nsASXULWindowBackToFrontEnumerator;
|
||||
|
||||
protected:
|
||||
virtual ~nsWindowMediator();
|
||||
|
||||
public:
|
||||
nsWindowMediator();
|
||||
|
||||
nsresult Init();
|
||||
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIWINDOWMEDIATOR
|
||||
NS_DECL_NSIWINDOWMEDIATOR_44
|
||||
NS_DECL_NSIOBSERVER
|
||||
|
||||
static nsresult GetDOMWindow(nsIXULWindow* inWindow,
|
||||
nsCOMPtr<nsPIDOMWindowOuter>& outDOMWindow);
|
||||
|
||||
private:
|
||||
int32_t AddEnumerator(nsAppShellWindowEnumerator* inEnumerator);
|
||||
int32_t RemoveEnumerator(nsAppShellWindowEnumerator* inEnumerator);
|
||||
nsWindowInfo* MostRecentWindowInfo(const char16_t* inType,
|
||||
bool aSkipPrivateBrowsingOrClosed = false);
|
||||
|
||||
nsresult UnregisterWindow(nsWindowInfo *inInfo);
|
||||
nsWindowInfo *GetInfoFor(nsIXULWindow *aWindow);
|
||||
nsWindowInfo *GetInfoFor(nsIWidget *aWindow);
|
||||
void SortZOrderFrontToBack();
|
||||
void SortZOrderBackToFront();
|
||||
|
||||
nsTArray<nsAppShellWindowEnumerator*> mEnumeratorList;
|
||||
nsWindowInfo *mOldestWindow;
|
||||
nsWindowInfo *mTopmostWindow;
|
||||
int32_t mTimeStamp;
|
||||
bool mSortingZOrder;
|
||||
bool mReady;
|
||||
|
||||
nsCOMArray<nsIWindowMediatorListener> mListeners;
|
||||
};
|
||||
|
||||
#endif
|
||||
2334
xpfe/appshell/nsXULWindow.cpp
Normal file
2334
xpfe/appshell/nsXULWindow.cpp
Normal file
File diff suppressed because it is too large
Load diff
199
xpfe/appshell/nsXULWindow.h
Normal file
199
xpfe/appshell/nsXULWindow.h
Normal file
|
|
@ -0,0 +1,199 @@
|
|||
/* -*- 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/. */
|
||||
|
||||
#ifndef nsXULWindow_h__
|
||||
#define nsXULWindow_h__
|
||||
|
||||
// Local Includes
|
||||
#include "nsChromeTreeOwner.h"
|
||||
#include "nsContentTreeOwner.h"
|
||||
|
||||
// Helper classes
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsTArray.h"
|
||||
#include "nsString.h"
|
||||
#include "nsWeakReference.h"
|
||||
#include "nsCOMArray.h"
|
||||
#include "nsRect.h"
|
||||
#include "Units.h"
|
||||
|
||||
// Interfaces needed
|
||||
#include "nsIBaseWindow.h"
|
||||
#include "nsIDocShell.h"
|
||||
#include "nsIDocShellTreeItem.h"
|
||||
#include "nsIDOMWindow.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIXULWindow.h"
|
||||
#include "nsIPrompt.h"
|
||||
#include "nsIAuthPrompt.h"
|
||||
#include "nsIXULBrowserWindow.h"
|
||||
#include "nsIWeakReference.h"
|
||||
#include "nsIWidgetListener.h"
|
||||
#include "nsITabParent.h"
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
class Element;
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
||||
// nsXULWindow
|
||||
|
||||
#define NS_XULWINDOW_IMPL_CID \
|
||||
{ /* 8eaec2f3-ed02-4be2-8e0f-342798477298 */ \
|
||||
0x8eaec2f3, \
|
||||
0xed02, \
|
||||
0x4be2, \
|
||||
{ 0x8e, 0x0f, 0x34, 0x27, 0x98, 0x47, 0x72, 0x98 } \
|
||||
}
|
||||
|
||||
class nsContentShellInfo;
|
||||
|
||||
class nsXULWindow : public nsIBaseWindow,
|
||||
public nsIInterfaceRequestor,
|
||||
public nsIXULWindow,
|
||||
public nsSupportsWeakReference
|
||||
{
|
||||
friend class nsChromeTreeOwner;
|
||||
friend class nsContentTreeOwner;
|
||||
|
||||
public:
|
||||
NS_DECL_THREADSAFE_ISUPPORTS
|
||||
|
||||
NS_DECL_NSIINTERFACEREQUESTOR
|
||||
NS_DECL_NSIXULWINDOW
|
||||
NS_DECL_NSIBASEWINDOW
|
||||
|
||||
NS_DECLARE_STATIC_IID_ACCESSOR(NS_XULWINDOW_IMPL_CID)
|
||||
|
||||
void LockUntilChromeLoad() { mLockedUntilChromeLoad = true; }
|
||||
bool IsLocked() const { return mLockedUntilChromeLoad; }
|
||||
void IgnoreXULSizeMode(bool aEnable) { mIgnoreXULSizeMode = aEnable; }
|
||||
void WasRegistered() { mRegistered = true; }
|
||||
|
||||
protected:
|
||||
enum persistentAttributes {
|
||||
PAD_MISC = 0x1,
|
||||
PAD_POSITION = 0x2,
|
||||
PAD_SIZE = 0x4
|
||||
};
|
||||
|
||||
explicit nsXULWindow(uint32_t aChromeFlags);
|
||||
virtual ~nsXULWindow();
|
||||
|
||||
NS_IMETHOD EnsureChromeTreeOwner();
|
||||
NS_IMETHOD EnsureContentTreeOwner();
|
||||
NS_IMETHOD EnsurePrimaryContentTreeOwner();
|
||||
NS_IMETHOD EnsurePrompter();
|
||||
NS_IMETHOD EnsureAuthPrompter();
|
||||
|
||||
void OnChromeLoaded();
|
||||
void StaggerPosition(int32_t &aRequestedX, int32_t &aRequestedY,
|
||||
int32_t aSpecWidth, int32_t aSpecHeight);
|
||||
bool LoadPositionFromXUL(int32_t aSpecWidth, int32_t aSpecHeight);
|
||||
bool LoadSizeFromXUL(int32_t& aSpecWidth, int32_t& aSpecHeight);
|
||||
void SetSpecifiedSize(int32_t aSpecWidth, int32_t aSpecHeight);
|
||||
bool LoadMiscPersistentAttributesFromXUL();
|
||||
void SyncAttributesToWidget();
|
||||
NS_IMETHOD SavePersistentAttributes();
|
||||
|
||||
NS_IMETHOD GetWindowDOMWindow(mozIDOMWindowProxy** aDOMWindow);
|
||||
mozilla::dom::Element* GetWindowDOMElement() const;
|
||||
|
||||
// See nsIDocShellTreeOwner for docs on next two methods
|
||||
nsresult ContentShellAdded(nsIDocShellTreeItem* aContentShell,
|
||||
bool aPrimary, bool aTargetable,
|
||||
const nsAString& aID);
|
||||
nsresult ContentShellRemoved(nsIDocShellTreeItem* aContentShell);
|
||||
NS_IMETHOD GetPrimaryContentSize(int32_t* aWidth,
|
||||
int32_t* aHeight);
|
||||
NS_IMETHOD SetPrimaryContentSize(int32_t aWidth,
|
||||
int32_t aHeight);
|
||||
nsresult GetRootShellSize(int32_t* aWidth,
|
||||
int32_t* aHeight);
|
||||
nsresult SetRootShellSize(int32_t aWidth,
|
||||
int32_t aHeight);
|
||||
|
||||
NS_IMETHOD SizeShellTo(nsIDocShellTreeItem* aShellItem, int32_t aCX,
|
||||
int32_t aCY);
|
||||
NS_IMETHOD ExitModalLoop(nsresult aStatus);
|
||||
NS_IMETHOD CreateNewChromeWindow(int32_t aChromeFlags, nsITabParent* aOpeningTab, mozIDOMWindowProxy* aOpenerWindow, nsIXULWindow **_retval);
|
||||
NS_IMETHOD CreateNewContentWindow(int32_t aChromeFlags, nsITabParent* aOpeningTab, mozIDOMWindowProxy* aOpenerWindow, nsIXULWindow **_retval);
|
||||
NS_IMETHOD GetHasPrimaryContent(bool* aResult);
|
||||
|
||||
void EnableParent(bool aEnable);
|
||||
bool ConstrainToZLevel(bool aImmediate, nsWindowZ *aPlacement,
|
||||
nsIWidget *aReqBelow, nsIWidget **aActualBelow);
|
||||
void PlaceWindowLayersBehind(uint32_t aLowLevel, uint32_t aHighLevel,
|
||||
nsIXULWindow *aBehind);
|
||||
void SetContentScrollbarVisibility(bool aVisible);
|
||||
bool GetContentScrollbarVisibility();
|
||||
void PersistentAttributesDirty(uint32_t aDirtyFlags);
|
||||
|
||||
nsChromeTreeOwner* mChromeTreeOwner;
|
||||
nsContentTreeOwner* mContentTreeOwner;
|
||||
nsContentTreeOwner* mPrimaryContentTreeOwner;
|
||||
nsCOMPtr<nsIWidget> mWindow;
|
||||
nsCOMPtr<nsIDocShell> mDocShell;
|
||||
nsCOMPtr<nsPIDOMWindowOuter> mDOMWindow;
|
||||
nsCOMPtr<nsIWeakReference> mParentWindow;
|
||||
nsCOMPtr<nsIPrompt> mPrompter;
|
||||
nsCOMPtr<nsIAuthPrompt> mAuthPrompter;
|
||||
nsCOMPtr<nsIXULBrowserWindow> mXULBrowserWindow;
|
||||
nsCOMPtr<nsIDocShellTreeItem> mPrimaryContentShell;
|
||||
nsTArray<nsContentShellInfo*> mContentShells; // array of doc shells by id
|
||||
nsresult mModalStatus;
|
||||
bool mContinueModalLoop;
|
||||
bool mDebuting; // being made visible right now
|
||||
bool mChromeLoaded; // True when chrome has loaded
|
||||
bool mShowAfterLoad;
|
||||
bool mIntrinsicallySized;
|
||||
bool mCenterAfterLoad;
|
||||
bool mIsHiddenWindow;
|
||||
bool mLockedUntilChromeLoad;
|
||||
bool mIgnoreXULSize;
|
||||
bool mIgnoreXULPosition;
|
||||
bool mChromeFlagsFrozen;
|
||||
bool mIgnoreXULSizeMode;
|
||||
// mDestroying is used to prevent reentry into into Destroy(), which can
|
||||
// otherwise happen due to script running as we tear down various things.
|
||||
bool mDestroying;
|
||||
bool mRegistered;
|
||||
uint32_t mContextFlags;
|
||||
uint32_t mPersistentAttributesDirty; // persistentAttributes
|
||||
uint32_t mPersistentAttributesMask;
|
||||
uint32_t mChromeFlags;
|
||||
nsString mTitle;
|
||||
nsIntRect mOpenerScreenRect; // the screen rect of the opener
|
||||
|
||||
nsCOMArray<nsIWeakReference> mTargetableShells; // targetable shells only
|
||||
|
||||
nsCOMPtr<nsITabParent> mPrimaryTabParent;
|
||||
private:
|
||||
nsresult GetPrimaryTabParentSize(int32_t* aWidth, int32_t* aHeight);
|
||||
nsresult GetPrimaryContentShellSize(int32_t* aWidth, int32_t* aHeight);
|
||||
nsresult SetPrimaryTabParentSize(int32_t aWidth, int32_t aHeight);
|
||||
};
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(nsXULWindow, NS_XULWINDOW_IMPL_CID)
|
||||
|
||||
// nsContentShellInfo
|
||||
// Used to map shell IDs to nsIDocShellTreeItems.
|
||||
|
||||
class nsContentShellInfo
|
||||
{
|
||||
public:
|
||||
nsContentShellInfo(const nsAString& aID,
|
||||
nsIWeakReference* aContentShell);
|
||||
~nsContentShellInfo();
|
||||
|
||||
public:
|
||||
nsString id; // The identifier of the content shell
|
||||
nsWeakPtr child; // content shell (weak reference to nsIDocShellTreeItem)
|
||||
};
|
||||
|
||||
#endif /* nsXULWindow_h__ */
|
||||
5
xpfe/appshell/test/chrome.ini
Normal file
5
xpfe/appshell/test/chrome.ini
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
[DEFAULT]
|
||||
skip-if = os == 'android'
|
||||
|
||||
[test_hiddenPrivateWindow.xul]
|
||||
[test_windowlessBrowser.xul]
|
||||
45
xpfe/appshell/test/test_hiddenPrivateWindow.xul
Normal file
45
xpfe/appshell/test/test_hiddenPrivateWindow.xul
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
<?xml version="1.0"?>
|
||||
<?xml-stylesheet href="chrome://global/skin" type="text/css"?>
|
||||
<?xml-stylesheet href="chrome://mochikit/content/tests/SimpleTest/test.css"
|
||||
type="text/css"?>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=815847
|
||||
-->
|
||||
<window title="Mozilla Bug 815847"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js" />
|
||||
|
||||
<body xmlns="http://www.w3.org/1999/xhtml">
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=815847">Mozilla Bug 815847</a>
|
||||
<p id="display"></p>
|
||||
<div id="content" style="display: none">
|
||||
|
||||
</div>
|
||||
<pre id="test">
|
||||
</pre>
|
||||
</body>
|
||||
|
||||
<script class="testbody" type="application/javascript">
|
||||
<![CDATA[
|
||||
|
||||
var Cu = Components.utils;
|
||||
|
||||
Cu.import('resource://gre/modules/Services.jsm');
|
||||
Cu.import('resource://gre/modules/PrivateBrowsingUtils.jsm');
|
||||
|
||||
ok(Services.appShell.hiddenWindow, "hiddenWindow should exist");
|
||||
ok(Services.appShell.hiddenDOMWindow, "hiddenDOMWindow should exist");
|
||||
ok(Services.appShell.hiddenPrivateWindow, "hiddenPrivateWindow should exist");
|
||||
ok(Services.appShell.hiddenPrivateDOMWindow, "hiddenPrivateDOMWindow should exist");
|
||||
|
||||
ok(!PrivateBrowsingUtils.isWindowPrivate(Services.appShell.hiddenWindow.docShell), "hiddenWindow should not be private");
|
||||
ok(!PrivateBrowsingUtils.isWindowPrivate(Services.appShell.hiddenDOMWindow), "hiddenDOMWindow should not be private");
|
||||
ok(PrivateBrowsingUtils.isWindowPrivate(Services.appShell.hiddenPrivateWindow.docShell), "hiddenPrivateWindow should be private");
|
||||
ok(PrivateBrowsingUtils.isWindowPrivate(Services.appShell.hiddenPrivateDOMWindow), "hiddenPrivateDOMWindow should be private");
|
||||
|
||||
]]>
|
||||
</script>
|
||||
|
||||
</window>
|
||||
75
xpfe/appshell/test/test_windowlessBrowser.xul
Normal file
75
xpfe/appshell/test/test_windowlessBrowser.xul
Normal file
|
|
@ -0,0 +1,75 @@
|
|||
<?xml version="1.0"?>
|
||||
<?xml-stylesheet href="chrome://global/skin" type="text/css"?>
|
||||
<?xml-stylesheet href="chrome://mochikit/content/tests/SimpleTest/test.css"
|
||||
type="text/css"?>
|
||||
<!--
|
||||
https://bugzilla.mozilla.org/show_bug.cgi?id=815847
|
||||
-->
|
||||
<window title="Mozilla Bug 815847"
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
|
||||
<script type="application/javascript"
|
||||
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js" />
|
||||
|
||||
<body xmlns="http://www.w3.org/1999/xhtml">
|
||||
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=1214174">Mozilla Bug 1214174</a>
|
||||
<p id="display"></p>
|
||||
<div id="content" style="display: none">
|
||||
|
||||
</div>
|
||||
<pre id="test">
|
||||
</pre>
|
||||
</body>
|
||||
|
||||
<script class="testbody" type="application/javascript">
|
||||
<![CDATA[
|
||||
|
||||
var Cu = Components.utils;
|
||||
var Ci = Components.interfaces;
|
||||
|
||||
Cu.import('resource://gre/modules/Services.jsm');
|
||||
|
||||
function testWindowlessBrowser(chromePrivileged) {
|
||||
var webNav = Services.appShell.createWindowlessBrowser(chromePrivileged);
|
||||
|
||||
ok(webNav, "createWindowlessBrowser should return a wevNav");
|
||||
|
||||
let interfaceRequestor = webNav.QueryInterface(Ci.nsIInterfaceRequestor);
|
||||
let docShell = interfaceRequestor.getInterface(Ci.nsIDocShell);
|
||||
|
||||
ok(docShell, "docShell should be defined");
|
||||
ok(docShell.contentViewer.DOMDocument.defaultView, "docShell defaultView should be defined");
|
||||
|
||||
var win = docShell.contentViewer.DOMDocument.defaultView;
|
||||
|
||||
ok(win.screenX == 0, "window.screenX should be 0 in a windowless browser");
|
||||
ok(win.screenY == 0, "window.screenY should be 0 in a windowless browser");
|
||||
ok(win.outerWidth == 0, "window.outerWidth should be 0 in a windowless browser");
|
||||
ok(win.outerHeight == 0, "window.outerHeight should be 0 in a windowless browser");
|
||||
|
||||
ok(win.sidebar, "window.sidebar should be defined");
|
||||
ok(win.external, "window.external should be defined");
|
||||
|
||||
var exception;
|
||||
|
||||
try {
|
||||
win.external.AddSearchProvider("http://test-fake.url");
|
||||
} catch(e) {
|
||||
exception = e;
|
||||
}
|
||||
|
||||
ok(!exception, "window.external.AddSearchProvider should be ignore withour raising an exception");
|
||||
|
||||
webNav.close();
|
||||
}
|
||||
|
||||
info("Test Bug 1214174 on a content privileged windowless browser");
|
||||
testWindowlessBrowser(false);
|
||||
|
||||
info("Test Bug 1214174 on a chrome privileged windowless browser");
|
||||
testWindowlessBrowser(true);
|
||||
|
||||
]]>
|
||||
</script>
|
||||
|
||||
</window>
|
||||
9
xpfe/components/autocomplete/jar.mn
Normal file
9
xpfe/components/autocomplete/jar.mn
Normal file
|
|
@ -0,0 +1,9 @@
|
|||
# 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/.
|
||||
|
||||
toolkit.jar:
|
||||
content/global/autocomplete.xml (resources/content/autocomplete.xml)
|
||||
|
||||
comm.jar:
|
||||
content/communicator/autocomplete.css (resources/content/autocomplete.css)
|
||||
7
xpfe/components/autocomplete/moz.build
Normal file
7
xpfe/components/autocomplete/moz.build
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
JAR_MANIFESTS += ['jar.mn']
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
/* 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/. */
|
||||
|
||||
|
||||
.autocomplete-result-popupset {
|
||||
width: 0 !important;
|
||||
}
|
||||
|
||||
.autocomplete-result-popup {
|
||||
display: -moz-popup !important;
|
||||
}
|
||||
|
||||
/* the C++ implementation of widgets is too eager to make popups visible.
|
||||
this causes problems (bug 120155 and others), thus this workaround: */
|
||||
.autocomplete-result-popup[hidden="true"] {
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
.autocomplete-tree {
|
||||
-moz-user-focus: ignore;
|
||||
}
|
||||
|
||||
.autocomplete-history-dropmarker {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.autocomplete-history-dropmarker[enablehistory="true"] {
|
||||
display: -moz-box;
|
||||
}
|
||||
|
||||
/* The following rule is here to fix bug 96899 (and now 117952).
|
||||
Somehow trees create a situation
|
||||
in which a popupset flows itself as if its popup child is directly within it
|
||||
instead of the placeholder child that should actually be inside the popupset.
|
||||
This is a stopgap measure, and it does not address the real bug. */
|
||||
popupset {
|
||||
max-width: 0px;
|
||||
width: 0px;
|
||||
min-width: 0%;
|
||||
min-height: 0%;
|
||||
}
|
||||
|
||||
treecolpicker {
|
||||
display: none;
|
||||
}
|
||||
1646
xpfe/components/autocomplete/resources/content/autocomplete.xml
Normal file
1646
xpfe/components/autocomplete/resources/content/autocomplete.xml
Normal file
File diff suppressed because it is too large
Load diff
15
xpfe/components/build/moz.build
Normal file
15
xpfe/components/build/moz.build
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
SOURCES += [
|
||||
'nsModule.cpp',
|
||||
]
|
||||
|
||||
FINAL_LIBRARY = 'xul'
|
||||
|
||||
LOCAL_INCLUDES += [
|
||||
'../directory',
|
||||
]
|
||||
44
xpfe/components/build/nsModule.cpp
Normal file
44
xpfe/components/build/nsModule.cpp
Normal file
|
|
@ -0,0 +1,44 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "mozilla/ModuleUtils.h"
|
||||
#include "nsDirectoryViewer.h"
|
||||
#include "rdf.h"
|
||||
#include "nsRDFCID.h"
|
||||
#include "nsCURILoader.h"
|
||||
|
||||
// Factory constructors
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsHTTPIndex, Init)
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR(nsDirectoryViewerFactory)
|
||||
|
||||
NS_DEFINE_NAMED_CID(NS_DIRECTORYVIEWERFACTORY_CID);
|
||||
NS_DEFINE_NAMED_CID(NS_HTTPINDEX_SERVICE_CID);
|
||||
|
||||
static const mozilla::Module::CIDEntry kXPFECIDs[] = {
|
||||
{ &kNS_DIRECTORYVIEWERFACTORY_CID, false, nullptr, nsDirectoryViewerFactoryConstructor },
|
||||
{ &kNS_HTTPINDEX_SERVICE_CID, false, nullptr, nsHTTPIndexConstructor },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module::ContractIDEntry kXPFEContracts[] = {
|
||||
{ "@mozilla.org/xpfe/http-index-format-factory-constructor", &kNS_DIRECTORYVIEWERFACTORY_CID },
|
||||
{ NS_HTTPINDEX_SERVICE_CONTRACTID, &kNS_HTTPINDEX_SERVICE_CID },
|
||||
{ NS_HTTPINDEX_DATASOURCE_CONTRACTID, &kNS_HTTPINDEX_SERVICE_CID },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module::CategoryEntry kXPFECategories[] = {
|
||||
{ "Gecko-Content-Viewers", "application/http-index-format", "@mozilla.org/xpfe/http-index-format-factory-constructor" },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module kXPFEModule = {
|
||||
mozilla::Module::kVersion,
|
||||
kXPFECIDs,
|
||||
kXPFEContracts,
|
||||
kXPFECategories
|
||||
};
|
||||
|
||||
NSMODULE_DEFN(application) = &kXPFEModule;
|
||||
20
xpfe/components/directory/moz.build
Normal file
20
xpfe/components/directory/moz.build
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
XPIDL_SOURCES += [
|
||||
'nsIHTTPIndex.idl',
|
||||
]
|
||||
|
||||
XPIDL_MODULE = 'directory'
|
||||
|
||||
SOURCES += [
|
||||
'nsDirectoryViewer.cpp',
|
||||
]
|
||||
|
||||
FINAL_LIBRARY = 'xul'
|
||||
|
||||
if CONFIG['GNU_CXX']:
|
||||
CXXFLAGS += ['-Wno-error=shadow']
|
||||
1393
xpfe/components/directory/nsDirectoryViewer.cpp
Normal file
1393
xpfe/components/directory/nsDirectoryViewer.cpp
Normal file
File diff suppressed because it is too large
Load diff
126
xpfe/components/directory/nsDirectoryViewer.h
Normal file
126
xpfe/components/directory/nsDirectoryViewer.h
Normal file
|
|
@ -0,0 +1,126 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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/. */
|
||||
|
||||
#ifndef nsdirectoryviewer__h____
|
||||
#define nsdirectoryviewer__h____
|
||||
|
||||
#include "nsCOMPtr.h"
|
||||
#include "nsIStreamListener.h"
|
||||
#include "nsIContentViewer.h"
|
||||
#include "nsIHTTPIndex.h"
|
||||
#include "nsIRDFService.h"
|
||||
#include "nsIRDFDataSource.h"
|
||||
#include "nsIRDFLiteral.h"
|
||||
#include "nsIDocumentLoaderFactory.h"
|
||||
#include "nsITimer.h"
|
||||
#include "nsXPIDLString.h"
|
||||
#include "nsIDirIndexListener.h"
|
||||
#include "nsIFTPChannel.h"
|
||||
#include "nsCycleCollectionParticipant.h"
|
||||
#include "nsIInterfaceRequestor.h"
|
||||
#include "nsIURI.h"
|
||||
|
||||
class nsIMutableArray;
|
||||
|
||||
class nsDirectoryViewerFactory : public nsIDocumentLoaderFactory
|
||||
{
|
||||
public:
|
||||
nsDirectoryViewerFactory();
|
||||
|
||||
// nsISupports interface
|
||||
NS_DECL_ISUPPORTS
|
||||
NS_DECL_NSIDOCUMENTLOADERFACTORY
|
||||
|
||||
protected:
|
||||
virtual ~nsDirectoryViewerFactory();
|
||||
};
|
||||
|
||||
class nsHTTPIndex final : public nsIHTTPIndex,
|
||||
public nsIRDFDataSource,
|
||||
public nsIStreamListener,
|
||||
public nsIDirIndexListener,
|
||||
public nsIInterfaceRequestor,
|
||||
public nsIFTPEventSink
|
||||
{
|
||||
private:
|
||||
|
||||
// note: these are NOT statics due to the native of nsHTTPIndex
|
||||
// where it may or may not be treated as a singleton
|
||||
|
||||
nsCOMPtr<nsIRDFResource> kNC_Child;
|
||||
nsCOMPtr<nsIRDFResource> kNC_Comment;
|
||||
nsCOMPtr<nsIRDFResource> kNC_Loading;
|
||||
nsCOMPtr<nsIRDFResource> kNC_URL;
|
||||
nsCOMPtr<nsIRDFResource> kNC_Description;
|
||||
nsCOMPtr<nsIRDFResource> kNC_ContentLength;
|
||||
nsCOMPtr<nsIRDFResource> kNC_LastModified;
|
||||
nsCOMPtr<nsIRDFResource> kNC_ContentType;
|
||||
nsCOMPtr<nsIRDFResource> kNC_FileType;
|
||||
nsCOMPtr<nsIRDFResource> kNC_IsContainer;
|
||||
nsCOMPtr<nsIRDFLiteral> kTrueLiteral;
|
||||
nsCOMPtr<nsIRDFLiteral> kFalseLiteral;
|
||||
|
||||
nsCOMPtr<nsIRDFService> mDirRDF;
|
||||
|
||||
protected:
|
||||
// We grab a reference to the content viewer container (which
|
||||
// indirectly owns us) so that we can insert ourselves as a global
|
||||
// in the script context _after_ the XUL doc has been embedded into
|
||||
// content viewer. We'll know that this has happened once we receive
|
||||
// an OnStartRequest() notification
|
||||
|
||||
nsCOMPtr<nsIRDFDataSource> mInner;
|
||||
nsCOMPtr<nsIMutableArray> mConnectionList;
|
||||
nsCOMPtr<nsIMutableArray> mNodeList;
|
||||
nsCOMPtr<nsITimer> mTimer;
|
||||
nsCOMPtr<nsIDirIndexParser> mParser;
|
||||
nsCString mBaseURL;
|
||||
nsCString mEncoding;
|
||||
bool mBindToGlobalObject;
|
||||
nsIInterfaceRequestor* mRequestor; // WEAK
|
||||
nsCOMPtr<nsIRDFResource> mDirectory;
|
||||
|
||||
explicit nsHTTPIndex(nsIInterfaceRequestor* aRequestor);
|
||||
nsresult CommonInit(void);
|
||||
nsresult Init(nsIURI* aBaseURL);
|
||||
void GetDestination(nsIRDFResource* r, nsXPIDLCString& dest);
|
||||
bool isWellknownContainerURI(nsIRDFResource *r);
|
||||
nsresult AddElement(nsIRDFResource *parent, nsIRDFResource *prop,
|
||||
nsIRDFNode *child);
|
||||
|
||||
static void FireTimer(nsITimer* aTimer, void* aClosure);
|
||||
|
||||
virtual ~nsHTTPIndex();
|
||||
|
||||
public:
|
||||
nsHTTPIndex();
|
||||
nsresult Init(void);
|
||||
|
||||
static nsresult Create(nsIURI* aBaseURI, nsIInterfaceRequestor* aContainer,
|
||||
nsIHTTPIndex** aResult);
|
||||
|
||||
// nsIHTTPIndex interface
|
||||
NS_DECL_NSIHTTPINDEX
|
||||
|
||||
// NSIRDFDataSource interface
|
||||
NS_DECL_NSIRDFDATASOURCE
|
||||
|
||||
NS_DECL_NSIREQUESTOBSERVER
|
||||
NS_DECL_NSISTREAMLISTENER
|
||||
|
||||
NS_DECL_NSIDIRINDEXLISTENER
|
||||
NS_DECL_NSIINTERFACEREQUESTOR
|
||||
NS_DECL_NSIFTPEVENTSINK
|
||||
|
||||
// nsISupports interface
|
||||
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsHTTPIndex, nsIHTTPIndex)
|
||||
};
|
||||
|
||||
// {82776710-5690-11d3-BE36-00104BDE6048}
|
||||
#define NS_DIRECTORYVIEWERFACTORY_CID \
|
||||
{ 0x82776710, 0x5690, 0x11d3, { 0xbe, 0x36, 0x0, 0x10, 0x4b, 0xde, 0x60, 0x48 } }
|
||||
|
||||
#endif // nsdirectoryviewer__h____
|
||||
50
xpfe/components/directory/nsIHTTPIndex.idl
Normal file
50
xpfe/components/directory/nsIHTTPIndex.idl
Normal file
|
|
@ -0,0 +1,50 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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/. */
|
||||
|
||||
/*
|
||||
|
||||
The interface to an HTTP index
|
||||
|
||||
*/
|
||||
|
||||
#include "nsISupports.idl"
|
||||
|
||||
interface nsIStreamListener;
|
||||
interface nsIRDFDataSource;
|
||||
interface nsIRDFNode;
|
||||
interface nsIRDFResource;
|
||||
|
||||
[scriptable, uuid(6F2BDBD0-58C3-11d3-BE36-00104BDE6048)]
|
||||
interface nsIHTTPIndex : nsISupports
|
||||
{
|
||||
/**
|
||||
* The base URL of the HTTP index
|
||||
*/
|
||||
readonly attribute string BaseURL;
|
||||
|
||||
/**
|
||||
* The RDF datasource that contains the HTTP index information.
|
||||
*/
|
||||
readonly attribute nsIRDFDataSource DataSource;
|
||||
|
||||
/**
|
||||
* The charset to use for decoding FTP filenames
|
||||
*/
|
||||
attribute string encoding;
|
||||
};
|
||||
|
||||
%{C++
|
||||
|
||||
// {{2587e382-1324-11d4-a652-eadbb2be3484}
|
||||
#define NS_HTTPINDEX_SERVICE_CID \
|
||||
{ 0x2587e382, 0x1324, 0x11d4, { 0xa6, 0x52, 0xea, 0xdb, 0xb2, 0xbe, 0x34, 0x84 } }
|
||||
|
||||
#define NS_HTTPINDEX_SERVICE_CONTRACTID \
|
||||
"@mozilla.org/browser/httpindex-service;1"
|
||||
|
||||
#define NS_HTTPINDEX_DATASOURCE_CONTRACTID \
|
||||
"@mozilla.org/rdf/datasource;1?name=httpindex"
|
||||
|
||||
%}
|
||||
12
xpfe/components/moz.build
Normal file
12
xpfe/components/moz.build
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
DIRS += [
|
||||
'windowds',
|
||||
'directory',
|
||||
'build',
|
||||
]
|
||||
|
||||
17
xpfe/components/windowds/moz.build
Normal file
17
xpfe/components/windowds/moz.build
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
|
||||
# vim: set filetype=python:
|
||||
# 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/.
|
||||
|
||||
XPIDL_SOURCES += [
|
||||
'nsIWindowDataSource.idl',
|
||||
]
|
||||
|
||||
XPIDL_MODULE = 'windowds'
|
||||
|
||||
SOURCES += [
|
||||
'nsWindowDataSource.cpp',
|
||||
]
|
||||
|
||||
FINAL_LIBRARY = 'xul'
|
||||
17
xpfe/components/windowds/nsIWindowDataSource.idl
Normal file
17
xpfe/components/windowds/nsIWindowDataSource.idl
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "nsISupports.idl"
|
||||
#include "nsIDOMWindow.idl"
|
||||
|
||||
// interface for accessing RDF-specific data from the window datasource
|
||||
[scriptable, uuid(3722A5B9-5323-4ed0-BB1A-8299F27A4E89)]
|
||||
interface nsIWindowDataSource : nsISupports
|
||||
{
|
||||
/**
|
||||
* for the given resource name, return the window
|
||||
*/
|
||||
nsIDOMWindow getWindowForResource(in string inResource);
|
||||
};
|
||||
519
xpfe/components/windowds/nsWindowDataSource.cpp
Normal file
519
xpfe/components/windowds/nsWindowDataSource.cpp
Normal file
|
|
@ -0,0 +1,519 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "nsWindowDataSource.h"
|
||||
#include "nsIXULWindow.h"
|
||||
#include "rdf.h"
|
||||
#include "nsIRDFContainerUtils.h"
|
||||
#include "nsIServiceManager.h"
|
||||
#include "nsReadableUtils.h"
|
||||
#include "nsIObserverService.h"
|
||||
#include "nsIWindowMediator.h"
|
||||
#include "nsXPCOMCID.h"
|
||||
#include "mozilla/ModuleUtils.h"
|
||||
#include "nsString.h"
|
||||
|
||||
// just to do the reverse-lookup! sheesh.
|
||||
#include "nsIInterfaceRequestorUtils.h"
|
||||
#include "nsIDocShell.h"
|
||||
|
||||
uint32_t nsWindowDataSource::windowCount = 0;
|
||||
|
||||
nsIRDFResource* nsWindowDataSource::kNC_Name = nullptr;
|
||||
nsIRDFResource* nsWindowDataSource::kNC_WindowRoot = nullptr;
|
||||
nsIRDFResource* nsWindowDataSource::kNC_KeyIndex = nullptr;
|
||||
|
||||
nsIRDFService* nsWindowDataSource::gRDFService = nullptr;
|
||||
|
||||
uint32_t nsWindowDataSource::gRefCnt = 0;
|
||||
|
||||
#define URINC_WINDOWROOT "NC:WindowMediatorRoot"
|
||||
#define URINC_NAME NC_NAMESPACE_URI "Name"
|
||||
#define URINC_KEYINDEX NC_NAMESPACE_URI "KeyIndex"
|
||||
|
||||
nsresult
|
||||
nsWindowDataSource::Init()
|
||||
{
|
||||
nsresult rv;
|
||||
|
||||
if (gRefCnt++ == 0) {
|
||||
rv = CallGetService("@mozilla.org/rdf/rdf-service;1", &gRDFService);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
gRDFService->GetResource(NS_LITERAL_CSTRING(URINC_WINDOWROOT), &kNC_WindowRoot);
|
||||
gRDFService->GetResource(NS_LITERAL_CSTRING(URINC_NAME), &kNC_Name);
|
||||
gRDFService->GetResource(NS_LITERAL_CSTRING(URINC_KEYINDEX), &kNC_KeyIndex);
|
||||
}
|
||||
|
||||
mInner = do_CreateInstance("@mozilla.org/rdf/datasource;1?name=in-memory-datasource", &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
nsCOMPtr<nsIRDFContainerUtils> rdfc =
|
||||
do_GetService("@mozilla.org/rdf/container-utils;1", &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
rv = rdfc->MakeSeq(this, kNC_WindowRoot, getter_AddRefs(mContainer));
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
nsCOMPtr<nsIWindowMediator> windowMediator =
|
||||
do_GetService(NS_WINDOWMEDIATOR_CONTRACTID, &rv);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
rv = windowMediator->AddListener(this);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
nsCOMPtr<nsIObserverService> observerService =
|
||||
do_GetService(NS_OBSERVERSERVICE_CONTRACTID, &rv);
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
rv = observerService->AddObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID,
|
||||
false);
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsWindowDataSource::~nsWindowDataSource()
|
||||
{
|
||||
if (--gRefCnt == 0) {
|
||||
NS_IF_RELEASE(kNC_Name);
|
||||
NS_IF_RELEASE(kNC_KeyIndex);
|
||||
NS_IF_RELEASE(kNC_WindowRoot);
|
||||
NS_IF_RELEASE(gRDFService);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowDataSource::Observe(nsISupports *aSubject, const char* aTopic, const char16_t *aData)
|
||||
{
|
||||
if (strcmp(aTopic, NS_XPCOM_SHUTDOWN_OBSERVER_ID) == 0) {
|
||||
// release these objects so that they release their reference
|
||||
// to us
|
||||
mContainer = nullptr;
|
||||
mInner = nullptr;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_CLASS(nsWindowDataSource)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_UNLINK_0(nsWindowDataSource)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(nsWindowDataSource)
|
||||
// XXX mContainer?
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mInner)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(nsWindowDataSource)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(nsWindowDataSource)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsWindowDataSource)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIObserver)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIWindowMediatorListener)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIWindowDataSource)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIRDFDataSource)
|
||||
NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIObserver)
|
||||
NS_INTERFACE_MAP_END
|
||||
|
||||
// nsIWindowMediatorListener implementation
|
||||
// handle notifications from the window mediator and reflect them into
|
||||
// RDF
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowDataSource::OnWindowTitleChange(nsIXULWindow *window,
|
||||
const char16_t *newTitle)
|
||||
{
|
||||
nsresult rv;
|
||||
|
||||
nsCOMPtr<nsIRDFResource> windowResource;
|
||||
mWindowResources.Get(window, getter_AddRefs(windowResource));
|
||||
|
||||
// oops, make sure this window is in the hashtable!
|
||||
if (!windowResource) {
|
||||
OnOpenWindow(window);
|
||||
mWindowResources.Get(window, getter_AddRefs(windowResource));
|
||||
}
|
||||
|
||||
NS_ENSURE_TRUE(windowResource, NS_ERROR_UNEXPECTED);
|
||||
|
||||
nsCOMPtr<nsIRDFLiteral> newTitleLiteral;
|
||||
rv = gRDFService->GetLiteral(newTitle, getter_AddRefs(newTitleLiteral));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
// get the old title
|
||||
nsCOMPtr<nsIRDFNode> oldTitleNode;
|
||||
rv = GetTarget(windowResource, kNC_Name, true,
|
||||
getter_AddRefs(oldTitleNode));
|
||||
|
||||
// assert the change
|
||||
if (NS_SUCCEEDED(rv) && oldTitleNode)
|
||||
// has an existing window title, update it
|
||||
rv = Change(windowResource, kNC_Name, oldTitleNode, newTitleLiteral);
|
||||
else
|
||||
// removed from the tasklist
|
||||
rv = Assert(windowResource, kNC_Name, newTitleLiteral, true);
|
||||
|
||||
if (rv != NS_RDF_ASSERTION_ACCEPTED)
|
||||
{
|
||||
NS_ERROR("unable to set window name");
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowDataSource::OnOpenWindow(nsIXULWindow *window)
|
||||
{
|
||||
nsAutoCString windowId(NS_LITERAL_CSTRING("window-"));
|
||||
windowId.AppendInt(windowCount++, 10);
|
||||
|
||||
nsCOMPtr<nsIRDFResource> windowResource;
|
||||
gRDFService->GetResource(windowId, getter_AddRefs(windowResource));
|
||||
|
||||
mWindowResources.Put(window, windowResource);
|
||||
|
||||
// assert the new window
|
||||
if (mContainer)
|
||||
mContainer->AppendElement(windowResource);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowDataSource::OnCloseWindow(nsIXULWindow *window)
|
||||
{
|
||||
nsresult rv;
|
||||
nsCOMPtr<nsIRDFResource> resource;
|
||||
mWindowResources.Get(window, getter_AddRefs(resource));
|
||||
if (!resource) {
|
||||
return NS_ERROR_UNEXPECTED;
|
||||
}
|
||||
|
||||
mWindowResources.Remove(window);
|
||||
|
||||
// make sure we're not shutting down
|
||||
if (!mContainer) return NS_OK;
|
||||
|
||||
nsCOMPtr<nsIRDFNode> oldKeyNode;
|
||||
nsCOMPtr<nsIRDFInt> oldKeyInt;
|
||||
|
||||
// get the old keyIndex, if any
|
||||
rv = GetTarget(resource, kNC_KeyIndex, true,
|
||||
getter_AddRefs(oldKeyNode));
|
||||
if (NS_SUCCEEDED(rv) && (rv != NS_RDF_NO_VALUE))
|
||||
oldKeyInt = do_QueryInterface(oldKeyNode);
|
||||
|
||||
|
||||
// update RDF and keyindex - from this point forward we'll ignore
|
||||
// errors, because they just indicate some kind of RDF inconsistency
|
||||
int32_t winIndex = -1;
|
||||
rv = mContainer->IndexOf(resource, &winIndex);
|
||||
|
||||
if (NS_FAILED(rv))
|
||||
return NS_OK;
|
||||
|
||||
// unassert the old window, ignore any error
|
||||
mContainer->RemoveElement(resource, true);
|
||||
|
||||
nsCOMPtr<nsISimpleEnumerator> children;
|
||||
rv = mContainer->GetElements(getter_AddRefs(children));
|
||||
if (NS_FAILED(rv))
|
||||
return NS_OK;
|
||||
|
||||
bool more = false;
|
||||
|
||||
while (NS_SUCCEEDED(rv = children->HasMoreElements(&more)) && more) {
|
||||
nsCOMPtr<nsISupports> sup;
|
||||
rv = children->GetNext(getter_AddRefs(sup));
|
||||
if (NS_FAILED(rv))
|
||||
break;
|
||||
|
||||
nsCOMPtr<nsIRDFResource> windowResource = do_QueryInterface(sup, &rv);
|
||||
if (NS_FAILED(rv))
|
||||
continue;
|
||||
|
||||
int32_t currentIndex = -1;
|
||||
mContainer->IndexOf(windowResource, ¤tIndex);
|
||||
|
||||
// can skip updating windows with lower indexes
|
||||
// than the window that was removed
|
||||
if (currentIndex < winIndex)
|
||||
continue;
|
||||
|
||||
nsCOMPtr<nsIRDFNode> newKeyNode;
|
||||
nsCOMPtr<nsIRDFInt> newKeyInt;
|
||||
|
||||
rv = GetTarget(windowResource, kNC_KeyIndex, true,
|
||||
getter_AddRefs(newKeyNode));
|
||||
if (NS_SUCCEEDED(rv) && (rv != NS_RDF_NO_VALUE))
|
||||
newKeyInt = do_QueryInterface(newKeyNode);
|
||||
|
||||
// changing from one key index to another
|
||||
if (oldKeyInt && newKeyInt)
|
||||
Change(windowResource, kNC_KeyIndex, oldKeyInt, newKeyInt);
|
||||
// creating a new keyindex - probably window going
|
||||
// from (none) to "9"
|
||||
else if (newKeyInt)
|
||||
Assert(windowResource, kNC_KeyIndex, newKeyInt, true);
|
||||
|
||||
// somehow inserting a window above this one,
|
||||
// "9" to (none)
|
||||
else if (oldKeyInt)
|
||||
Unassert(windowResource, kNC_KeyIndex, oldKeyInt);
|
||||
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// nsIWindowDataSource implementation
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsWindowDataSource::GetWindowForResource(const char *aResourceString,
|
||||
nsIDOMWindow** aResult)
|
||||
{
|
||||
if (NS_WARN_IF(!aResourceString)) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIRDFResource> windowResource;
|
||||
gRDFService->GetResource(nsDependentCString(aResourceString),
|
||||
getter_AddRefs(windowResource));
|
||||
|
||||
// now reverse-lookup in the hashtable
|
||||
for (auto iter = mWindowResources.Iter(); !iter.Done(); iter.Next()) {
|
||||
nsIXULWindow* window = iter.Key();
|
||||
nsIRDFResource* resource = iter.UserData();
|
||||
|
||||
if (resource == windowResource) {
|
||||
// This sucks, we have to jump through docshell to go from
|
||||
// nsIXULWindow -> nsIDOMWindow.
|
||||
nsCOMPtr<nsIDocShell> docShell;
|
||||
window->GetDocShell(getter_AddRefs(docShell));
|
||||
|
||||
if (docShell) {
|
||||
nsCOMPtr<nsIDOMWindow> result = do_GetInterface(docShell);
|
||||
|
||||
*aResult = result;
|
||||
NS_IF_ADDREF(*aResult);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
||||
// nsIRDFDataSource implementation
|
||||
// mostly, we just forward to mInner, except:
|
||||
// GetURI() - need to return "rdf:window-mediator"
|
||||
// GetTarget() - need to handle kNC_KeyIndex
|
||||
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetURI(char * *aURI)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aURI);
|
||||
|
||||
*aURI = ToNewCString(NS_LITERAL_CSTRING("rdf:window-mediator"));
|
||||
|
||||
if (!*aURI)
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetTarget(nsIRDFResource *aSource, nsIRDFResource *aProperty, bool aTruthValue, nsIRDFNode **_retval)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(_retval);
|
||||
|
||||
// add extra nullptr checking for top-crash bug # 146466
|
||||
if (!gRDFService) return NS_RDF_NO_VALUE;
|
||||
if (!mInner) return NS_RDF_NO_VALUE;
|
||||
if (!mContainer) return NS_RDF_NO_VALUE;
|
||||
// special case kNC_KeyIndex before we forward to mInner
|
||||
if (aProperty == kNC_KeyIndex) {
|
||||
|
||||
int32_t theIndex = 0;
|
||||
nsresult rv = mContainer->IndexOf(aSource, &theIndex);
|
||||
if (NS_FAILED(rv)) return rv;
|
||||
|
||||
// only allow the range of 1 to 9 for single key access
|
||||
if (theIndex < 1 || theIndex > 9) return(NS_RDF_NO_VALUE);
|
||||
|
||||
nsCOMPtr<nsIRDFInt> indexInt;
|
||||
rv = gRDFService->GetIntLiteral(theIndex, getter_AddRefs(indexInt));
|
||||
if (NS_FAILED(rv)) return(rv);
|
||||
if (!indexInt) return(NS_ERROR_FAILURE);
|
||||
|
||||
indexInt.forget(_retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
return mInner->GetTarget(aSource, aProperty, aTruthValue, _retval);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetSource(nsIRDFResource *aProperty, nsIRDFNode *aTarget, bool aTruthValue, nsIRDFResource **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->GetSource(aProperty, aTarget, aTruthValue, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetSources(nsIRDFResource *aProperty, nsIRDFNode *aTarget, bool aTruthValue, nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->GetSources(aProperty, aTarget, aTruthValue, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetTargets(nsIRDFResource *aSource, nsIRDFResource *aProperty, bool aTruthValue, nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->GetTargets(aSource, aProperty, aTruthValue, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::Assert(nsIRDFResource *aSource, nsIRDFResource *aProperty, nsIRDFNode *aTarget, bool aTruthValue)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->Assert(aSource, aProperty, aTarget, aTruthValue);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::Unassert(nsIRDFResource *aSource, nsIRDFResource *aProperty, nsIRDFNode *aTarget)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->Unassert(aSource, aProperty, aTarget);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::Change(nsIRDFResource *aSource, nsIRDFResource *aProperty, nsIRDFNode *aOldTarget, nsIRDFNode *aNewTarget)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->Change(aSource, aProperty, aOldTarget, aNewTarget);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::Move(nsIRDFResource *aOldSource, nsIRDFResource *aNewSource, nsIRDFResource *aProperty, nsIRDFNode *aTarget)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->Move(aOldSource, aNewSource, aProperty, aTarget);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::HasAssertion(nsIRDFResource *aSource, nsIRDFResource *aProperty, nsIRDFNode *aTarget, bool aTruthValue, bool *_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->HasAssertion(aSource, aProperty, aTarget, aTruthValue, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::AddObserver(nsIRDFObserver *aObserver)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->AddObserver(aObserver);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::RemoveObserver(nsIRDFObserver *aObserver)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->RemoveObserver(aObserver);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::ArcLabelsIn(nsIRDFNode *aNode, nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->ArcLabelsIn(aNode, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::ArcLabelsOut(nsIRDFResource *aSource, nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->ArcLabelsOut(aSource, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetAllResources(nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->GetAllResources(_retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::IsCommandEnabled(nsISupports *aSources, nsIRDFResource *aCommand, nsISupports *aArguments, bool *_retval)
|
||||
{
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::DoCommand(nsISupports *aSources, nsIRDFResource *aCommand, nsISupports *aArguments)
|
||||
{
|
||||
return NS_ERROR_NOT_IMPLEMENTED;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::GetAllCmds(nsIRDFResource *aSource, nsISimpleEnumerator **_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->GetAllCmds(aSource, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::HasArcIn(nsIRDFNode *aNode, nsIRDFResource *aArc, bool *_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->HasArcIn(aNode, aArc, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::HasArcOut(nsIRDFResource *aSource, nsIRDFResource *aArc, bool *_retval)
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->HasArcOut(aSource, aArc, _retval);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::BeginUpdateBatch()
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->BeginUpdateBatch();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP nsWindowDataSource::EndUpdateBatch()
|
||||
{
|
||||
if (mInner)
|
||||
return mInner->EndUpdateBatch();
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// The module goop
|
||||
|
||||
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsWindowDataSource, Init)
|
||||
|
||||
NS_DEFINE_NAMED_CID(NS_WINDOWDATASOURCE_CID);
|
||||
|
||||
static const mozilla::Module::CIDEntry kWindowDSCIDs[] = {
|
||||
{ &kNS_WINDOWDATASOURCE_CID, false, nullptr, nsWindowDataSourceConstructor },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module::ContractIDEntry kWindowDSContracts[] = {
|
||||
{ NS_RDF_DATASOURCE_CONTRACTID_PREFIX "window-mediator", &kNS_WINDOWDATASOURCE_CID },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module::CategoryEntry kWindowDSCategories[] = {
|
||||
{ "app-startup", "Window Data Source", "service," NS_RDF_DATASOURCE_CONTRACTID_PREFIX "window-mediator" },
|
||||
{ nullptr }
|
||||
};
|
||||
|
||||
static const mozilla::Module kWindowDSModule = {
|
||||
mozilla::Module::kVersion,
|
||||
kWindowDSCIDs,
|
||||
kWindowDSContracts,
|
||||
kWindowDSCategories
|
||||
};
|
||||
|
||||
NSMODULE_DEFN(nsWindowDataSourceModule) = &kWindowDSModule;
|
||||
59
xpfe/components/windowds/nsWindowDataSource.h
Normal file
59
xpfe/components/windowds/nsWindowDataSource.h
Normal file
|
|
@ -0,0 +1,59 @@
|
|||
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
|
||||
/* 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 "nsIRDFDataSource.h"
|
||||
#include "nsIWindowMediatorListener.h"
|
||||
#include "nsIWindowDataSource.h"
|
||||
#include "nsIObserver.h"
|
||||
|
||||
#include "nsHashKeys.h"
|
||||
#include "nsIRDFService.h"
|
||||
#include "nsIRDFContainer.h"
|
||||
#include "nsInterfaceHashtable.h"
|
||||
#include "nsCycleCollectionParticipant.h"
|
||||
|
||||
// {C744CA3D-840B-460a-8D70-7CE63C51C958}
|
||||
#define NS_WINDOWDATASOURCE_CID \
|
||||
{ 0xc744ca3d, 0x840b, 0x460a, \
|
||||
{ 0x8d, 0x70, 0x7c, 0xe6, 0x3c, 0x51, 0xc9, 0x58 } }
|
||||
|
||||
|
||||
class nsWindowDataSource final : public nsIRDFDataSource,
|
||||
public nsIObserver,
|
||||
public nsIWindowMediatorListener,
|
||||
public nsIWindowDataSource
|
||||
{
|
||||
public:
|
||||
nsWindowDataSource() { }
|
||||
|
||||
nsresult Init();
|
||||
|
||||
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
|
||||
NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsWindowDataSource,
|
||||
nsIRDFDataSource)
|
||||
NS_DECL_NSIOBSERVER
|
||||
NS_DECL_NSIWINDOWMEDIATORLISTENER
|
||||
NS_DECL_NSIWINDOWDATASOURCE
|
||||
NS_DECL_NSIRDFDATASOURCE
|
||||
|
||||
protected:
|
||||
virtual ~nsWindowDataSource();
|
||||
|
||||
private:
|
||||
|
||||
// mapping of window -> RDF resource
|
||||
nsInterfaceHashtable<nsPtrHashKey<nsIXULWindow>, nsIRDFResource> mWindowResources;
|
||||
|
||||
static uint32_t windowCount;
|
||||
static uint32_t gRefCnt;
|
||||
|
||||
nsCOMPtr<nsIRDFDataSource> mInner;
|
||||
nsCOMPtr<nsIRDFContainer> mContainer;
|
||||
|
||||
static nsIRDFResource* kNC_Name;
|
||||
static nsIRDFResource* kNC_KeyIndex;
|
||||
static nsIRDFResource* kNC_WindowRoot;
|
||||
static nsIRDFService* gRDFService;
|
||||
};
|
||||
5
xpfe/test/child-window.html
Normal file
5
xpfe/test/child-window.html
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
<html><body onload="
|
||||
var gLoadEventTime = (new Date()).getTime();
|
||||
if (window.opener)
|
||||
window.setTimeout('window.opener.childIsOpen('+gLoadEventTime+');',1000);
|
||||
"></body></html>
|
||||
244
xpfe/test/winopen.js
Normal file
244
xpfe/test/winopen.js
Normal file
|
|
@ -0,0 +1,244 @@
|
|||
// target for window.open()
|
||||
const KID_URL = "child-window.html";
|
||||
|
||||
// formats final results
|
||||
const SERVER_URL = "http://jrgm.mcom.com/cgi-bin/window-open-2.0/openreport.pl";
|
||||
|
||||
// let system settle between each window.open
|
||||
const OPENER_DELAY = 1000;
|
||||
|
||||
// three phases: single open/close; overlapped open/close; open-all/close-all
|
||||
var PHASE_ONE = 10;
|
||||
var PHASE_TWO = 0;
|
||||
var PHASE_THREE = 0;
|
||||
|
||||
// keep this many windows concurrently open during overlapped phase
|
||||
var OVERLAP_COUNT = 3;
|
||||
|
||||
// repeat three phases CYCLES times
|
||||
var CYCLES = 1;
|
||||
|
||||
// autoclose flag
|
||||
var AUTOCLOSE = 1;
|
||||
|
||||
// Chrome url for child windows.
|
||||
var KID_CHROME = null;
|
||||
var SAVED_CHROME = null;
|
||||
|
||||
// URL options and correspnding vars.
|
||||
const options = [ [ "phase1", "PHASE_ONE", false ],
|
||||
[ "phase2", "PHASE_TWO", false ],
|
||||
[ "phase3", "PHASE_THREE", false ],
|
||||
[ "overlap", "OVERLAP_COUNT", false ],
|
||||
[ "cycles", "CYCLES", false ],
|
||||
[ "chrome", "KID_CHROME", true ],
|
||||
[ "close", "AUTOCLOSE", false ] ];
|
||||
|
||||
// Note: You can attach search options to the url for this file to control
|
||||
// any of the options in the array above. E.g., specifying
|
||||
// mozilla --chrome "file:///D|/mozilla/xpfe/test/winopen.xul?phase1=16&close=0"
|
||||
// will run this script with PHASE_ONE=16 and AUTOCLOSE=0.
|
||||
//
|
||||
// On Win32, you must enclose the --chrome option in quotes in order pass funny Win32 shell
|
||||
// characters such as '&' or '|'!
|
||||
|
||||
var opts = window.location.search.substring(1).split( '&' );
|
||||
for ( opt in opts ) {
|
||||
for ( var i in options ) {
|
||||
if ( opts[opt].indexOf( options[i][0]+"=" ) == 0 ) {
|
||||
var newVal = opts[opt].split( '=' )[ 1 ];
|
||||
// wrap with quotes, if required.
|
||||
if ( options[i][2] ) {
|
||||
newVal = '"' + newVal + '"';
|
||||
}
|
||||
eval( options[i][1] + "=" + newVal + ";" );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var prefs = null;
|
||||
|
||||
if ( KID_CHROME ) {
|
||||
// Reset browser.chromeURL so it points to KID_CHROME.
|
||||
// This will cause window.open in openWindow to open that chrome.
|
||||
netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
|
||||
prefs = Components.classes["@mozilla.org/preferences-service;1"]
|
||||
.getService( Components.interfaces.nsIPrefBranch );
|
||||
SAVED_CHROME = prefs.getCharPref( "browser.chromeURL" );
|
||||
prefs.setCharPref( "browser.chromeURL", KID_CHROME );
|
||||
}
|
||||
|
||||
const CYCLE_SIZE = PHASE_ONE + PHASE_TWO + PHASE_THREE;
|
||||
const MAX_INDEX = CYCLE_SIZE * CYCLES; // total number of windows to open
|
||||
|
||||
var windowList = []; // handles to opened windows
|
||||
var startingTimes = []; // time that window.open is called
|
||||
var openingTimes = []; // time that child window took to fire onload
|
||||
var closingTimes = []; // collect stats for case of closing >1 windows
|
||||
var currentIndex = 0;
|
||||
|
||||
|
||||
function childIsOpen(aTime) {
|
||||
openingTimes[currentIndex] = aTime - startingTimes[currentIndex];
|
||||
updateDisplay(currentIndex, openingTimes[currentIndex]);
|
||||
reapWindows(currentIndex);
|
||||
currentIndex++;
|
||||
if (currentIndex < MAX_INDEX)
|
||||
scheduleNextWindow();
|
||||
else
|
||||
window.setTimeout(reportResults, OPENER_DELAY);
|
||||
}
|
||||
|
||||
|
||||
function updateDisplay(index, time) {
|
||||
var formIndex = document.getElementById("formIndex");
|
||||
if (formIndex)
|
||||
formIndex.setAttribute("value", index+1);
|
||||
var formTime = document.getElementById("formTime");
|
||||
if (formTime)
|
||||
formTime.setAttribute("value", time);
|
||||
}
|
||||
|
||||
|
||||
function scheduleNextWindow() {
|
||||
window.setTimeout(openWindow, OPENER_DELAY);
|
||||
}
|
||||
|
||||
|
||||
function closeOneWindow(aIndex) {
|
||||
var win = windowList[aIndex];
|
||||
// no-op if window is already closed
|
||||
if (win && !win.closed) {
|
||||
win.close();
|
||||
windowList[aIndex] = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function closeAllWindows(aRecordTimeToClose) {
|
||||
var timeToClose = (new Date()).getTime();
|
||||
var count = 0;
|
||||
for (var i = 0; i < windowList.length; i++) {
|
||||
if (windowList[i])
|
||||
count++;
|
||||
closeOneWindow(i);
|
||||
}
|
||||
if (aRecordTimeToClose && count > 0) {
|
||||
timeToClose = (new Date()).getTime() - timeToClose;
|
||||
closingTimes.push(parseInt(timeToClose/count));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// close some, none, or all open windows in the list
|
||||
function reapWindows() {
|
||||
var modIndex = currentIndex % CYCLE_SIZE;
|
||||
if (modIndex < PHASE_ONE-1) {
|
||||
// first phase in each "cycle", are single open/close sequences
|
||||
closeOneWindow(currentIndex);
|
||||
}
|
||||
else if (PHASE_ONE-1 <= modIndex && modIndex < PHASE_ONE+PHASE_TWO-1) {
|
||||
// next phase in each "cycle", keep N windows concurrently open
|
||||
closeOneWindow(currentIndex - OVERLAP_COUNT);
|
||||
}
|
||||
else if (modIndex == PHASE_ONE+PHASE_TWO-1) {
|
||||
// end overlapping windows cycle; close all windows
|
||||
closeAllWindows(false);
|
||||
}
|
||||
else if (PHASE_ONE+PHASE_TWO <= modIndex && modIndex < CYCLE_SIZE-1) {
|
||||
// do nothing; keep adding windows
|
||||
}
|
||||
else if (modIndex == CYCLE_SIZE-1) {
|
||||
// end open-all/close-all phase; close windows, recording time to close
|
||||
closeAllWindows(true);
|
||||
}
|
||||
}
|
||||
|
||||
function calcMedian( numbers ) {
|
||||
if ( numbers.length == 0 ) {
|
||||
return 0;
|
||||
} else if ( numbers.length == 1 ) {
|
||||
return numbers[0];
|
||||
} else if ( numbers.length == 2 ) {
|
||||
return ( numbers[0] + numbers[1] ) / 2;
|
||||
} else {
|
||||
numbers.sort( function (a,b){ return a-b; } );
|
||||
var n = Math.floor( numbers.length / 2 );
|
||||
return numbers.length % 2 ? numbers[n] : ( numbers[n-1] + numbers[n] ) / 2;
|
||||
}
|
||||
}
|
||||
|
||||
function reportResults() {
|
||||
//XXX need to create a client-side method to do this?
|
||||
var opening = openingTimes.join(':'); // times for each window open
|
||||
var closing = closingTimes.join(':'); // these are for >1 url, as a group
|
||||
//var ua = escape(navigator.userAgent).replace(/\+/g, "%2B"); // + == ' ', on servers
|
||||
//var reportURL = SERVER_URL +
|
||||
// "?opening=" + opening +
|
||||
// "&closing=" + closing +
|
||||
// "&maxIndex=" + MAX_INDEX +
|
||||
// "&cycleSize=" + CYCLE_SIZE +
|
||||
//"&ua=" + ua;
|
||||
//window.open(reportURL, "test-results");
|
||||
var avgOpenTime = 0;
|
||||
var minOpenTime = 99999;
|
||||
var maxOpenTime = 0;
|
||||
var medOpenTime = calcMedian( openingTimes.slice(1) );
|
||||
// ignore first open
|
||||
for (i = 1; i < MAX_INDEX; i++) {
|
||||
avgOpenTime += openingTimes[i];
|
||||
if ( minOpenTime > openingTimes[i] ) {
|
||||
minOpenTime = openingTimes[i];
|
||||
}
|
||||
if ( maxOpenTime < openingTimes[i] ) {
|
||||
maxOpenTime = openingTimes[i];
|
||||
}
|
||||
}
|
||||
avgOpenTime = Math.round(avgOpenTime / (MAX_INDEX - 1));
|
||||
dump("openingTimes="+openingTimes.slice(1)+"\n");
|
||||
dump("avgOpenTime:" + avgOpenTime + "\n" );
|
||||
dump("minOpenTime:" + minOpenTime + "\n" );
|
||||
dump("maxOpenTime:" + maxOpenTime + "\n" );
|
||||
dump("medOpenTime:" + medOpenTime + "\n" );
|
||||
dump("__xulWinOpenTime:" + medOpenTime + "\n");
|
||||
// Close the root window, if required.
|
||||
if ( AUTOCLOSE ) {
|
||||
window.close();
|
||||
} else {
|
||||
document.getElementById("formTimes").value = openingTimes.slice(1);
|
||||
document.getElementById("formAvg").value = avgOpenTime;
|
||||
document.getElementById("formMin").value = minOpenTime;
|
||||
document.getElementById("formMax").value = maxOpenTime;
|
||||
document.getElementById("formMed").value = medOpenTime;
|
||||
document.getElementById("formAgain").setAttribute( "disabled", "false" );
|
||||
}
|
||||
}
|
||||
|
||||
function tryAgain() {
|
||||
document.getElementById("formAgain").setAttribute( "disabled", "true" );
|
||||
windowList = [];
|
||||
startingTimes = [];
|
||||
openingTimes = [];
|
||||
closingTimes = [];
|
||||
currentIndex = 0;
|
||||
openWindow();
|
||||
}
|
||||
|
||||
function restoreChromeURL() {
|
||||
// Restore browser.chromeURL pref.
|
||||
if ( KID_CHROME && SAVED_CHROME.length ) {
|
||||
netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
|
||||
prefs.setCharPref( "browser.chromeURL", SAVED_CHROME );
|
||||
}
|
||||
}
|
||||
|
||||
function openWindow() {
|
||||
startingTimes[currentIndex] = (new Date()).getTime();
|
||||
var path = window.location.pathname.substring( 0, window.location.pathname.lastIndexOf('/') );
|
||||
var url = window.location.protocol + "//" +
|
||||
window.location.hostname + path + "/" +
|
||||
KID_URL;
|
||||
windowList[currentIndex] = window.open(url, currentIndex);
|
||||
}
|
||||
|
||||
|
||||
75
xpfe/test/winopen.xul
Normal file
75
xpfe/test/winopen.xul
Normal file
|
|
@ -0,0 +1,75 @@
|
|||
<?xml version="1.0"?> <?xml-stylesheet href="chrome://global/skin/" type="text/css"?>
|
||||
<window
|
||||
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
|
||||
orient="vertical"
|
||||
height="300"
|
||||
width="400"
|
||||
windowtype="opener:test"
|
||||
onunload="restoreChromeURL();"
|
||||
onload="scheduleNextWindow();">
|
||||
|
||||
<script src="winopen.js" type="application/x-javascript"></script>
|
||||
|
||||
<groupbox orient="vertical">
|
||||
<caption label="Window Opening Test"/>
|
||||
<html>
|
||||
This will open a series of browser windows, either "one at a
|
||||
time" or in a sequence of some form. When this test is complete
|
||||
a final window will be opened which will report the overall results.
|
||||
</html>
|
||||
<separator class="thick"/>
|
||||
<grid>
|
||||
<columns><column/><column/></columns>
|
||||
<rows>
|
||||
<row align="center">
|
||||
<text value="Index:"/>
|
||||
<textbox id="formIndex" size="6" value=""/>
|
||||
</row>
|
||||
<row align="center">
|
||||
<text value="Time:"/>
|
||||
<textbox id="formTime" size="6" value=""/>
|
||||
<text value="msec"/>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
<separator class="thick"/>
|
||||
</groupbox>
|
||||
|
||||
<groupbox orient="vertical">
|
||||
<caption label="Results"/>
|
||||
<grid>
|
||||
<columns>
|
||||
<column/>
|
||||
<column/>
|
||||
</columns>
|
||||
<rows>
|
||||
<row align="center">
|
||||
<text value="Times (ignoring the first):"/>
|
||||
<textbox id="formTimes" size="45" value=""/>
|
||||
</row>
|
||||
<row align="center">
|
||||
<text value="Txul (median):"/>
|
||||
<hbox>
|
||||
<textbox id="formMed" size="6" value=""/>
|
||||
<spring/>
|
||||
<button id="formAgain" onclick="tryAgain();" label="Try again" disabled="true"/>
|
||||
</hbox>
|
||||
</row>
|
||||
<row align="center">
|
||||
<text value="Avg:"/>
|
||||
<hbox><textbox id="formAvg" size="6" value=""/></hbox>
|
||||
</row>
|
||||
<row align="center">
|
||||
<text value="Min:"/>
|
||||
<hbox><textbox id="formMin" size="6" value=""/></hbox>
|
||||
</row>
|
||||
<row align="center">
|
||||
<text value="Max:"/>
|
||||
<hbox><textbox id="formMax" size="6" value=""/></hbox>
|
||||
</row>
|
||||
</rows>
|
||||
</grid>
|
||||
</groupbox>
|
||||
|
||||
</window>
|
||||
|
||||
Loading…
Add table
Add a link
Reference in a new issue