mozilla-central merge

This commit is contained in:
Oleg Romashin 2008-08-08 13:05:00 +03:00
commit 12059d0133
766 changed files with 24917 additions and 20177 deletions

View File

@ -94,7 +94,10 @@ EXTRA_DSO_LDOPTS += $(MOZ_GTK2_LIBS)
endif
ifeq ($(OS_ARCH),WINNT)
OS_LIBS += oleaut32.lib
OS_LIBS += \
oleaut32.lib \
version.lib \
$(NULL)
endif
include $(topsrcdir)/config/rules.mk

View File

@ -112,12 +112,23 @@ nsIAccessibilityService *nsAccessNode::GetAccService()
* Class nsAccessNode
*/
//-----------------------------------------------------
// construction
//-----------------------------------------------------
NS_IMPL_QUERY_INTERFACE2(nsAccessNode, nsIAccessNode, nsPIAccessNode)
NS_IMPL_ADDREF(nsAccessNode)
NS_IMPL_RELEASE_WITH_DESTROY(nsAccessNode, LastRelease())
////////////////////////////////////////////////////////////////////////////////
// nsAccessible. nsISupports
NS_IMPL_CYCLE_COLLECTION_0(nsAccessNode)
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsAccessNode)
NS_INTERFACE_MAP_ENTRY(nsIAccessNode)
NS_INTERFACE_MAP_ENTRY(nsPIAccessNode)
NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIAccessNode)
NS_INTERFACE_MAP_END
NS_IMPL_CYCLE_COLLECTING_ADDREF_AMBIGUOUS(nsAccessNode, nsIAccessNode)
NS_IMPL_CYCLE_COLLECTING_RELEASE_FULL(nsAccessNode, nsIAccessNode,
LastRelease())
////////////////////////////////////////////////////////////////////////////////
// nsAccessible. Constructor
nsAccessNode::nsAccessNode(nsIDOMNode *aNode, nsIWeakReference* aShell):
mDOMNode(aNode), mWeakShell(aShell)

View File

@ -74,13 +74,16 @@ class nsIDocShellTreeItem;
typedef nsInterfaceHashtable<nsVoidPtrHashKey, nsIAccessNode>
nsAccessNodeHashtable;
class nsAccessNode: public nsIAccessNode, public nsPIAccessNode
class nsAccessNode: public nsIAccessNode,
public nsPIAccessNode
{
public: // construction, destruction
nsAccessNode(nsIDOMNode *, nsIWeakReference* aShell);
virtual ~nsAccessNode();
NS_DECL_ISUPPORTS
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsAccessNode, nsIAccessNode)
NS_DECL_NSIACCESSNODE
NS_DECL_NSPIACCESSNODE

View File

@ -65,6 +65,7 @@
#include "nsIEventStateManager.h"
#include "nsISelection2.h"
#include "nsISelectionController.h"
#include "nsGUIEvent.h"
#include "nsContentCID.h"
#include "nsComponentManagerUtils.h"
@ -291,6 +292,48 @@ nsAccUtils::HasListener(nsIContent *aContent, const nsAString& aEventType)
return listenerManager && listenerManager->HasListenersFor(aEventType);
}
PRBool
nsAccUtils::DispatchMouseEvent(PRUint32 aEventType,
nsIPresShell *aPresShell,
nsIContent *aContent)
{
nsIFrame *frame = aPresShell->GetPrimaryFrameFor(aContent);
if (!frame)
return PR_FALSE;
nsIFrame* rootFrame = aPresShell->GetRootFrame();
if (!rootFrame)
return PR_FALSE;
nsCOMPtr<nsIWidget> rootWidget = rootFrame->GetWindow();
if (!rootWidget)
return PR_FALSE;
// Compute x and y coordinates.
nsPoint point = frame->GetOffsetToExternal(rootFrame);
nsSize size = frame->GetSize();
nsPresContext* presContext = aPresShell->GetPresContext();
PRInt32 x = presContext->AppUnitsToDevPixels(point.x + size.width / 2);
PRInt32 y = presContext->AppUnitsToDevPixels(point.y + size.height / 2);
// Fire mouse event.
nsMouseEvent event(PR_TRUE, aEventType, rootWidget,
nsMouseEvent::eReal, nsMouseEvent::eNormal);
event.refPoint = nsIntPoint(x, y);
event.clickCount = 1;
event.button = nsMouseEvent::eLeftButton;
event.time = PR_IntervalNow();
nsEventStatus status = nsEventStatus_eIgnore;
aPresShell->HandleEventWithTarget(&event, frame, aContent, &status);
return PR_TRUE;
}
PRUint32
nsAccUtils::GetAccessKeyFor(nsIContent *aContent)
{

View File

@ -124,6 +124,17 @@ public:
*/
static PRBool HasListener(nsIContent *aContent, const nsAString& aEventType);
/**
* Send mouse events to the given element.
*
* @param aEventType an event type (see nsGUIEvent.h for constants)
* @param aPresShell the presshell for the given element
* @param aContent the element element
*/
static PRBool DispatchMouseEvent(PRUint32 aEventType,
nsIPresShell *aPresShell,
nsIContent *aContent);
/**
* Return an accesskey registered on the given element by
* nsIEventStateManager or 0 if there is no registered accesskey.

View File

@ -140,9 +140,23 @@ nsAccessibleDOMStringList::Contains(const nsAString& aString, PRBool *aResult)
* Class nsAccessible
*/
//-----------------------------------------------------
// construction
//-----------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
// nsAccessible. nsISupports
NS_IMPL_CYCLE_COLLECTION_CLASS(nsAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsAccessible, nsAccessNode)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mParent)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mFirstChild)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mNextSibling)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsAccessible, nsAccessNode)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mParent)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mFirstChild)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mNextSibling)
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_IMPL_ADDREF_INHERITED(nsAccessible, nsAccessNode)
NS_IMPL_RELEASE_INHERITED(nsAccessible, nsAccessNode)
@ -189,6 +203,11 @@ nsresult nsAccessible::QueryInterface(REFNSIID aIID, void** aInstancePtr)
// based on role attribute and aria-multiselectable
*aInstancePtr = nsnull;
if (aIID.Equals(NS_GET_IID(nsXPCOMCycleCollectionParticipant))) {
*aInstancePtr = &NS_CYCLE_COLLECTION_NAME(nsAccessible);
return NS_OK;
}
if (aIID.Equals(NS_GET_IID(nsIAccessible))) {
*aInstancePtr = static_cast<nsIAccessible*>(this);
NS_ADDREF_THIS();
@ -483,7 +502,7 @@ NS_IMETHODIMP nsAccessible::SetFirstChild(nsIAccessible *aFirstChild)
NS_IMETHODIMP nsAccessible::SetNextSibling(nsIAccessible *aNextSibling)
{
mNextSibling = aNextSibling? aNextSibling: DEAD_END_ACCESSIBLE;
mNextSibling = aNextSibling;
return NS_OK;
}
@ -538,15 +557,13 @@ NS_IMETHODIMP nsAccessible::InvalidateChildren()
// CacheChildren() is called.
// Note: we don't want to start creating accessibles at this point,
// so don't use GetNextSibling() here. (bug 387252)
nsAccessible* child = static_cast<nsAccessible*>(mFirstChild);
nsAccessible* child = static_cast<nsAccessible*>(mFirstChild.get());
while (child) {
child->mParent = nsnull;
if (child->mNextSibling == DEAD_END_ACCESSIBLE) {
break;
}
nsIAccessible *next = child->mNextSibling;
nsCOMPtr<nsIAccessible> next = child->mNextSibling;
child->mNextSibling = nsnull;
child = static_cast<nsAccessible*>(next);
child = static_cast<nsAccessible*>(next.get());
}
mAccChildCount = eChildCountUninitialized;
@ -608,9 +625,8 @@ NS_IMETHODIMP nsAccessible::GetNextSibling(nsIAccessible * *aNextSibling)
if (mNextSibling || !mParent) {
// If no parent, don't try to calculate a new sibling
// It either means we're at the root or shutting down the parent
if (mNextSibling != DEAD_END_ACCESSIBLE) {
NS_IF_ADDREF(*aNextSibling = mNextSibling);
}
NS_IF_ADDREF(*aNextSibling = mNextSibling);
return NS_OK;
}
@ -3137,40 +3153,30 @@ NS_IMETHODIMP nsAccessible::GetNativeInterface(void **aOutAccessible)
void nsAccessible::DoCommandCallback(nsITimer *aTimer, void *aClosure)
{
NS_ASSERTION(gDoCommandTimer, "How did we get here if there was no gDoCommandTimer?");
NS_ASSERTION(gDoCommandTimer,
"How did we get here if there was no gDoCommandTimer?");
NS_RELEASE(gDoCommandTimer);
nsIContent *content = reinterpret_cast<nsIContent*>(aClosure);
nsCOMPtr<nsIDOMXULElement> xulElement(do_QueryInterface(content));
if (xulElement) {
xulElement->Click();
}
else {
nsIDocument *doc = content->GetDocument();
if (!doc) {
return;
}
nsCOMPtr<nsIPresShell> presShell = doc->GetPrimaryShell();
nsPIDOMWindow *outerWindow = doc->GetWindow();
if (presShell && outerWindow) {
nsAutoPopupStatePusher popupStatePusher(outerWindow, openAllowed);
nsCOMPtr<nsIContent> content =
reinterpret_cast<nsIContent*>(aClosure);
nsMouseEvent downEvent(PR_TRUE, NS_MOUSE_BUTTON_DOWN, nsnull,
nsMouseEvent::eSynthesized);
nsMouseEvent upEvent(PR_TRUE, NS_MOUSE_BUTTON_UP, nsnull,
nsMouseEvent::eSynthesized);
nsMouseEvent clickEvent(PR_TRUE, NS_MOUSE_CLICK, nsnull,
nsMouseEvent::eSynthesized);
nsIDocument *doc = content->GetDocument();
if (!doc)
return;
nsEventStatus eventStatus = nsEventStatus_eIgnore;
content->DispatchDOMEvent(&downEvent, nsnull,
presShell->GetPresContext(), &eventStatus);
content->DispatchDOMEvent(&upEvent, nsnull,
presShell->GetPresContext(), &eventStatus);
content->DispatchDOMEvent(&clickEvent, nsnull,
presShell->GetPresContext(), &eventStatus);
}
}
nsCOMPtr<nsIPresShell> presShell = doc->GetPrimaryShell();
// Scroll into view.
presShell->ScrollContentIntoView(content, NS_PRESSHELL_SCROLL_ANYWHERE,
NS_PRESSHELL_SCROLL_ANYWHERE);
// Fire mouse down and mouse up events.
PRBool res = nsAccUtils::DispatchMouseEvent(NS_MOUSE_BUTTON_DOWN, presShell,
content);
if (!res)
return;
nsAccUtils::DispatchMouseEvent(NS_MOUSE_BUTTON_UP, presShell, content);
}
/*

View File

@ -69,9 +69,6 @@ class nsIView;
#define NS_OK_NO_ARIA_VALUE \
NS_ERROR_GENERATE_SUCCESS(NS_ERROR_MODULE_GENERAL, 0x21)
// When mNextSibling is set to this, it indicates there ar eno more siblings
#define DEAD_END_ACCESSIBLE static_cast<nsIAccessible*>((void*)1)
// Saves a data member -- if child count equals this value we haven't
// cached children or child count yet
enum { eChildCountUninitialized = -1 };
@ -106,6 +103,8 @@ public:
virtual ~nsAccessible();
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsAccessible, nsAccessNode)
NS_DECL_NSIACCESSIBLE
NS_DECL_NSPIACCESSIBLE
NS_DECL_NSIACCESSIBLEHYPERLINK
@ -272,7 +271,9 @@ protected:
// Data Members
nsCOMPtr<nsIAccessible> mParent;
nsIAccessible *mFirstChild, *mNextSibling;
nsCOMPtr<nsIAccessible> mFirstChild;
nsCOMPtr<nsIAccessible> mNextSibling;
nsRoleMapEntry *mRoleMapEntry; // Non-null indicates author-supplied role; possibly state & value as well
PRInt32 mAccChildCount;
};

View File

@ -57,7 +57,22 @@
PRBool nsAccEvent::gLastEventFromUserInput = PR_FALSE;
nsIDOMNode* nsAccEvent::gLastEventNodeWeak = 0;
NS_IMPL_ISUPPORTS2(nsAccEvent, nsAccEvent, nsIAccessibleEvent)
////////////////////////////////////////////////////////////////////////////////
// nsAccEvent. nsISupports
NS_IMPL_CYCLE_COLLECTION_2(nsAccEvent, mAccessible, mDocAccessible)
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsAccEvent)
NS_INTERFACE_MAP_ENTRY(nsIAccessibleEvent)
NS_INTERFACE_MAP_ENTRY(nsAccEvent)
NS_INTERFACE_MAP_ENTRY(nsISupports)
NS_INTERFACE_MAP_END
NS_IMPL_CYCLE_COLLECTING_ADDREF(nsAccEvent)
NS_IMPL_CYCLE_COLLECTING_RELEASE(nsAccEvent)
////////////////////////////////////////////////////////////////////////////////
// nsAccEvent. Constructors
nsAccEvent::nsAccEvent(PRUint32 aEventType, nsIAccessible *aAccessible,
PRBool aIsAsynch, EEventRule aEventRule):

View File

@ -49,6 +49,7 @@
#include "nsIAccessibleDocument.h"
#include "nsIDOMNode.h"
#include "nsString.h"
#include "nsCycleCollectionParticipant.h"
class nsIPresShell;
@ -93,7 +94,9 @@ public:
EEventRule aEventRule = eRemoveDupes);
virtual ~nsAccEvent() {}
NS_DECL_ISUPPORTS
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_CLASS(nsAccEvent)
NS_DECL_NSIACCESSIBLEEVENT
static void GetLastEventAttributes(nsIDOMNode *aNode,
@ -105,13 +108,13 @@ protected:
void CaptureIsFromUserInput(PRBool aIsAsynch);
PRBool mIsFromUserInput;
private:
PRUint32 mEventType;
EEventRule mEventRule;
nsCOMPtr<nsIAccessible> mAccessible;
nsCOMPtr<nsIDOMNode> mDOMNode;
nsCOMPtr<nsIAccessibleDocument> mDocAccessible;
private:
static PRBool gLastEventFromUserInput;
static nsIDOMNode* gLastEventNodeWeak;

View File

@ -50,11 +50,48 @@ nsApplicationAccessible::nsApplicationAccessible():
{
}
////////////////////////////////////////////////////////////////////////////////
// nsISupports
NS_IMPL_ISUPPORTS_INHERITED0(nsApplicationAccessible,
nsAccessible)
NS_IMPL_CYCLE_COLLECTION_CLASS(nsApplicationAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsApplicationAccessible,
nsAccessible)
nsCOMPtr<nsISimpleEnumerator> enumerator;
tmp->mChildren->Enumerate(getter_AddRefs(enumerator));
nsCOMPtr<nsIWeakReference> childWeakRef;
nsCOMPtr<nsIAccessible> accessible;
PRBool hasMoreElements;
while(NS_SUCCEEDED(enumerator->HasMoreElements(&hasMoreElements))
&& hasMoreElements) {
enumerator->GetNext(getter_AddRefs(childWeakRef));
accessible = do_QueryReferent(childWeakRef);
if (accessible) {
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, accessible);
cb.NoteXPCOMChild(accessible);
}
}
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsApplicationAccessible,
nsAccessible)
tmp->mChildren->Clear();
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsApplicationAccessible)
NS_INTERFACE_MAP_END_INHERITING(nsAccessible)
NS_IMPL_ADDREF_INHERITED(nsApplicationAccessible, nsAccessible)
NS_IMPL_RELEASE_INHERITED(nsApplicationAccessible, nsAccessible)
////////////////////////////////////////////////////////////////////////////////
// nsIAccessNode
NS_IMETHODIMP
nsApplicationAccessible::Init()
{

View File

@ -63,6 +63,8 @@ public:
// nsISupports
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsApplicationAccessible,
nsAccessible)
// nsPIAccessNode
NS_IMETHOD Init();

View File

@ -188,11 +188,14 @@ nsLinkableAccessible::GetActionName(PRUint8 aIndex, nsAString& aName)
NS_IMETHODIMP
nsLinkableAccessible::DoAction(PRUint8 aIndex)
{
if (aIndex != eAction_Jump)
return NS_ERROR_INVALID_ARG;
nsCOMPtr<nsIAccessible> actionAcc = GetActionAccessible();
if (actionAcc)
return actionAcc->DoAction(aIndex);
return NS_ERROR_INVALID_ARG;
return nsHyperTextAccessibleWrap::DoAction(aIndex);
}
NS_IMETHODIMP

View File

@ -135,7 +135,34 @@ nsDocAccessible::~nsDocAccessible()
{
}
NS_INTERFACE_MAP_BEGIN(nsDocAccessible)
////////////////////////////////////////////////////////////////////////////////
// nsDocAccessible. nsISupports
PR_STATIC_CALLBACK(PLDHashOperator)
ElementTraverser(const void *aKey, nsIAccessNode *aAccessNode,
void *aUserArg)
{
nsCycleCollectionTraversalCallback *cb =
static_cast<nsCycleCollectionTraversalCallback*>(aUserArg);
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(*cb, aAccessNode);
cb->NoteXPCOMChild(aAccessNode);
return PL_DHASH_NEXT;
}
NS_IMPL_CYCLE_COLLECTION_CLASS(nsDocAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INHERITED(nsDocAccessible, nsAccessible)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMARRAY(mEventsToFire)
tmp->mAccessNodeCache.EnumerateRead(ElementTraverser, &cb);
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_INHERITED(nsDocAccessible, nsAccessible)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMARRAY(mEventsToFire)
tmp->ClearCache(tmp->mAccessNodeCache);
NS_IMPL_CYCLE_COLLECTION_UNLINK_END
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION_INHERITED(nsDocAccessible)
NS_INTERFACE_MAP_ENTRY(nsIAccessibleDocument)
NS_INTERFACE_MAP_ENTRY(nsPIAccessibleDocument)
NS_INTERFACE_MAP_ENTRY(nsIDocumentObserver)

View File

@ -65,6 +65,8 @@ class nsDocAccessible : public nsHyperTextAccessibleWrap,
public nsSupportsWeakReference
{
NS_DECL_ISUPPORTS_INHERITED
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsDocAccessible, nsAccessible)
NS_DECL_NSIACCESSIBLEDOCUMENT
NS_DECL_NSPIACCESSIBLEDOCUMENT
NS_DECL_NSIOBSERVER

View File

@ -37,6 +37,7 @@
* ***** END LICENSE BLOCK ***** */
#include "nsAccessNodeWrap.h"
#include <tchar.h>
#include "ISimpleDOMNode_i.c"
#include "nsAccessibilityAtoms.h"
#include "nsIAccessibilityService.h"
@ -66,6 +67,8 @@ LPFNNOTIFYWINEVENT nsAccessNodeWrap::gmNotifyWinEvent = nsnull;
LPFNGETGUITHREADINFO nsAccessNodeWrap::gmGetGUIThreadInfo = nsnull;
PRBool nsAccessNodeWrap::gIsEnumVariantSupportDisabled = 0;
// Used to determine whether an IAccessible2 compatible screen reader is loaded.
PRBool nsAccessNodeWrap::gIsIA2Disabled = PR_FALSE;
nsIAccessibleTextChangeEvent *nsAccessNodeWrap::gTextEvent = nsnull;
@ -599,6 +602,8 @@ void nsAccessNodeWrap::InitAccessibility()
gmGetGUIThreadInfo = (LPFNGETGUITHREADINFO)GetProcAddress(gmUserLib,"GetGUIThreadInfo");
}
DoATSpecificProcessing();
nsAccessNode::InitXPAccessibility();
}
@ -655,3 +660,40 @@ GetHRESULT(nsresult aResult)
}
}
PRBool nsAccessNodeWrap::IsOnlyMsaaCompatibleJawsPresent()
{
HMODULE jhookhandle = ::GetModuleHandleW(NS_LITERAL_STRING("jhook").get());
if (!jhookhandle)
return PR_FALSE; // No JAWS, or some other screen reader, use IA2
PRUnichar fileName[MAX_PATH];
::GetModuleFileNameW(jhookhandle, fileName, MAX_PATH);
DWORD dummy;
DWORD length = ::GetFileVersionInfoSizeW(fileName, &dummy);
LPBYTE versionInfo = new BYTE[length];
::GetFileVersionInfoW(fileName, 0, length, versionInfo);
UINT uLen;
VS_FIXEDFILEINFO *fixedFileInfo;
::VerQueryValueW(versionInfo, L"\\", (LPVOID*)&fixedFileInfo, &uLen);
DWORD dwFileVersionMS = fixedFileInfo->dwFileVersionMS;
DWORD dwFileVersionLS = fixedFileInfo->dwFileVersionLS;
delete [] versionInfo;
DWORD dwLeftMost = HIWORD(dwFileVersionMS);
// DWORD dwSecondLeft = LOWORD(dwFileVersionMS);
DWORD dwSecondRight = HIWORD(dwFileVersionLS);
// DWORD dwRightMost = LOWORD(dwFileVersionLS);
return (dwLeftMost < 8
|| (dwLeftMost == 8 && dwSecondRight < 2173));
}
void nsAccessNodeWrap::DoATSpecificProcessing()
{
if (IsOnlyMsaaCompatibleJawsPresent())
// All versions below 8.0.2173 are not compatible
gIsIA2Disabled = PR_TRUE;
}

