Bug 1310385 - Remove support for UndoManager; r=smaug

There hasn't been any traction on this feature, and we keep
paying the maintenance and code size and memory usage penalty
of having this implementation.

We can revive this from VCS history in the future if we decide
to start working on it again.  In the mean time, it's better
to remove it.
This commit is contained in:
Ehsan Akhgari 2016-10-14 20:56:52 -04:00
parent 80ad2ce758
commit 1978fee9f2
28 changed files with 0 additions and 2499 deletions

View File

@ -138,7 +138,6 @@ namespace dom {
class Animation;
class CustomElementRegistry;
class Link;
class UndoManager;
class DOMRect;
class DOMRectList;
class DestinationInsertionPointList;
@ -868,20 +867,6 @@ public:
void GetGridFragments(nsTArray<RefPtr<Grid>>& aResult);
virtual already_AddRefed<UndoManager> GetUndoManager()
{
return nullptr;
}
virtual bool UndoScope()
{
return false;
}
virtual void SetUndoScope(bool aUndoScope, ErrorResult& aError)
{
}
already_AddRefed<Animation>
Animate(JSContext* aContext,
JS::Handle<JSObject*> aKeyframes,

View File

@ -102,7 +102,6 @@
#include "nsRuleProcessorData.h"
#include "nsTextNode.h"
#include "mozilla/dom/NodeListBinding.h"
#include "mozilla/dom/UndoManager.h"
#ifdef MOZ_XUL
#include "nsIXULDocument.h"
@ -531,7 +530,6 @@ nsNodeSupportsWeakRefTearoff::GetWeakReference(nsIWeakReference** aInstancePtr)
FragmentOrElement::nsDOMSlots::nsDOMSlots()
: nsINode::nsSlots(),
mDataset(nullptr),
mUndoManager(nullptr),
mBindingParent(nullptr)
{
}
@ -555,9 +553,6 @@ FragmentOrElement::nsDOMSlots::Traverse(nsCycleCollectionTraversalCallback &cb,
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "mSlots->mAttributeMap");
cb.NoteXPCOMChild(mAttributeMap.get());
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "mSlots->mUndoManager");
cb.NoteXPCOMChild(mUndoManager.get());
if (aIsXUL) {
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "mSlots->mControllers");
cb.NoteXPCOMChild(mControllers);
@ -606,7 +601,6 @@ FragmentOrElement::nsDOMSlots::Unlink(bool aIsXUL)
mShadowRoot = nullptr;
mContainingShadow = nullptr;
mChildrenList = nullptr;
mUndoManager = nullptr;
mCustomElementData = nullptr;
mClassList = nullptr;
}

View File

