mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Backed out 4 changesets (bug 1137557) for causing intermittent Gij switching_test.js failures.
Backed out changeset ce86cf91f423 (bug 1137557) Backed out changeset 83af10efcd3c (bug 1137557) Backed out changeset e48ed45d1c80 (bug 1137557) Backed out changeset 81e93b60a622 (bug 1137557) CLOSED TREE
This commit is contained in:
parent
aab82229b5
commit
7fe71e3d8e
@ -4,7 +4,6 @@
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "gfxPrefs.h"
|
||||
#include "mozilla/EventForwards.h"
|
||||
#include "mozilla/TextEventDispatcher.h"
|
||||
#include "mozilla/TextEvents.h"
|
||||
@ -285,11 +284,8 @@ TextInputProcessor::MaybeDispatchKeydownForComposition(
|
||||
return result;
|
||||
}
|
||||
|
||||
uint32_t consumedFlags = 0;
|
||||
|
||||
result.mResult = KeydownInternal(*aKeyboardEvent, aKeyFlags, false,
|
||||
consumedFlags);
|
||||
result.mDoDefault = !consumedFlags;
|
||||
result.mDoDefault);
|
||||
if (NS_WARN_IF(NS_FAILED(result.mResult))) {
|
||||
result.mCanContinue = false;
|
||||
return result;
|
||||
@ -758,9 +754,9 @@ NS_IMETHODIMP
|
||||
TextInputProcessor::Keydown(nsIDOMKeyEvent* aDOMKeyEvent,
|
||||
uint32_t aKeyFlags,
|
||||
uint8_t aOptionalArgc,
|
||||
uint32_t* aConsumedFlags)
|
||||
bool* aDoDefault)
|
||||
{
|
||||
MOZ_RELEASE_ASSERT(aConsumedFlags, "aConsumedFlags must not be nullptr");
|
||||
MOZ_RELEASE_ASSERT(aDoDefault, "aDoDefault must not be nullptr");
|
||||
MOZ_RELEASE_ASSERT(nsContentUtils::IsCallerChrome());
|
||||
if (!aOptionalArgc) {
|
||||
aKeyFlags = 0;
|
||||
@ -773,33 +769,16 @@ TextInputProcessor::Keydown(nsIDOMKeyEvent* aDOMKeyEvent,
|
||||
if (NS_WARN_IF(!originalKeyEvent)) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
return KeydownInternal(*originalKeyEvent, aKeyFlags, true, *aConsumedFlags);
|
||||
}
|
||||
|
||||
TextEventDispatcher::DispatchTo
|
||||
TextInputProcessor::GetDispatchTo() const
|
||||
{
|
||||
// Support asynchronous tests.
|
||||
if (mForTests) {
|
||||
return gfxPrefs::TestEventsAsyncEnabled() ?
|
||||
TextEventDispatcher::eDispatchToParentProcess :
|
||||
TextEventDispatcher::eDispatchToCurrentProcess;
|
||||
}
|
||||
|
||||
// Otherwise, TextInputProcessor supports only keyboard apps on B2G.
|
||||
// Keyboard apps on B2G doesn't want to dispatch keyboard events to
|
||||
// chrome process. Therefore, this should dispatch key events only in
|
||||
// the current process.
|
||||
return TextEventDispatcher::eDispatchToCurrentProcess;
|
||||
return KeydownInternal(*originalKeyEvent, aKeyFlags, true, *aDoDefault);
|
||||
}
|
||||
|
||||
nsresult
|
||||
TextInputProcessor::KeydownInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
uint32_t aKeyFlags,
|
||||
bool aAllowToDispatchKeypress,
|
||||
uint32_t& aConsumedFlags)
|
||||
bool& aDoDefault)
|
||||
{
|
||||
aConsumedFlags = KEYEVENT_NOT_CONSUMED;
|
||||
aDoDefault = false;
|
||||
|
||||
// We shouldn't modify the internal WidgetKeyboardEvent.
|
||||
WidgetKeyboardEvent keyEvent(aKeyboardEvent);
|
||||
@ -808,8 +787,7 @@ TextInputProcessor::KeydownInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
return rv;
|
||||
}
|
||||
|
||||
aConsumedFlags = (aKeyFlags & KEY_DEFAULT_PREVENTED) ? KEYDOWN_IS_CONSUMED :
|
||||
KEYEVENT_NOT_CONSUMED;
|
||||
aDoDefault = !(aKeyFlags & KEY_DEFAULT_PREVENTED);
|
||||
|
||||
if (WidgetKeyboardEvent::GetModifierForKeyName(keyEvent.mKeyNameIndex)) {
|
||||
ModifierKeyData modifierKeyData(keyEvent);
|
||||
@ -836,27 +814,19 @@ TextInputProcessor::KeydownInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsEventStatus status = aConsumedFlags ? nsEventStatus_eConsumeNoDefault :
|
||||
nsEventStatus_eIgnore;
|
||||
if (!mDispatcher->DispatchKeyboardEvent(NS_KEY_DOWN, keyEvent, status,
|
||||
GetDispatchTo())) {
|
||||
nsEventStatus status = aDoDefault ? nsEventStatus_eIgnore :
|
||||
nsEventStatus_eConsumeNoDefault;
|
||||
if (!mDispatcher->DispatchKeyboardEvent(NS_KEY_DOWN, keyEvent, status)) {
|
||||
// If keydown event isn't dispatched, we don't need to dispatch keypress
|
||||
// events.
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
aConsumedFlags |=
|
||||
(status == nsEventStatus_eConsumeNoDefault) ? KEYDOWN_IS_CONSUMED :
|
||||
KEYEVENT_NOT_CONSUMED;
|
||||
|
||||
if (aAllowToDispatchKeypress &&
|
||||
mDispatcher->MaybeDispatchKeypressEvents(keyEvent, status,
|
||||
GetDispatchTo())) {
|
||||
aConsumedFlags |=
|
||||
(status == nsEventStatus_eConsumeNoDefault) ? KEYPRESS_IS_CONSUMED :
|
||||
KEYEVENT_NOT_CONSUMED;
|
||||
if (aAllowToDispatchKeypress) {
|
||||
mDispatcher->MaybeDispatchKeypressEvents(keyEvent, status);
|
||||
}
|
||||
|
||||
aDoDefault = (status != nsEventStatus_eConsumeNoDefault);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
@ -920,8 +890,7 @@ TextInputProcessor::KeyupInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
|
||||
nsEventStatus status = aDoDefault ? nsEventStatus_eIgnore :
|
||||
nsEventStatus_eConsumeNoDefault;
|
||||
mDispatcher->DispatchKeyboardEvent(NS_KEY_UP, keyEvent, status,
|
||||
GetDispatchTo());
|
||||
mDispatcher->DispatchKeyboardEvent(NS_KEY_UP, keyEvent, status);
|
||||
aDoDefault = (status != nsEventStatus_eConsumeNoDefault);
|
||||
return NS_OK;
|
||||
}
|
||||
|
@ -9,7 +9,6 @@
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "mozilla/EventForwards.h"
|
||||
#include "mozilla/TextEventDispatcher.h"
|
||||
#include "mozilla/TextEventDispatcherListener.h"
|
||||
#include "nsAutoPtr.h"
|
||||
#include "nsITextInputProcessor.h"
|
||||
@ -18,6 +17,10 @@
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
namespace widget{
|
||||
class TextEventDispatcher;
|
||||
} // namespace widget
|
||||
|
||||
class TextInputProcessor final : public nsITextInputProcessor
|
||||
, public widget::TextEventDispatcherListener
|
||||
{
|
||||
@ -57,11 +60,10 @@ private:
|
||||
nsresult KeydownInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
uint32_t aKeyFlags,
|
||||
bool aAllowToDispatchKeypress,
|
||||
uint32_t& aConsumedFlags);
|
||||
bool& aDoDefault);
|
||||
nsresult KeyupInternal(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
uint32_t aKeyFlags,
|
||||
bool& aDoDefault);
|
||||
TextEventDispatcher::DispatchTo GetDispatchTo() const;
|
||||
nsresult IsValidStateForComposition();
|
||||
void UnlinkFromTextEventDispatcher();
|
||||
nsresult PrepareKeyboardEventToDispatch(WidgetKeyboardEvent& aKeyboardEvent,
|
||||
|
@ -2340,8 +2340,8 @@ function runKeyTests()
|
||||
reset();
|
||||
var doDefaultKeydown = TIP.keydown(keyA);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYPRESS_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyA) should return 0x02 because the keypress event should be consumed by the input element");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyA) should return false because the keypress event should be consumed by the input element");
|
||||
is(events.length, 2,
|
||||
description + "TIP.keydown(keyA) should cause keydown and keypress event");
|
||||
checkKeyAttrs("TIP.keydown(keyA)", events[0],
|
||||
@ -2371,8 +2371,8 @@ function runKeyTests()
|
||||
reset();
|
||||
doDefaultKeydown = TIP.keydown(keyEnter);
|
||||
|
||||
is(doDefaultKeydown, 0,
|
||||
description + "TIP.keydown(keyEnter) should return 0");
|
||||
ok(doDefaultKeydown,
|
||||
description + "TIP.keydown(keyEnter) should return true");
|
||||
is(events.length, 2,
|
||||
description + "TIP.keydown(keyEnter) should cause keydown and keypress event");
|
||||
checkKeyAttrs("TIP.keydown(keyEnter)", events[0],
|
||||
@ -2402,8 +2402,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyB, TIP.KEY_DEFAULT_PREVENTED);
|
||||
doDefaultKeyup = TIP.keyup(keyB, TIP.KEY_DEFAULT_PREVENTED);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYDOWN_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyB, TIP.KEY_DEFAULT_PREVENTED) should return 0x01 because it's marked as consumed at dispatching the event");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyB, TIP.KEY_DEFAULT_PREVENTED) should return false because it's marked as consumed at dispatching the event");
|
||||
ok(!doDefaultKeyup,
|
||||
description + "TIP.keyup(keyB, TIP.KEY_DEFAULT_PREVENTED) should return false because it's marked as consumed at dispatching the event");
|
||||
is(events.length, 2,
|
||||
@ -2423,7 +2423,7 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyABC);
|
||||
doDefaultKeyup = TIP.keyup(keyABC);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYPRESS_IS_CONSUMED,
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyABC) should return false because the keypress events should be consumed by the input element");
|
||||
ok(doDefaultKeyup,
|
||||
description + "TIP.keyup(keyABC) should return true");
|
||||
@ -2450,8 +2450,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyEnterPrintable, TIP.KEY_FORCE_PRINTABLE_KEY);
|
||||
doDefaultKeyup = TIP.keyup(keyEnterPrintable, TIP.KEY_FORCE_PRINTABLE_KEY);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYPRESS_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyEnterPrintable, TIP.KEY_FORCE_PRINTABLE_KEY) should return 0x02 because the keypress events should be consumed by the input element");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyEnterPrintable, TIP.KEY_FORCE_PRINTABLE_KEY) should return false because the keypress events should be consumed by the input element");
|
||||
ok(doDefaultKeyup,
|
||||
description + "TIP.keyup(keyEnterPrintable, TIP.KEY_FORCE_PRINTABLE_KEY) should return true");
|
||||
is(events.length, 7,
|
||||
@ -2480,8 +2480,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyWithModifiers);
|
||||
doDefaultKeyup = TIP.keyup(keyWithModifiers);
|
||||
|
||||
is(doDefaultKeydown, 0,
|
||||
description + "TIP.keydown(keyWithModifiers) should return 0");
|
||||
ok(doDefaultKeydown,
|
||||
description + "TIP.keydown(keyWithModifiers) should return true");
|
||||
ok(doDefaultKeyup,
|
||||
description + "TIP.keyup(keyWithModifiers) should return true");
|
||||
is(events.length, 3,
|
||||
@ -2502,8 +2502,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyA);
|
||||
doDefaultKeyup = TIP.keyup(keyA);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYDOWN_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyA) should return 0x01 because keydown event's preventDefault should be called");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyA) should return false because keydown event's preventDefault should be called");
|
||||
ok(doDefaultKeyup,
|
||||
description + "TIP.keyup(keyA) should return true");
|
||||
is(events.length, 2,
|
||||
@ -2521,8 +2521,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyA);
|
||||
doDefaultKeyup = TIP.keyup(keyA);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYPRESS_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyA) should return 0x02 because keypress event's preventDefault should be called");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyA) should return false because keypress event's preventDefault should be called");
|
||||
ok(doDefaultKeyup,
|
||||
description + "TIP.keyup(keyA) should return true");
|
||||
is(events.length, 3,
|
||||
@ -2543,8 +2543,8 @@ function runKeyTests()
|
||||
doDefaultKeydown = TIP.keydown(keyA);
|
||||
doDefaultKeyup = TIP.keyup(keyA);
|
||||
|
||||
is(doDefaultKeydown, TIP.KEYPRESS_IS_CONSUMED,
|
||||
description + "TIP.keydown(keyA) should return 0x02 because the key event should be consumed by the input element");
|
||||
ok(!doDefaultKeydown,
|
||||
description + "TIP.keydown(keyA) should return false because the key event should be consumed by the input element");
|
||||
ok(!doDefaultKeyup,
|
||||
description + "TIP.keyup(keyA) should return false because keyup event's preventDefault should be called");
|
||||
is(events.length, 3,
|
||||
|
@ -573,7 +573,7 @@ MozInputContext.prototype = {
|
||||
|
||||
switch (msg.name) {
|
||||
case "Keyboard:SendKey:Result:OK":
|
||||
resolver.resolve(true);
|
||||
resolver.resolve();
|
||||
break;
|
||||
case "Keyboard:SendKey:Result:Error":
|
||||
resolver.reject(json.error);
|
||||
@ -596,7 +596,7 @@ MozInputContext.prototype = {
|
||||
break;
|
||||
case "Keyboard:SetComposition:Result:OK": // Fall through.
|
||||
case "Keyboard:EndComposition:Result:OK":
|
||||
resolver.resolve(true);
|
||||
resolver.resolve();
|
||||
break;
|
||||
default:
|
||||
dump("Could not find a handler for " + msg.name);
|
||||
@ -738,79 +738,40 @@ MozInputContext.prototype = {
|
||||
return this.replaceSurroundingText(null, offset, length);
|
||||
},
|
||||
|
||||
sendKey: function ic_sendKey(dictOrKeyCode, charCode, modifiers, repeat) {
|
||||
if (typeof dictOrKeyCode === 'number') {
|
||||
// XXX: modifiers are ignored in this API method.
|
||||
|
||||
return this._sendPromise((resolverId) => {
|
||||
cpmmSendAsyncMessageWithKbID(this, 'Keyboard:SendKey', {
|
||||
contextId: this._contextId,
|
||||
sendKey: function ic_sendKey(keyCode, charCode, modifiers, repeat) {
|
||||
let self = this;
|
||||
return this._sendPromise(function(resolverId) {
|
||||
cpmmSendAsyncMessageWithKbID(self, 'Keyboard:SendKey', {
|
||||
contextId: self._contextId,
|
||||
requestId: resolverId,
|
||||
method: 'sendKey',
|
||||
keyCode: dictOrKeyCode,
|
||||
keyCode: keyCode,
|
||||
charCode: charCode,
|
||||
modifiers: modifiers,
|
||||
repeat: repeat
|
||||
});
|
||||
});
|
||||
} else if (typeof dictOrKeyCode === 'object') {
|
||||
return this._sendPromise((resolverId) => {
|
||||
cpmmSendAsyncMessageWithKbID(this, 'Keyboard:SendKey', {
|
||||
contextId: this._contextId,
|
||||
requestId: resolverId,
|
||||
method: 'sendKey',
|
||||
keyboardEventDict: this._getkeyboardEventDict(dictOrKeyCode)
|
||||
});
|
||||
});
|
||||
} else {
|
||||
// XXX: Should not reach here; implies WebIDL binding error.
|
||||
throw new TypeError('Unknown argument passed.');
|
||||
}
|
||||
},
|
||||
|
||||
keydown: function ic_keydown(dict) {
|
||||
return this._sendPromise((resolverId) => {
|
||||
cpmmSendAsyncMessageWithKbID(this, 'Keyboard:SendKey', {
|
||||
contextId: this._contextId,
|
||||
requestId: resolverId,
|
||||
method: 'keydown',
|
||||
keyboardEventDict: this._getkeyboardEventDict(dict)
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
keyup: function ic_keyup(dict) {
|
||||
return this._sendPromise((resolverId) => {
|
||||
cpmmSendAsyncMessageWithKbID(this, 'Keyboard:SendKey', {
|
||||
contextId: this._contextId,
|
||||
requestId: resolverId,
|
||||
method: 'keyup',
|
||||
keyboardEventDict: this._getkeyboardEventDict(dict)
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
setComposition: function ic_setComposition(text, cursor, clauses, dict) {
|
||||
setComposition: function ic_setComposition(text, cursor, clauses) {
|
||||
let self = this;
|
||||
return this._sendPromise((resolverId) => {
|
||||
return this._sendPromise(function(resolverId) {
|
||||
cpmmSendAsyncMessageWithKbID(self, 'Keyboard:SetComposition', {
|
||||
contextId: self._contextId,
|
||||
requestId: resolverId,
|
||||
text: text,
|
||||
cursor: (typeof cursor !== 'undefined') ? cursor : text.length,
|
||||
clauses: clauses || null,
|
||||
keyboardEventDict: this._getkeyboardEventDict(dict)
|
||||
clauses: clauses || null
|
||||
});
|
||||
});
|
||||
},
|
||||
|
||||
endComposition: function ic_endComposition(text, dict) {
|
||||
endComposition: function ic_endComposition(text) {
|
||||
let self = this;
|
||||
return this._sendPromise((resolverId) => {
|
||||
return this._sendPromise(function(resolverId) {
|
||||
cpmmSendAsyncMessageWithKbID(self, 'Keyboard:EndComposition', {
|
||||
contextId: self._contextId,
|
||||
requestId: resolverId,
|
||||
text: text || '',
|
||||
keyboardEventDict: this._getkeyboardEventDict(dict)
|
||||
text: text || ''
|
||||
});
|
||||
});
|
||||
},
|
||||
@ -825,43 +786,6 @@ MozInputContext.prototype = {
|
||||
}
|
||||
callback(aResolverId);
|
||||
});
|
||||
},
|
||||
|
||||
// Take a MozInputMethodKeyboardEventDict dict, creates a keyboardEventDict
|
||||
// object that can be sent to forms.js
|
||||
_getkeyboardEventDict: function(dict) {
|
||||
if (typeof dict !== 'object' || !dict.key) {
|
||||
return;
|
||||
}
|
||||
|
||||
var keyboardEventDict = {
|
||||
key: dict.key,
|
||||
code: dict.code,
|
||||
repeat: dict.repeat,
|
||||
flags: 0
|
||||
};
|
||||
|
||||
if (dict.printable) {
|
||||
keyboardEventDict.flags |=
|
||||
Ci.nsITextInputProcessor.KEY_FORCE_PRINTABLE_KEY;
|
||||
}
|
||||
|
||||
if (/^[a-zA-Z0-9]$/.test(dict.key)) {
|
||||
// keyCode must follow the key value in this range;
|
||||
// disregard the keyCode from content.
|
||||
keyboardEventDict.keyCode = dict.key.toUpperCase().charCodeAt(0);
|
||||
} else if (typeof dict.keyCode === 'number') {
|
||||
// Allow keyCode to be specified for other key values.
|
||||
keyboardEventDict.keyCode = dict.keyCode;
|
||||
|
||||
// Allow keyCode to be explicitly set to zero.
|
||||
if (dict.keyCode === 0) {
|
||||
keyboardEventDict.flags |=
|
||||
Ci.nsITextInputProcessor.KEY_KEEP_KEYCODE_ZERO;
|
||||
}
|
||||
}
|
||||
|
||||
return keyboardEventDict;
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -11,7 +11,6 @@ dump("###################################### forms.js loaded\n");
|
||||
let Ci = Components.interfaces;
|
||||
let Cc = Components.classes;
|
||||
let Cu = Components.utils;
|
||||
let Cr = Components.results;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
@ -19,50 +18,10 @@ XPCOMUtils.defineLazyServiceGetter(Services, "fm",
|
||||
"@mozilla.org/focus-manager;1",
|
||||
"nsIFocusManager");
|
||||
|
||||
/*
|
||||
* A WeakMap to map window to objects keeping it's TextInputProcessor instance.
|
||||
*/
|
||||
let WindowMap = {
|
||||
// WeakMap of <window, object> pairs.
|
||||
_map: null,
|
||||
|
||||
/*
|
||||
* Set the object associated to the window and return it.
|
||||
*/
|
||||
_getObjForWin: function(win) {
|
||||
if (!this._map) {
|
||||
this._map = new WeakMap();
|
||||
}
|
||||
if (this._map.has(win)) {
|
||||
return this._map.get(win);
|
||||
} else {
|
||||
let obj = {
|
||||
tip: null
|
||||
};
|
||||
this._map.set(win, obj);
|
||||
|
||||
return obj;
|
||||
}
|
||||
},
|
||||
|
||||
getTextInputProcessor: function(win) {
|
||||
if (!win) {
|
||||
return;
|
||||
}
|
||||
let obj = this._getObjForWin(win);
|
||||
let tip = obj.tip
|
||||
|
||||
if (!tip) {
|
||||
tip = obj.tip = Cc["@mozilla.org/text-input-processor;1"]
|
||||
.createInstance(Ci.nsITextInputProcessor);
|
||||
}
|
||||
|
||||
if (!tip.beginInputTransaction(win, textInputProcessorCallback)) {
|
||||
tip = obj.tip = null;
|
||||
}
|
||||
return tip;
|
||||
}
|
||||
};
|
||||
XPCOMUtils.defineLazyGetter(this, "domWindowUtils", function () {
|
||||
return content.QueryInterface(Ci.nsIInterfaceRequestor)
|
||||
.getInterface(Ci.nsIDOMWindowUtils);
|
||||
});
|
||||
|
||||
const RESIZE_SCROLL_DELAY = 20;
|
||||
// In content editable node, when there are hidden elements such as <br>, it
|
||||
@ -82,151 +41,6 @@ let HTMLSelectElement = Ci.nsIDOMHTMLSelectElement;
|
||||
let HTMLOptGroupElement = Ci.nsIDOMHTMLOptGroupElement;
|
||||
let HTMLOptionElement = Ci.nsIDOMHTMLOptionElement;
|
||||
|
||||
function guessKeyNameFromKeyCode(KeyboardEvent, aKeyCode) {
|
||||
switch (aKeyCode) {
|
||||
case KeyboardEvent.DOM_VK_CANCEL:
|
||||
return "Cancel";
|
||||
case KeyboardEvent.DOM_VK_HELP:
|
||||
return "Help";
|
||||
case KeyboardEvent.DOM_VK_BACK_SPACE:
|
||||
return "Backspace";
|
||||
case KeyboardEvent.DOM_VK_TAB:
|
||||
return "Tab";
|
||||
case KeyboardEvent.DOM_VK_CLEAR:
|
||||
return "Clear";
|
||||
case KeyboardEvent.DOM_VK_RETURN:
|
||||
return "Enter";
|
||||
case KeyboardEvent.DOM_VK_SHIFT:
|
||||
return "Shift";
|
||||
case KeyboardEvent.DOM_VK_CONTROL:
|
||||
return "Control";
|
||||
case KeyboardEvent.DOM_VK_ALT:
|
||||
return "Alt";
|
||||
case KeyboardEvent.DOM_VK_PAUSE:
|
||||
return "Pause";
|
||||
case KeyboardEvent.DOM_VK_EISU:
|
||||
return "Eisu";
|
||||
case KeyboardEvent.DOM_VK_ESCAPE:
|
||||
return "Escape";
|
||||
case KeyboardEvent.DOM_VK_CONVERT:
|
||||
return "Convert";
|
||||
case KeyboardEvent.DOM_VK_NONCONVERT:
|
||||
return "NonConvert";
|
||||
case KeyboardEvent.DOM_VK_ACCEPT:
|
||||
return "Accept";
|
||||
case KeyboardEvent.DOM_VK_MODECHANGE:
|
||||
return "ModeChange";
|
||||
case KeyboardEvent.DOM_VK_PAGE_UP:
|
||||
return "PageUp";
|
||||
case KeyboardEvent.DOM_VK_PAGE_DOWN:
|
||||
return "PageDown";
|
||||
case KeyboardEvent.DOM_VK_END:
|
||||
return "End";
|
||||
case KeyboardEvent.DOM_VK_HOME:
|
||||
return "Home";
|
||||
case KeyboardEvent.DOM_VK_LEFT:
|
||||
return "ArrowLeft";
|
||||
case KeyboardEvent.DOM_VK_UP:
|
||||
return "ArrowUp";
|
||||
case KeyboardEvent.DOM_VK_RIGHT:
|
||||
return "ArrowRight";
|
||||
case KeyboardEvent.DOM_VK_DOWN:
|
||||
return "ArrowDown";
|
||||
case KeyboardEvent.DOM_VK_SELECT:
|
||||
return "Select";
|
||||
case KeyboardEvent.DOM_VK_PRINT:
|
||||
return "Print";
|
||||
case KeyboardEvent.DOM_VK_EXECUTE:
|
||||
return "Execute";
|
||||
case KeyboardEvent.DOM_VK_PRINTSCREEN:
|
||||
return "PrintScreen";
|
||||
case KeyboardEvent.DOM_VK_INSERT:
|
||||
return "Insert";
|
||||
case KeyboardEvent.DOM_VK_DELETE:
|
||||
return "Delete";
|
||||
case KeyboardEvent.DOM_VK_WIN:
|
||||
return "OS";
|
||||
case KeyboardEvent.DOM_VK_CONTEXT_MENU:
|
||||
return "ContextMenu";
|
||||
case KeyboardEvent.DOM_VK_SLEEP:
|
||||
return "Standby";
|
||||
case KeyboardEvent.DOM_VK_F1:
|
||||
return "F1";
|
||||
case KeyboardEvent.DOM_VK_F2:
|
||||
return "F2";
|
||||
case KeyboardEvent.DOM_VK_F3:
|
||||
return "F3";
|
||||
case KeyboardEvent.DOM_VK_F4:
|
||||
return "F4";
|
||||
case KeyboardEvent.DOM_VK_F5:
|
||||
return "F5";
|
||||
case KeyboardEvent.DOM_VK_F6:
|
||||
return "F6";
|
||||
case KeyboardEvent.DOM_VK_F7:
|
||||
return "F7";
|
||||
case KeyboardEvent.DOM_VK_F8:
|
||||
return "F8";
|
||||
case KeyboardEvent.DOM_VK_F9:
|
||||
return "F9";
|
||||
case KeyboardEvent.DOM_VK_F10:
|
||||
return "F10";
|
||||
case KeyboardEvent.DOM_VK_F11:
|
||||
return "F11";
|
||||
case KeyboardEvent.DOM_VK_F12:
|
||||
return "F12";
|
||||
case KeyboardEvent.DOM_VK_F13:
|
||||
return "F13";
|
||||
case KeyboardEvent.DOM_VK_F14:
|
||||
return "F14";
|
||||
case KeyboardEvent.DOM_VK_F15:
|
||||
return "F15";
|
||||
case KeyboardEvent.DOM_VK_F16:
|
||||
return "F16";
|
||||
case KeyboardEvent.DOM_VK_F17:
|
||||
return "F17";
|
||||
case KeyboardEvent.DOM_VK_F18:
|
||||
return "F18";
|
||||
case KeyboardEvent.DOM_VK_F19:
|
||||
return "F19";
|
||||
case KeyboardEvent.DOM_VK_F20:
|
||||
return "F20";
|
||||
case KeyboardEvent.DOM_VK_F21:
|
||||
return "F21";
|
||||
case KeyboardEvent.DOM_VK_F22:
|
||||
return "F22";
|
||||
case KeyboardEvent.DOM_VK_F23:
|
||||
return "F23";
|
||||
case KeyboardEvent.DOM_VK_F24:
|
||||
return "F24";
|
||||
case KeyboardEvent.DOM_VK_NUM_LOCK:
|
||||
return "NumLock";
|
||||
case KeyboardEvent.DOM_VK_SCROLL_LOCK:
|
||||
return "ScrollLock";
|
||||
case KeyboardEvent.DOM_VK_VOLUME_MUTE:
|
||||
return "VolumeMute";
|
||||
case KeyboardEvent.DOM_VK_VOLUME_DOWN:
|
||||
return "VolumeDown";
|
||||
case KeyboardEvent.DOM_VK_VOLUME_UP:
|
||||
return "VolumeUp";
|
||||
case KeyboardEvent.DOM_VK_META:
|
||||
return "Meta";
|
||||
case KeyboardEvent.DOM_VK_ALTGR:
|
||||
return "AltGraph";
|
||||
case KeyboardEvent.DOM_VK_ATTN:
|
||||
return "Attn";
|
||||
case KeyboardEvent.DOM_VK_CRSEL:
|
||||
return "CrSel";
|
||||
case KeyboardEvent.DOM_VK_EXSEL:
|
||||
return "ExSel";
|
||||
case KeyboardEvent.DOM_VK_EREOF:
|
||||
return "EraseEof";
|
||||
case KeyboardEvent.DOM_VK_PLAY:
|
||||
return "Play";
|
||||
default:
|
||||
return "Unidentified";
|
||||
}
|
||||
}
|
||||
|
||||
let FormVisibility = {
|
||||
/**
|
||||
* Searches upwards in the DOM for an element that has been scrolled.
|
||||
@ -370,41 +184,6 @@ let FormVisibility = {
|
||||
}
|
||||
};
|
||||
|
||||
// This object implements nsITextInputProcessorCallback
|
||||
let textInputProcessorCallback = {
|
||||
onNotify: function(aTextInputProcessor, aNotification) {
|
||||
try {
|
||||
switch (aNotification.type) {
|
||||
case "request-to-commit":
|
||||
// TODO: Send a notification through asyncMessage to the keyboard here.
|
||||
aTextInputProcessor.commitComposition();
|
||||
|
||||
break;
|
||||
case "request-to-cancel":
|
||||
// TODO: Send a notification through asyncMessage to the keyboard here.
|
||||
aTextInputProcessor.cancelComposition();
|
||||
|
||||
break;
|
||||
|
||||
case "notify-detached":
|
||||
// TODO: Send a notification through asyncMessage to the keyboard here.
|
||||
break;
|
||||
|
||||
// TODO: Manage _focusedElement for text input from here instead.
|
||||
// (except for <select> which will be need to handled elsewhere)
|
||||
case "notify-focus":
|
||||
break;
|
||||
|
||||
case "notify-blur":
|
||||
break;
|
||||
}
|
||||
} catch (e) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
let FormAssistant = {
|
||||
init: function fa_init() {
|
||||
addEventListener("focus", this, true, false);
|
||||
@ -653,7 +432,7 @@ let FormAssistant = {
|
||||
break;
|
||||
|
||||
case "keydown":
|
||||
if (!this.focusedElement || this._editing) {
|
||||
if (!this.focusedElement) {
|
||||
break;
|
||||
}
|
||||
|
||||
@ -661,7 +440,7 @@ let FormAssistant = {
|
||||
break;
|
||||
|
||||
case "keyup":
|
||||
if (!this.focusedElement || this._editing) {
|
||||
if (!this.focusedElement) {
|
||||
break;
|
||||
}
|
||||
|
||||
@ -723,132 +502,34 @@ let FormAssistant = {
|
||||
case "Forms:Input:SendKey":
|
||||
CompositionManager.endComposition('');
|
||||
|
||||
let win = target.ownerDocument.defaultView;
|
||||
let tip = WindowMap.getTextInputProcessor(win);
|
||||
if (!tip) {
|
||||
if (json.requestId) {
|
||||
sendAsyncMessage("Forms:SendKey:Result:Error", {
|
||||
requestId: json.requestId,
|
||||
error: "Unable to start input transaction."
|
||||
});
|
||||
let flags = domWindowUtils.KEY_FLAG_NOT_SYNTHESIZED_FOR_TESTS;
|
||||
this._editing = true;
|
||||
let doKeypress = domWindowUtils.sendKeyEvent('keydown', json.keyCode,
|
||||
json.charCode, json.modifiers, flags);
|
||||
if (doKeypress) {
|
||||
domWindowUtils.sendKeyEvent('keypress', json.keyCode,
|
||||
json.charCode, json.modifiers, flags);
|
||||
}
|
||||
|
||||
break;
|
||||
if(!json.repeat) {
|
||||
domWindowUtils.sendKeyEvent('keyup', json.keyCode,
|
||||
json.charCode, json.modifiers, flags);
|
||||
}
|
||||
|
||||
// If we receive a keyboardEventDict from json, that means the user
|
||||
// is calling the method with the new arguments.
|
||||
// Otherwise, we would have to construct our own keyboardEventDict
|
||||
// based on legacy values we have received.
|
||||
let keyboardEventDict = json.keyboardEventDict;
|
||||
let flags = 0;
|
||||
this._editing = false;
|
||||
|
||||
if (keyboardEventDict) {
|
||||
if ('flags' in keyboardEventDict) {
|
||||
flags = keyboardEventDict.flags;
|
||||
}
|
||||
} else {
|
||||
// The naive way to figure out if the key to dispatch is printable.
|
||||
let printable = !!json.charCode;
|
||||
|
||||
// For printable keys, the value should be the actual character.
|
||||
// For non-printable keys, it should be a value in the D3E spec.
|
||||
// Here we make some educated guess for it.
|
||||
let key = printable ?
|
||||
String.fromCharCode(json.charCode) :
|
||||
guessKeyNameFromKeyCode(win.KeyboardEvent, json.keyCode);
|
||||
|
||||
// keyCode from content is only respected when the key is not an
|
||||
// an alphanumeric character. We also ask TextInputProcessor not to
|
||||
// infer this value for non-printable keys to keep the original
|
||||
// behavior.
|
||||
let keyCode = (printable && /^[a-zA-Z0-9]$/.test(key)) ?
|
||||
key.toUpperCase().charCodeAt(0) :
|
||||
json.keyCode;
|
||||
|
||||
keyboardEventDict = {
|
||||
key: key,
|
||||
keyCode: keyCode,
|
||||
// We don't have any information to tell the virtual key the
|
||||
// user have interacted with.
|
||||
code: "",
|
||||
// We do not have the information to infer location of the virtual key
|
||||
// either (and we would need TextInputProcessor not to compute it).
|
||||
location: 0,
|
||||
// This indicates the key is triggered for repeats.
|
||||
repeat: json.repeat
|
||||
};
|
||||
|
||||
flags = tip.KEY_KEEP_KEY_LOCATION_STANDARD;
|
||||
if (!printable) {
|
||||
flags |= tip.KEY_NON_PRINTABLE_KEY;
|
||||
}
|
||||
if (!keyboardEventDict.keyCode) {
|
||||
flags |= tip.KEY_KEEP_KEYCODE_ZERO;
|
||||
}
|
||||
}
|
||||
|
||||
let keyboardEvent = new win.KeyboardEvent("", keyboardEventDict);
|
||||
|
||||
let keydownDefaultPrevented = false;
|
||||
try {
|
||||
switch (json.method) {
|
||||
case 'sendKey': {
|
||||
let consumedFlags = tip.keydown(keyboardEvent, flags);
|
||||
keydownDefaultPrevented =
|
||||
!!(tip.KEYDOWN_IS_CONSUMED & consumedFlags);
|
||||
if (!keyboardEventDict.repeat) {
|
||||
tip.keyup(keyboardEvent, flags);
|
||||
}
|
||||
break;
|
||||
}
|
||||
case 'keydown': {
|
||||
let consumedFlags = tip.keydown(keyboardEvent, flags);
|
||||
keydownDefaultPrevented =
|
||||
!!(tip.KEYDOWN_IS_CONSUMED & consumedFlags);
|
||||
break;
|
||||
}
|
||||
case 'keyup': {
|
||||
tip.keyup(keyboardEvent, flags);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
} catch (err) {
|
||||
dump("forms.js:" + err.toString() + "\n");
|
||||
|
||||
if (json.requestId) {
|
||||
if (err instanceof Ci.nsIException &&
|
||||
err.result == Cr.NS_ERROR_ILLEGAL_VALUE) {
|
||||
sendAsyncMessage("Forms:SendKey:Result:Error", {
|
||||
requestId: json.requestId,
|
||||
error: "The values specified are illegal."
|
||||
});
|
||||
} else {
|
||||
sendAsyncMessage("Forms:SendKey:Result:Error", {
|
||||
requestId: json.requestId,
|
||||
error: "Unable to type into destroyed input."
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
if (json.requestId) {
|
||||
if (keydownDefaultPrevented) {
|
||||
sendAsyncMessage("Forms:SendKey:Result:Error", {
|
||||
requestId: json.requestId,
|
||||
error: "Key event(s) was cancelled."
|
||||
});
|
||||
} else {
|
||||
if (json.requestId && doKeypress) {
|
||||
sendAsyncMessage("Forms:SendKey:Result:OK", {
|
||||
requestId: json.requestId,
|
||||
selectioninfo: this.getSelectionInfo()
|
||||
});
|
||||
}
|
||||
else if (json.requestId && !doKeypress) {
|
||||
sendAsyncMessage("Forms:SendKey:Result:Error", {
|
||||
requestId: json.requestId,
|
||||
error: "Keydown event got canceled"
|
||||
});
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case "Forms:Select:Choice":
|
||||
@ -961,7 +642,7 @@ let FormAssistant = {
|
||||
|
||||
case "Forms:SetComposition": {
|
||||
CompositionManager.setComposition(target, json.text, json.cursor,
|
||||
json.clauses, json.keyboardEventDict);
|
||||
json.clauses);
|
||||
sendAsyncMessage("Forms:SetComposition:Result:OK", {
|
||||
requestId: json.requestId,
|
||||
selectioninfo: this.getSelectionInfo()
|
||||
@ -970,7 +651,7 @@ let FormAssistant = {
|
||||
}
|
||||
|
||||
case "Forms:EndComposition": {
|
||||
CompositionManager.endComposition(json.text, json.keyboardEventDict);
|
||||
CompositionManager.endComposition(json.text);
|
||||
sendAsyncMessage("Forms:EndComposition:Result:OK", {
|
||||
requestId: json.requestId,
|
||||
selectioninfo: this.getSelectionInfo()
|
||||
@ -1489,8 +1170,7 @@ function replaceSurroundingText(element, text, offset, length) {
|
||||
|
||||
let CompositionManager = {
|
||||
_isStarted: false,
|
||||
_tip: null,
|
||||
_KeyboardEventForWin: null,
|
||||
_textInputProcessor: null,
|
||||
_clauseAttrMap: {
|
||||
'raw-input':
|
||||
Ci.nsITextInputProcessor.ATTR_RAW_CLAUSE,
|
||||
@ -1502,7 +1182,35 @@ let CompositionManager = {
|
||||
Ci.nsITextInputProcessor.ATTR_SELECTED_CLAUSE
|
||||
},
|
||||
|
||||
setComposition: function cm_setComposition(element, text, cursor, clauses, dict) {
|
||||
_callback: function cm_callback(aTIP, aNotification)
|
||||
{
|
||||
try {
|
||||
switch (aNotification.type) {
|
||||
case "request-to-commit":
|
||||
aTIP.commitComposition();
|
||||
break;
|
||||
case "request-to-cancel":
|
||||
aTIP.cancelComposition();
|
||||
break;
|
||||
}
|
||||
} catch (e) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
},
|
||||
|
||||
_prepareTextInputProcessor: function cm_prepareTextInputProcessor(aWindow)
|
||||
{
|
||||
if (!this._textInputProcessor) {
|
||||
this._textInputProcessor =
|
||||
Cc["@mozilla.org/text-input-processor;1"].
|
||||
createInstance(Ci.nsITextInputProcessor);
|
||||
}
|
||||
return this._textInputProcessor.beginInputTransaction(aWindow,
|
||||
this._callback);
|
||||
},
|
||||
|
||||
setComposition: function cm_setComposition(element, text, cursor, clauses) {
|
||||
// Check parameters.
|
||||
if (!element) {
|
||||
return;
|
||||
@ -1540,57 +1248,30 @@ let CompositionManager = {
|
||||
}
|
||||
|
||||
let win = element.ownerDocument.defaultView;
|
||||
let tip = WindowMap.getTextInputProcessor(win);
|
||||
if (!tip) {
|
||||
if (!this._prepareTextInputProcessor(win)) {
|
||||
return;
|
||||
}
|
||||
// Update the composing text.
|
||||
tip.setPendingCompositionString(text);
|
||||
this._textInputProcessor.setPendingCompositionString(text);
|
||||
for (var i = 0; i < clauseLens.length; i++) {
|
||||
if (!clauseLens[i]) {
|
||||
continue;
|
||||
}
|
||||
tip.appendClauseToPendingComposition(clauseLens[i], clauseAttrs[i]);
|
||||
this._textInputProcessor.appendClauseToPendingComposition(clauseLens[i],
|
||||
clauseAttrs[i]);
|
||||
}
|
||||
if (cursor >= 0) {
|
||||
tip.setCaretInPendingComposition(cursor);
|
||||
}
|
||||
|
||||
if (!dict) {
|
||||
this._isStarted = tip.flushPendingComposition();
|
||||
} else {
|
||||
let keyboardEvent = new win.KeyboardEvent("", dict);
|
||||
let flags = dict.flags;
|
||||
this._isStarted = tip.flushPendingComposition(keyboardEvent, flags);
|
||||
}
|
||||
|
||||
if (this._isStarted) {
|
||||
this._tip = tip;
|
||||
this._KeyboardEventForWin = win.KeyboardEvent;
|
||||
this._textInputProcessor.setCaretInPendingComposition(cursor);
|
||||
}
|
||||
this._isStarted = this._textInputProcessor.flushPendingComposition();
|
||||
},
|
||||
|
||||
endComposition: function cm_endComposition(text, dict) {
|
||||
endComposition: function cm_endComposition(text) {
|
||||
if (!this._isStarted) {
|
||||
return;
|
||||
}
|
||||
let tip = this._tip;
|
||||
if (!tip) {
|
||||
return;
|
||||
}
|
||||
|
||||
text = text || "";
|
||||
if (!dict) {
|
||||
tip.commitCompositionWith(text);
|
||||
} else {
|
||||
let keyboardEvent = new this._KeyboardEventForWin("", dict);
|
||||
let flags = dict.flags;
|
||||
tip.commitCompositionWith(text, keyboardEvent, flags);
|
||||
}
|
||||
|
||||
this._textInputProcessor.commitCompositionWith(text ? text : "");
|
||||
this._isStarted = false;
|
||||
this._tip = null;
|
||||
this._KeyboardEventForWin = null;
|
||||
},
|
||||
|
||||
// Composition ends due to external actions.
|
||||
@ -1600,7 +1281,5 @@ let CompositionManager = {
|
||||
}
|
||||
|
||||
this._isStarted = false;
|
||||
this._tip = null;
|
||||
this._KeyboardEventForWin = null;
|
||||
}
|
||||
};
|
||||
|
@ -26,4 +26,3 @@ support-files =
|
||||
[test_two_inputs.html]
|
||||
[test_two_selects.html]
|
||||
[test_unload.html]
|
||||
[test_bug1137557.html]
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -254,7 +254,7 @@ interface nsITextInputProcessorCallback;
|
||||
* TIP.keyup(leftShift);
|
||||
*/
|
||||
|
||||
[scriptable, builtinclass, uuid(581f6619-76ed-478c-905d-b8e6553a714a)]
|
||||
[scriptable, builtinclass, uuid(6617a9f6-3e16-4086-9e1e-c8a6c5d505c7)]
|
||||
interface nsITextInputProcessor : nsISupports
|
||||
{
|
||||
/**
|
||||
@ -489,12 +489,6 @@ interface nsITextInputProcessor : nsISupports
|
||||
// or emulating legacy API behavior.
|
||||
const unsigned long KEY_DONT_DISPATCH_MODIFIER_KEY_EVENT = 0x00000020;
|
||||
|
||||
// These values can be used to do bitwise operation with the return value of
|
||||
// the keydown() method.
|
||||
const unsigned long KEYEVENT_NOT_CONSUMED = 0x00000000;
|
||||
const unsigned long KEYDOWN_IS_CONSUMED = 0x00000001;
|
||||
const unsigned long KEYPRESS_IS_CONSUMED = 0x00000002;
|
||||
|
||||
/**
|
||||
* keydown() may dispatch a keydown event and some keypress events if
|
||||
* preceding keydown event isn't consumed and they are necessary.
|
||||
@ -535,19 +529,12 @@ interface nsITextInputProcessor : nsISupports
|
||||
* each instance and set automatically.
|
||||
* @param aKeyFlags Special flags. The values can be some of KEY_*
|
||||
* constants.
|
||||
* @return KEYEVENT_NOT_CONSUMED, if the keydown event nor
|
||||
* the following keypress event(s) are consumed.
|
||||
* KEYDOWN_IS_CONSUMED, if the keydown event is
|
||||
* consumed. No keypress event will be dispatched in
|
||||
* this case.
|
||||
* KEYPRESS_IS_CONSUMED, if the keypress event(s) is
|
||||
* consumed when dispatched.
|
||||
* Note that keypress event is always consumed by
|
||||
* native code for the printable keys (indicating the
|
||||
* default action has been taken).
|
||||
* @return true if neither the keydown event or following
|
||||
* keypress events is *not* consumed.
|
||||
* Otherwise, i.e., preventDefault() is called, false.
|
||||
*/
|
||||
[optional_argc]
|
||||
unsigned long keydown(in nsIDOMKeyEvent aKeyboardEvent,
|
||||
boolean keydown(in nsIDOMKeyEvent aKeyboardEvent,
|
||||
[optional] in unsigned long aKeyFlags);
|
||||
|
||||
/**
|
||||
|
@ -192,54 +192,17 @@ interface MozInputContext: EventTarget {
|
||||
attribute EventHandler onsurroundingtextchange;
|
||||
|
||||
/*
|
||||
* Send a string/character with its key events. There are two ways of invocating
|
||||
* the method for backward compability purpose.
|
||||
*
|
||||
* (1) The recommended way, allow specifying DOM level 3 properties like |code|.
|
||||
* @param dictOrKeyCode See MozInputMethodKeyboardEventDict.
|
||||
* @param charCode disregarded
|
||||
* @param modifiers disregarded
|
||||
* @param repeat disregarded
|
||||
*
|
||||
* (2) Deprecated, reserved for backward compability.
|
||||
* @param dictOrKeyCode keyCode of the key to send, should be one of the DOM_VK_ value in KeyboardEvent.
|
||||
* @param charCode charCode of the character, should be 0 for non-printable keys.
|
||||
* @param modifiers this paramater is no longer honored.
|
||||
* send a character with its key events.
|
||||
* @param modifiers see http://mxr.mozilla.org/mozilla-central/source/dom/interfaces/base/nsIDOMWindowUtils.idl#206
|
||||
* @param repeat indicates whether a key would be sent repeatedly.
|
||||
*
|
||||
* @return A promise. Resolve to true if succeeds.
|
||||
* Rejects to a string indicating the error.
|
||||
*
|
||||
* @return true if succeeds. Otherwise false if the input context becomes void.
|
||||
* Alternative: sendKey(KeyboardEvent event), but we will likely
|
||||
* waste memory for creating the KeyboardEvent object.
|
||||
* Note that, if you want to send a key n times repeatedly, make sure set
|
||||
* parameter repeat to true and invoke sendKey n times, and invoke keyup
|
||||
* after the end of the input.
|
||||
* parameter repeat to true and invoke sendKey n-1 times, and then set
|
||||
* repeat to false in the last invoke.
|
||||
*/
|
||||
Promise<boolean> sendKey((MozInputMethodRequiredKeyboardEventDict or long) dictOrKeyCode,
|
||||
optional long charCode,
|
||||
optional long modifiers,
|
||||
optional boolean repeat);
|
||||
|
||||
/*
|
||||
* Send a string/character with keydown, and keypress events.
|
||||
* keyup should be called afterwards to ensure properly sequence.
|
||||
*
|
||||
* @param dict See MozInputMethodKeyboardEventDict.
|
||||
*
|
||||
* @return A promise. Resolve to true if succeeds.
|
||||
* Rejects to a string indicating the error.
|
||||
*/
|
||||
Promise<boolean> keydown(MozInputMethodRequiredKeyboardEventDict dict);
|
||||
|
||||
/*
|
||||
* Send a keyup event. keydown should be called first to ensure properly sequence.
|
||||
*
|
||||
* @param dict See MozInputMethodKeyboardEventDict.
|
||||
*
|
||||
* @return A promise. Resolve to true if succeeds.
|
||||
* Rejects to a string indicating the error.
|
||||
*
|
||||
*/
|
||||
Promise<boolean> keyup(MozInputMethodRequiredKeyboardEventDict dict);
|
||||
Promise<boolean> sendKey(long keyCode, long charCode, long modifiers, optional boolean repeat);
|
||||
|
||||
/*
|
||||
* Set current composing text. This method will start composition or update
|
||||
@ -255,10 +218,6 @@ interface MozInputContext: EventTarget {
|
||||
* cursor will be positioned after the composition text.
|
||||
* @param clauses The array of composition clause information. If not set,
|
||||
* only one clause is supported.
|
||||
* @param dict The properties of the keyboard event that cause the composition
|
||||
* to set. keydown or keyup event will be fired if it's necessary.
|
||||
* For compatibility, we recommend that you should always set this argument
|
||||
* if it's caused by a key operation.
|
||||
*
|
||||
* The composing text, which is shown with underlined style to distinguish
|
||||
* from the existing text, is used to compose non-ASCII characters from
|
||||
@ -272,10 +231,9 @@ interface MozInputContext: EventTarget {
|
||||
* To finish composition and commit text to current input field, an IME
|
||||
* should call |endComposition|.
|
||||
*/
|
||||
Promise<boolean> setComposition(DOMString text,
|
||||
optional long cursor,
|
||||
optional sequence<CompositionClauseParameters> clauses,
|
||||
optional MozInputMethodKeyboardEventDict dict);
|
||||
// XXXbz what is this promise resolved with?
|
||||
Promise<any> setComposition(DOMString text, optional long cursor,
|
||||
optional sequence<CompositionClauseParameters> clauses);
|
||||
|
||||
/*
|
||||
* End composition, clear the composing text and commit given text to
|
||||
@ -283,10 +241,6 @@ interface MozInputContext: EventTarget {
|
||||
* position.
|
||||
* @param text The text to commited before cursor position. If empty string
|
||||
* is given, no text will be committed.
|
||||
* @param dict The properties of the keyboard event that cause the composition
|
||||
* to end. keydown or keyup event will be fired if it's necessary.
|
||||
* For compatibility, we recommend that you should always set this argument
|
||||
* if it's caused by a key operation.
|
||||
*
|
||||
* Note that composition always ends automatically with nothing to commit if
|
||||
* the composition does not explicitly end by calling |endComposition|, but
|
||||
@ -294,8 +248,8 @@ interface MozInputContext: EventTarget {
|
||||
* |replaceSurroundingText|, |deleteSurroundingText|, user moving the
|
||||
* cursor, changing the focus, etc.
|
||||
*/
|
||||
Promise<boolean> endComposition(optional DOMString text,
|
||||
optional MozInputMethodKeyboardEventDict dict);
|
||||
// XXXbz what is this promise resolved with?
|
||||
Promise<any> endComposition(optional DOMString text);
|
||||
};
|
||||
|
||||
enum CompositionClauseSelectionType {
|
||||
@ -309,66 +263,3 @@ dictionary CompositionClauseParameters {
|
||||
DOMString selectionType = "raw-input";
|
||||
long length;
|
||||
};
|
||||
|
||||
/*
|
||||
* A MozInputMethodKeyboardEventDictBase contains the following properties,
|
||||
* indicating the properties of the keyboard event caused.
|
||||
*
|
||||
* This is the base dictionary type for us to create two child types that could
|
||||
* be used as argument type in two types of methods, as WebIDL parser required.
|
||||
*
|
||||
*/
|
||||
dictionary MozInputMethodKeyboardEventDictBase {
|
||||
/*
|
||||
* String/character to output, or a registered name of non-printable key.
|
||||
* (To be defined in the inheriting dictionary types.)
|
||||
*/
|
||||
// DOMString key;
|
||||
/*
|
||||
* String/char indicating the virtual hardware key pressed. Optional.
|
||||
* Must be a value defined in
|
||||
* http://www.w3.org/TR/DOM-Level-3-Events-code/#keyboard-chording-virtual
|
||||
* If your keyboard app emulates physical keyboard layout, this value should
|
||||
* not be empty string. Otherwise, it should be empty string.
|
||||
*/
|
||||
DOMString code = "";
|
||||
/*
|
||||
* keyCode of the keyboard event. Optional.
|
||||
* To be disregarded if |key| is an alphanumeric character.
|
||||
* If the key causes inputting a character and if your keyboard app emulates
|
||||
* a physical keyboard layout, this value should be same as the value used
|
||||
* by Firefox for desktop. If the key causes inputting an ASCII character
|
||||
* but if your keyboard app doesn't emulate any physical keyboard layouts,
|
||||
* the value should be proper value for the key value.
|
||||
*/
|
||||
long? keyCode;
|
||||
/*
|
||||
* Indicates whether a key would be sent repeatedly. Optional.
|
||||
*/
|
||||
boolean repeat = false;
|
||||
/*
|
||||
* Optional. True if |key| property is explicitly referring to a printable key.
|
||||
* When this is set, key will be printable even if the |key| value matches any
|
||||
* of the registered name of non-printable keys.
|
||||
*/
|
||||
boolean printable = false;
|
||||
};
|
||||
|
||||
/*
|
||||
* For methods like setComposition() and endComposition(), the optional
|
||||
* dictionary type argument is really optional when all of it's property
|
||||
* are optional.
|
||||
* This dictionary type is used to denote that argument.
|
||||
*/
|
||||
dictionary MozInputMethodKeyboardEventDict : MozInputMethodKeyboardEventDictBase {
|
||||
DOMString? key;
|
||||
};
|
||||
|
||||
/*
|
||||
* For methods like keydown() and keyup(), the dictionary type argument is
|
||||
* considered required only if at least one of it's property is required.
|
||||
* This dictionary type is used to denote that argument.
|
||||
*/
|
||||
dictionary MozInputMethodRequiredKeyboardEventDict : MozInputMethodKeyboardEventDictBase {
|
||||
required DOMString key;
|
||||
};
|
||||
|
@ -140,34 +140,16 @@ nsresult
|
||||
TextEventDispatcher::DispatchEvent(nsIWidget* aWidget,
|
||||
WidgetGUIEvent& aEvent,
|
||||
nsEventStatus& aStatus)
|
||||
{
|
||||
MOZ_ASSERT(!aEvent.AsInputEvent(), "Use DispatchInputEvent()");
|
||||
|
||||
nsRefPtr<TextEventDispatcher> kungFuDeathGrip(this);
|
||||
nsCOMPtr<nsIWidget> widget(aWidget);
|
||||
mDispatchingEvent++;
|
||||
nsresult rv = widget->DispatchEvent(&aEvent, aStatus);
|
||||
mDispatchingEvent--;
|
||||
return rv;
|
||||
}
|
||||
|
||||
nsresult
|
||||
TextEventDispatcher::DispatchInputEvent(nsIWidget* aWidget,
|
||||
WidgetInputEvent& aEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo)
|
||||
{
|
||||
nsRefPtr<TextEventDispatcher> kungFuDeathGrip(this);
|
||||
nsCOMPtr<nsIWidget> widget(aWidget);
|
||||
mDispatchingEvent++;
|
||||
|
||||
// If the event is dispatched via nsIWidget::DispatchInputEvent(), it
|
||||
// sends the event to the parent process first since APZ needs to handle it
|
||||
// first. However, some callers (e.g., keyboard apps on B2G and tests
|
||||
// expecting synchronous dispatch) don't want this to do that.
|
||||
nsresult rv = NS_OK;
|
||||
if (aDispatchTo == eDispatchToParentProcess) {
|
||||
aStatus = widget->DispatchInputEvent(&aEvent);
|
||||
if (aEvent.AsInputEvent() &&
|
||||
(!aEvent.mFlags.mIsSynthesizedForTests || gfxPrefs::TestEventsAsyncEnabled()))
|
||||
{
|
||||
aStatus = widget->DispatchInputEvent(aEvent.AsInputEvent());
|
||||
} else {
|
||||
rv = widget->DispatchEvent(&aEvent, aStatus);
|
||||
}
|
||||
@ -304,11 +286,9 @@ bool
|
||||
TextEventDispatcher::DispatchKeyboardEvent(
|
||||
uint32_t aMessage,
|
||||
const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo)
|
||||
nsEventStatus& aStatus)
|
||||
{
|
||||
return DispatchKeyboardEventInternal(aMessage, aKeyboardEvent, aStatus,
|
||||
aDispatchTo);
|
||||
return DispatchKeyboardEventInternal(aMessage, aKeyboardEvent, aStatus);
|
||||
}
|
||||
|
||||
bool
|
||||
@ -316,7 +296,6 @@ TextEventDispatcher::DispatchKeyboardEventInternal(
|
||||
uint32_t aMessage,
|
||||
const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo,
|
||||
uint32_t aIndexOfKeypress)
|
||||
{
|
||||
MOZ_ASSERT(aMessage == NS_KEY_DOWN || aMessage == NS_KEY_UP ||
|
||||
@ -395,15 +374,14 @@ TextEventDispatcher::DispatchKeyboardEventInternal(
|
||||
keyEvent.mPluginEvent.Clear();
|
||||
// TODO: Manage mUniqueId here.
|
||||
|
||||
DispatchInputEvent(mWidget, keyEvent, aStatus, aDispatchTo);
|
||||
DispatchEvent(mWidget, keyEvent, aStatus);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
TextEventDispatcher::MaybeDispatchKeypressEvents(
|
||||
const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo)
|
||||
nsEventStatus& aStatus)
|
||||
{
|
||||
// If the key event was consumed, keypress event shouldn't be fired.
|
||||
if (aStatus == nsEventStatus_eConsumeNoDefault) {
|
||||
@ -423,7 +401,7 @@ TextEventDispatcher::MaybeDispatchKeypressEvents(
|
||||
for (size_t i = 0; i < keypressCount; i++) {
|
||||
aStatus = nsEventStatus_eIgnore;
|
||||
if (!DispatchKeyboardEventInternal(NS_KEY_PRESS, aKeyboardEvent,
|
||||
aStatus, aDispatchTo, i)) {
|
||||
aStatus, i)) {
|
||||
// The widget must have been gone.
|
||||
break;
|
||||
}
|
||||
|
@ -180,26 +180,6 @@ public:
|
||||
*/
|
||||
nsresult NotifyIME(const IMENotification& aIMENotification);
|
||||
|
||||
|
||||
/**
|
||||
* DispatchTo indicates whether the event may be dispatched to its parent
|
||||
* process first (if there is) or not. If the event is dispatched to the
|
||||
* parent process, APZ will handle it first. Otherwise, the event won't be
|
||||
* handled by APZ if it's in a child process.
|
||||
*/
|
||||
enum DispatchTo
|
||||
{
|
||||
// The event may be dispatched to its parent process if there is a parent.
|
||||
// In such case, the event will be handled asynchronously. Additionally,
|
||||
// the event may be sent to its child process if a child process (including
|
||||
// the dispatching process) has focus.
|
||||
eDispatchToParentProcess = 0,
|
||||
// The event must be dispatched in the current process. But of course,
|
||||
// the event may be sent to a child process when it has focus. If there is
|
||||
// no child process, the event may be handled synchronously.
|
||||
eDispatchToCurrentProcess = 1
|
||||
};
|
||||
|
||||
/**
|
||||
* DispatchKeyboardEvent() maybe dispatches aKeyboardEvent.
|
||||
*
|
||||
@ -212,13 +192,11 @@ public:
|
||||
* set nsEventStatus_eIgnore. After dispatching
|
||||
* a event and it's consumed this returns
|
||||
* nsEventStatus_eConsumeNoDefault.
|
||||
* @param aDispatchTo See comments of DispatchTo.
|
||||
* @return true if an event is dispatched. Otherwise, false.
|
||||
*/
|
||||
bool DispatchKeyboardEvent(uint32_t aMessage,
|
||||
const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo = eDispatchToParentProcess);
|
||||
nsEventStatus& aStatus);
|
||||
|
||||
/**
|
||||
* MaybeDispatchKeypressEvents() maybe dispatches a keypress event which is
|
||||
@ -232,14 +210,11 @@ public:
|
||||
* When this method dispatches one or more keypress
|
||||
* events and one of them is consumed, this returns
|
||||
* nsEventStatus_eConsumeNoDefault.
|
||||
* @param aDispatchTo See comments of DispatchTo.
|
||||
* @return true if one or more events are dispatched.
|
||||
* Otherwise, false.
|
||||
*/
|
||||
bool MaybeDispatchKeypressEvents(const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo =
|
||||
eDispatchToParentProcess);
|
||||
nsEventStatus& aStatus);
|
||||
|
||||
private:
|
||||
// mWidget is owner of the instance. When this is created, this is set.
|
||||
@ -298,7 +273,6 @@ private:
|
||||
*/
|
||||
void InitEvent(WidgetGUIEvent& aEvent) const;
|
||||
|
||||
|
||||
/**
|
||||
* DispatchEvent() dispatches aEvent on aWidget.
|
||||
*/
|
||||
@ -306,16 +280,6 @@ private:
|
||||
WidgetGUIEvent& aEvent,
|
||||
nsEventStatus& aStatus);
|
||||
|
||||
/**
|
||||
* DispatchInputEvent() dispatches aEvent on aWidget.
|
||||
*
|
||||
* @param aDispatchTo See comments of DispatchTo.
|
||||
*/
|
||||
nsresult DispatchInputEvent(nsIWidget* aWidget,
|
||||
WidgetInputEvent& aEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo);
|
||||
|
||||
/**
|
||||
* StartCompositionAutomaticallyIfNecessary() starts composition if it hasn't
|
||||
* been started it yet.
|
||||
@ -344,7 +308,6 @@ private:
|
||||
* set nsEventStatus_eIgnore. After dispatching
|
||||
* a event and it's consumed this returns
|
||||
* nsEventStatus_eConsumeNoDefault.
|
||||
* @param aDispatchTo See comments of DispatchTo.
|
||||
* @param aIndexOfKeypress This must be 0 if aMessage isn't NS_KEY_PRESS or
|
||||
* aKeyboard.mKeyNameIndex isn't
|
||||
* KEY_NAME_INDEX_USE_STRING. Otherwise, i.e.,
|
||||
@ -357,8 +320,6 @@ private:
|
||||
bool DispatchKeyboardEventInternal(uint32_t aMessage,
|
||||
const WidgetKeyboardEvent& aKeyboardEvent,
|
||||
nsEventStatus& aStatus,
|
||||
DispatchTo aDispatchTo =
|
||||
eDispatchToParentProcess,
|
||||
uint32_t aIndexOfKeypress = 0);
|
||||
};
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user