View File

@ -158,12 +158,20 @@ class nsAccessNodeWrap : public nsAccessNode,
static int FilterA11yExceptions(unsigned int aCode, EXCEPTION_POINTERS *aExceptionInfo);
static PRBool IsOnlyMsaaCompatibleJawsPresent();
static void DoATSpecificProcessing();
protected:
void GetAccessibleFor(nsIDOMNode *node, nsIAccessible **newAcc);
ISimpleDOMNode* MakeAccessNode(nsIDOMNode *node);
static PRBool gIsEnumVariantSupportDisabled;
/**
* Used to determine whether an IAccessible2 compatible screen reader is
* loaded. Currently used for JAWS versions older than 8.0.2173.
*/
static PRBool gIsIA2Disabled;
/**
* It is used in nsHyperTextAccessibleWrap for IA2::newText/oldText
* implementation.

View File

@ -117,7 +117,7 @@ __try {
*ppv = static_cast<IEnumVARIANT*>(this);
} else if (IID_IServiceProvider == iid)
*ppv = static_cast<IServiceProvider*>(this);
else if (IID_IAccessible2 == iid)
else if (IID_IAccessible2 == iid && !gIsIA2Disabled)
*ppv = static_cast<IAccessible2*>(this);
if (NULL == *ppv) {

View File

@ -47,6 +47,7 @@ include $(topsrcdir)/config/rules.mk
_TEST_FILES =\
moz.png \
nsIAccessible_actions.js \
nsIAccessible_name.css \
nsIAccessible_name.xbl \
test_aria_activedescendant.html \
@ -56,6 +57,8 @@ _TEST_FILES =\
test_cssattrs.html \
test_groupattrs.xul \
$(warning test_table_indexes.html temporarily disabled) \
test_nsIAccessible_actions.html \
test_nsIAccessible_actions.xul \
test_nsIAccessible_name.html \
test_nsIAccessible_name.xul \
test_nsIAccessibleTable_1.html \

View File

@ -0,0 +1,150 @@
////////////////////////////////////////////////////////////////////////////////
// General
const nsIAccessibleRetrieval = Components.interfaces.nsIAccessibleRetrieval;
const nsIAccessibleRole = Components.interfaces.nsIAccessibleRole;
var gAccRetrieval = null;
function initialize()
{
gAccRetrieval = Components.classes["@mozilla.org/accessibleRetrieval;1"].
getService(nsIAccessibleRetrieval);
}
addLoadEvent(initialize);
////////////////////////////////////////////////////////////////////////////////
// Event constants
const MOUSEDOWN_EVENT = 1;
const MOUSEUP_EVENT = 2;
const CLICK_EVENT = 4;
const COMMAND_EVENT = 8;
const CLICK_EVENTS = MOUSEDOWN_EVENT | MOUSEUP_EVENT | CLICK_EVENT;
const ALL_EVENTS = CLICK_EVENTS | COMMAND_EVENT;
////////////////////////////////////////////////////////////////////////////////
// Public functions
function testActions(aArray, aIndex)
{
if (!aIndex)
aIndex = 0;
if (aIndex == aArray.length) {
SimpleTest.finish();
return;
}
var ID = aArray[aIndex].ID;
var actionName = aArray[aIndex].actionName;
var events = aArray[aIndex].events;
var elm = document.getElementById(ID);
if (!elm) {
ok(false, "There is no element with ID " + ID);
SimpleTest.finish();
return null;
}
var acc = null;
try {
acc = gAccRetrieval.getAccessibleFor(elm);
} catch(e) {
}
if (!acc) {
ok(false, "There is no accessible for " + ID);
SimpleTest.finish();
return null;
}
is(acc.getActionName(0), actionName,
"Wrong action name of the accessible for " + ID);
gEventHandler.initialize(ID, elm, events);
acc.doAction(0);
window.setTimeout(
function()
{
gEventHandler.checkEvents();
testActions(aArray, aIndex + 1);
},
200
);
}
////////////////////////////////////////////////////////////////////////////////
// Private
var gEventHandler =
{
initialize: function(aID, aElm, aExpectedEvents)
{
this.ID = aID,
this.element = aElm;
this.mExpectedEvents = aExpectedEvents;
this.mFiredEvents = 0;
if (this.mExpectedEvents & MOUSEDOWN_EVENT)
aElm.addEventListener("mousedown", this, false);
if (this.mExpectedEvents & MOUSEUP_EVENT)
aElm.addEventListener("mouseup", this, false);
if (this.mExpectedEvents & CLICK_EVENT)
aElm.addEventListener("click", this, false);
if (this.mExpectedEvents & COMMAND_EVENT)
aElm.addEventListener("command", this, false);
},
checkEvents: function()
{
if (this.mExpectedEvents & MOUSEDOWN_EVENT) {
ok(this.mFiredEvents & MOUSEDOWN_EVENT,
"mousedown hasn't been fired for " + this.ID);
this.element.removeEventListener("mousedown", this, false);
}
if (this.mExpectedEvents & MOUSEUP_EVENT) {
ok(this.mFiredEvents & MOUSEUP_EVENT,
"mouseup hasn't been fired for " + this.ID);
this.element.removeEventListener("mouseup", this, false);
}
if (this.mExpectedEvents & CLICK_EVENT) {
ok(this.mFiredEvents & CLICK_EVENT,
"click hasn't been fired for " + this.ID);
this.element.removeEventListener("click", this, false);
}
if (this.mExpectedEvents & COMMAND_EVENT) {
ok(this.mFiredEvents & COMMAND_EVENT,
"command hasn't been fired for " + this.ID);
this.element.removeEventListener("command", this, false);
}
},
ID: "",
element: null,
handleEvent : function(aEvent)
{
if (aEvent.type == "mousedown")
this.mFiredEvents |= MOUSEDOWN_EVENT;
else if(aEvent.type == "mouseup")
this.mFiredEvents |= MOUSEUP_EVENT;
else if(aEvent.type == "click")
this.mFiredEvents |= CLICK_EVENT;
else if(aEvent.type == "command")
this.mFiredEvents |= COMMAND_EVENT;
},
mExpectedEvents: 0,
mFiredEvents: 0
};

View File

@ -0,0 +1,49 @@
<html>
<head>
<title>nsIAccessible actions testing</title>
<link rel="stylesheet" type="text/css"
href="chrome://mochikit/content/tests/SimpleTest/test.css" />
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/nsIAccessible_actions.js"></script>
<script type="application/javascript">
function doTest()
{
var actionsArray = [
{
ID: "clickable",
actionName: "click",
events: CLICK_EVENTS
}
];
testActions(actionsArray);
}
SimpleTest.waitForExplicitFinish();
addLoadEvent(doTest);
</script>
</head>
<body>
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=410765"
title="nsIAccessible actions testing">
Mozilla Bug 410765
</a>
<p id="display"></p>
<div id="content" style="display: none"></div>
<pre id="test">
</pre>
<div id="clickable" onclick="">Clickable text</div>
</body>
</html>

View File

@ -0,0 +1,98 @@
<?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"?>
<?xml-stylesheet href="chrome://mochikit/content/a11y/accessible/nsIAccessible_name.css"
type="text/css"?>
<window xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
title="nsIAccessible actions testing">
<script type="application/javascript"
src="chrome://mochikit/content/MochiKit/packed.js"></script>
<script type="application/javascript"
src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js" />
<script type="application/javascript"
src="chrome://mochikit/content/a11y/accessible/nsIAccessible_actions.js" />
<script type="application/javascript">
<![CDATA[
function doTest()
{
var actionsArray = [
{
ID: "menu",
actionName: "click",
events: CLICK_EVENTS
},
{
ID: "submenu",
actionName: "click",
events: CLICK_EVENTS
},
{
ID: "menuitem",
actionName: "click",
events: ALL_EVENTS
},
{
ID: "button",
actionName: "press",
events: ALL_EVENTS
},
{
ID: "buttonmenu",
actionName: "press",
events: CLICK_EVENTS
},
{
ID: "buttonmenu_item",
actionName: "click",
events: CLICK_EVENTS
}
];
testActions(actionsArray);
}
SimpleTest.waitForExplicitFinish();
addLoadEvent(doTest);
]]>
</script>
<body xmlns="http://www.w3.org/1999/xhtml">
<a target="_blank"
href="https://bugzilla.mozilla.org/show_bug.cgi?id=410765"
title="nsIAccessible actions testing">
Mozilla Bug 410765
</a>
<p id="display"></p>
<div id="content" style="display: none">
</div>
<pre id="test">
</pre>
</body>
<menubar>
<menu label="menu" id="menu">
<menupopup>
<menuitem label="menu item" id="menuitem"/>
<menu label="submenu" id="submenu">
<menupopup>
<menuitem label="menu item"/>
</menupopup>
</menu>
</menupopup>
</menu>
</menubar>
<button label="button" id="button"/>
<button type="menu" id="buttonmenu" label="button">
<menupopup>
<menuitem label="item1" id="buttonmenu_item"/>
<menuitem label="item1"/>
</menupopup>
</button>
</window>

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.7 KiB

View File

@ -29,6 +29,7 @@
# Jeff Walden <jwalden+code@mit.edu>
# Johnathan Nightingale <johnath@mozilla.com>
# Justin Dolske <dolske@mozilla.com>
# Ehsan Akhgari <ehsan.akhgari@gmail.com>
#
# Alternatively, the contents of this file may be used under the terms of
# either the GNU General Public License Version 2 or later (the "GPL"), or
@ -80,13 +81,32 @@
}
}
]]></script>
<style type="text/css"><![CDATA[
#errorPageContainer {
background: url('chrome://browser/content/aboutRobots-icon.png') left 0 no-repeat -moz-Field;
-moz-background-origin: content;
}
#errorTrailerDescText {
float: right;
}
body[dir=rtl] #errorPageContainer {
background-image: url('chrome://browser/content/aboutRobots-icon-rtl.png');
background-position: right 0;
}
body[dir=rtl] #errorTrailerDescText {
float: left;
}
]]></style>
</head>
<body dir="&locale.dir;">
<!-- PAGE CONTAINER (for styling purposes only) -->
<div id="errorPageContainer"
style="background: url('chrome://browser/content/aboutRobots-icon.png') left 0 no-repeat -moz-Field; -moz-background-origin: content;">
<div id="errorPageContainer">
<!-- Error Title -->
<div id="errorTitle">
@ -113,7 +133,7 @@
<!-- Short Description -->
<div id="errorTrailerDesc">
<p id="errorTrailerDescText" style="float: right;">&robots.errorTrailerDescText;</p>
<p id="errorTrailerDescText">&robots.errorTrailerDescText;</p>
</div>
</div>

View File

@ -104,10 +104,14 @@
<!-- for url bar autocomplete -->
<panel type="autocomplete-richlistbox" chromedir="&locale.dir;" id="PopupAutoCompleteRichResult" noautofocus="true" hidden="true"/>
<!-- XXX panel element that has one or more text fields should not be
top-most panel, for IME users. See bug 433340 comment 100. -->
<panel id="editBookmarkPanel"
orient="vertical"
ignorekeys="true"
hidden="true"
noautohide="true"
onpopupshowing="this.removeAttribute('noautohide');"
onpopupshown="StarUI.panelShown(event);"
aria-labelledby="editBookmarkPanelTitle">
<hbox flex="1" align="top">

View File

@ -278,7 +278,6 @@
mTab: aTab,
mBrowser: aBrowser,
mBlank: aStartsBlank,
mLastURI: null,
// cache flags for correct status bar update after tab switching
mStateFlags: 0,
@ -1389,6 +1388,18 @@
<method name="removeTab">
<parameter name="aTab"/>
<body>
<![CDATA[
this._endRemoveTab(this._beginRemoveTab(aTab, true));
]]>
</body>
</method>
<!-- Returns the tab being removed. This might not be the same as aTab,
in cases when aTab is not actually a tab -->
<method name="_beginRemoveTab">
<parameter name="aTab"/>
<parameter name="aFireBeforeUnload"/>
<body>
<![CDATA[
this._browsers = null; // invalidate cache
@ -1403,9 +1414,11 @@
return;
}
var ds = this.getBrowserForTab(aTab).docShell;
if (ds.contentViewer && !ds.contentViewer.permitUnload())
return;
if (aFireBeforeUnload) {
var ds = this.getBrowserForTab(aTab).docShell;
if (ds.contentViewer && !ds.contentViewer.permitUnload())
return;
}
// see notes in addTab
var _delayedUpdate = function(aTabContainer) {
@ -1435,15 +1448,7 @@
evt.initEvent("TabClose", true, false);
aTab.dispatchEvent(evt);
var index = -1;
if (this.mCurrentTab == aTab)
index = this.mTabContainer.selectedIndex;
else {
// Find and locate the tab in our list.
for (var i = 0; i < l; i++)
if (this.mTabContainer.childNodes[i] == aTab)
index = i;
}
var index = aTab._tPos;
// Remove the tab's filter and progress listener.
const filter = this.mTabFilters[index];
@ -1459,22 +1464,34 @@
// We are no longer the primary content area.
oldBrowser.setAttribute("type", "content-targetable");
// Get the index of the tab we're removing before unselecting it
var currentIndex = this.mTabContainer.selectedIndex;
var oldTab = aTab;
// clean up the before/afterselected attributes before removing the tab
oldTab._selected = false;
// Remove this tab as the owner of any other tabs, since it's going away.
for (i = 0; i < this.mTabContainer.childNodes.length; ++i) {
for (var i = 0; i < this.mTabs.length; ++i) {
var tab = this.mTabContainer.childNodes[i];
if ("owner" in tab && tab.owner == oldTab)
if ("owner" in tab && tab.owner == aTab)
// |tab| is a child of the tab we're removing, make it an orphan
tab.owner = null;
}
return aTab;
]]>
</body>
</method>
<method name="_endRemoveTab">
<parameter name="aTab"/>
<body>
<![CDATA[
var browser = this.getBrowserForTab(aTab);
var length = this.mTabs.length;
// Get the index of the tab we're removing before unselecting it
var currentIndex = this.mTabContainer.selectedIndex;
var index = aTab._tPos;
// clean up the before/afterselected attributes before removing the
// tab. But make sure this happens after we grab currentIndex.
aTab._selected = false;
// Because of the way XBL works (fields just set JS
// properties on the element) and the code we have in place
// to preserve the JS objects for any elements that have
@ -1485,16 +1502,18 @@
// XBL implementation of nsIObserver still works. But
// clearing focusedWindow happens below because it gets
// reset by updateCurrentBrowser.
oldBrowser.destroy();
browser.destroy();
if (oldBrowser == this.mCurrentBrowser)
if (browser == this.mCurrentBrowser)
this.mCurrentBrowser = null;
// Remove the tab
this.mTabContainer.removeChild(oldTab);
this.mTabContainer.removeChild(aTab);
// Update our length
--length;
// invalidate cache, because mTabContainer is about to change
this._browsers = null;
this.mPanelContainer.removeChild(oldBrowser.parentNode);
this.mPanelContainer.removeChild(browser.parentNode);
try {
// if we're at the right side (and not the logical end,
@ -1523,24 +1542,24 @@
else if (currentIndex < index)
newIndex = currentIndex;
else {
if ("owner" in oldTab && oldTab.owner &&
if ("owner" in aTab && aTab.owner &&
this.mPrefs.getBoolPref("browser.tabs.selectOwnerOnClose")) {
for (i = 0; i < this.mTabContainer.childNodes.length; ++i) {
for (var i = 0; i < length; ++i) {
tab = this.mTabContainer.childNodes[i];
if (tab == oldTab.owner) {
if (tab == aTab.owner) {
newIndex = i;
break;
}
}
}
if (newIndex == -1)
newIndex = (index == l - 1) ? index - 1 : index;
newIndex = (index == length) ? index - 1 : index;
}
// Select the new tab
this.selectedTab = this.mTabContainer.childNodes[newIndex];
this.selectedTab = this.mTabs[newIndex];
for (i = oldTab._tPos; i < this.mTabContainer.childNodes.length; i++) {
for (i = aTab._tPos; i < length; i++) {
this.mTabContainer.childNodes[i]._tPos = i;
}
this.mTabBox.selectedPanel = this.getBrowserForTab(this.mCurrentTab).parentNode;
@ -1549,8 +1568,53 @@
this.updateCurrentBrowser();
// see comment above destroy above
oldBrowser.focusedWindow = null;
oldBrowser.focusedElement = null;
browser.focusedWindow = null;
browser.focusedElement = null;
]]>
</body>
</method>
<method name="swapBrowsersAndCloseOther">
<parameter name="aOurTab"/>
<parameter name="aOtherTab"/>
<body>
<![CDATA[
var remoteBrowser =
aOtherTab.ownerDocument.defaultView.getBrowser();
var tabCount = remoteBrowser.mTabs.length;
// First, start teardown of the other browser. Make sure to not
// fire the beforeunload event in the process.
var tabToRemove = remoteBrowser._beginRemoveTab(aOtherTab, false);
// Unhook our progress listener
var ourIndex = aOurTab._tPos;
const filter = this.mTabFilters[ourIndex];
var tabListener = this.mTabListeners[ourIndex];
var ourBrowser = this.getBrowserForTab(aOurTab);
ourBrowser.webProgress.removeProgressListener(filter);
filter.removeProgressListener(tabListener);
var tabListenerBlank = tabListener.mBlank;
// Swap the docshells
ourBrowser.swapDocShells(remoteBrowser.getBrowserForTab(aOtherTab));
// Finish tearing down the tab that's going away.
remoteBrowser._endRemoveTab(tabToRemove);
// Restore the progress listener
tabListener = this.mTabProgressListener(aOurTab, ourBrowser,
tabListenerBlank);
this.mTabListeners[ourIndex] = tabListener;
filter.addProgressListener(tabListener,
Components.interfaces.nsIWebProgress.NOTIFY_ALL);
ourBrowser.webProgress.addProgressListener(filter,
Components.interfaces.nsIWebProgress.NOTIFY_ALL);
// close the other window if this was its last tab
if (tabCount == 1)
aOtherTab.ownerDocument.defaultView.close();
]]>
</body>
</method>
@ -1879,19 +1943,26 @@
}
}
else if (draggedTab) {
// copy the dropped tab and remove it from the other window
// (making it seem to have moved between windows)
// swap the dropped tab with a new one we create and then close
// it in the other window (making it seem to have moved between
// windows)
newIndex = this.getNewIndex(aEvent);
newTab = this.duplicateTab(draggedTab);
this.moveTabTo(newTab, newIndex);
this.selectedTab = newTab;
newTab = this.addTab("about:blank");
var newBrowser = this.getBrowserForTab(newTab);
// Stop the about:blank load
newBrowser.stop();
// make sure it has a docshell
newBrowser.docShell;
var remoteBrowser = draggedTab.ownerDocument.defaultView.getBrowser();
var tabCount = remoteBrowser.tabContainer.childNodes.length;
remoteBrowser.removeTab(draggedTab);
// close the other window if this was its last tab
if (tabCount == 1)
draggedTab.ownerDocument.defaultView.close();
this.moveTabTo(newTab, newIndex);
this.swapBrowsersAndCloseOther(newTab, draggedTab);
// We need to set selectedTab after we've done
// swapBrowsersAndCloseOther, so that the updateCurrentBrowser
// it triggers will correctly update our URL bar.
this.selectedTab = newTab;
this.setTabTitle(newTab);
}
else {
var url = transferUtils.retrieveURLFromData(aXferData.data, aXferData.flavour.contentType);

View File

@ -59,6 +59,8 @@ _BROWSER_FILES = browser_bug321000.js \
autodiscovery.html \
moz.png \
browser_getshortcutoruri.js \
browser_page_style_menu.js \
page_style_sample.html \
$(NULL)
ifneq (,$(filter mac cocoa,$(MOZ_WIDGET_TOOLKIT)))

View File

@ -0,0 +1,66 @@
function test() {
waitForExplicitFinish();
finish();
return;
var tab = gBrowser.addTab();
gBrowser.selectedTab = tab;
tab.linkedBrowser.addEventListener("load", checkPageStyleMenu, true);
content.location =
"chrome://mochikit/content/browser/browser/base/content/test/page_style_sample.html";
}
function checkPageStyleMenu() {
var menupopup = document.getElementById("pageStyleMenu")
.getElementsByTagName("menupopup")[0];
stylesheetFillPopup(menupopup);
var items = [];
var current = menupopup.getElementsByTagName("menuseparator")[0];
while (current.nextSibling) {
current = current.nextSibling;
items.push(current);
}
var validLinks = 0;
Array.forEach(content.document.getElementsByTagName("link"), function (link) {
var title = link.getAttribute("title");
var rel = link.getAttribute("rel");
var media = link.getAttribute("media");
var idstring = "link " + (title ? title : "without title and") +
" with rel=\"" + rel + "\"" +
(media ? " and media=\"" + media + "\"" : "");
var item = items.filter(function (item) item.label == title);
var found = item.length == 1;
var checked = found && (item[0].getAttribute("checked") == "true");
switch (link.getAttribute("data-state")) {
case "0":
ok(!found, idstring + " does not show up in page style menu");
break;
case "0-todo":
validLinks++;
todo(!found, idstring + " should not show up in page style menu");
ok(!checked, idstring + " is not selected");
break;
case "1":
validLinks++;
ok(found, idstring + " shows up in page style menu");
ok(!checked, idstring + " is not selected");
break;
case "2":
validLinks++;
ok(found, idstring + " shows up in page style menu");
ok(checked, idstring + " is selected");
break;
default:
throw "data-state attribute is missing or has invalid value";
}
});
is(validLinks, items.length, "all valid links found");
gBrowser.removeCurrentTab();
finish();
}

View File

@ -0,0 +1,31 @@
<html>
<head>
<title>Test for page style menu</title>
<!-- data-state values:
0: should not appear in the page style menu
0-todo: should not appear in the page style menu, but does
1: should appear in the page style menu
2: should appear in the page style menu as the selected stylesheet -->
<link data-state="1" href="404.css" title="1" rel="alternate stylesheet">
<link data-state="0" title="2" rel="alternate stylesheet">
<link data-state="0" href="404.css" rel="alternate stylesheet">
<link data-state="0" href="404.css" title="" rel="alternate stylesheet">
<link data-state="1" href="404.css" title="3" rel="stylesheet alternate">
<link data-state="1" href="404.css" title="4" rel=" alternate stylesheet ">
<link data-state="1" href="404.css" title="5" rel="alternate stylesheet">
<link data-state="2" href="404.css" title="6" rel="stylesheet">
<link data-state="1" href="404.css" title="7" rel="foo stylesheet">
<link data-state="0" href="404.css" title="8" rel="alternate">
<link data-state="1" href="404.css" title="9" rel="alternate STYLEsheet">
<link data-state="1" href="404.css" title="10" rel="alternate stylesheet" media="">
<link data-state="1" href="404.css" title="11" rel="alternate stylesheet" media="all">
<link data-state="1" href="404.css" title="12" rel="alternate stylesheet" media="ALL ">
<link data-state="1" href="404.css" title="13" rel="alternate stylesheet" media="screen">
<link data-state="1" href="404.css" title="14" rel="alternate stylesheet" media=" Screen">
<link data-state="1" href="404.css" title="15" rel="alternate stylesheet" media="screen foo">
<link data-state="1" href="404.css" title="16" rel="alternate stylesheet" media="all screen">
<link data-state="0-todo" href="404.css" title="17" rel="alternate stylesheet" media="allscreen">
<link data-state="0-todo" href="404.css" title="18" rel="alternate stylesheet" media="_all">
</head>
<body></body>
</html>

View File

@ -15,6 +15,7 @@ browser.jar:
content/browser/aboutDialog.css (content/aboutDialog.css)
* content/browser/aboutRobots.xhtml (content/aboutRobots.xhtml)
content/browser/aboutRobots-icon.png (content/aboutRobots-icon.png)
content/browser/aboutRobots-icon-rtl.png (content/aboutRobots-icon-rtl.png)
content/browser/aboutRobots-widget-left.png (content/aboutRobots-widget-left.png)
content/browser/aboutRobots-widget-right.png (content/aboutRobots-widget-right.png)
* content/browser/browser.css (content/browser.css)

View File

@ -63,8 +63,7 @@
<hbox align="center">
<label value="&search.label;" accesskey="&search.accesskey;" control="search-box"/>
<textbox id="search-box" flex="1"
type="timed" timeout="500"
<textbox id="search-box" flex="1" type="search"
oncommand="searchBookmarks(this.value);"/>
</hbox>

View File

@ -86,7 +86,7 @@
<hbox align="center">
<label value="&find.label;" accesskey="&find.accesskey;"
control="search-box"/>
<textbox id="search-box" flex="1" type="timed" timeout="500"
<textbox id="search-box" flex="1" type="search"
oncommand="searchHistory(this.value);"/>
<button id="viewButton" style="min-width:0px !important;" type="menu"
label="&view.label;" accesskey="&view.accesskey;" selectedsort="day"

View File

@ -902,12 +902,12 @@
<getter><![CDATA[
// By default, the insertion point is at the top level, at the end.
var index = PlacesUtils.bookmarks.DEFAULT_INDEX;
var folderId = 0;
var container = null;
var orientation = Ci.nsITreeView.DROP_BEFORE;
var isTag = false;
if (PlacesUtils.nodeIsFolder(this._resultNode)) {
folderId = PlacesUtils.getConcreteItemId(this._resultNode);
container = this._resultNode;
isTag = PlacesUtils.nodeIsTagQuery(this._resultNode);
}
@ -917,20 +917,37 @@
if (!popupNode.node) {
// If a static menuitem is selected the insertion point
// is inside the folder, at the end.
folderId = PlacesUtils.getConcreteItemId(selectedNode);
container = selectedNode;
orientation = Ci.nsITreeView.DROP_ON;
}
else {
// In all other cases the insertion point is before that node.
folderId = PlacesUtils.getConcreteItemId(selectedNode.parent);
container = selectedNode.parent;
index = PlacesUtils.getIndexOfNode(selectedNode);
isTag = PlacesUtils.nodeIsTagQuery(selectedNode.parent);
}
}
return new InsertionPoint(folderId, index, orientation, isTag);
if (this._disallowInsertion(container))
return null;
return new InsertionPoint(PlacesUtils.getConcreteItemId(container),
index, orientation, isTag);
]]></getter>
</property>
<method name="_disallowInsertion">
<parameter name="aContainer"/>
<body><![CDATA[
// allow dropping into Tag containers
if (PlacesUtils.nodeIsTagQuery(aContainer))
return false;
// Disallow insertion of items under readonly folders
return (!PlacesUtils.nodeIsFolder(aContainer) ||
PlacesUtils.nodeIsReadOnly(aContainer));
]]></body>
</method>
<!-- nsIPlacesView -->
<method name="selectAll">
<body/>

View File

@ -385,7 +385,7 @@
<getter><![CDATA[
// By default, the insertion point is at the top level, at the end.
var index = PlacesUtils.bookmarks.DEFAULT_INDEX;
var folderId = PlacesUtils.getConcreteItemId(this._result.root);
var container = this._result.root;
var orientation = Ci.nsITreeView.DROP_BEFORE;
var isTag = false;
@ -395,20 +395,37 @@
if (!popupNode.node) {
// If a static menuitem is selected the insertion point
// is inside the folder, at the end.
folderId = PlacesUtils.getConcreteItemId(selectedNode);
container = selectedNode;
orientation = Ci.nsITreeView.DROP_ON;
}
else {
// In all other cases the insertion point is before that node.
folderId = PlacesUtils.getConcreteItemId(selectedNode.parent);
container = selectedNode.parent;
index = PlacesUtils.getIndexOfNode(selectedNode);
isTag = PlacesUtils.nodeIsTagQuery(selectedNode.parent);
}
}
return new InsertionPoint(folderId, index, orientation, isTag);
if (this._disallowInsertion(container))
return null;
return new InsertionPoint(PlacesUtils.getConcreteItemId(container),
index, orientation, isTag);
]]></getter>
</property>
<method name="_disallowInsertion">
<parameter name="aContainer"/>
<body><![CDATA[
// allow dropping into Tag containers
if (PlacesUtils.nodeIsTagQuery(aContainer))
return false;
// Disallow insertion of items under readonly folders
return (!PlacesUtils.nodeIsFolder(aContainer) ||
PlacesUtils.nodeIsReadOnly(aContainer));
]]></body>
</method>
<!-- nsIPlacesView -->
<method name="selectAll">
<body><![CDATA[

View File

@ -1602,36 +1602,7 @@ var gApplicationsPane = {
* Filter the list when the user enters a filter term into the filter field.
*/
filter: function() {
if (this._filter.value == "") {
this.clearFilter();
return;
}
this._rebuildView();
document.getElementById("clearFilter").disabled = false;
},
_filterTimeout: null,
onFilterInput: function() {
if (this._filterTimeout)
clearTimeout(this._filterTimeout);
this._filterTimeout = setTimeout("gApplicationsPane.filter()", 500);
},
onFilterKeyPress: function(aEvent) {
if (aEvent.keyCode == KeyEvent.DOM_VK_ESCAPE)
this.clearFilter();
},
clearFilter: function() {
this._filter.value = "";
this._rebuildView();
this._filter.focus();
document.getElementById("clearFilter").disabled = true;
},
focusFilterBox: function() {

View File

@ -110,12 +110,11 @@
<key key="&focusSearch2.key;" modifiers="accel" oncommand="gApplicationsPane.focusFilterBox();"/>
</keyset>
<hbox align="center">
<label accesskey="&filter.accesskey;" control="filter">&filter.label;</label>
<textbox id="filter" flex="1" oninput="gApplicationsPane.onFilterInput();"
onkeypress="gApplicationsPane.onFilterKeyPress(event);"/>
<button id="clearFilter" icon="clear" label="&clear.label;" accesskey="&clear.accesskey;"
oncommand="gApplicationsPane.clearFilter();" disabled="true"/>
<hbox>
<textbox id="filter" flex="1"
type="search"
emptytext="&filter.emptytext;"
oncommand="gApplicationsPane.filter();"/>
</hbox>
<separator class="thin"/>

View File

@ -228,10 +228,7 @@ SessionStoreService.prototype = {
this._initialState.session && this._initialState.session.state &&
this._initialState.session.state == STATE_RUNNING_STR;
// restore the features of the first window from localstore.rdf
WINDOW_ATTRIBUTES.forEach(function(aAttr) {
delete this._initialState.windows[0][aAttr];
}, this);
// make sure that at least the first window doesn't have anything hidden
delete this._initialState.windows[0].hidden;
}
catch (ex) { debug("The session file is invalid: " + ex); }

View File

@ -222,7 +222,7 @@ static SETTING gSettings[] = {
};
PRBool
nsWindowsShellService::IsDefaultBrowserVista(PRBool aStartupCheck, PRBool* aIsDefaultBrowser)
nsWindowsShellService::IsDefaultBrowserVista(PRBool* aIsDefaultBrowser)
{
#if !defined(MOZ_DISABLE_VISTA_SDK_REQUIREMENTS)
IApplicationAssociationRegistration* pAAR;
@ -238,12 +238,6 @@ nsWindowsShellService::IsDefaultBrowserVista(PRBool aStartupCheck, PRBool* aIsDe
APP_REG_NAME,
aIsDefaultBrowser);
// If this is the first browser window, maintain internal state that we've
// checked this session (so that subsequent window opens don't show the
// default browser dialog).
if (aStartupCheck)
mCheckedThisSession = PR_TRUE;
pAAR->Release();
return PR_TRUE;
}
@ -316,26 +310,29 @@ nsWindowsShellService::IsDefaultBrowser(PRBool aStartupCheck,
::ZeroMemory(currValue, sizeof(currValue));
HKEY theKey;
rv = OpenKeyForReading(HKEY_CLASSES_ROOT, key, &theKey);
if (NS_SUCCEEDED(rv)) {
DWORD len = sizeof currValue;
DWORD res = ::RegQueryValueExW(theKey, PromiseFlatString(value).get(),
NULL, NULL, (LPBYTE)currValue, &len);
// Close the key we opened.
::RegCloseKey(theKey);
if (REG_FAILED(res) ||
!dataLongPath.Equals(currValue, CaseInsensitiveCompare) &&
!dataShortPath.Equals(currValue, CaseInsensitiveCompare)) {
// Key wasn't set, or was set to something else (something else became the default browser)
*aIsDefaultBrowser = PR_FALSE;
return NS_OK;
}
if (NS_FAILED(rv)) {
*aIsDefaultBrowser = PR_FALSE;
return NS_OK;
}
DWORD len = sizeof currValue;
DWORD res = ::RegQueryValueExW(theKey, PromiseFlatString(value).get(),
NULL, NULL, (LPBYTE)currValue, &len);
// Close the key we opened.
::RegCloseKey(theKey);
if (REG_FAILED(res) ||
!dataLongPath.Equals(currValue, CaseInsensitiveCompare) &&
!dataShortPath.Equals(currValue, CaseInsensitiveCompare)) {
// Key wasn't set, or was set to something other than our registry entry
*aIsDefaultBrowser = PR_FALSE;
return NS_OK;
}
}
// Only check if Firefox is the default browser on Vista if the previous
// checks show that Firefox is the default browser.
if (aIsDefaultBrowser)
IsDefaultBrowserVista(aStartupCheck, aIsDefaultBrowser);
if (*aIsDefaultBrowser)
IsDefaultBrowserVista(aIsDefaultBrowser);
return NS_OK;
}
@ -358,8 +355,8 @@ nsWindowsShellService::SetDefaultBrowser(PRBool aClaimAllTypes, PRBool aForAllUs
rv = appHelper->AppendNative(NS_LITERAL_CSTRING("helper.exe"));
NS_ENSURE_SUCCESS(rv, rv);
nsCAutoString appHelperPath;
rv = appHelper->GetNativePath(appHelperPath);
nsAutoString appHelperPath;
rv = appHelper->GetPath(appHelperPath);
NS_ENSURE_SUCCESS(rv, rv);
if (aForAllUsers) {
@ -368,11 +365,11 @@ nsWindowsShellService::SetDefaultBrowser(PRBool aClaimAllTypes, PRBool aForAllUs
appHelperPath.AppendLiteral(" /SetAsDefaultAppUser");
}
STARTUPINFO si = {sizeof(si), 0};
STARTUPINFOW si = {sizeof(si), 0};
PROCESS_INFORMATION pi = {0};
BOOL ok = CreateProcess(NULL, (LPSTR)appHelperPath.get(), NULL, NULL,
FALSE, 0, NULL, NULL, &si, &pi);
BOOL ok = CreateProcessW(NULL, (LPWSTR)appHelperPath.get(), NULL, NULL,
FALSE, 0, NULL, NULL, &si, &pi);
if (!ok)
return NS_ERROR_FAILURE;
@ -766,8 +763,8 @@ nsWindowsShellService::GetUnreadMailCount(PRUint32* aCount)
if (REG_SUCCEEDED(res))
*aCount = unreadCount;
// Close the key we opened.
::RegCloseKey(accountKey);
// Close the key we opened.
::RegCloseKey(accountKey);
}
return NS_OK;

View File

@ -57,16 +57,9 @@ public:
NS_DECL_NSIWINDOWSSHELLSERVICE
protected:
PRBool IsDefaultBrowserVista(PRBool aStartupCheck, PRBool* aIsDefaultBrowser);
PRBool IsDefaultBrowserVista(PRBool* aIsDefaultBrowser);
PRBool GetMailAccountKey(HKEY* aResult);
void SetRegKey(const nsString& aKeyName,
const nsString& aValueName,
const nsString& aValue, PRBool aHKLMOnly);
DWORD DeleteRegKey(HKEY baseKey, const nsString& keyName);
DWORD DeleteRegKeyDefaultValue(HKEY baseKey,
const nsString& keyName);
private:
PRBool mCheckedThisSession;

View File

@ -1,7 +1,6 @@
af
ar
be
bg
ca
cs
da
@ -18,7 +17,6 @@ ga-IE
gu-IN
he
hu
hy-AM
id
it
ja
@ -38,9 +36,7 @@ pt-BR
pt-PT
ro
ru
si
sk
sl
sq
sr
sv-SE

View File

@ -7,8 +7,4 @@
<!ENTITY focusSearch1.key "f">
<!ENTITY focusSearch2.key "k">
<!ENTITY filter.label "Search:">
<!ENTITY filter.accesskey "S">
<!ENTITY clear.label "Clear">
<!ENTITY clear.accesskey "l">
<!ENTITY filter.emptytext "Search">

View File

@ -84,8 +84,11 @@ MOZ_CHROME_FILE_FORMAT = @MOZ_CHROME_FILE_FORMAT@
MOZ_WIDGET_TOOLKIT = @MOZ_WIDGET_TOOLKIT@
MOZ_GFX_TOOLKIT = @MOZ_GFX_TOOLKIT@
MOZ_DFB = @MOZ_DFB@
MOZ_X11 = @MOZ_X11@
MOZ_PANGO = @MOZ_PANGO@
MOZ_JS_LIBS = @MOZ_JS_LIBS@
MOZ_DEBUG = @MOZ_DEBUG@

View File

@ -80,7 +80,6 @@ cairo-atsui.h
cairo-beos.h
cairo-ft.h
cairo-glitz.h
cairo-nquartz.h
cairo-os2.h
cairo-pdf.h
cairo-ps.h
@ -88,6 +87,8 @@ cairo-quartz.h
cairo-win32.h
cairo-xlib.h
cairo-xlib-xrender.h
cairo-directfb.h
cairo-qpainter.h
#endif
callconv.h
Carbon/Carbon.h

View File

@ -50,7 +50,7 @@ sub daysFromBuildID
{
my ($buildid,) = @_;
my ($y, $m, $d, $h) = ($buildid =~ /^(\d{4})(\d{2})(\d{2})(\d{2})$/);
my ($y, $m, $d, $h) = ($buildid =~ /^(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})$/);
$d || die("Unrecognized buildid string.");
my $secondstodays = 60 * 60 * 24;

View File

@ -965,7 +965,7 @@ MOZ_PNG_LIBS='$(call EXPAND_LIBNAME_PATH,mozpng,$(DEPTH)/modules/libimg/png)'
MOZ_JS_LIBS='-L$(LIBXUL_DIST)/bin -lmozjs'
DYNAMIC_XPCOM_LIBS='-L$(LIBXUL_DIST)/bin -lxpcom -lxpcom_core'
MOZ_FIX_LINK_PATHS='-Wl,-rpath-link,$(LIBXUL_DIST)/bin'
MOZ_FIX_LINK_PATHS='-Wl,-rpath-link,$(LIBXUL_DIST)/bin -Wl,-rpath-link,$(PREFIX)/lib'
XPCOM_FROZEN_LDOPTS='-L$(LIBXUL_DIST)/bin -lxpcom'
LIBXUL_LIBS='$(XPCOM_FROZEN_LDOPTS) -lxul'
XPCOM_GLUE_LDOPTS='$(LIBXUL_DIST)/lib/$(LIB_PREFIX)xpcomglue_s.$(LIB_SUFFIX) $(XPCOM_FROZEN_LDOPTS)'
@ -4708,6 +4708,7 @@ MOZ_ARG_HEADER(Toolkit Options)
OS/2 - cairo-os2
Win32 - cairo-windows
WinCE - windows
Gtk2 with DirectFB - cairo-gtk2-dfb
* - cairo-gtk2
* - cairo-qt],
[ _DEFAULT_TOOLKIT=$enableval ],
@ -4716,6 +4717,8 @@ MOZ_ARG_HEADER(Toolkit Options)
if test "$_DEFAULT_TOOLKIT" = "photon" \
-o "$_DEFAULT_TOOLKIT" = "cairo-windows" \
-o "$_DEFAULT_TOOLKIT" = "cairo-gtk2" \
-o "$_DEFAULT_TOOLKIT" = "cairo-gtk2-dfb" \
-o "$_DEFAULT_TOOLKIT" = "cairo-gtk2-x11" \
-o "$_DEFAULT_TOOLKIT" = "cairo-qt" \
-o "$_DEFAULT_TOOLKIT" = "cairo-beos" \
-o "$_DEFAULT_TOOLKIT" = "cairo-os2" \
@ -4726,11 +4729,7 @@ MOZ_ARG_HEADER(Toolkit Options)
dnl so ignore everything after the first comma (",").
MOZ_WIDGET_TOOLKIT=`echo "$_DEFAULT_TOOLKIT" | sed -e "s/,.*$//"`
else
if test "$no_x" != "yes"; then
AC_MSG_ERROR([Toolkit must be cairo-gtk2 or cairo-qt.])
else
AC_MSG_ERROR([Toolkit must be $_PLATFORM_DEFAULT_TOOLKIT (if supported).])
fi
AC_MSG_ERROR([You must specify a default toolkit (perhaps $_PLATFORM_DEFAULT_TOOLKIT).])
fi
AC_DEFINE_UNQUOTED(MOZ_DEFAULT_TOOLKIT,"$MOZ_WIDGET_TOOLKIT")
@ -4750,24 +4749,51 @@ cairo-windows)
MOZ_GFX_TOOLKIT=cairo
;;
cairo-gtk2)
cairo-gtk2|cairo-gtk2-x11)
MOZ_WIDGET_TOOLKIT=gtk2
MOZ_GFX_TOOLKIT=cairo
MOZ_ENABLE_GTK2=1
MOZ_ENABLE_XREMOTE=1
AC_DEFINE(MOZ_X11)
MOZ_X11=1
TK_CFLAGS='$(MOZ_GTK2_CFLAGS)'
TK_LIBS='$(MOZ_GTK2_LIBS)'
AC_DEFINE(MOZ_WIDGET_GTK2)
;;
cairo-gtk2-dfb)
MOZ_WIDGET_TOOLKIT=gtk2
MOZ_GFX_TOOLKIT=cairo
MOZ_ENABLE_GTK2=1
AC_DEFINE(MOZ_DFB)
MOZ_DFB=1
TK_CFLAGS='$(MOZ_GTK2_CFLAGS)'
TK_LIBS='$(MOZ_GTK2_LIBS)'
AC_DEFINE(MOZ_WIDGET_GTK2)
if test "$no_x" != "yes"; then
AC_MSG_WARN([Disabling X when DirectFB is specified.])
no_x=yes
fi
;;
cairo-qt)
MOZ_WIDGET_TOOLKIT=qt
MOZ_GFX_TOOLKIT=cairo
MOZ_ENABLE_QT=1
MOZ_ENABLE_XREMOTE=1
AC_DEFINE(MOZ_X11)
MOZ_X11=1
TK_CFLAGS='$(MOZ_QT_CFLAGS)'
TK_LIBS='$(MOZ_QT_LIBS)'
AC_DEFINE(MOZ_WIDGET_QT)
;;
cairo-beos)
MOZ_WIDGET_TOOLKIT=beos
MOZ_GFX_TOOLKIT=cairo
@ -4807,10 +4833,17 @@ if test "$MOZ_ENABLE_XREMOTE"; then
fi
if test "$COMPILE_ENVIRONMENT"; then
if test "$MOZ_ENABLE_GTK2"
then
PKG_CHECK_MODULES(MOZ_GTK2, gtk+-2.0 >= $GTK2_VERSION gtk+-unix-print-2.0 gdk-x11-2.0 glib-2.0 gobject-2.0)
fi
if test "$MOZ_ENABLE_GTK2"; then
if test "$MOZ_X11"; then
GDK_PACKAGES=gdk-x11-2.0
elif test "$MOZ_DFB"; then
PKG_CHECK_MODULES(MOZ_DFB, directfb >= 1.1.0)
GDK_PACKAGES=directfb
fi
PKG_CHECK_MODULES(MOZ_GTK2, gtk+-2.0 >= $GTK2_VERSION gtk+-unix-print-2.0 glib-2.0 gobject-2.0 $GDK_PACKAGES)
fi
fi # COMPILE_ENVIRONMENT
AC_SUBST(MOZ_DEFAULT_TOOLKIT)
@ -4906,12 +4939,7 @@ AC_SUBST(MOZ_QT_LIBS)
AC_SUBST(MOC)
if test "$MOZ_ENABLE_GTK2" \
|| test "$MOZ_ENABLE_QT"
then
AC_DEFINE(MOZ_X11)
MOZ_X11=1
fi
AC_SUBST(MOZ_DFB)
AC_SUBST(MOZ_X11)
dnl ========================================================
@ -5026,19 +5054,47 @@ fi
AC_DEFINE_UNQUOTED(MOZ_DISTRIBUTION_ID,"$MOZ_DISTRIBUTION_ID")
AC_SUBST(MOZ_DISTRIBUTION_ID)
dnl ========================================================
dnl complex text support off by default
dnl ========================================================
MOZ_PANGO=1
MOZ_ARG_DISABLE_BOOL(pango,
[ --disable-pango Disable usage of Pango ],
MOZ_PANGO=,
MOZ_PANGO=1)
dnl ========================================================
dnl = Xft and Pango
dnl ========================================================
if test "$MOZ_ENABLE_GTK2"
then
PKG_CHECK_MODULES(MOZ_XFT, xft)
AC_SUBST(MOZ_XFT_CFLAGS)
AC_SUBST(MOZ_XFT_LIBS)
if test "$MOZ_X11"; then
PKG_CHECK_MODULES(MOZ_XFT, xft)
AC_SUBST(MOZ_XFT_CFLAGS)
AC_SUBST(MOZ_XFT_LIBS)
fi
AC_SUBST(MOZ_PANGO)
PKG_CHECK_MODULES(_PANGOCHK, pango >= $PANGO_VERSION)
PKG_CHECK_MODULES(MOZ_PANGO, pango >= $PANGO_VERSION pangocairo >= $PANGO_VERSION pangoft2 >= $PANGO_VERSION)
AC_SUBST(MOZ_PANGO_CFLAGS)
AC_SUBST(MOZ_PANGO_LIBS)
if test "$MOZ_PANGO"
then
PKG_CHECK_MODULES(MOZ_PANGO, pango >= $PANGO_VERSION pangocairo >= $PANGO_VERSION pangoft2 >= $PANGO_VERSION)
AC_SUBST(MOZ_PANGO_CFLAGS)
AC_SUBST(MOZ_PANGO_LIBS)
AC_DEFINE(MOZ_PANGO)
else
PKG_CHECK_MODULES(MOZ_PANGO, pango >= $PANGO_VERSION pangoft2 >= $PANGO_VERSION)
AC_SUBST(MOZ_PANGO_CFLAGS)
AC_SUBST(MOZ_PANGO_LIBS)
PKG_CHECK_MODULES(FT2, freetype2 > 6.1.0 fontconfig)
AC_SUBST(FT2_CFLAGS)
AC_SUBST(FT2_LIBS)
fi
fi
dnl ========================================================