@ -101,7 +101,6 @@ namespace mozilla {
namespace dom {
class ShadowRoot;
class UndoManager;
class FragmentOrElement : public nsIContent
{
@ -272,12 +271,6 @@ public:
*/
nsDOMStringMap* mDataset; // [Weak]
/**
* The .undoManager property.
* @see nsGenericHTMLElement::GetUndoManager
*/
RefPtr<UndoManager> mUndoManager;
/**
* SMIL Overridde style rules (for SMIL animation of CSS properties)
* @see nsIContent::GetSMILOverrideStyle

View File

@ -217,7 +217,6 @@
#include "mozilla/dom/NodeFilterBinding.h"
#include "mozilla/OwningNonNull.h"
#include "mozilla/dom/TabChild.h"
#include "mozilla/dom/UndoManager.h"
#include "mozilla/dom/WebComponentsBinding.h"
#include "mozilla/dom/CustomElementRegistryBinding.h"
#include "mozilla/dom/CustomElementRegistry.h"
@ -1711,7 +1710,6 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN_INTERNAL(nsDocument)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mOriginalDocument)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mCachedEncoder)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mStateObjectCached)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mUndoManager)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mDocumentTimeline)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mPendingAnimationTracker)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mTemplateContentsOwner)
@ -1795,7 +1793,6 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(nsDocument)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mDOMImplementation)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mImageMaps)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mCachedEncoder)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mUndoManager)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mDocumentTimeline)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mPendingAnimationTracker)
NS_IMPL_CYCLE_COLLECTION_UNLINK(mTemplateContentsOwner)
@ -2955,22 +2952,6 @@ nsDocument::GetAllowPlugins(bool * aAllowPlugins)
return NS_OK;
}
already_AddRefed<UndoManager>
nsDocument::GetUndoManager()
{
Element* rootElement = GetRootElement();
if (!rootElement) {
return nullptr;
}
if (!mUndoManager) {
mUndoManager = new UndoManager(rootElement);
}
RefPtr<UndoManager> undoManager = mUndoManager;
return undoManager.forget();
}
bool
nsDocument::IsElementAnimateEnabled(JSContext* /*unused*/, JSObject* /*unused*/)
{

View File

@ -95,7 +95,6 @@ class EventChainPreVisitor;
namespace dom {
class BoxObject;
class ImageTracker;
class UndoManager;
struct LifecycleCallbacks;
class CallbackFunction;
@ -599,8 +598,6 @@ public:
virtual nsresult GetAllowPlugins(bool* aAllowPlugins) override;
virtual already_AddRefed<mozilla::dom::UndoManager> GetUndoManager() override;
static bool IsElementAnimateEnabled(JSContext* aCx, JSObject* aObject);
static bool IsWebAnimationsEnabled(JSContext* aCx, JSObject* aObject);
virtual mozilla::dom::DocumentTimeline* Timeline() override;
@ -1571,8 +1568,6 @@ private:
// Tracking for plugins in the document.
nsTHashtable< nsPtrHashKey<nsIObjectLoadingContent> > mPlugins;
RefPtr<mozilla::dom::UndoManager> mUndoManager;
RefPtr<mozilla::dom::DocumentTimeline> mDocumentTimeline;
mozilla::LinkedList<mozilla::dom::DocumentTimeline> mTimelines;

View File

@ -1280,7 +1280,6 @@ GK_ATOM(u, "u")
GK_ATOM(ul, "ul")
GK_ATOM(underflow, "underflow")
GK_ATOM(undetermined, "undetermined")
GK_ATOM(undoscope, "undoscope")
GK_ATOM(unload, "unload")
GK_ATOM(unparsedEntityUri, "unparsed-entity-uri")
GK_ATOM(upperFirst, "upper-first")

View File

@ -155,7 +155,6 @@ class SVGSVGElement;
class Touch;
class TouchList;
class TreeWalker;
class UndoManager;
class XPathEvaluator;
class XPathExpression;
class XPathNSResolver;
@ -2378,8 +2377,6 @@ public:
*/
virtual Element* LookupImageElement(const nsAString& aElementId) = 0;
virtual already_AddRefed<mozilla::dom::UndoManager> GetUndoManager() = 0;
virtual mozilla::dom::DocumentTimeline* Timeline() = 0;
virtual mozilla::LinkedList<mozilla::dom::DocumentTimeline>& Timelines() = 0;

View File

@ -1170,10 +1170,6 @@ DOMInterfaces = {
'wrapperCache': False,
},
'UndoManager': {
'implicitJSContext' : [ 'undo', 'redo', 'transact' ],
},
'VTTCue': {
'nativeType': 'mozilla::dom::TextTrackCue'
},

View File

@ -204,10 +204,6 @@ const kEventConstructors = {
return new DownloadEvent(aName, aProps);
},
},
DOMTransactionEvent: { create: function (aName, aProps) {
return new DOMTransactionEvent(aName, aProps);
},
},
DragEvent: { create: function (aName, aProps) {
var e = document.createEvent("dragevent");
e.initDragEvent(aName, aProps.bubbles, aProps.cancelable,

File diff suppressed because it is too large Load Diff

View File

@ -1,106 +0,0 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef mozilla_dom_UndoManager_h
#define mozilla_dom_UndoManager_h
#include "mozilla/dom/UndoManagerBinding.h"
#include "nsCycleCollectionParticipant.h"
#include "nsCOMPtr.h"
#include "nsCOMArray.h"
#include "nsIContent.h"
#include "nsTArray.h"
#include "nsWrapperCache.h"
#include "mozilla/dom/Nullable.h"
class nsITransactionManager;
namespace mozilla {
class ErrorResult;
namespace dom {
class DOMTransaction;
class DOMTransactionCallback;
class UndoManager final : public nsISupports,
public nsWrapperCache
{
friend class TxnScopeGuard;
public:
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(UndoManager)
explicit UndoManager(nsIContent* aNode);
void Transact(JSContext* aCx, DOMTransaction& aTransaction,
bool aMerge, ErrorResult& aRv);
void Undo(JSContext* aCx, ErrorResult& aRv);
void Redo(JSContext* acx, ErrorResult& aRv);
void Item(uint32_t aIndex,
Nullable<nsTArray<RefPtr<DOMTransaction> > >& aItems,
ErrorResult& aRv);
uint32_t GetLength(ErrorResult& aRv);
uint32_t GetPosition(ErrorResult& aRv);
void ClearUndo(ErrorResult& aRv);
void ClearRedo(ErrorResult& aRv);
void Disconnect();
nsISupports* GetParentObject() const
{
return mHostNode;
}
virtual JSObject* WrapObject(JSContext* aCx, JS::Handle<JSObject*> aGivenProto) override
{
return mozilla::dom::UndoManagerBinding::Wrap(aCx, this, aGivenProto);
}
nsITransactionManager* GetTransactionManager();
protected:
virtual ~UndoManager();
nsCOMPtr<nsITransactionManager> mTxnManager;
nsCOMPtr<nsIContent> mHostNode;
/**
* Executes |aTransaction| as a manual transaction.
*/
void ManualTransact(DOMTransaction* aTransaction,
ErrorResult& aRv);
/**
* Executes |aTransaction| as an automatic transaction, calling
* aCallback to do the work.
*/
void AutomaticTransact(DOMTransaction* aTransaction,
DOMTransactionCallback* aCallback,
ErrorResult& aRv);
/**
* Appends the transactions in the undo transaction history at |aIndex|
* to the array |aItems|.
*/
void ItemInternal(uint32_t aIndex,
nsTArray<DOMTransaction*>& aItems,
ErrorResult& aRv);
/**
* Dispatches an event to the undo scope host.
* @param aPreviousPosition The index of the transaction that
* triggered the event.
*/
void DispatchTransactionEvent(JSContext* aCx, const nsAString& aType,
uint32_t aPreviousPosition,
ErrorResult& aRv);
bool mInTransaction;
bool mIsDisconnected;
};
} // namespace dom
} // namespace mozilla
#endif

View File

@ -118,7 +118,6 @@ EXPORTS.mozilla.dom += [
'RadioNodeList.h',
'TextTrackManager.h',
'TimeRanges.h',
'UndoManager.h',
'ValidityState.h',
]
@ -208,7 +207,6 @@ UNIFIED_SOURCES += [
'RadioNodeList.cpp',
'TextTrackManager.cpp',
'TimeRanges.cpp',
'UndoManager.cpp',
'ValidityState.cpp',
'VideoDocument.cpp',
]

View File

@ -90,7 +90,6 @@
#include "mozilla/Preferences.h"
#include "mozilla/dom/FromParser.h"
#include "mozilla/dom/Link.h"
#include "mozilla/dom/UndoManager.h"
#include "mozilla/BloomFilter.h"
#include "nsVariant.h"
@ -809,8 +808,6 @@ nsGenericHTMLElement::SetAttr(int32_t aNameSpaceID, nsIAtom* aName,
{
bool contentEditable = aNameSpaceID == kNameSpaceID_None &&
aName == nsGkAtoms::contenteditable;
bool undoScope = aNameSpaceID == kNameSpaceID_None &&
aName == nsGkAtoms::undoscope;
bool accessKey = aName == nsGkAtoms::accesskey &&
aNameSpaceID == kNameSpaceID_None;
@ -836,11 +833,6 @@ nsGenericHTMLElement::SetAttr(int32_t aNameSpaceID, nsIAtom* aName,
ChangeEditableState(change);
}
if (undoScope) {
rv = SetUndoScopeInternal(true);
NS_ENSURE_SUCCESS(rv, rv);
}
if (accessKey && !aValue.IsEmpty()) {
SetFlags(NODE_HAS_ACCESSKEY);
RegAccessKey();
@ -867,10 +859,6 @@ nsGenericHTMLElement::UnsetAttr(int32_t aNameSpaceID, nsIAtom* aAttribute,
contentEditable = true;
contentEditableChange = GetContentEditableValue() == eTrue ? -1 : 0;
}
else if (aAttribute == nsGkAtoms::undoscope) {
nsresult rv = SetUndoScopeInternal(false);
NS_ENSURE_SUCCESS(rv, rv);
}
else if (aAttribute == nsGkAtoms::accesskey) {
// Have to unregister before clearing flag. See UnregAccessKey
UnregAccessKey();
@ -1782,78 +1770,6 @@ nsGenericHTMLElement::IsInteractiveHTMLContent(bool aIgnoreTabindex) const
(!aIgnoreTabindex && HasAttr(kNameSpaceID_None, nsGkAtoms::tabindex));
}
already_AddRefed<UndoManager>
nsGenericHTMLElement::GetUndoManager()
{
nsDOMSlots* slots = GetExistingDOMSlots();
if (slots && slots->mUndoManager) {
RefPtr<UndoManager> undoManager = slots->mUndoManager;
return undoManager.forget();
} else {
return nullptr;
}
}
bool
nsGenericHTMLElement::UndoScope()
{
nsDOMSlots* slots = GetExistingDOMSlots();
return slots && slots->mUndoManager;
}
void
nsGenericHTMLElement::SetUndoScope(bool aUndoScope, mozilla::ErrorResult& aError)
{
nsresult rv = SetUndoScopeInternal(aUndoScope);
if (NS_FAILED(rv)) {
aError.Throw(rv);
return;
}
// The undoScope property must reflect the undoscope boolean attribute.
if (aUndoScope) {
rv = SetAttr(kNameSpaceID_None, nsGkAtoms::undoscope,
NS_LITERAL_STRING(""), true);
} else {
rv = UnsetAttr(kNameSpaceID_None, nsGkAtoms::undoscope, true);
}
if (NS_FAILED(rv)) {
aError.Throw(rv);
return;
}
}
nsresult
nsGenericHTMLElement::SetUndoScopeInternal(bool aUndoScope)
{
if (aUndoScope) {
nsDOMSlots* slots = DOMSlots();
if (!slots->mUndoManager) {
slots->mUndoManager = new UndoManager(this);
}
} else {
nsDOMSlots* slots = GetExistingDOMSlots();
if (slots && slots->mUndoManager) {
// Clear transaction history and disconnect.
ErrorResult rv;
slots->mUndoManager->ClearRedo(rv);
if (rv.Failed()) {
return rv.StealNSResult();
}
slots->mUndoManager->ClearUndo(rv);
if (rv.Failed()) {
return rv.StealNSResult();
}
slots->mUndoManager->Disconnect();
slots->mUndoManager = nullptr;
}
}
return NS_OK;
}
// static
bool
nsGenericHTMLElement::TouchEventsEnabled(JSContext* aCx, JSObject* aGlobal)

View File

@ -275,10 +275,6 @@ protected:
virtual ~nsGenericHTMLElement() {}
public:
virtual already_AddRefed<mozilla::dom::UndoManager> GetUndoManager() override;
virtual bool UndoScope() override;
virtual void SetUndoScope(bool aUndoScope, mozilla::ErrorResult& aError) override;
/**
* Get width and height, using given image request if attributes are unset.
* Pass a reference to the image request, since the method may change the
@ -1151,8 +1147,6 @@ protected:
*/
bool IsEditableRoot() const;
nsresult SetUndoScopeInternal(bool aUndoScope);
private:
void ChangeEditableState(int32_t aChange);
};

View File

@ -439,11 +439,9 @@ skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop spec
[test_bug803677.html]
[test_bug821307.html]
[test_bug827126.html]
[test_bug827426.html]
[test_bug838582.html]
[test_bug839371.html]
[test_bug839913.html]
[test_bug840877.html]
[test_bug841466.html]
skip-if = (toolkit == 'gonk' && debug) #debug-only failure
[test_bug845057.html]
@ -542,7 +540,6 @@ skip-if = buildapp == 'mulet' || buildapp == 'b2g' || toolkit == 'android' # b2g
[test_style_attributes_reflection.html]
[test_track.html]
[test_ul_attributes_reflection.html]
[test_undoManager.html]
[test_input_files_not_nsIFile.html]
[test_ignoreuserfocus.html]
[test_fragment_form_pointer.html]

View File

@ -1,48 +0,0 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=827426
-->
<head>
<title>Test for Bug 827426</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=827426">Mozilla Bug 827426</a>
<p id="display"></p>
<div id="content">foo</div>
<pre id="test">
<script class="testbody" type="text/javascript">
/** Test for Bug 827426 **/
var elem = document.getElementById("content");
var undoManager = document.undoManager;
var transaction = {
executeAutomatic: function() {
elem.childNodes[0].appendData("bar");
},
};
// Perform transaction
undoManager.transact(transaction, false);
// Make mutation external to UndoManager.
elem.childNodes[0].deleteData(0, 6);
// Call undo/redo a few times and make sure nothing bad happens.
undoManager.undo();
undoManager.redo();
undoManager.undo();
undoManager.redo();
undoManager.undo();
ok(true, "Nothing bad happened with external mutation.");
</script>
</pre>
</body>
</html>

View File

@ -1,36 +0,0 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=840877
-->
<head>
<title>Test for Bug 840877</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=840877">Mozilla Bug 840877</a>
<p id="display"></p>
<div id="content"></div>
<pre id="test">
<script class="testbody" type="text/javascript">
/** Test for Bug 840877 **/
var root = document.documentElement;
var undoMan = document.undoManager;
var newChild = document.createElement("div");
// Removing the documentElement from the document removes the element from the document's undo scope.
document.removeChild(root);
undoMan.transact({ executeAutomatic: function() { root.appendChild(newChild); }}, true);
// Append the document element back so that we don't break mochitests.
document.appendChild(root);
// Element appended by executeAutomatic should be a child of the documentElement.
is(root.childNodes[root.childNodes.length - 1], newChild, "Document element should have child appened by transaction.");
</script>
</pre>
</body>
</html>

View File

@ -1,852 +0,0 @@
<!DOCTYPE HTML>
<html>
<!--
https://bugzilla.mozilla.org/show_bug.cgi?id=617532
-->
<head>
<title>Test for Bug 617532</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=617532">Mozilla Bug 617532</a>
<p id="display"></p>
<div id="content"></div>
<pre id="test">
<script class="testbody" type="text/javascript">
/** Test for Bug 617532 **/
/**
* Tests for typical use cases.
*/
var content = document.getElementById("content");
// Test appending text to a text node.
var textAppend = {
label: "textAppend",
executeAutomatic: function() {
var box = document.getElementById("box");
box.firstChild.appendData(" and more text");
}
};
testTransaction([textAppend],
[getTextMatchFunction("box with text"),
getTextMatchFunction("box with text and more text")]);
// Test replacing text in a text node.
var textReplace = {
label: "textReplace",
executeAutomatic: function() {
var box = document.getElementById("box");
box.firstChild.replaceData(0, 3, "div");
}
};
testTransaction([textReplace],
[getTextMatchFunction("box with text"),
getTextMatchFunction("div with text")]);
// Test inserting text in a text node.
var textInsert = {
label: "textInsert",
executeAutomatic: function() {
var box = document.getElementById("box");
box.firstChild.insertData(0, "a ");
}
};
testTransaction([textInsert],
[getTextMatchFunction("box with text"),
getTextMatchFunction("a box with text")]);
// Test deleting text in a text node.
var textDelete = {
label: "textDelete",
executeAutomatic: function() {
var box = document.getElementById("box");
box.firstChild.deleteData(3, 10);
}
};
testTransaction([textDelete],
[getTextMatchFunction("box with text"),
getTextMatchFunction("box")]);
// Test creating a new attribute.
var createAttribute = {
label: "createAttribute",
executeAutomatic: function() {
var box = document.getElementById("box");
box.setAttribute("data-new", "new");
}
};
testTransaction([createAttribute],
[getAttrAbsentFunction("data-new"),
getAttrIsFunction("data-new", "new")]);
// Test changing an attribute.
var changeAttribute = {
label: "changeAttribute",
executeAutomatic: function() {
var box = document.getElementById("box");
box.setAttribute("data-test", "change");
}
};
testTransaction([changeAttribute],
[getAttrIsFunction("data-test", "test"),
getAttrIsFunction("data-test", "change")]);
// Test remove an attribute.
var removeAttribute = {
label: "removeAttribute",
executeAutomatic: function() {
var box = document.getElementById("box");
box.removeAttribute("data-test");
}
};
testTransaction([removeAttribute],
[getAttrIsFunction("data-test", "test"),
getAttrAbsentFunction("data-test")]);
// Test remove an attribute.
var removeAttribute = {
label: "removeAttribute",
executeAutomatic: function() {
var box = document.getElementById("box");
box.removeAttribute("data-test");
}
};
testTransaction([removeAttribute],
[getAttrIsFunction("data-test", "test"),
getAttrAbsentFunction("data-test")]);
// Test appending child element to box.
var appendChild = {
label: "appendChild",
executeAutomatic: function() {
var box = document.getElementById("box");
box.appendChild(document.createElement("div"));
}
};
testTransaction([appendChild],
[getChildCountFunction(1),
getChildCountFunction(2)]);
// Test appending document fragment with multiple elements to box.
var appendFragment = {
label: "appendFragment",
executeAutomatic: function() {
var box = document.getElementById("box");
var fragment = document.createDocumentFragment();
fragment.appendChild(document.createElement("div"));
fragment.appendChild(document.createElement("div"));
fragment.appendChild(document.createElement("div"));
box.appendChild(fragment);
}
};
testTransaction([appendFragment],
[getChildCountFunction(1),
getChildCountFunction(4)]);
// Test appending a child then removing a child.
var removeChild = {
label: "removeChild",
executeAutomatic: function() {
var box = document.getElementById("box");
box.removeChild(box.firstChild);
}
};
testTransaction([removeChild],
[getChildCountFunction(1),
getChildCountFunction(0)]);
// Test appending a child then removing a child.
var applyInnerHTML = {
label: "applyInnerHTML",
executeAutomatic: function() {
var box = document.getElementById("box");
box.innerHTML = "<div>one</div><div>two</div><div>three</div>";
}
};
testTransaction([applyInnerHTML],
[getChildCountFunction(1),
getChildCountFunction(3)]);
// Test multiple append children and multiple remove children.
testTransaction([appendChild, appendChild, appendChild, appendChild,
removeChild, removeChild, removeChild],
[getChildCountFunction(1),
getChildCountFunction(2),
getChildCountFunction(3),
getChildCountFunction(4),
getChildCountFunction(5),
getChildCountFunction(4),
getChildCountFunction(3),
getChildCountFunction(2)]);
/**
* Creates a div element containing the text "box with text".
* Has an id of "box". Has an attribute "data-test" with the value of "test".
*/
function createTextBoxElement() {
var box = document.createElement("div");
box.setAttribute("id", "box");
box.setAttribute("data-test", "test");
box.textContent = "box with text";
return box;
}
function getTextMatchFunction(matchText) {
return function(box) {
is(box.textContent, matchText, "Text content did not match expected content");
}
}
function getAttrAbsentFunction(attrName) {
return function(box) {
ok(!box.hasAttribute(attrName), "Element should not have attribute");
}
}
function getAttrIsFunction(attrName, attrValue) {
return function(box) {
is(box.getAttribute(attrName), attrValue, "Element attribute is not the expected value");
}
}
function getChildCountFunction(count) {
return function(box) {
is(box.childNodes.length, count, "Element has incorrect number of children");
}
}
/**
* Test transactions by applying, undoing and redoing a sequence of transactions.
* At each step the state of the host node is evaluated for the expected state.
* @param transactions An array of transactions to apply.
* @param evaluators An array of functions which take an element as its only argument
* and evaluates the state of the element for correctness. The
* nth transaction in the transactions array is evaluated by the
* n+1th function in the evaluators array. The first element of
* the evaluators array evaluates the initial state of the host
* node. Thus there should always be one more element in the
* evaluators array than the transactions array.
* @param merges An optional set of integers indicating which indices in the transactions
* array should be merged with the previous transaction.
*/
function testTransaction(transactions, evaluators, merges) {
if (!merges) {
merges = [];
}
var box = createTextBoxElement();
box.undoScope = true;
content.appendChild(box);
var manager = box.undoManager;
is(manager.length, 0, "Initial lenght of UndoManager should be 0");
is(manager.position, 0, "Initial position of UndoManager should be 0");
// Apply transactions and ensure the contents of the box have the
// expected values.
var expectedLength = 0;
for (var i = 0; i < transactions.length; i++) {
var merge = merges.indexOf(i) == -1 ? false : true;
if (!merge || i == 0) {
expectedLength++;
}
manager.transact(transactions[i], merge);
evaluators[i+1](box);
// Length and position should increase by 1.
is(manager.length, expectedLength, "UndoManager length is incorrect after transaction");
is(manager.position, 0, "UndoManager position is incorrect after transaction");
}
// Undo all the transactions and make sure the content of box is the
// expected content.
var expectedPosition = 0;
for (var i = transactions.length - 1; i >= 0; i--) {
// Don't evaluate if the transaction was merged.
if (merges.indexOf(i) == -1) {
expectedPosition++;
manager.undo();
evaluators[i](box);
// Length and position should decrease by one.
is(manager.length, expectedLength, "UndoManager length should not change after undo");
is(manager.position, expectedPosition, "UndoManager position is incorrect after undo");
}
}
// Redo all the transactions and make sure the content of the box is
// the expected content.
for (var i = 0; i < transactions.length; i++) {
// Don't evaluate if the next transaction was merged into the current transaction.
if (merges.indexOf(i+1) == -1) {
expectedPosition--;
manager.redo();
evaluators[i+1](box);
// Length and position should increase by 1.
is(manager.length, expectedLength, "UndoManager length should not change after redo");
is(manager.position, expectedPosition, "UndoManager position is incorrect after redo");
}
}
content.removeChild(box);
}
testUndoRedoOnEmptyManager(0, 1);
testUndoRedoOnEmptyManager(1, 0);
testUndoRedoOnEmptyManager(2, 1);
testUndoRedoOnEmptyManager(1, 2);
testUndoRedoOnEmptyManager(2, 2);
/**
* Test undo/redo when there is no undo transactions.
* Makes sure that nothing bad happens (eg. crash) and that position and length
* don't change.
*/
function testUndoRedoOnEmptyManager(numUndo, numRedo) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
var manager = box.undoManager;
for (var i = 0; i < numUndo; i++) {
manager.undo();
is(manager.length, 0, "Undo should not change number of transacstions");
is(manager.position, 0, "Undo should not change position");
}
for (var i = 0; i < numRedo; i++) {
manager.redo();
is(manager.length, 0, "Undo should not change number of transacstions");
is(manager.position, 0, "Undo should not change position");
}
content.removeChild(box);
}
// Test item()
testItem(10, 0);
testItem(10, 1);
testItem(10, 10);
testItem(10, 5);
testItem(1, 1);
/**
* Create a UndoManager with numTxns transactions and calls undo numUndo
* times. Ensures that items are in the correct order.
*/
function testItem(numTxns, numUndo) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
var manager = box.undoManager;
for (var i = 0; i < numTxns; i++) {
var dummyTxn = {label: null, execute: function(){}, value: i};
manager.transact(dummyTxn, false);
}
for (var i = 0; i < numUndo; i++) {
manager.undo();
}
for (var i = 0; i < manager.length; i++) {
var txns = manager.item(i);
is(txns[0].value, numTxns - i - 1, "item() returned the incorrect transaction");
}
content.removeChild(box);
}
testClearUndoRedoGetItem(10, 10, true);
testClearUndoRedoGetItem(1, 1, true);
testClearUndoRedoGetItem(1, 0, true);
testClearUndoRedoGetItem(10, 0, true);
testClearUndoRedoGetItem(10, 6, true);
testClearUndoRedoGetItem(10, 10, false);
testClearUndoRedoGetItem(1, 1, false);
testClearUndoRedoGetItem(1, 0, false);
testClearUndoRedoGetItem(10, 0, false);
testClearUndoRedoGetItem(10, 6, false);
/**
* Test clear undo/redo and ensure that item() returns the correct transaction.
*/
function testClearUndoRedoGetItem(numTxns, numUndo, clearRedo) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
var manager = box.undoManager;
for (var i = 0; i < numTxns; i++) {
var dummyTxn = {label: null, execute: function(){}, value: i};
manager.transact(dummyTxn, false);
}
for (var i = 0; i < numUndo; i++) {
manager.undo();
}
is(manager.length, numTxns, "UndoManager has incorrect number of transactions");
is(manager.position, numUndo, "UndoManager has incorrect position");
// Check for the correct length and position.
if (clearRedo) {
manager.clearRedo();
is(manager.position, 0, "UndoManager is incorrect position after clearRedo")
is(manager.length, numTxns - numUndo, "UndoManager has incorrect number of transactions after clearRedo");
} else {
manager.clearUndo();
is(manager.position, numUndo, "UndoManager should be at position 0 after clearUndo");
is(manager.length, numUndo, "UndoManager has incorrect number of transactions after clearUndo");
}
// Check that the most recent transaction (if one exists) is the correct one.
if (manager.length > 0) {
var newestTxn = manager.item(0)[0];
if (clearRedo) {
is(newestTxn.value + 1, numTxns - numUndo, "item() returned the incorrect transaction after clearRedo");
} else {
is(newestTxn.value + 1, numTxns, "item() returned the incorrect transaction after clearUndo");
}
}
content.removeChild(box);
}
testOutOfBoundsItem(0, -1);
testOutOfBoundsItem(0, 0);
testOutOfBoundsItem(0, 1);
testOutOfBoundsItem(1, -1);
testOutOfBoundsItem(1, 1);
testOutOfBoundsItem(2, 2);
testOutOfBoundsItem(2, 3);
/**
* Out of bound access to item.
*/
function testOutOfBoundsItem(numTxns, itemNum) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
var manager = box.undoManager;
for (var i = 0; i < numTxns; i++) {
var dummyTxn = {label: null, execute: function(){}};
manager.transact(dummyTxn, false);
}
is(null, manager.item(itemNum), "Accessing out of bounds item should return null.");
content.removeChild(box);
}
/**
* Should not be able to access undoManager from within a transaction.
*/
var accessUndoManagerLength = {
label: "accessUndoManagerLength",
executeAutomatic: function() {
var box = document.getElementById("box");
is(0, box.undoManager.length, "Length should not change until after transaction is executed.");
}
};
transactExpectNoException(accessUndoManagerLength);
var accessUndoManagerPosition = {
label: "accessUndoManagerPosition",
executeAutomatic: function() {
var box = document.getElementById("box");
is(0, box.undoManager.position, "Position should not change until after transaction is executed.");
}
};
transactExpectNoException(accessUndoManagerPosition);
var accessUndoManagerUndo = {
label: "accessUndoManagerUndo",
executeAutomatic: function() {
var box = document.getElementById("box");
box.undoManager.undo();
}
};
transactExpectException(accessUndoManagerUndo);
var accessUndoManagerRedo = {
label: "accessUndoManagerRedo",
executeAutomatic: function() {
var box = document.getElementById("box");
box.undoManager.redo();
}
};
transactExpectException(accessUndoManagerRedo);
function transactExpectNoException(transaction) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
try {
box.undoManager.transact(transaction, false);
ok(true, "Transaction should not cause UndoManager to throw an exception.");
} catch (ex) {
ok(false, "Transaction should not cause UndoManager to throw an exception.");
}
content.removeChild(box);
}
function transactExpectException(transaction) {
var box = createTextBoxElement();
content.appendChild(box);
box.undoScope = true;
try {
box.undoManager.managedTransaction(transaction);
ok(false, "Transaction should cause UndoManager to throw an exception.");
} catch (ex) {
ok(true, "Transaction should cause UndoManager to throw an exception.");
}
content.removeChild(box);
}
/**
* Should be able to access other undoManager from within a transaction.
*/
modifyOtherManager(accessUndoManagerLength);
modifyOtherManager(accessUndoManagerPosition);
modifyOtherManager(accessUndoManagerUndo);
modifyOtherManager(accessUndoManagerRedo);
function modifyOtherManager(transaction) {
var otherElement = document.createElement('div');
var box = createTextBoxElement();
content.appendChild(box);
content.appendChild(otherElement);
otherElement.undoScope = true;
box.undoScope = true;
try {
otherElement.undoManager.transact(transaction, false);
ok(true, "Should not throw exception when UndoManager accesses other undo manager");
} catch (ex) {
ok(false, "Should not throw exception when UndoManager accesses other undo manager");
}
content.removeChild(box);
content.removeChild(otherElement);
}
/**
* Tests for usage of undo manager with modifications to the host node outside
* of the manager. Such usage is not supported but it should not cause bad
* things to happen (eg. crash).
*/
// Remove the last characters from text, so that the deleteData range is out of bounds.
function removeLastCharactersExternal(element) {
element.firstChild.deleteData(3, 10);
}
testExternalMutation(removeLastCharactersExternal, textInsert);
testExternalMutation(removeLastCharactersExternal, textAppend);
// Change attribute value.
function changeAttributeExternal(element) {
element.setAttribute("data-test", "bad");
}
testExternalMutation(changeAttributeExternal, createAttribute);
testExternalMutation(changeAttributeExternal, changeAttribute);
testExternalMutation(changeAttributeExternal, removeAttribute);
function removeAttributeExternal(element) {
element.removeAttribute("data-test");
}
testExternalMutation(removeAttributeExternal, createAttribute);
testExternalMutation(removeAttributeExternal, changeAttribute);
testExternalMutation(removeAttributeExternal, removeAttribute);
// removing children
function removeAllChildrenExternal(element) {
while (element.firstChild) {
element.removeChild(element.firstChild);
}
}
testExternalMutation(removeAllChildrenExternal, appendChild);
testExternalMutation(removeAllChildrenExternal, applyInnerHTML);
// Insert child
function appendChildExternal(element) {
var newElement = document.createElement("span");
element.appendChild(newElement);
}
testExternalMutation(appendChildExternal, appendChild);
testExternalMutation(appendChildExternal, applyInnerHTML);
function testExternalMutation(externalMutation, transaction) {
var box = createTextBoxElement();
box.undoScope = true;
content.appendChild(box);
box.undoManager.transact(transaction, false);
externalMutation(box);
try {
box.undoManager.undo();
ok(true, "Should not throw exception when undo is called on the transaction manager");
} catch (ex) {
ok(false, "Should not throw exception when undo is called on the transaction manager");
}
try {
box.undoManager.redo();
ok(true, "Should not throw exception when redo is called on the transaction manager");
} catch (ex) {
ok(false, "Should not throw exception when redo is called on the transaction manager");
}
content.removeChild(box);
}
// Tests for manual transactions.
var appendChildManual = {
label: "appendChild",
execute: function() {
this.element = document.createElement("div");
this.redo();
},
redo: function() {
var box = document.getElementById("box");
box.appendChild(this.element);
},
undo: function() {
var box = document.getElementById("box");
box.removeChild(this.element);
}
};
testTransaction([appendChildManual],
[getChildCountFunction(1),
getChildCountFunction(2)]);
testTransaction([appendChildManual, appendChild],
[getChildCountFunction(1),
getChildCountFunction(2),
getChildCountFunction(3)]);
testTransaction([appendChild, appendChildManual, appendChild],
[getChildCountFunction(1),
getChildCountFunction(2),
getChildCountFunction(3),
getChildCountFunction(4)]);
// Tests for merge
testTransaction([appendChild, appendChild, appendChild],
[getChildCountFunction(1),
getChildCountFunction(2),
getChildCountFunction(3),
getChildCountFunction(4)],
[1]);
// Passing invalid objects to transact.
transactExpectException({});
transactExpectException({label: "hi"});
transactExpectException({label: "hi", executeAutomatic: null});
transactExpectException({label: "hi", execute: null});
transactExpectException({label: "hi", executeAutomatic: 1});
transactExpectException({label: "hi", execute: 1});
transactExpectException({label: "hi", execute: function() {}, redo: null});
// make sure the document undomanager exists.
ok(document.undoManager, "Document should have an undo manager.");
// Make sure that the UndoManager only records transactions within scope.
var parent = document.createElement("div");
var child = document.createElement("div");
parent.appendChild(child);
parent.undoScope = true;
child.undoScope = true;
var innerHTMLToBye = {
label: "hiToBye",
executeAutomatic: function() {
child.innerHTML = "bye";
}
};
child.innerHTML = "hello";
parent.undoManager.transact(innerHTMLToBye, false);
parent.undoManager.undo();
// The parent undo manager should not have recorded transactions for the children.
// Thus the innerHTML should not have been undone.
is(child.innerHTML, "bye", "Inner HTML of child should not be undone because it is not in parent scope.");
// Disconnect test.
var dummyNode = document.createElement("div");
dummyNode.undoScope = true;
var dummyManager = dummyNode.undoManager;
dummyManager.transact({label: null, execute: function() {}}, false);
dummyNode.undoScope = false;
is(dummyManager.length, 0, "All transactions should be cleared.");
try {
dummyManager.transact({label: null, execute: function() {}}, false);
ok(false, "Should not be able to transact in disconnected UndoManager.");
} catch (ex) {
ok(true, "Should not be able to transact in disconnected UndoManager.");
}
// Undo call before and after undo/redo.
dummyNode = document.createElement("div");
dummyNode.undoScope = true;
dummyNode.innerHTML = "hello";
var undoRedoTransaction = {
label: "undoRedoTransaction",
undoCall: 0,
redoCall: 0,
executeAutomatic: function () {
dummyNode.innerHTML = "bye";
},
undo: function() {
is(dummyNode.innerHTML, "hello", "redo should be called after transaction is undone.");
this.undoCall++;
},
redo: function() {
is(dummyNode.innerHTML, "bye", "redo should be called after transaction is redone.");
this.redoCall++;
}
};
dummyNode.undoManager.transact(undoRedoTransaction, false);
is(undoRedoTransaction.undoCall, 0, "undo should not have been called yet.");
is(undoRedoTransaction.redoCall, 0, "redo should not have been called yet.");
dummyNode.undoManager.undo();
is(undoRedoTransaction.undoCall, 1, "undo should be called once.");
is(undoRedoTransaction.redoCall, 0, "redo should not have been called yet.");
dummyNode.undoManager.redo();
is(undoRedoTransaction.undoCall, 1, "undo should be called once.");
is(undoRedoTransaction.redoCall, 1, "redo should be called once.");
// Attribute setting.
var dummyNode = document.createElement("div");
ok(!dummyNode.undoManager, "UndoManager should not exist for element without undoscope attribute.");
dummyNode.setAttribute("undoscope", "");
ok(dummyNode.undoManager, "UndoManager should exist for element with undoscope attribute.");
dummyNode.removeAttribute("undoscope");
ok(!dummyNode.undoManager, "UndoManager should not exist for element without undoscope attribute.");
dummyNode = document.createElement("div");
dummyNode.undoScope = true;
is(dummyNode.getAttribute("undoscope"), "", "undoscope attribute should reflect undoScope property.");
dummyNode.undoScope = false;
ok(!dummyNode.hasAttribute("undoscope"), "undoscope attribute should not exist if undoScope property is false.");
// Event test
dummyNode = document.createElement("div");
dummyNode.undoScope = true;
var transactionOne = {
transactCount: 0,
undoCount: 0,
redoCount: 0,
label: "transactionOne",
execute: function() {},
};
var transactionTwo = {
transactCount: 0,
undoCount: 0,
redoCount: 0,
label: "transactionTwo",
execute: function() {},
};
var transactionThree = {
transactCount: 0,
undoCount: 0,
redoCount: 0,
label: "transactionThree",
execute: function() {},
};
dummyNode.addEventListener("DOMTransaction", function(e) { e.transactions[0].transactCount++; });
dummyNode.addEventListener("undo", function(e) { e.transactions[0].undoCount++; });
dummyNode.addEventListener("redo", function(e) { e.transactions[0].redoCount++; });
dummyNode.undoManager.transact(transactionOne, false);
checkTransactionEvents(transactionOne, 1, 0, 0);
dummyNode.undoManager.transact(transactionTwo, false);
checkTransactionEvents(transactionTwo, 1, 0, 0);
dummyNode.undoManager.transact(transactionThree, false);
checkTransactionEvents(transactionThree, 1, 0, 0);
// Should do nothing, no events dispatched.
dummyNode.undoManager.redo();
checkTransactionEvents(transactionThree, 1, 0, 0);
dummyNode.undoManager.undo();
checkTransactionEvents(transactionThree, 1, 1, 0);
dummyNode.undoManager.redo();
checkTransactionEvents(transactionThree, 1, 1, 1);
dummyNode.undoManager.undo();
checkTransactionEvents(transactionThree, 1, 2, 1);
dummyNode.undoManager.undo();
checkTransactionEvents(transactionTwo, 1, 1, 0);
dummyNode.undoManager.undo();
checkTransactionEvents(transactionOne, 1, 1, 0);
// Should do nothing, no events dispatched.
dummyNode.undoManager.undo();
checkTransactionEvents(transactionOne, 1, 1, 0);
function checkTransactionEvents(transaction, expectedTransact, expectedUndo, expectedRedo) {
is(transaction.transactCount, expectedTransact, "DOMTransaction event was dispatched an unexpected number of times.");
is(transaction.undoCount, expectedUndo, "undo event was dispatched an unexpected number of times.");
is(transaction.redoCount, expectedRedo, "redo event was dispatched an unexpected number of times.");
}
</script>
</pre>
</body>
</html>

View File

@ -348,8 +348,6 @@ var interfaceNamesInGlobalScope =
"DOMStringMap",
// IMPORTANT: Do not change this list without review from a DOM peer!
"DOMTokenList",
// IMPORTANT: Do not change this list without review from a DOM peer!
"DOMTransactionEvent",
// IMPORTANT: Do not change this list without review from a DOM peer!
"DragEvent",
// IMPORTANT: Do not change this list without review from a DOM peer!
@ -1175,8 +1173,6 @@ var interfaceNamesInGlobalScope =
{name: "U2F", disabled: true},
// IMPORTANT: Do not change this list without review from a DOM peer!
"UIEvent",
// IMPORTANT: Do not change this list without review from a DOM peer!
"UndoManager",
// IMPORTANT: Do not change this list without review from a DOM peer!
"URL",
// IMPORTANT: Do not change this list without review from a DOM peer!

View File

@ -1,22 +0,0 @@
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/.
*
* The origin of this IDL file is
* http://dvcs.w3.org/hg/undomanager/raw-file/tip/undomanager.html
*
* Copyright © 2012 W3C® (MIT, ERCIM, Keio), All Rights Reserved. W3C
* liability, trademark and document use rules apply.
*/
callback DOMTransactionCallback = void();
callback interface DOMTransaction {
readonly attribute DOMString? label;
readonly attribute DOMTransactionCallback? executeAutomatic;
readonly attribute DOMTransactionCallback? execute;
readonly attribute DOMTransactionCallback? undo;
readonly attribute DOMTransactionCallback? redo;
};

View File

@ -1,16 +0,0 @@
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/.
*/
[Constructor(DOMString type, optional DOMTransactionEventInit eventInitDict)]
interface DOMTransactionEvent : Event
{
readonly attribute any transactions;
};
dictionary DOMTransactionEventInit : EventInit
{
any transactions = null;
};

View File

@ -302,12 +302,6 @@ partial interface Document {
readonly attribute Element? scrollingElement;
};
// http://dvcs.w3.org/hg/undomanager/raw-file/tip/undomanager.html
partial interface Document {
[Pref="dom.undo_manager.enabled"]
readonly attribute UndoManager? undoManager;
};
// http://dev.w3.org/2006/webapi/selectors-api2/#interface-definitions
partial interface Document {
[Throws, Pure]

View File

@ -208,14 +208,6 @@ partial interface Element {
readonly attribute long scrollLeftMax;
};
// http://dvcs.w3.org/hg/undomanager/raw-file/tip/undomanager.html
partial interface Element {
[Pref="dom.undo_manager.enabled"]
readonly attribute UndoManager? undoManager;
[SetterThrows,Pref="dom.undo_manager.enabled"]
attribute boolean undoScope;
};
// http://domparsing.spec.whatwg.org/#extensions-to-the-element-interface
partial interface Element {
[Pure,SetterThrows,TreatNullAs=EmptyString]

View File

@ -81,7 +81,6 @@ Touch implements LegacyQueryInterface;
TouchList implements LegacyQueryInterface;
TreeColumns implements LegacyQueryInterface;
TreeWalker implements LegacyQueryInterface;
UndoManager implements LegacyQueryInterface;
ValidityState implements LegacyQueryInterface;
WebSocket implements LegacyQueryInterface;
Window implements LegacyQueryInterface;

View File

@ -1,24 +0,0 @@
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/.
*
* The origin of this IDL file is
* http://dvcs.w3.org/hg/undomanager/raw-file/tip/undomanager.html
*
* Copyright © 2012 W3C® (MIT, ERCIM, Keio), All Rights Reserved. W3C
* liability, trademark and document use rules apply.
*/
[Pref="dom.undo_manager.enabled"]
interface UndoManager {
[Throws] void transact(DOMTransaction transaction, boolean merge);
[Throws] void undo();
[Throws] void redo();
[Throws] sequence<DOMTransaction>? item(unsigned long index);
[Throws] readonly attribute unsigned long length;
[Throws] readonly attribute unsigned long position;
[Throws] void clearUndo();
[Throws] void clearRedo();
};

View File

@ -136,7 +136,6 @@ WEBIDL_FILES = [
'DOMStringList.webidl',
'DOMStringMap.webidl',
'DOMTokenList.webidl',
'DOMTransaction.webidl',
'Downloads.webidl',
'DragEvent.webidl',
'DynamicsCompressorNode.webidl',
@ -579,7 +578,6 @@ WEBIDL_FILES = [
'UDPMessageEvent.webidl',
'UDPSocket.webidl',
'UIEvent.webidl',
'UndoManager.webidl',
'URL.webidl',
'URLSearchParams.webidl',
'USSDSession.webidl',
@ -679,7 +677,6 @@ WEBIDL_FILES += [
'CustomEvent.webidl',
'DeviceOrientationEvent.webidl',
'DeviceStorageChangeEvent.webidl',
'DOMTransactionEvent.webidl',
'HashChangeEvent.webidl',
'MozSettingsEvent.webidl',
'PageTransitionEvent.webidl',
@ -774,7 +771,6 @@ GENERATED_EVENTS_WEBIDL_FILES = [
'DeviceProximityEvent.webidl',
'DeviceStorageAreaChangedEvent.webidl',
'DeviceStorageChangeEvent.webidl',
'DOMTransactionEvent.webidl',
'DownloadEvent.webidl',
'ErrorEvent.webidl',
'FontFaceSetLoadEvent.webidl',

View File

@ -205,9 +205,6 @@ pref("dom.keyboardevent.code.enabled", true);
// even if this is true).
pref("dom.keyboardevent.dispatch_during_composition", false);
// Whether the UndoManager API is enabled
pref("dom.undo_manager.enabled", false);
// Whether URL,Location,Link::GetHash should be percent encoded
// in setter and percent decoded in getter (old behaviour = true)
pref("dom.url.encode_decode_hash", true);

View File

@ -53,7 +53,6 @@ user_pref("media.gmp-manager.url.override", "http://%(server)s/dummy-gmp-manager
user_pref("media.gmp-manager.updateEnabled", false);
user_pref("dom.w3c_touch_events.enabled", 1);
user_pref("layout.accessiblecaret.enabled_on_touch", false);
user_pref("dom.undo_manager.enabled", true);
user_pref("dom.webcomponents.enabled", true);
user_pref("dom.webcomponents.customelements.enabled", true);
user_pref("dom.htmlimports.enabled", true);