View File

@ -223,9 +223,7 @@ public:
virtual void SetBaseTarget(const nsAString &aBaseTarget) = 0;
/**
* Return a standard name for the document's character set. This
* will trigger a startDocumentLoad if necessary to answer the
* question.
* Return a standard name for the document's character set.
*/
const nsCString& GetDocumentCharacterSet() const
{

View File

@ -76,8 +76,23 @@ interface nsIFrameLoader : nsISupports
readonly attribute boolean depthTooGreat;
};
[scriptable, uuid(feaf9285-05ac-4898-a69f-c3bd350767e4)]
[scriptable, uuid(641c2d90-4ada-4367-bdb1-80831614161d)]
interface nsIFrameLoaderOwner : nsISupports
{
/**
* The frame loader owned by this nsIFrameLoaderOwner
*/
readonly attribute nsIFrameLoader frameLoader;
/**
* Swap frame loaders with the given nsIFrameLoaderOwner. This may
* only be posible in a very limited range of circumstances, or
* never, depending on the object implementing this interface.
*
* @throws NS_ERROR_NOT_IMPLEMENTED if the swapping logic is not
* implemented for the two given frame loader owners.
* @throws NS_ERROR_DOM_SECURITY_ERR if the swap is not allowed on
* security grounds.
*/
void swapFrameLoaders(in nsIFrameLoaderOwner aOtherOwner);
};

View File

@ -82,6 +82,11 @@ public:
virtual void GetScriptCharset(nsAString& charset) = 0;
/**
* Is the script deferred. Currently only supported by HTML scripts.
*/
virtual PRBool GetScriptDeferred() = 0;
void SetScriptLineNumber(PRUint32 aLineNumber)
{
mLineNumber = aLineNumber;

View File

@ -58,6 +58,11 @@ public:
}
return shell;
}
PRBool HasMoreThanOneShell() {
return mDoc->mPresShells.Length() > 1;
}
private:
static void* operator new(size_t) CPP_THROW_NEW { return 0; }
static void operator delete(void*, size_t) {}

View File

@ -1711,6 +1711,8 @@ nsDocument::StartDocumentLoad(const char* aCommand, nsIChannel* aChannel,
mMayStartLayout = PR_FALSE;
mHaveInputEncoding = PR_TRUE;
if (aReset) {
Reset(aChannel, aLoadGroup);
}
@ -3174,6 +3176,10 @@ nsDocument::BeginLoad()
// unblocking it while we know the document is loading.
BlockOnload();
if (mScriptLoader) {
mScriptLoader->BeginDeferringScripts();
}
NS_DOCUMENT_NOTIFY_OBSERVERS(BeginLoad, (this));
}
@ -3417,6 +3423,10 @@ nsDocument::DispatchContentLoadedEvents()
} while (parent);
}
if (mScriptLoader) {
mScriptLoader->EndDeferringScripts();
}
UnblockOnload(PR_TRUE);
}
@ -4959,7 +4969,12 @@ nsDocument::LookupNamespaceURI(const nsAString& aNamespacePrefix,
NS_IMETHODIMP
nsDocument::GetInputEncoding(nsAString& aInputEncoding)
{
return GetCharacterSet(aInputEncoding);
if (mHaveInputEncoding) {
return GetCharacterSet(aInputEncoding);
}
SetDOMStringToNull(aInputEncoding);
return NS_OK;
}
NS_IMETHODIMP

View File

@ -947,6 +947,10 @@ protected:
PRPackedBool mSynchronousDOMContentLoaded:1;
// If true, we have an input encoding. If this is false, then the
// document was created entirely in memory
PRPackedBool mHaveInputEncoding:1;
PRUint8 mXMLDeclarationBits;
PRUint8 mDefaultElementType;

View File

@ -354,7 +354,7 @@ nsDocumentEncoder::SerializeToStringRecursive(nsIDOMNode* aNode,
PRBool aDontSerializeRoot)
{
nsresult rv = NS_OK;
PRBool serializeClonedChildren;
PRBool serializeClonedChildren = PR_FALSE;
nsCOMPtr<nsIDOMNode> maybeFixedNode;
if (mNodeFixup)

View File

@ -22,6 +22,7 @@
*
* Contributor(s):
* Johnny Stenback <jst@netscape.com> (original author)
* Boris Zbarsky <bzbarsky@mit.edu>
*
* Alternatively, the contents of this file may be used under the terms of
* either of the GNU General Public License Version 2 or later (the "GPL"),
@ -65,6 +66,12 @@
#include "nsIScriptSecurityManager.h"
#include "nsFrameLoader.h"
#include "nsIDOMEventTarget.h"
#include "nsIFrame.h"
#include "nsIFrameFrame.h"
#include "nsDOMError.h"
#include "nsPresShellIterator.h"
#include "nsGUIEvent.h"
#include "nsEventDispatcher.h"
#include "nsIURI.h"
#include "nsIURL.h"
@ -281,6 +288,367 @@ nsFrameLoader::Finalize()
mDocShell = nsnull;
}
static void
FirePageHideEvent(nsIDocShellTreeItem* aItem,
nsIDOMEventTarget* aChromeEventHandler)
{
nsPageTransitionEvent event(PR_TRUE, NS_PAGE_HIDE, PR_TRUE);
nsCOMPtr<nsIDOMDocument> doc = do_GetInterface(aItem);
event.target = do_QueryInterface(doc);
nsEventDispatcher::Dispatch(aChromeEventHandler, nsnull, &event);
PRInt32 childCount = 0;
aItem->GetChildCount(&childCount);
nsAutoTArray<nsCOMPtr<nsIDocShellTreeItem>, 8> kids;
kids.AppendElements(childCount);
for (PRInt32 i = 0; i < childCount; ++i) {
aItem->GetChildAt(i, getter_AddRefs(kids[i]));
}
for (PRUint32 i = 0; i < kids.Length(); ++i) {
if (kids[i]) {
FirePageHideEvent(kids[i], aChromeEventHandler);
}
}
}
static void
FirePageShowEvent(nsIDocShellTreeItem* aItem,
nsIDOMEventTarget* aChromeEventHandler)
{
PRInt32 childCount = 0;
aItem->GetChildCount(&childCount);
nsAutoTArray<nsCOMPtr<nsIDocShellTreeItem>, 8> kids;
kids.AppendElements(childCount);
for (PRInt32 i = 0; i < childCount; ++i) {
aItem->GetChildAt(i, getter_AddRefs(kids[i]));
}
for (PRUint32 i = 0; i < kids.Length(); ++i) {
if (kids[i]) {
FirePageShowEvent(kids[i], aChromeEventHandler);
}
}
nsPageTransitionEvent event(PR_TRUE, NS_PAGE_SHOW, PR_TRUE);
nsCOMPtr<nsIDOMDocument> doc = do_GetInterface(aItem);
event.target = do_QueryInterface(doc);
nsEventDispatcher::Dispatch(aChromeEventHandler, nsnull, &event);
}
static void
SetTreeOwnerAndChromeEventHandlerOnDocshellTree(nsIDocShellTreeItem* aItem,
nsIDocShellTreeOwner* aOwner,
nsIDOMEventTarget* aHandler)
{
NS_PRECONDITION(aItem, "Must have item");
#ifdef DEBUG
PRInt32 itemType;
aItem->GetItemType(&itemType);
NS_ASSERTION(itemType == nsIDocShellTreeItem::typeContent,
"How did something else get in here?");
#endif
aItem->SetTreeOwner(aOwner);
nsCOMPtr<nsIDocShell> shell(do_QueryInterface(aItem));
shell->SetChromeEventHandler(aHandler);
PRInt32 childCount = 0;
aItem->GetChildCount(&childCount);
for (PRInt32 i = 0; i < childCount; ++i) {
nsCOMPtr<nsIDocShellTreeItem> item;
aItem->GetChildAt(i, getter_AddRefs(item));
SetTreeOwnerAndChromeEventHandlerOnDocshellTree(item, aOwner, aHandler);
}
}
/**
* Set the type of the treeitem and hook it up to the treeowner.
* @param aItem the treeitem we're wrking working with
* @param aOwningContent the content node that owns aItem
* @param aTreeOwner the relevant treeowner; might be null
* @param aParentType the nsIDocShellTreeItem::GetType of our parent docshell
* @param aParentNode if non-null, the docshell we should be added as a child to
*
* @return whether aItem is top-level content
*/
static PRBool
AddTreeItemToTreeOwner(nsIDocShellTreeItem* aItem, nsIContent* aOwningContent,
nsIDocShellTreeOwner* aOwner, PRInt32 aParentType,
nsIDocShellTreeNode* aParentNode)
{
NS_PRECONDITION(aItem, "Must have docshell treeitem");
NS_PRECONDITION(aOwningContent, "Must have owning content");
nsAutoString value;
PRBool isContent = PR_FALSE;
if (aOwningContent->IsNodeOfType(nsINode::eXUL)) {
aOwningContent->GetAttr(kNameSpaceID_None, nsGkAtoms::type, value);
}
// we accept "content" and "content-xxx" values.
// at time of writing, we expect "xxx" to be "primary" or "targetable", but
// someday it might be an integer expressing priority or something else.
isContent = value.LowerCaseEqualsLiteral("content") ||
StringBeginsWith(value, NS_LITERAL_STRING("content-"),
nsCaseInsensitiveStringComparator());
if (isContent) {
// The web shell's type is content.
aItem->SetItemType(nsIDocShellTreeItem::typeContent);
} else {
// Inherit our type from our parent webshell. If it is
// chrome, we'll be chrome. If it is content, we'll be
// content.
aItem->SetItemType(aParentType);
}
// Now that we have our type set, add ourselves to the parent, as needed.
if (aParentNode) {
aParentNode->AddChild(aItem);
}
PRBool retval = PR_FALSE;
if (aParentType == nsIDocShellTreeItem::typeChrome && isContent) {
retval = PR_TRUE;
PRBool is_primary = value.LowerCaseEqualsLiteral("content-primary");
if (aOwner) {
PRBool is_targetable = is_primary ||
value.LowerCaseEqualsLiteral("content-targetable");
aOwner->ContentShellAdded(aItem, is_primary, is_targetable, value);
}
}
return retval;
}
nsresult
nsFrameLoader::SwapWithOtherLoader(nsFrameLoader* aOther,
nsRefPtr<nsFrameLoader>& aFirstToSwap,
nsRefPtr<nsFrameLoader>& aSecondToSwap)
{
NS_PRECONDITION((aFirstToSwap == this && aSecondToSwap == aOther) ||
(aFirstToSwap == aOther && aSecondToSwap == this),
"Swapping some sort of random loaders?");
nsIContent* ourContent = mOwnerContent;
nsIContent* otherContent = aOther->mOwnerContent;
if (!ourContent || !otherContent) {
// Can't handle this
return NS_ERROR_NOT_IMPLEMENTED;
}
// Make sure there are no same-origin issues
PRBool equal;
nsresult rv =
ourContent->NodePrincipal()->Equals(otherContent->NodePrincipal(), &equal);
if (NS_FAILED(rv) || !equal) {
// Security problems loom. Just bail on it all
return NS_ERROR_DOM_SECURITY_ERR;
}
nsCOMPtr<nsIDocShell> ourDochell = GetExistingDocShell();
nsCOMPtr<nsIDocShell> otherDocshell = aOther->GetExistingDocShell();
if (!ourDochell || !otherDocshell) {
// How odd
return NS_ERROR_NOT_IMPLEMENTED;
}
// To avoid having to mess with session history, avoid swapping
// frameloaders that don't correspond to root same-type docshells.
nsCOMPtr<nsIDocShellTreeItem> ourTreeItem = do_QueryInterface(ourDochell);
nsCOMPtr<nsIDocShellTreeItem> otherTreeItem =
do_QueryInterface(otherDocshell);
nsCOMPtr<nsIDocShellTreeItem> ourRootTreeItem, otherRootTreeItem;
ourTreeItem->GetSameTypeRootTreeItem(getter_AddRefs(ourRootTreeItem));
otherTreeItem->GetSameTypeRootTreeItem(getter_AddRefs(otherRootTreeItem));
if (ourRootTreeItem != ourTreeItem || otherRootTreeItem != otherTreeItem) {
return NS_ERROR_NOT_IMPLEMENTED;
}
// Also make sure that the two docshells are the same type. Otherwise
// swapping is certainly not safe. As far as that goes, make sure we only
// swap typeContent docshells, since otherwise it's hard to get treeowners
// right.
PRInt32 ourType = nsIDocShellTreeItem::typeChrome;
PRInt32 otherType = nsIDocShellTreeItem::typeChrome;
ourTreeItem->GetItemType(&ourType);
otherTreeItem->GetItemType(&otherType);
if (ourType != nsIDocShellTreeItem::typeContent ||
otherType != nsIDocShellTreeItem::typeContent) {
return NS_ERROR_NOT_IMPLEMENTED;
}
// Save off the tree owners, frame elements, chrome event handlers, and
// docshell and document parents before doing anything else.
nsCOMPtr<nsIDocShellTreeOwner> ourOwner, otherOwner;
ourTreeItem->GetTreeOwner(getter_AddRefs(ourOwner));
otherTreeItem->GetTreeOwner(getter_AddRefs(otherOwner));
// Note: it's OK to have null treeowners.
nsCOMPtr<nsIDocShellTreeItem> ourParentItem, otherParentItem;
ourTreeItem->GetParent(getter_AddRefs(ourParentItem));
otherTreeItem->GetParent(getter_AddRefs(otherParentItem));
if (!ourParentItem || !otherParentItem) {
return NS_ERROR_NOT_IMPLEMENTED;
}
nsCOMPtr<nsPIDOMWindow> ourWindow = do_GetInterface(ourDochell);
nsCOMPtr<nsPIDOMWindow> otherWindow = do_GetInterface(otherDocshell);
nsCOMPtr<nsIDOMElement> ourFrameElement =
ourWindow->GetFrameElementInternal();
nsCOMPtr<nsIDOMElement> otherFrameElement =
otherWindow->GetFrameElementInternal();
nsCOMPtr<nsIDOMEventTarget> ourChromeEventHandler =
do_QueryInterface(ourWindow->GetChromeEventHandler());
nsCOMPtr<nsIDOMEventTarget> otherChromeEventHandler =
do_QueryInterface(otherWindow->GetChromeEventHandler());
NS_ASSERTION(SameCOMIdentity(ourFrameElement, ourContent) &&
SameCOMIdentity(otherFrameElement, otherContent) &&
SameCOMIdentity(ourChromeEventHandler, ourContent) &&
SameCOMIdentity(otherChromeEventHandler, otherContent),
"How did that happen, exactly?");
nsCOMPtr<nsIDocument> ourChildDocument =
do_QueryInterface(ourWindow->GetExtantDocument());
nsCOMPtr<nsIDocument> otherChildDocument =
do_QueryInterface(otherWindow->GetExtantDocument());
if (!ourChildDocument || !otherChildDocument) {
// This shouldn't be happening
return NS_ERROR_NOT_IMPLEMENTED;
}
nsCOMPtr<nsIDocument> ourParentDocument =
ourChildDocument->GetParentDocument();
nsCOMPtr<nsIDocument> otherParentDocument =
otherChildDocument->GetParentDocument();
// Make sure to swap docshells between the two frames.
nsIDocument* ourDoc = ourContent->GetCurrentDoc();
nsIDocument* otherDoc = otherContent->GetCurrentDoc();
if (!ourDoc || !otherDoc) {
// Again, how odd, given that we had docshells
return NS_ERROR_NOT_IMPLEMENTED;
}
NS_ASSERTION(ourDoc == ourParentDocument, "Unexpected parent document");
NS_ASSERTION(otherDoc == otherParentDocument, "Unexpected parent document");
nsPresShellIterator iter1(ourDoc);
nsPresShellIterator iter2(otherDoc);
if (iter1.HasMoreThanOneShell() || iter2.HasMoreThanOneShell()) {
return NS_ERROR_NOT_IMPLEMENTED;
}
nsIPresShell* ourShell = ourDoc->GetPrimaryShell();
nsIPresShell* otherShell = otherDoc->GetPrimaryShell();
if (!ourShell || !otherShell) {
return NS_ERROR_NOT_IMPLEMENTED;
}
if (mInSwap || aOther->mInSwap) {
return NS_ERROR_NOT_IMPLEMENTED;
}
mInSwap = aOther->mInSwap = PR_TRUE;
// Fire pagehide events. Note that we do NOT fire these in the normal way,
// but just fire them on the chrome event handlers.
FirePageHideEvent(ourTreeItem, ourChromeEventHandler);
FirePageHideEvent(otherTreeItem, otherChromeEventHandler);
nsIFrame* ourFrame = ourShell->GetPrimaryFrameFor(ourContent);
nsIFrame* otherFrame = otherShell->GetPrimaryFrameFor(otherContent);
if (!ourFrame || !otherFrame) {
mInSwap = aOther->mInSwap = PR_FALSE;
FirePageShowEvent(ourTreeItem, ourChromeEventHandler);
FirePageShowEvent(otherTreeItem, otherChromeEventHandler);
return NS_ERROR_NOT_IMPLEMENTED;
}
nsIFrameFrame* ourFrameFrame = nsnull;
CallQueryInterface(ourFrame, &ourFrameFrame);
if (!ourFrameFrame) {
mInSwap = aOther->mInSwap = PR_FALSE;
FirePageShowEvent(ourTreeItem, ourChromeEventHandler);
FirePageShowEvent(otherTreeItem, otherChromeEventHandler);
return NS_ERROR_NOT_IMPLEMENTED;
}
// OK. First begin to swap the docshells in the two nsIFrames
rv = ourFrameFrame->BeginSwapDocShells(otherFrame);
if (NS_FAILED(rv)) {
mInSwap = aOther->mInSwap = PR_FALSE;
FirePageShowEvent(ourTreeItem, ourChromeEventHandler);
FirePageShowEvent(otherTreeItem, otherChromeEventHandler);
return rv;
}
// Now move the docshells to the right docshell trees. Note that this
// resets their treeowners to null.
ourParentItem->RemoveChild(ourTreeItem);
otherParentItem->RemoveChild(otherTreeItem);
if (ourType == nsIDocShellTreeItem::typeContent) {
ourOwner->ContentShellRemoved(ourTreeItem);
otherOwner->ContentShellRemoved(otherTreeItem);
}
ourParentItem->AddChild(otherTreeItem);
otherParentItem->AddChild(ourTreeItem);
// Restore the correct treeowners
SetTreeOwnerAndChromeEventHandlerOnDocshellTree(ourTreeItem, otherOwner,
otherChromeEventHandler);
SetTreeOwnerAndChromeEventHandlerOnDocshellTree(otherTreeItem, ourOwner,
ourChromeEventHandler);
AddTreeItemToTreeOwner(ourTreeItem, otherContent, otherOwner,
nsIDocShellTreeItem::typeChrome, nsnull);
AddTreeItemToTreeOwner(otherTreeItem, ourContent, ourOwner,
nsIDocShellTreeItem::typeChrome, nsnull);
// SetSubDocumentFor nulls out parent documents on the old child doc if a
// new non-null document is passed in, so just go ahead and remove both
// kids before reinserting in the parent subdoc maps, to avoid
// complications.
ourParentDocument->SetSubDocumentFor(ourContent, nsnull);
otherParentDocument->SetSubDocumentFor(otherContent, nsnull);
ourParentDocument->SetSubDocumentFor(ourContent, otherChildDocument);
otherParentDocument->SetSubDocumentFor(otherContent, ourChildDocument);
ourWindow->SetFrameElementInternal(otherFrameElement);
otherWindow->SetFrameElementInternal(ourFrameElement);
mOwnerContent = otherContent;
aOther->mOwnerContent = ourContent;
aFirstToSwap.swap(aSecondToSwap);
// We shouldn't have changed frames, but be really careful about it
if (ourFrame == ourShell->GetPrimaryFrameFor(ourContent) &&
otherFrame == otherShell->GetPrimaryFrameFor(otherContent)) {
ourFrameFrame->EndSwapDocShells(otherFrame);
}
ourParentDocument->FlushPendingNotifications(Flush_Layout);
otherParentDocument->FlushPendingNotifications(Flush_Layout);
FirePageShowEvent(ourTreeItem, otherChromeEventHandler);
FirePageShowEvent(otherTreeItem, ourChromeEventHandler);
mInSwap = aOther->mInSwap = PR_FALSE;
return NS_OK;
}
NS_IMETHODIMP
nsFrameLoader::Destroy()
{
@ -402,52 +770,13 @@ nsFrameLoader::EnsureDocShell()
PRInt32 parentType;
parentAsItem->GetItemType(&parentType);
nsAutoString value;
PRBool isContent = PR_FALSE;
if (mOwnerContent->IsNodeOfType(nsINode::eXUL)) {
mOwnerContent->GetAttr(kNameSpaceID_None, nsGkAtoms::type, value);
}
// we accept "content" and "content-xxx" values.
// at time of writing, we expect "xxx" to be "primary" or "targetable", but
// someday it might be an integer expressing priority or something else.
isContent = value.LowerCaseEqualsLiteral("content") ||
StringBeginsWith(value, NS_LITERAL_STRING("content-"),
nsCaseInsensitiveStringComparator());
if (isContent) {
// The web shell's type is content.
docShellAsItem->SetItemType(nsIDocShellTreeItem::typeContent);
} else {
// Inherit our type from our parent webshell. If it is
// chrome, we'll be chrome. If it is content, we'll be
// content.
docShellAsItem->SetItemType(parentType);
}
parentAsNode->AddChild(docShellAsItem);
if (parentType == nsIDocShellTreeItem::typeChrome && isContent) {
mIsTopLevelContent = PR_TRUE;
// XXXbz why is this in content code, exactly? We should handle
// this some other way..... Not sure how yet.
nsCOMPtr<nsIDocShellTreeOwner> parentTreeOwner;
parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner));
PRBool is_primary = value.LowerCaseEqualsLiteral("content-primary");
if (parentTreeOwner) {
PRBool is_targetable = is_primary ||
value.LowerCaseEqualsLiteral("content-targetable");
parentTreeOwner->ContentShellAdded(docShellAsItem, is_primary,
is_targetable, value);
}
}
// XXXbz why is this in content code, exactly? We should handle
// this some other way..... Not sure how yet.
nsCOMPtr<nsIDocShellTreeOwner> parentTreeOwner;
parentAsItem->GetTreeOwner(getter_AddRefs(parentTreeOwner));
mIsTopLevelContent =
AddTreeItemToTreeOwner(docShellAsItem, mOwnerContent, parentTreeOwner,
parentType, parentAsNode);
// Make sure all shells have links back to the content element
// in the nearest enclosing chrome shell.

View File

@ -60,7 +60,8 @@ public:
mDepthTooGreat(PR_FALSE),
mIsTopLevelContent(PR_FALSE),
mDestroyCalled(PR_FALSE),
mInDestructor(PR_FALSE)
mInDestructor(PR_FALSE),
mInSwap(PR_FALSE)
{}
~nsFrameLoader() {
@ -75,6 +76,13 @@ public:
nsresult ReallyStartLoading();
void Finalize();
nsIDocShell* GetExistingDocShell() { return mDocShell; }
// The guts of an nsIFrameLoaderOwner::SwapFrameLoader implementation. A
// frame loader owner needs to call this, and pass in the two references to
// nsRefPtrs for frame loaders that need to be swapped.
nsresult SwapWithOtherLoader(nsFrameLoader* aOther,
nsRefPtr<nsFrameLoader>& aFirstToSwap,
nsRefPtr<nsFrameLoader>& aSecondToSwap);
private:
NS_HIDDEN_(nsresult) EnsureDocShell();
@ -84,10 +92,11 @@ private:
nsCOMPtr<nsIDocShell> mDocShell;
nsCOMPtr<nsIURI> mURIToLoad;
nsIContent *mOwnerContent; // WEAK
PRPackedBool mDepthTooGreat;
PRPackedBool mIsTopLevelContent;
PRPackedBool mDestroyCalled;
PRPackedBool mInDestructor;
PRPackedBool mDepthTooGreat : 1;
PRPackedBool mIsTopLevelContent : 1;
PRPackedBool mDestroyCalled : 1;
PRPackedBool mInDestructor : 1;
PRPackedBool mInSwap : 1;
};
#endif

View File

@ -486,6 +486,22 @@ nsImageLoadingContent::LoadImage(const nsAString& aNewURI,
NS_ENSURE_SUCCESS(rv, rv);
// XXXbiesi fire onerror if that failed?
PRBool equal;
if (aNewURI.IsEmpty() &&
doc->GetDocumentURI() &&
NS_SUCCEEDED(doc->GetDocumentURI()->Equals(imageURI, &equal)) &&
equal) {
// Loading an embedded img from the same URI as the document URI will not work
// as a resource cannot recursively embed itself. Attempting to do so generally
// results in having to pre-emptively close down an in-flight HTTP transaction
// and then incurring the significant cost of establishing a new TCP channel.
// This is generally triggered from <img src="">
// In light of that, just skip loading it..
return NS_OK;
}
NS_TryToSetImmutable(imageURI);
return LoadImage(imageURI, aForce, aNotify, doc);

View File

@ -670,6 +670,12 @@ nsObjectLoadingContent::GetFrameLoader(nsIFrameLoader** aFrameLoader)
return NS_OK;
}
NS_IMETHODIMP
nsObjectLoadingContent::SwapFrameLoaders(nsIFrameLoaderOwner* aOtherLoader)
{
return NS_ERROR_NOT_IMPLEMENTED;
}
// nsIObjectLoadingContent
NS_IMETHODIMP
nsObjectLoadingContent::GetActualType(nsACString& aType)

View File

@ -98,6 +98,7 @@ public:
nsCOMPtr<nsIScriptElement> mElement;
PRPackedBool mLoading; // Are we still waiting for a load to complete?
PRPackedBool mDefer; // Is execution defered?
PRPackedBool mIsInline; // Is the script inline or loaded?
nsString mScriptText; // Holds script for loaded scripts
PRUint32 mJSVersion;
@ -125,8 +126,8 @@ nsScriptLoader::~nsScriptLoader()
{
mObservers.Clear();
for (PRInt32 i = 0; i < mPendingRequests.Count(); i++) {
mPendingRequests[i]->FireScriptAvailable(NS_ERROR_ABORT);
for (PRInt32 i = 0; i < mRequests.Count(); i++) {
mRequests[i]->FireScriptAvailable(NS_ERROR_ABORT);
}
// Unblock the kids, in case any of them moved to a different document
@ -379,6 +380,10 @@ nsScriptLoader::ProcessScriptElement(nsIScriptElement *aElement)
nsRefPtr<nsScriptLoadRequest> request = new nsScriptLoadRequest(aElement, version);
NS_ENSURE_TRUE(request, NS_ERROR_OUT_OF_MEMORY);
request->mDefer = mDeferEnabled && aElement->GetScriptDeferred();
PRBool hadPendingRequests = !!GetFirstPendingRequest();
// First check to see if this is an external script
nsCOMPtr<nsIURI> scriptURI = aElement->GetScriptURI();
if (scriptURI) {
@ -448,20 +453,23 @@ nsScriptLoader::ProcessScriptElement(nsIScriptElement *aElement)
// If we've got existing pending requests, add ourselves
// to this list.
if (mPendingRequests.Count() == 0 && ReadyToExecuteScripts() &&
nsContentUtils::IsSafeToRunScript()) {
if (!request->mDefer && !hadPendingRequests &&
ReadyToExecuteScripts() && nsContentUtils::IsSafeToRunScript()) {
return ProcessRequest(request);
}
}
// Add the request to our pending requests list
NS_ENSURE_TRUE(mPendingRequests.AppendObject(request),
// Add the request to our requests list
NS_ENSURE_TRUE(mRequests.AppendObject(request),
NS_ERROR_OUT_OF_MEMORY);
if (request->mDefer) {
return NS_OK;
}
// If there weren't any pending requests before, and this one is
// ready to execute, do that as soon as it's safe.
if (mPendingRequests.Count() == 1 && !request->mLoading &&
ReadyToExecuteScripts()) {
if (!request->mLoading && !hadPendingRequests && ReadyToExecuteScripts()) {
nsContentUtils::AddScriptRunner(new nsRunnableMethod<nsScriptLoader>(this,
&nsScriptLoader::ProcessPendingRequests));
}
@ -612,10 +620,22 @@ nsScriptLoader::EvaluateScript(nsScriptLoadRequest* aRequest,
return rv;
}
nsScriptLoadRequest*
nsScriptLoader::GetFirstPendingRequest()
{
for (PRInt32 i = 0; i < mRequests.Count(); ++i) {
if (!mRequests[i]->mDefer) {
return mRequests[i];
}
}
return nsnull;
}
void
nsScriptLoader::ProcessPendingRequestsAsync()
{
if (mPendingRequests.Count() || !mPendingChildLoaders.IsEmpty()) {
if (GetFirstPendingRequest() || !mPendingChildLoaders.IsEmpty()) {
nsCOMPtr<nsIRunnable> ev = new nsRunnableMethod<nsScriptLoader>(this,
&nsScriptLoader::ProcessPendingRequests);
@ -627,9 +647,10 @@ void
nsScriptLoader::ProcessPendingRequests()
{
nsRefPtr<nsScriptLoadRequest> request;
while (mPendingRequests.Count() && ReadyToExecuteScripts() &&
!(request = mPendingRequests[0])->mLoading) {
mPendingRequests.RemoveObjectAt(0);
while (ReadyToExecuteScripts() &&
(request = GetFirstPendingRequest()) &&
!request->mLoading) {
mRequests.RemoveObject(request);
ProcessRequest(request);
}
@ -800,7 +821,7 @@ nsScriptLoader::OnStreamComplete(nsIStreamLoader* aLoader,
nsresult rv = PrepareLoadedRequest(request, aLoader, aStatus, aStringLen,
aString);
if (NS_FAILED(rv)) {
mPendingRequests.RemoveObject(request);
mRequests.RemoveObject(request);
FireScriptAvailable(rv, request);
}
@ -863,7 +884,7 @@ nsScriptLoader::PrepareLoadedRequest(nsScriptLoadRequest* aRequest,
// inserting the request in the array. However it's an unlikely case
// so if you see this assertion it is likely something else that is
// wrong, especially if you see it more than once.
NS_ASSERTION(mPendingRequests.IndexOf(aRequest) >= 0,
NS_ASSERTION(mRequests.IndexOf(aRequest) >= 0,
"aRequest should be pending!");
// Mark this as loaded
@ -901,3 +922,14 @@ nsScriptLoader::ShouldExecuteScript(nsIDocument* aDocument,
rv = channelPrincipal->Subsumes(docPrincipal, &subsumes);
return NS_SUCCEEDED(rv) && subsumes;
}
void
nsScriptLoader::EndDeferringScripts()
{
mDeferEnabled = PR_FALSE;
for (PRUint32 i = 0; i < mRequests.Count(); ++i) {
mRequests[i]->mDefer = PR_FALSE;
}
ProcessPendingRequests();
}

View File

@ -187,6 +187,24 @@ public:
static PRBool ShouldExecuteScript(nsIDocument* aDocument,
nsIChannel* aChannel);
/**
* Starts deferring deferred scripts and puts them in the mDeferredRequests
* queue instead.
*/
void BeginDeferringScripts()
{
mDeferEnabled = PR_TRUE;
}
/**
* Stops defering scripts and immediately processes the mDeferredRequests
* queue.
*
* WARNING: This function will syncronously execute content scripts, so be
* prepared that the world might change around you.
*/
void EndDeferringScripts();
protected:
/**
* Process any pending requests asyncronously (i.e. off an event) if there
@ -229,14 +247,18 @@ protected:
PRUint32 aStringLen,
const PRUint8* aString);
// Returns the first pending (non deferred) request
nsScriptLoadRequest* GetFirstPendingRequest();
nsIDocument* mDocument; // [WEAK]
nsCOMArray<nsIScriptLoaderObserver> mObservers;
nsCOMArray<nsScriptLoadRequest> mPendingRequests;
nsCOMArray<nsScriptLoadRequest> mRequests;
nsCOMPtr<nsIScriptElement> mCurrentScript;
// XXXbz do we want to cycle-collect these or something? Not sure.
nsTArray< nsRefPtr<nsScriptLoader> > mPendingChildLoaders;
PRUint32 mBlockerCount;
PRPackedBool mEnabled;
PRPackedBool mDeferEnabled;
};
#endif //__nsScriptLoader_h__

View File

@ -84,6 +84,7 @@
#include "nsLayoutStatics.h"
#include "nsDOMError.h"
#include "nsIHTMLDocument.h"
#include "nsIDOM3Document.h"
#include "nsWhitespaceTokenizer.h"
#include "nsIMultiPartChannel.h"
#include "nsIScriptObjectPrincipal.h"
@ -702,9 +703,15 @@ nsXMLHttpRequest::ConvertBodyToText(nsAString& aOutBuffer)
nsresult rv = NS_OK;
nsCAutoString dataCharset;
nsCOMPtr<nsIDocument> document(do_QueryInterface(mDocument));
nsCOMPtr<nsIDOM3Document> document(do_QueryInterface(mDocument));
if (document) {
dataCharset = document->GetDocumentCharacterSet();
nsAutoString inputEncoding;
document->GetInputEncoding(inputEncoding);
if (DOMStringIsNull(inputEncoding)) {
dataCharset.AssignLiteral("UTF-8");
} else {
CopyUTF16toUTF8(inputEncoding, dataCharset);
}
} else {
if (NS_FAILED(DetectCharset(dataCharset)) || dataCharset.IsEmpty()) {
// MS documentation states UTF-8 is default for responseText

View File

@ -192,6 +192,8 @@ _TEST_FILES = test_bug5141.html \
test_NodeIterator_basics_filters.xhtml \
test_NodeIterator_mutations_1.xhtml \
test_NodeIterator_mutations_2.html \
test_bug28293.html \
file_bug28293.sjs \
$(NULL)
libs:: $(_TEST_FILES)

View File

@ -0,0 +1,5 @@
function handleRequest(request, response)
{
response.setHeader("Content-Type", "text/plain", false);
response.write(decodeURIComponent(request.queryString));
}

View File

@ -0,0 +1,99 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=28293
-->
<head>
<title>Test for Bug 28293</title>
<script type="text/javascript" src="/MochiKit/MochiKit.js"></script>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
<script>
res = 'A';
SimpleTest.waitForExplicitFinish();
onload = function () {
res+='2';
s = document.createElement('script');
s.textContent="res+='g';";
s.defer = true;
document.body.appendChild(s);
res+='3';
s = document.createElement('script');
s.src="file_bug28293.sjs?res+='h';";
s.defer = true;
document.body.appendChild(s);
s = document.createElement('script');
s.textContent="res+='i';done()";
s.defer = true;
document.body.appendChild(s);
res+='4';
}
function done() {
is(res, "ABCDEFGHIJ1abcdefM2g34hi", "scripts executed in the wrong order");
ok(!fHadExecuted, "Dynamic script executed too late");
SimpleTest.finish();
}
</script>
</head>
<body>
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=28293">Mozilla Bug 28293</a>
<script defer>
res += 'a';
</script>
<script defer src="data:text/plain,res+='b'"></script>
<script defer>
res += 'c';
</script>
<script>
res += 'B';
</script>
<script>
res += 'C';
s = document.createElement('script');
s.src="file_bug28293.sjs?res+='d';";
s.defer = true;
document.body.appendChild(s);
s = document.createElement('script');
s.textContent="res+='D';";
document.body.appendChild(s);
res += 'E';
</script>
<script>
res += 'F';
document.addEventListener("DOMContentLoaded", function() {
res += '1'
s = document.createElement('script');
s.src="file_bug28293.sjs?res+='M';";
document.body.appendChild(s);
}, false);
res += 'G';
</script>
<script defer>
res += 'e';
</script>
<script src="file_bug28293.sjs?res+='H';"></script>
<script>
res += 'I';
s = document.createElement('script');
s.src="file_bug28293.sjs?fHadExecuted=(res.indexOf('f')>=0);";
document.body.appendChild(s);
res += 'J';
</script>
<script defer>
res += 'f';
</script>
</body>
</html>

View File

@ -375,6 +375,12 @@ protected:
PRUint32 mSaveCount;
/**
* Flag to avoid duplicate calls to InvalidateFrame. Set to true whenever
* Redraw is called, reset to false when Render is called.
*/
PRBool mIsFrameInvalid;
/**
* Draws a rectangle in the given style; used by FillRect and StrokeRect.
*/
@ -551,7 +557,7 @@ NS_NewCanvasRenderingContext2D(nsIDOMCanvasRenderingContext2D** aResult)
nsCanvasRenderingContext2D::nsCanvasRenderingContext2D()
: mValid(PR_FALSE), mOpaque(PR_FALSE), mCanvasElement(nsnull),
mSaveCount(0), mStyleStack(20)
mSaveCount(0), mIsFrameInvalid(PR_FALSE), mStyleStack(20)
{
}
@ -566,6 +572,7 @@ nsCanvasRenderingContext2D::Destroy()
mSurface = nsnull;
mThebes = nsnull;
mValid = PR_FALSE;
mIsFrameInvalid = PR_FALSE;
}
nsresult
@ -737,7 +744,12 @@ nsCanvasRenderingContext2D::Redraw()
if (!mCanvasElement)
return NS_OK;
return mCanvasElement->InvalidateFrame();
if (!mIsFrameInvalid) {
mIsFrameInvalid = PR_TRUE;
return mCanvasElement->InvalidateFrame();
}
return NS_OK;
}
void
@ -855,6 +867,7 @@ nsCanvasRenderingContext2D::Render(gfxContext *ctx)
if (mOpaque)
ctx->SetOperator(op);
mIsFrameInvalid = PR_FALSE;
return rv;
}
@ -1378,7 +1391,7 @@ NS_IMETHODIMP
nsCanvasRenderingContext2D::Clip()
{
mThebes->Clip();
return Redraw();
return NS_OK;
}
NS_IMETHODIMP

View File

@ -41,10 +41,10 @@
#include "nsEvent.h"
#include "nsISupports.h"
// {889792DC-22D8-4d1a-AC3D-58AD7DEBA17B}
// {901B82D5-67C0-45ad-86AE-AB9A6BD74111}
#define NS_IPRIVATECOMPOSITIONEVENT_IID \
{ 0x889792dc, 0x22d8, 0x4d1a, \
{ 0xac, 0x3d, 0x58, 0xad, 0x7d, 0xeb, 0xa1, 0x7b }}
{ 0x901b82d5, 0x67c0, 0x45ad, \
{ 0x86, 0xae, 0xab, 0x9a, 0x6b, 0xd7, 0x41, 0x11 } }
class nsIPrivateCompositionEvent : public nsISupports {
@ -52,8 +52,6 @@ public:
NS_DECLARE_STATIC_IID_ACCESSOR(NS_IPRIVATECOMPOSITIONEVENT_IID)
NS_IMETHOD GetCompositionReply(struct nsTextEventReply** aReply) = 0;
NS_IMETHOD GetReconversionReply(nsReconversionEventReply** aReply) = 0;
NS_IMETHOD GetQueryCaretRectReply(nsQueryCaretRectEventReply** aReply) = 0;
};
NS_DEFINE_STATIC_IID_ACCESSOR(nsIPrivateCompositionEvent,

View File

@ -788,12 +788,6 @@ NS_METHOD nsDOMEvent::DuplicatePrivateData()
isInputEvent = PR_TRUE;
break;
}
case NS_RECONVERSION_EVENT:
{
newEvent = new nsReconversionEvent(PR_FALSE, msg, nsnull);
isInputEvent = PR_TRUE;
break;
}
case NS_MOUSE_SCROLL_EVENT:
{
nsMouseScrollEvent* mouseScrollEvent =
@ -885,12 +879,6 @@ NS_METHOD nsDOMEvent::DuplicatePrivateData()
static_cast<nsUIEvent*>(mEvent)->detail);
break;
}
case NS_QUERYCARETRECT_EVENT:
{
newEvent = new nsQueryCaretRectEvent(PR_FALSE, msg, nsnull);
isInputEvent = PR_TRUE;
break;
}
case NS_PAGETRANSITION_EVENT:
{
newEvent =

View File

@ -370,8 +370,7 @@ nsDOMUIEvent::GetPreventDefault(PRBool* aReturn)
NS_METHOD nsDOMUIEvent::GetCompositionReply(nsTextEventReply** aReply)
{
if((mEvent->eventStructType == NS_RECONVERSION_EVENT) ||
(mEvent->message == NS_COMPOSITION_START) ||
if((mEvent->message == NS_COMPOSITION_START) ||
(mEvent->message == NS_COMPOSITION_QUERY))
{
*aReply = &(static_cast<nsCompositionEvent*>(mEvent)->theReply);
@ -381,30 +380,6 @@ NS_METHOD nsDOMUIEvent::GetCompositionReply(nsTextEventReply** aReply)
return NS_ERROR_FAILURE;
}
NS_METHOD
nsDOMUIEvent::GetReconversionReply(nsReconversionEventReply** aReply)
{
if (mEvent->eventStructType == NS_RECONVERSION_EVENT)
{
*aReply = &(static_cast<nsReconversionEvent*>(mEvent)->theReply);
return NS_OK;
}
*aReply = nsnull;
return NS_ERROR_FAILURE;
}
NS_METHOD
nsDOMUIEvent::GetQueryCaretRectReply(nsQueryCaretRectEventReply** aReply)
{
if (mEvent->eventStructType == NS_QUERYCARETRECT_EVENT)
{
*aReply = &(static_cast<nsQueryCaretRectEvent*>(mEvent)->theReply);
return NS_OK;
}
*aReply = nsnull;
return NS_ERROR_FAILURE;
}
NS_METHOD
nsDOMUIEvent::DuplicatePrivateData()
{

View File

@ -67,8 +67,6 @@ public:
// nsIPrivateCompositionEvent interface
NS_IMETHOD GetCompositionReply(nsTextEventReply** aReply);
NS_IMETHOD GetReconversionReply(nsReconversionEventReply** aReply);
NS_IMETHOD GetQueryCaretRectReply(nsQueryCaretRectEventReply** aReply);
// Forward to nsDOMEvent
NS_FORWARD_TO_NSDOMEVENT

View File

@ -562,8 +562,6 @@ nsEventDispatcher::CreateEvent(nsPresContext* aPresContext,
static_cast<nsMutationEvent*>(aEvent));
case NS_GUI_EVENT:
case NS_COMPOSITION_EVENT:
case NS_RECONVERSION_EVENT:
case NS_QUERYCARETRECT_EVENT:
case NS_SCROLLPORT_EVENT:
return NS_NewDOMUIEvent(aDOMEvent, aPresContext,
static_cast<nsGUIEvent*>(aEvent));

View File

@ -225,11 +225,7 @@ static const EventDispatchData sCompositionEvents[] = {
{ NS_COMPOSITION_END,
HANDLER(&nsIDOMCompositionListener::HandleEndComposition) },
{ NS_COMPOSITION_QUERY,
HANDLER(&nsIDOMCompositionListener::HandleQueryComposition) },
{ NS_RECONVERSION_QUERY,
HANDLER(&nsIDOMCompositionListener::HandleQueryReconversion) },
{ NS_QUERYCARETRECT,
HANDLER(&nsIDOMCompositionListener::HandleQueryCaretRect) }
HANDLER(&nsIDOMCompositionListener::HandleQueryComposition) }
};
static const EventDispatchData sTextEvents[] = {

View File

@ -3001,6 +3001,13 @@ nsGenericHTMLFrameElement::GetFrameLoader(nsIFrameLoader **aFrameLoader)
return NS_OK;
}
NS_IMETHODIMP
nsGenericHTMLFrameElement::SwapFrameLoaders(nsIFrameLoaderOwner* aOtherOwner)
{
// We don't support this yet
return NS_ERROR_NOT_IMPLEMENTED;
}
nsresult
nsGenericHTMLFrameElement::LoadSrc()
{

View File

@ -408,6 +408,8 @@ nsHTMLMediaElement::nsHTMLMediaElement(nsINodeInfo *aNodeInfo, PRBool aFromParse
nsHTMLMediaElement::~nsHTMLMediaElement()
{
if (mDecoder)
mDecoder->Stop();
}
NS_IMETHODIMP
@ -513,6 +515,9 @@ nsresult nsHTMLMediaElement::BindToTree(nsIDocument* aDocument, nsIContent* aPar
void nsHTMLMediaElement::UnbindFromTree(PRBool aDeep,
PRBool aNullParent)
{
if (!mPaused && mNetworkState != nsIDOMHTMLMediaElement::EMPTY)
Pause();
nsGenericHTMLElement::UnbindFromTree(aDeep, aNullParent);
}

View File

@ -338,6 +338,7 @@ public:
virtual already_AddRefed<nsIURI> GetScriptURI();
virtual void GetScriptText(nsAString& text);
virtual void GetScriptCharset(nsAString& charset);
virtual PRBool GetScriptDeferred();
// nsIContent
virtual nsresult BindToTree(nsIDocument* aDocument, nsIContent* aParent,
@ -524,6 +525,15 @@ nsHTMLScriptElement::GetScriptCharset(nsAString& charset)
GetCharset(charset);
}
PRBool
nsHTMLScriptElement::GetScriptDeferred()
{
PRBool defer;
GetDefer(&defer);
return defer;
}
PRBool
nsHTMLScriptElement::HasScriptContent()
{

View File

@ -143,10 +143,10 @@ nsresult nsHTMLVideoElement::BindToTree(nsIDocument* aDocument, nsIContent* aPar
void nsHTMLVideoElement::UnbindFromTree(PRBool aDeep,
PRBool aNullParent)
{
nsHTMLMediaElement::UnbindFromTree(aDeep, aNullParent);
if (mDecoder)
mDecoder->ElementUnavailable();
nsHTMLMediaElement::UnbindFromTree(aDeep, aNullParent);
}
nsresult nsHTMLVideoElement::InitializeDecoder(nsAString& aChosenMediaResource)

View File

@ -317,6 +317,9 @@ private:
// the metadata then it should start playing.
PRPackedBool mPlayAfterLoad;
// True if we are registered with the observer service for shutdown.
PRPackedBool mNotifyOnShutdown;
/******
* The following member variables can be accessed from any thread.
******/

View File

@ -260,6 +260,7 @@ nsOggDecoder::nsOggDecoder() :
mVideoNextFrameTime(0.0),
mLoadInProgress(PR_FALSE),
mPlayAfterLoad(PR_FALSE),
mNotifyOnShutdown(PR_FALSE),
mVideoCurrentFrameTime(0.0),
mInitialVolume(1.0),
mAudioRate(0),
@ -286,15 +287,6 @@ PRBool nsOggDecoder::Init()
mDecodeEvent = new nsVideoDecodeEvent(this);
mPresentationEvent = new nsVideoPresentationEvent(this);
nsCOMPtr<nsIObserverService> observerService =
do_GetService("@mozilla.org/observer-service;1");
if (observerService) {
observerService->AddObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID, PR_FALSE);
}
else {
NS_WARNING("Could not get an observer service. Video decoding events may not shutdown cleanly.");
}
return mFirstFrameLock &&
mFirstFrameCondVar &&
mDecodeEvent && mDecodeEvent->Init() &&
@ -473,6 +465,20 @@ nsresult nsOggDecoder::Play()
StartPlaybackThreads();
}
if (!mNotifyOnShutdown) {
nsCOMPtr<nsIObserverService> observerService =
do_GetService("@mozilla.org/observer-service;1");
if (observerService) {
mNotifyOnShutdown =
NS_SUCCEEDED(observerService->AddObserver(this,
NS_XPCOM_SHUTDOWN_OBSERVER_ID,
PR_FALSE));
}
else {
NS_WARNING("Could not get an observer service. Video decoding events may not shutdown cleanly.");
}
}
return NS_OK;
}
@ -514,6 +520,15 @@ void nsOggDecoder::Stop()
}
mPaused = PR_TRUE;
mVideoCurrentFrameTime = 0.0;
if (mNotifyOnShutdown) {
nsCOMPtr<nsIObserverService> observerService =
do_GetService("@mozilla.org/observer-service;1");
if (observerService) {
mNotifyOnShutdown = PR_FALSE;
observerService->RemoveObserver(this, NS_XPCOM_SHUTDOWN_OBSERVER_ID);
}
}
}
void nsOggDecoder::HandleVideoData(int track_num, OggPlayVideoData* video_data) {

View File

@ -173,7 +173,6 @@ nsresult nsVideoDecoder::StartProgress()
nsresult nsVideoDecoder::StopProgress()
{
return NS_OK;
nsresult rv = NS_OK;
if (mProgressTimer) {
rv = mProgressTimer->Cancel();

Binary file not shown.

View File

@ -52,8 +52,10 @@ _TEST_FILES = test_autoplay.html \
test_paused.html \
test_playbackRate.html \
test_readyState.html \
test_start.html \
$(NULL)
test_start.html \
# test_bug448534.html \
320x240.ogg \
$(NULL)
libs:: $(_TEST_FILES)
$(INSTALL) $(foreach f,$^,"$f") $(DEPTH)/_tests/testing/mochitest/tests/$(relativesrcdir)

View File

@ -0,0 +1,51 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=448534
-->
<head>
<title>Test for Bug 448534</title>
<script type="text/javascript" src="/MochiKit/MochiKit.js"></script>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body>
<a target="_blank" href="https://bugzilla.mozilla.org/show_bug.cgi?id=448535">Mozilla Bug 448534</a>
<!-- Ogg video obtained from Theora test suite: http://v2v.cc/~j/theora_testsuite/ -->
<video id='v'
src='320x240.ogg'
onplay='return started();'
onpause='return stopped();'></video>
<pre id="test">
<script class="testbody" type="text/javascript">
var v = $('v');
var played = false;
var passed = false;
function started() {
ok(!v.paused, "Video should not be paused while playing");
v.parentNode.removeChild(v);
played = true;
return false;
}
function stopped() {
ok(v.paused, "Video should be paused after removing from the Document");
passed = true;
return false;
}
setTimeout(function () {
ok(played, "Video did not send play event");
ok(passed, "Video was not paused when removed from the Document");
SimpleTest.finish();
return false;
}, 6000);
v.play();
SimpleTest.waitForExplicitFinish();
</script>
</pre>
</body>
</html>

View File

@ -256,12 +256,8 @@ nsSVGAElement::IsLink(nsIURI** aURI) const
nsIContent::ATTR_VALUE_NO_MATCH) {
nsCOMPtr<nsIURI> baseURI = GetBaseURI();
// Get absolute URI
// XXX: should really be using href->GetStringValue(), but nsSVGElement::
// ParseAttribute has set the nsAttrValue type to eSVGValue, so we need
// to use the more expensive ToString (generates, rather than fetches).
nsAutoString hrefStr;
href->ToString(hrefStr);
nsContentUtils::NewURIWithDocumentCharset(aURI, hrefStr,
nsContentUtils::NewURIWithDocumentCharset(aURI,
mStringAttributes[HREF].GetAnimValue(),
GetOwnerDoc(), baseURI);
// must promise out param is non-null if we return true
return !!*aURI;
@ -274,7 +270,7 @@ nsSVGAElement::IsLink(nsIURI** aURI) const
void
nsSVGAElement::GetLinkTarget(nsAString& aTarget)
{
GetAttr(kNameSpaceID_None, nsGkAtoms::target, aTarget);
aTarget = mStringAttributes[TARGET].GetAnimValue();
if (aTarget.IsEmpty()) {
static nsIContent::AttrValuesArray sShowVals[] =

View File

@ -641,6 +641,24 @@ nsSVGElement::ResetOldStyleBaseType(nsISVGValue *svg_value)
}
}
nsChangeHint
nsSVGElement::GetAttributeChangeHint(const nsIAtom* aAttribute,
PRInt32 aModType) const
{
nsChangeHint retval =
nsSVGElementBase::GetAttributeChangeHint(aAttribute, aModType);
if (aAttribute == nsGkAtoms::requiredFeatures ||
aAttribute == nsGkAtoms::requiredExtensions ||
aAttribute == nsGkAtoms::systemLanguage) {
// It would be nice to only reconstruct the frame if the value returned by
// NS_SVG_PassesConditionalProcessingTests has changed, but we don't know
// that
NS_UpdateHint(retval, nsChangeHint_ReconstructFrame);
}
return retval;
}
PRBool
nsSVGElement::IsNodeOfType(PRUint32 aFlags) const
{

View File

@ -87,6 +87,9 @@ public:
virtual nsresult UnsetAttr(PRInt32 aNameSpaceID, nsIAtom* aAttribute,
PRBool aNotify);
virtual nsChangeHint GetAttributeChangeHint(const nsIAtom* aAttribute,
PRInt32 aModType) const;
virtual PRBool IsNodeOfType(PRUint32 aFlags) const;
virtual already_AddRefed<nsIURI> GetBaseURI() const;

View File

@ -189,6 +189,10 @@ ElementSupportsAttributes(const nsIAtom *aTagName, PRUint16 aAttr)
PRBool
NS_SVG_PassesConditionalProcessingTests(nsIContent *aContent)
{
if (!aContent->IsNodeOfType(nsINode::eELEMENT)) {
return PR_FALSE;
}
if (!ElementSupportsAttributes(aContent->Tag(), ATTRS_CONDITIONAL)) {
return PR_TRUE;
}

View File

@ -63,6 +63,7 @@
#include "imgIContainer.h"
#include "gfxIImageFrame.h"
#include "nsIImage.h"
#include "nsNetUtil.h"
#include "nsSVGAnimatedPreserveAspectRatio.h"
#include "nsSVGPreserveAspectRatio.h"
#include "nsIInterfaceRequestorUtils.h"
@ -5194,10 +5195,11 @@ public:
NS_FORWARD_NSIDOMNODE(nsSVGFEImageElementBase::)
NS_FORWARD_NSIDOMELEMENT(nsSVGFEImageElementBase::)
virtual nsresult Clone(nsINodeInfo *aNodeInfo, nsINode **aResult) const;
// nsSVGElement
virtual void DidChangeString(PRUint8 aAttrEnum, PRBool aDoSetAttr);
virtual nsresult AfterSetAttr(PRInt32 aNamespaceID, nsIAtom* aName,
const nsAString* aValue, PRBool aNotify);
// nsIContent
virtual nsresult Clone(nsINodeInfo *aNodeInfo, nsINode **aResult) const;
virtual nsresult BindToTree(nsIDocument* aDocument, nsIContent* aParent,
nsIContent* aBindingParent,
@ -5218,6 +5220,8 @@ private:
// Invalidate users of the filter containing this element.
void Invalidate();
nsresult LoadSVGImage(PRBool aForce, PRBool aNotify);
protected:
virtual PRBool OperatesOnSRGB(nsSVGFilterInstance*,
PRUint32, Image*) { return PR_TRUE; }
@ -5293,25 +5297,25 @@ nsSVGFEImageElement::Init()
}
//----------------------------------------------------------------------
// nsIContent methods:
nsresult
nsSVGFEImageElement::AfterSetAttr(PRInt32 aNamespaceID, nsIAtom* aName,
const nsAString* aValue, PRBool aNotify)
nsSVGFEImageElement::LoadSVGImage(PRBool aForce, PRBool aNotify)
{
if (aNamespaceID == kNameSpaceID_XLink && aName == nsGkAtoms::href) {
nsAutoString href;
if (GetAttr(kNameSpaceID_XLink, nsGkAtoms::href, href)) {
// Note: no need to notify here; since we're just now being bound
// we don't have any frames or anything yet.
LoadImage(href, PR_FALSE, PR_FALSE);
}
}
// resolve href attribute
nsCOMPtr<nsIURI> baseURI = GetBaseURI();
return nsSVGFEImageElementBase::AfterSetAttr(aNamespaceID, aName,
aValue, aNotify);
nsAutoString href(mStringAttributes[HREF].GetAnimValue());
href.Trim(" \t\n\r");
if (baseURI && !href.IsEmpty())
NS_MakeAbsoluteURI(href, href, baseURI);
return LoadImage(href, aForce, aNotify);
}
//----------------------------------------------------------------------
// nsIContent methods:
nsresult
nsSVGFEImageElement::BindToTree(nsIDocument* aDocument, nsIContent* aParent,
nsIContent* aBindingParent,
@ -5324,12 +5328,9 @@ nsSVGFEImageElement::BindToTree(nsIDocument* aDocument, nsIContent* aParent,
// Our base URI may have changed; claim that our URI changed, and the
// nsImageLoadingContent will decide whether a new image load is warranted.
nsAutoString href;
if (GetAttr(kNameSpaceID_XLink, nsGkAtoms::href, href)) {
// Note: no need to notify here; since we're just now being bound
// we don't have any frames or anything yet.
LoadImage(href, PR_FALSE, PR_FALSE);
}
// Note: no need to notify here; since we're just now being bound
// we don't have any frames or anything yet.
LoadSVGImage(PR_FALSE, PR_FALSE);
return rv;
}
@ -5433,6 +5434,16 @@ nsSVGFEImageElement::GetStringInfo()
NS_ARRAY_LENGTH(sStringInfo));
}
void
nsSVGFEImageElement::DidChangeString(PRUint8 aAttrEnum, PRBool aDoSetAttr)
{
nsSVGFEImageElementBase::DidChangeString(aAttrEnum, aDoSetAttr);
if (aAttrEnum == HREF) {
LoadSVGImage(PR_TRUE, PR_TRUE);
}
}
//----------------------------------------------------------------------
// imgIDecoderObserver methods
@ -5655,8 +5666,6 @@ nsSVGFEDisplacementMapElement::Filter(nsSVGFilterInstance *instance,
return NS_OK;
}
NS_ASSERTION(instance->GetSurfaceRect().Size() == instance->GetFilterSpaceSize(),
"Surface size optimization should have been disabled, see ComputeNeededSourceBBoxes");
PRInt32 width = instance->GetSurfaceWidth();
PRInt32 height = instance->GetSurfaceHeight();

View File

@ -99,7 +99,7 @@ public:
virtual nsresult Clone(nsINodeInfo *aNodeInfo, nsINode **aResult) const;
protected:
void GetSrc(nsAString& src);
nsresult LoadSVGImage(PRBool aForce, PRBool aNotify);
virtual LengthAttributesInfo GetLengthInfo();
virtual StringAttributesInfo GetStringInfo();
@ -255,13 +255,6 @@ nsSVGImageElement::DidChangeString(PRUint8 aAttrEnum, PRBool aDoSetAttr)
nsSVGImageElementBase::DidChangeString(aAttrEnum, aDoSetAttr);
if (aAttrEnum == HREF) {
nsAutoString href;
GetSrc(href);
#ifdef DEBUG_tor
fprintf(stderr, "nsSVGImageElement - URI <%s>\n", ToNewCString(href));
#endif
// If caller is not chrome and dom.disable_image_src_set is true,
// prevent setting image.src by exiting early
if (nsContentUtils::GetBoolPref("dom.disable_image_src_set") &&
@ -269,25 +262,25 @@ nsSVGImageElement::DidChangeString(PRUint8 aAttrEnum, PRBool aDoSetAttr)
return;
}
LoadImage(href, PR_TRUE, PR_TRUE);
LoadSVGImage(PR_TRUE, PR_TRUE);
}
}
//----------------------------------------------------------------------
void nsSVGImageElement::GetSrc(nsAString& src)
nsresult
nsSVGImageElement::LoadSVGImage(PRBool aForce, PRBool aNotify)
{
// resolve href attribute
nsCOMPtr<nsIURI> baseURI = GetBaseURI();
nsAutoString relURIStr(mStringAttributes[HREF].GetAnimValue());
relURIStr.Trim(" \t\n\r");
nsAutoString href(mStringAttributes[HREF].GetAnimValue());
href.Trim(" \t\n\r");
if (baseURI && !relURIStr.IsEmpty())
NS_MakeAbsoluteURI(src, relURIStr, baseURI);
else
src = relURIStr;
if (baseURI && !href.IsEmpty())
NS_MakeAbsoluteURI(href, href, baseURI);
return LoadImage(href, aForce, aNotify);
}
//----------------------------------------------------------------------
@ -305,12 +298,9 @@ nsSVGImageElement::BindToTree(nsIDocument* aDocument, nsIContent* aParent,
// Our base URI may have changed; claim that our URI changed, and the
// nsImageLoadingContent will decide whether a new image load is warranted.
nsAutoString href;
if (GetAttr(kNameSpaceID_XLink, nsGkAtoms::href, href)) {
// Note: no need to notify here; since we're just now being bound
// we don't have any frames or anything yet.
LoadImage(href, PR_FALSE, PR_FALSE);
}
// Note: no need to notify here; since we're just now being bound
// we don't have any frames or anything yet.
LoadSVGImage(PR_FALSE, PR_FALSE);
return rv;
}

View File

@ -79,6 +79,7 @@ public:
virtual already_AddRefed<nsIURI> GetScriptURI();
virtual void GetScriptText(nsAString& text);
virtual void GetScriptCharset(nsAString& charset);
virtual PRBool GetScriptDeferred();
// nsScriptElement
virtual PRBool HasScriptContent();
@ -212,6 +213,12 @@ nsSVGScriptElement::GetScriptCharset(nsAString& charset)
charset.Truncate();
}
PRBool
nsSVGScriptElement::GetScriptDeferred()
{
return PR_FALSE;
}
//----------------------------------------------------------------------
// nsScriptElement methods

View File

@ -81,8 +81,7 @@ nsSVGSwitchElement::MaybeInvalidate()
PRUint32 count = GetChildCount();
for (PRUint32 i = 0; i < count; i++) {
nsIContent * child = GetChildAt(i);
if (child->IsNodeOfType(nsINode::eELEMENT) &&
NS_SVG_PassesConditionalProcessingTests(child)) {
if (NS_SVG_PassesConditionalProcessingTests(child)) {
if (mActiveChild == child) {
return;
@ -108,8 +107,7 @@ nsSVGSwitchElement::UpdateActiveChild()
PRUint32 count = GetChildCount();
for (PRUint32 i = 0; i < count; i++) {
nsIContent * child = GetChildAt(i);
if (child->IsNodeOfType(nsINode::eELEMENT) &&
NS_SVG_PassesConditionalProcessingTests(child)) {
if (NS_SVG_PassesConditionalProcessingTests(child)) {
mActiveChild = child;
return;
}

View File

@ -58,8 +58,8 @@ class nsIAtom;
class nsIPrincipal;
#define NS_IXBLSERVICE_IID \
{ 0x98b28f4e, 0x698f, 0x4f77, \
{ 0xa8, 0x9e, 0x65, 0xf5, 0xd0, 0xde, 0x6a, 0xbf } }
{ 0x8d3b37f5, 0xde7e, 0x4595, \
{ 0xb8, 0x56, 0xf7, 0x11, 0xe8, 0xe7, 0xb5, 0x59 } }
class nsIXBLService : public nsISupports
{
@ -90,6 +90,7 @@ public:
// Hooks up the global key event handlers to the document root.
NS_IMETHOD AttachGlobalKeyHandler(nsPIDOMEventTarget* aTarget)=0;
NS_IMETHOD DetachGlobalKeyHandler(nsPIDOMEventTarget* aTarget)=0;
};

View File

@ -700,6 +700,10 @@ nsXBLService::AttachGlobalKeyHandler(nsPIDOMEventTarget* aTarget)
if (!piTarget)
return NS_ERROR_FAILURE;
// the listener already exists, so skip this
if (contentNode && contentNode->GetProperty(nsGkAtoms::listener))
return NS_OK;
nsCOMPtr<nsIDOMElement> elt(do_QueryInterface(contentNode));
// Create the key handler
@ -720,8 +724,53 @@ nsXBLService::AttachGlobalKeyHandler(nsPIDOMEventTarget* aTarget)
target->AddGroupedEventListener(NS_LITERAL_STRING("keypress"), handler,
PR_FALSE, systemGroup);
// Release. Do this so that only the event receiver holds onto the key handler.
if (contentNode)
return contentNode->SetProperty(nsGkAtoms::listener, handler,
nsPropertyTable::SupportsDtorFunc, PR_TRUE);
// release the handler. The reference will be maintained by the event target,
// and, if there is a content node, the property.
NS_RELEASE(handler);
return NS_OK;
}
//
// DetachGlobalKeyHandler
//
// Removes a key handler added by DeatchGlobalKeyHandler.
//
NS_IMETHODIMP
nsXBLService::DetachGlobalKeyHandler(nsPIDOMEventTarget* aTarget)
{
nsCOMPtr<nsPIDOMEventTarget> piTarget = aTarget;
nsCOMPtr<nsIContent> contentNode(do_QueryInterface(aTarget));
if (!contentNode) // detaching is only supported for content nodes
return NS_ERROR_FAILURE;
// Only attach if we're really in a document
nsCOMPtr<nsIDocument> doc = contentNode->GetCurrentDoc();
if (doc)
piTarget = do_QueryInterface(doc);
if (!piTarget)
return NS_ERROR_FAILURE;
nsIDOMEventListener* handler =
static_cast<nsIDOMEventListener*>(contentNode->GetProperty(nsGkAtoms::listener));
if (!handler)
return NS_ERROR_FAILURE;
nsCOMPtr<nsIDOMEventGroup> systemGroup;
piTarget->GetSystemEventGroup(getter_AddRefs(systemGroup));
nsCOMPtr<nsIDOM3EventTarget> target = do_QueryInterface(piTarget);
target->RemoveGroupedEventListener(NS_LITERAL_STRING("keydown"), handler,
PR_FALSE, systemGroup);
target->RemoveGroupedEventListener(NS_LITERAL_STRING("keyup"), handler,
PR_FALSE, systemGroup);
target->RemoveGroupedEventListener(NS_LITERAL_STRING("keypress"), handler,
PR_FALSE, systemGroup);
contentNode->DeleteProperty(nsGkAtoms::listener);
return NS_OK;
}

View File

@ -88,6 +88,7 @@ class nsXBLService : public nsIXBLService,
// Used by XUL key bindings and for window XBL.
NS_IMETHOD AttachGlobalKeyHandler(nsPIDOMEventTarget* aTarget);
NS_IMETHOD DetachGlobalKeyHandler(nsPIDOMEventTarget* aTarget);
NS_DECL_NSIOBSERVER

View File

@ -356,6 +356,13 @@ nsXBLWindowKeyHandler::WalkHandlers(nsIDOMEvent* aKeyEvent, nsIAtom* aEventType)
}
}
nsCOMPtr<nsIContent> content = do_QueryInterface(el);
// skip keysets that are disabled
if (content && content->AttrValueIs(kNameSpaceID_None, nsGkAtoms::disabled,
nsGkAtoms::_true, eCaseMatters)) {
return NS_OK;
}
WalkHandlersInternal(aKeyEvent, aEventType, mHandler);
nsINativeKeyBindings *nativeBindings;

View File

@ -764,7 +764,6 @@ txMozillaXMLOutput::startHTMLElement(nsIContent* aElement, PRBool aIsHTML)
nsresult
txMozillaXMLOutput::endHTMLElement(nsIContent* aElement)
{
nsresult rv;
nsIAtom *atom = aElement->Tag();
if (mTableState == ADDED_TBODY) {
@ -809,10 +808,11 @@ txMozillaXMLOutput::endHTMLElement(nsIContent* aElement)
aElement->GetAttr(kNameSpaceID_None, txHTMLAtoms::href, value);
nsCOMPtr<nsIURI> baseURI;
rv = NS_NewURI(getter_AddRefs(baseURI), value, nsnull);
NS_ENSURE_SUCCESS(rv, rv);
NS_NewURI(getter_AddRefs(baseURI), value, nsnull);
doc->SetBaseURI(baseURI); // The document checks if it is legal to set this base
if (baseURI) {
doc->SetBaseURI(baseURI); // The document checks if it is legal to set this base
}
}
else if (mCreatingNewDocument && atom == txHTMLAtoms::meta) {
// handle HTTP-EQUIV data

View File

@ -167,8 +167,6 @@
#define XUL_ELEMENT_CONTAINER_CONTENTS_BUILT \
(nsXULElement::eContainerContentsBuilt << XUL_ELEMENT_LAZY_STATE_OFFSET)
class nsIDocShell;
// Global object maintenance
nsICSSParser* nsXULPrototypeElement::sCSSParser = nsnull;
nsIXBLService * nsXULElement::gXBLService = nsnull;
@ -2118,6 +2116,36 @@ nsXULElement::GetFrameLoader(nsIFrameLoader **aFrameLoader)
return NS_OK;
}
nsresult
nsXULElement::SwapFrameLoaders(nsIFrameLoaderOwner* aOtherOwner)
{
nsCOMPtr<nsIContent> otherContent(do_QueryInterface(aOtherOwner));
NS_ENSURE_TRUE(otherContent, NS_ERROR_NOT_IMPLEMENTED);
nsXULElement* otherEl = FromContent(otherContent);
NS_ENSURE_TRUE(otherEl, NS_ERROR_NOT_IMPLEMENTED);
if (otherEl == this) {
// nothing to do
return NS_OK;
}
nsXULSlots *ourSlots = static_cast<nsXULSlots*>(GetExistingDOMSlots());
nsXULSlots *otherSlots =
static_cast<nsXULSlots*>(otherEl->GetExistingDOMSlots());
if (!ourSlots || !ourSlots->mFrameLoader ||
!otherSlots || !otherSlots->mFrameLoader) {
// Can't handle swapping when there is nothing to swap... yet.
return NS_ERROR_NOT_IMPLEMENTED;
}
return
ourSlots->mFrameLoader->SwapWithOtherLoader(otherSlots->mFrameLoader,
ourSlots->mFrameLoader,
otherSlots->mFrameLoader);
}
NS_IMETHODIMP
nsXULElement::GetParentTree(nsIDOMXULMultiSelectControlElement** aTreeElement)
{

View File

@ -625,8 +625,8 @@ public:
nsresult GetStyle(nsIDOMCSSStyleDeclaration** aStyle);
nsresult GetFrameLoader(nsIFrameLoader** aFrameLoader);
nsresult SwapFrameLoaders(nsIFrameLoaderOwner* aOtherOwner);
virtual void RecompileScriptEventListeners();
@ -664,7 +664,7 @@ protected:
nsXULSlots(PtrBits aFlags);
virtual ~nsXULSlots();
nsCOMPtr<nsIFrameLoader> mFrameLoader;
nsRefPtr<nsFrameLoader> mFrameLoader;
};
virtual nsINode::nsSlots* CreateSlots();

View File

@ -441,6 +441,8 @@ nsXULDocument::StartDocumentLoad(const char* aCommand, nsIChannel* aChannel,
mChannel = aChannel;
mHaveInputEncoding = PR_TRUE;
// Get the URI. Note that this should match nsDocShell::OnLoadingSite
nsresult rv =
NS_GetFinalChannelURI(aChannel, getter_AddRefs(mDocumentURI));
@ -1731,6 +1733,14 @@ nsXULDocument::RemoveSubtreeFromDocument(nsIContent* aElement)
// document.
nsresult rv;
if (aElement->NodeInfo()->Equals(nsGkAtoms::keyset, kNameSpaceID_XUL)) {
nsCOMPtr<nsIXBLService> xblService(do_GetService("@mozilla.org/xbl;1"));
if (xblService) {
nsCOMPtr<nsPIDOMEventTarget> piTarget(do_QueryInterface(aElement));
xblService->DetachGlobalKeyHandler(piTarget);
}
}
// 1. Remove any children from the document.
PRUint32 count = aElement->GetChildCount();

View File

@ -945,7 +945,7 @@ morkRow::NewRowCellCursor(morkEnv* ev, mdb_pos inPos)
{
if ( ev->Good() )
{
cursor->mCursor_Pos = inPos;
cursor->mRowCellCursor_Col = inPos;
outCursor = cursor;
}
else

View File

@ -1190,12 +1190,10 @@ nsDocShell::SetChromeEventHandler(nsIDOMEventTarget* aChromeEventHandler)
// Weak reference. Don't addref.
mChromeEventHandler = piTarget;
NS_ASSERTION(!mScriptGlobal,
"SetChromeEventHandler() called after the script global "
"object was created! This means that the script global "
"object in this docshell won't get the right chrome event "
"handler. You really don't want to see this assert, FIX "
"YOUR CODE!");
nsCOMPtr<nsPIDOMWindow> win(do_QueryInterface(mScriptGlobal));
if (win) {
win->SetChromeEventHandler(piTarget);
}
return NS_OK;
}

View File

@ -42,8 +42,8 @@ PEParseRuleWSOnly=Whitespace-only string given to be parsed as rule.
PEDeclDropped=Declaration dropped.
PEDeclSkipped=Skipped to next declaration.
PEUnknownProperty=Unknown property '%1$S'.
PEPropertyParsingError=Error in parsing value for property '%1$S'.
PEExpectEndProperty=Expected end of value for property but found '%1$S'.
PEValueParsingError=Error in parsing value for '%1$S'.
PEExpectEndValue=Expected end of value but found '%1$S'.
PESkipAtRuleEOF=end of unknown at-rule
PEUnknownAtRule=Unrecognized at-rule or error parsing at-rule '%1$S'.
PECharsetRuleEOF=charset string in @charset rule
@ -127,6 +127,8 @@ PEBadDeclOrRuleEnd2=Expected ';' or '}' to terminate declaration but found '%1$S
PEInaccessibleProperty2=Cannot specify value for internal property.
PECommentEOF=end of comment
SEUnterminatedString=Found unclosed string '%1$S'.
PEFontDescExpected=Expected font descriptor but found '%1$S'.
PEUnknownFontDesc=Unknown descriptor '%1$S' in @font-face rule.
PEMQExpectedExpressionStart=Expected '(' to start media query expression but found '%1$S'.
PEMQExpressionEOF=contents of media query expression
PEMQExpectedFeatureName=Expected media feature name but found '%1$S'.

View File

@ -96,6 +96,8 @@ public:
return mChromeEventHandler;
}
virtual void SetChromeEventHandler(nsPIDOMEventTarget* aChromeEventHandler) = 0;
PRBool HasMutationListeners(PRUint32 aMutationEventType) const
{
const nsPIDOMWindow *win;
@ -401,6 +403,10 @@ protected:
{
}
void SetChromeEventHandlerInternal(nsPIDOMEventTarget* aChromeEventHandler) {
mChromeEventHandler = aChromeEventHandler;
}
// These two variables are special in that they're set to the same
// value on both the outer window and the current inner window. Make
// sure you keep them in sync!

View File

@ -44,10 +44,10 @@
/*
* Key pressed / released / typed listener interface.
*/
// {F14B6491-E95B-11d2-9E85-0060089FE59B}
// {93A5A335-AA51-4d32-977D-3680B7722AD5}
#define NS_IDOMCOMPOSITIONLISTENER_IID \
{ 0xf14b6491, 0xe95b, 0x11d2, \
{ 0x9e, 0x85, 0x0, 0x60, 0x8, 0x9f, 0xe5, 0x9b } }
{ 0x93a5a335, 0xaa51, 0x4d32, \
{ 0x97, 0x7d, 0x36, 0x80, 0xb7, 0x72, 0x2a, 0xd5 } }
class nsIDOMCompositionListener : public nsIDOMEventListener {
@ -59,8 +59,6 @@ public:
NS_IMETHOD HandleStartComposition(nsIDOMEvent* aCompositionEvent) = 0;
NS_IMETHOD HandleEndComposition(nsIDOMEvent* aCompositionEvent) = 0;
NS_IMETHOD HandleQueryComposition(nsIDOMEvent* aCompositionEvent) = 0;
NS_IMETHOD HandleQueryReconversion(nsIDOMEvent* aCompositionEvent) = 0;
NS_IMETHOD HandleQueryCaretRect(nsIDOMEvent* aCompositionEvent) = 0;
};
NS_DEFINE_STATIC_IID_ACCESSOR(nsIDOMCompositionListener,

View File

@ -428,6 +428,10 @@ enum nsDOMClassInfoID {
eDOMClassInfo_Geolocation_id,
eDOMClassInfo_Geolocator_id,
// @font-face in CSS
eDOMClassInfo_CSSFontFaceRule_id,
eDOMClassInfo_CSSFontFaceStyleDecl_id,
// WhatWG Video Element
#if defined(MOZ_MEDIA)
eDOMClassInfo_HTMLVideoElement_id,

Some files were not shown because too many files have changed in this diff Show More