Bug 259454 IME input (e.g., Chinese, Japanese and Korean) cannot be performed in Find Toolbar when opened with "/" or "'" r=bryner, dbaron, sr=dbaron, a=benjamin

This commit is contained in:
masayuki%d-toybox.com 2005-06-24 04:25:43 +00:00
Родитель 021d45bcbb
Коммит d867376085
10 изменённых файлов: 245 добавлений и 143 удалений

Просмотреть файл

@ -426,7 +426,6 @@
flex="1" contenttooltip="aHTMLTooltip"
contentcontextmenu="contentAreaContextMenu"
onnewtab="BrowserOpenTab();"
onkeyup="onBrowserKeyUp(event);"
autocompletepopup="PopupAutoComplete"
ondragdrop="nsDragAndDrop.drop(event, contentAreaDNDObserver);"
onclick="return contentAreaClick(event, false);"/>

Просмотреть файл

@ -99,6 +99,9 @@ public:
NS_IMETHOD GetFocusedContent(nsIContent **aContent) = 0;
NS_IMETHOD SetFocusedContent(nsIContent* aContent) = 0;
// Get the previously-focused content node for this document
NS_IMETHOD GetLastFocusedContent(nsIContent **aContent) = 0;
NS_IMETHOD GetFocusedFrame(nsIFrame **aFrame) = 0;
NS_IMETHOD ContentRemoved(nsIContent* aContent) = 0;

Просмотреть файл

@ -4169,10 +4169,20 @@ NS_IMETHODIMP
nsEventStateManager::SetFocusedContent(nsIContent* aContent)
{
mCurrentFocus = aContent;
if (mCurrentFocus)
mLastFocus = mCurrentFocus;
mCurrentFocusFrame = nsnull;
return NS_OK;
}
NS_IMETHODIMP
nsEventStateManager::GetLastFocusedContent(nsIContent** aContent)
{
*aContent = mLastFocus;
NS_IF_ADDREF(*aContent);
return NS_OK;
}
NS_IMETHODIMP
nsEventStateManager::GetFocusedFrame(nsIFrame** aFrame)
{
@ -4204,6 +4214,11 @@ nsEventStateManager::ContentRemoved(nsIContent* aContent)
SetFocusedContent(nsnull);
}
if (mLastFocus &&
nsContentUtils::ContentIsDescendantOf(mLastFocus, aContent)) {
mLastFocus = nsnull;
}
if (mHoverContent &&
nsContentUtils::ContentIsDescendantOf(mHoverContent, aContent)) {
// Since hover is hierarchical, set the current hover to the
@ -4615,10 +4630,6 @@ nsEventStateManager::FocusElementButNotDocument(nsIContent *aContent)
focusController->GetFocusedElement(getter_AddRefs(oldFocusedElement));
nsCOMPtr<nsIContent> oldFocusedContent(do_QueryInterface(oldFocusedElement));
// Notify focus controller of new focus for this document
nsCOMPtr<nsIDOMElement> newFocusedElement(do_QueryInterface(aContent));
focusController->SetFocusedElement(newFocusedElement);
// Temporarily set mCurrentFocus so that esm::GetContentState() tells
// layout system to show focus on this element.
SetFocusedContent(aContent); // Reset back to null at the end of this method.

Просмотреть файл

@ -117,6 +117,7 @@ public:
NS_IMETHOD SetContentState(nsIContent *aContent, PRInt32 aState);
NS_IMETHOD GetFocusedContent(nsIContent **aContent);
NS_IMETHOD SetFocusedContent(nsIContent* aContent);
NS_IMETHOD GetLastFocusedContent(nsIContent **aContent);
NS_IMETHOD GetFocusedFrame(nsIFrame **aFrame);
NS_IMETHOD ContentRemoved(nsIContent* aContent);
NS_IMETHOD EventStatusOK(nsGUIEvent* aEvent, PRBool *aOK);
@ -305,6 +306,7 @@ protected:
nsCOMPtr<nsIContent> mDragOverContent;
nsCOMPtr<nsIContent> mURLTargetContent;
nsCOMPtr<nsIContent> mCurrentFocus;
nsCOMPtr<nsIContent> mLastFocus;
nsIFrame* mCurrentFocusFrame;
PRInt32 mCurrentTabIndex;

Просмотреть файл

@ -274,52 +274,55 @@ IsEventHandler(nsIAtom* aName)
return PR_FALSE;
}
return aName == nsLayoutAtoms::onclick ||
aName == nsLayoutAtoms::ondblclick ||
aName == nsLayoutAtoms::onmousedown ||
aName == nsLayoutAtoms::onmouseup ||
aName == nsLayoutAtoms::onmouseover ||
aName == nsLayoutAtoms::onmouseout ||
aName == nsLayoutAtoms::onmousemove ||
return aName == nsLayoutAtoms::onclick ||
aName == nsLayoutAtoms::ondblclick ||
aName == nsLayoutAtoms::onmousedown ||
aName == nsLayoutAtoms::onmouseup ||
aName == nsLayoutAtoms::onmouseover ||
aName == nsLayoutAtoms::onmouseout ||
aName == nsLayoutAtoms::onmousemove ||
aName == nsLayoutAtoms::onkeydown ||
aName == nsLayoutAtoms::onkeyup ||
aName == nsLayoutAtoms::onkeypress ||
aName == nsLayoutAtoms::onkeydown ||
aName == nsLayoutAtoms::onkeyup ||
aName == nsLayoutAtoms::onkeypress ||
aName == nsLayoutAtoms::onload ||
aName == nsLayoutAtoms::onunload ||
aName == nsLayoutAtoms::onabort ||
aName == nsLayoutAtoms::onerror ||
aName == nsLayoutAtoms::oncompositionstart ||
aName == nsLayoutAtoms::oncompositionend ||
aName == nsLayoutAtoms::onpopupshowing ||
aName == nsLayoutAtoms::onpopupshown ||
aName == nsLayoutAtoms::onpopuphiding ||
aName == nsLayoutAtoms::onpopuphidden ||
aName == nsLayoutAtoms::onclose ||
aName == nsLayoutAtoms::oncommand ||
aName == nsLayoutAtoms::onbroadcast ||
aName == nsLayoutAtoms::oncommandupdate ||
aName == nsLayoutAtoms::onload ||
aName == nsLayoutAtoms::onunload ||
aName == nsLayoutAtoms::onabort ||
aName == nsLayoutAtoms::onerror ||
aName == nsLayoutAtoms::onoverflow ||
aName == nsLayoutAtoms::onunderflow ||
aName == nsLayoutAtoms::onoverflowchanged ||
aName == nsLayoutAtoms::onpopupshowing ||
aName == nsLayoutAtoms::onpopupshown ||
aName == nsLayoutAtoms::onpopuphiding ||
aName == nsLayoutAtoms::onpopuphidden ||
aName == nsLayoutAtoms::onclose ||
aName == nsLayoutAtoms::oncommand ||
aName == nsLayoutAtoms::onbroadcast ||
aName == nsLayoutAtoms::oncommandupdate ||
aName == nsLayoutAtoms::onfocus ||
aName == nsLayoutAtoms::onblur ||
aName == nsLayoutAtoms::onoverflow ||
aName == nsLayoutAtoms::onunderflow ||
aName == nsLayoutAtoms::onoverflowchanged ||
aName == nsLayoutAtoms::onsubmit ||
aName == nsLayoutAtoms::onreset ||
aName == nsLayoutAtoms::onchange ||
aName == nsLayoutAtoms::onselect ||
aName == nsLayoutAtoms::oninput ||
aName == nsLayoutAtoms::onfocus ||
aName == nsLayoutAtoms::onblur ||
aName == nsLayoutAtoms::onpaint ||
aName == nsLayoutAtoms::onsubmit ||
aName == nsLayoutAtoms::onreset ||
aName == nsLayoutAtoms::onchange ||
aName == nsLayoutAtoms::onselect ||
aName == nsLayoutAtoms::oninput ||
aName == nsLayoutAtoms::ondragenter ||
aName == nsLayoutAtoms::ondragover ||
aName == nsLayoutAtoms::ondragexit ||
aName == nsLayoutAtoms::ondragdrop ||
aName == nsLayoutAtoms::ondraggesture ||
aName == nsLayoutAtoms::onpaint ||
aName == nsLayoutAtoms::ondragenter ||
aName == nsLayoutAtoms::ondragover ||
aName == nsLayoutAtoms::ondragexit ||
aName == nsLayoutAtoms::ondragdrop ||
aName == nsLayoutAtoms::ondraggesture ||
aName == nsLayoutAtoms::oncontextmenu;
}

Просмотреть файл

@ -4,8 +4,10 @@
<label value="&find.label;"/>
<hbox id="find-field-container">
<textbox id="find-field" oninput="find(this.value);" onfocus="onFindBarFocus();"
onkeypress="onFindBarKeyPress(event);" onblur="onFindBarBlur();"/>
<textbox id="find-field" oninput="find(this.value);"
onkeypress="onFindBarKeyPress(event);" onblur="onFindBarBlur();"
oncompositionstart="onFindBarCompositionStart(event);"
oncompositionend="onFindBarCompositionEnd(event);"/>
</hbox>
<toolbarbutton id="find-next" label="&findNext.label;" tooltiptext="&findNext.tooltip;"
command="cmd_findAgain" disabled="true" accesskey="&findNext.accesskey;"/>

Просмотреть файл

@ -21,6 +21,7 @@
#
# Contributor(s):
# Blake Ross <blake@cs.stanford.edu> (Original Author)
# Masayuki Nakano <masayuki@d-toybox.com>
#
# Alternatively, the contents of this file may be used under the terms of
# either the GNU General Public License Version 2 or later (the "GPL"), or
@ -46,6 +47,9 @@ const CHAR_CODE_APOSTROPHE = "'".charCodeAt(0);
// Global find variables
var gFindMode = FIND_NORMAL;
var gFoundLink = null;
var gTmpOutline = null;
var gTmpOutlineOffset = "0";
var gQuickFindTimeout = null;
var gQuickFindTimeoutLength = 0;
var gHighlightTimeout = null;
@ -53,14 +57,12 @@ var gUseTypeAheadFind = false;
var gWrappedToTopStr = "";
var gWrappedToBottomStr = "";
var gNotFoundStr = "";
var gTypeAheadFindBuffer = "";
var gIsBack = true;
var gBackProtectBuffer = 3;
var gFlashFindBar = 0;
var gFlashFindBarCount = 6;
var gFlashFindBarTimeout = null;
var gLastHighlightString = "";
var gTypeAheadLinksOnly = false;
var gIsIMEComposing = false;
// DOMRange used during highlighting
var searchRange;
@ -327,6 +329,41 @@ function closeFindBar()
setTimeout(delayedCloseFindBar, 0);
}
function fireKeypressEvent(target, evt)
{
if (!target)
return;
var event = document.createEvent("KeyEvents");
event.initKeyEvent(evt.type, evt.canBubble, evt.cancelable,
evt.view, evt.ctrlKey, evt.altKey, evt.shiftKey,
evt.metaKey, evt.keyCode, evt.charCode);
target.dispatchEvent(event);
}
function setFoundLink(foundLink)
{
if (gFoundLink == foundLink)
return;
if (gFoundLink) {
// restore original outline
gFoundLink.style.outline = gTmpOutline;
gFoundLink.style.outlineOffset = gTmpOutlineOffset;
}
if (foundLink) {
// backup original outline
gTmpOutline = foundLink.style.outline;
gTmpOutlineOffset = foundLink.style.outlineOffset;
// draw pseudo focus rect
// XXX Should we change the following style for FAYT pseudo focus?
// XXX Shouldn't we change default design if outline is visible already?
foundLink.style.outline = "1px dotted invert";
foundLink.style.outlineOffset = "0;";
}
gFoundLink = foundLink;
}
function delayedCloseFindBar()
{
var findField = document.getElementById("find-field");
@ -334,12 +371,16 @@ function delayedCloseFindBar()
.getService(Components.interfaces.nsIWindowWatcher);
if (window == ww.activeWindow && document.commandDispatcher.focusedElement &&
document.commandDispatcher.focusedElement.parentNode.parentNode == findField) {
window.content.focus();
if (gFoundLink)
gFoundLink.focus();
else
window.content.focus();
}
var findToolbar = document.getElementById("FindToolbar");
findToolbar.hidden = true;
gTypeAheadFindBuffer = "";
setFindMode(FIND_NORMAL);
setFoundLink(null);
changeSelectionColor(false);
if (gQuickFindTimeout) {
clearTimeout(gQuickFindTimeout);
@ -383,15 +424,10 @@ function shouldFastFind(evt)
return true;
}
function onFindBarFocus()
{
toggleLinkFocus(false);
}
function onFindBarBlur()
{
toggleLinkFocus(true);
changeSelectionColor(false);
setFoundLink(null);
}
function onBrowserMouseUp(evt)
@ -402,103 +438,77 @@ function onBrowserMouseUp(evt)
}
function onBrowserKeyPress(evt)
{
{
// Check focused elt
if (!shouldFastFind(evt))
return;
var findField = document.getElementById("find-field");
if (gFindMode != FIND_NORMAL && gQuickFindTimeout) {
if (evt.keyCode == KeyEvent.DOM_VK_BACK_SPACE) {
if (findField.value) {
findField.value = findField.value.substr(0, findField.value.length - 1);
gIsBack = true;
gBackProtectBuffer = 3;
}
else if (gBackProtectBuffer > 0) {
gBackProtectBuffer--;
}
if (gIsBack || gBackProtectBuffer > 0)
evt.preventDefault();
find(findField.value);
}
else if (evt.keyCode == KeyEvent.DOM_VK_ESCAPE) {
closeFindBar();
evt.preventDefault();
}
else if (evt.charCode) {
if (evt.charCode == CHAR_CODE_SPACE)
evt.preventDefault();
findField.value += String.fromCharCode(evt.charCode);
find(findField.value);
}
if (gFindMode != FIND_NORMAL && gQuickFindTimeout) {
if (!evt.charCode)
return;
selectFindBar();
focusFindBar();
fireKeypressEvent(findField.inputField, evt);
evt.preventDefault();
return;
}
if (evt.charCode == CHAR_CODE_APOSTROPHE || evt.charCode == CHAR_CODE_SLASH ||
(gUseTypeAheadFind && evt.charCode && evt.charCode != CHAR_CODE_SPACE)) {
gFindMode = (evt.charCode == CHAR_CODE_APOSTROPHE ||
(gTypeAheadLinksOnly && evt.charCode != CHAR_CODE_SLASH))
? FIND_LINKS : FIND_TYPEAHEAD;
toggleLinkFocus(true);
if (openFindBar()) {
setFindCloseTimeout();
var findMode = (evt.charCode == CHAR_CODE_APOSTROPHE ||
(gTypeAheadLinksOnly && evt.charCode != CHAR_CODE_SLASH))
? FIND_LINKS : FIND_TYPEAHEAD;
setFindMode(findMode);
if (openFindBar()) {
setFindCloseTimeout();
selectFindBar();
focusFindBar();
findField.value = "";
if (gUseTypeAheadFind &&
evt.charCode != CHAR_CODE_APOSTROPHE &&
evt.charCode != CHAR_CODE_SLASH) {
gTypeAheadFindBuffer += String.fromCharCode(evt.charCode);
findField.value = gTypeAheadFindBuffer;
find(findField.value);
}
else {
findField.value = "";
}
evt.charCode != CHAR_CODE_SLASH)
fireKeypressEvent(findField.inputField, evt);
evt.preventDefault();
}
else {
if (gFindMode == FIND_NORMAL) {
// XXXldb This code appears unreachable.
selectFindBar();
focusFindBar();
selectFindBar();
focusFindBar();
if (gFindMode != FIND_NORMAL) {
findField.value = "";
fireKeypressEvent(findField.inputField, evt);
evt.preventDefault();
}
else {
findField.value = String.fromCharCode(evt.charCode);
find(findField.value);
}
}
}
}
}
function toggleLinkFocus(aFocusLinks)
{
var fastFind = getBrowser().fastFind;
fastFind.focusLinks = aFocusLinks;
}
function onBrowserKeyUp(evt)
{
if (evt.keyCode == KeyEvent.DOM_VK_BACK_SPACE)
gIsBack = false;
}
function onFindBarKeyPress(evt)
{
if (evt.keyCode == KeyEvent.DOM_VK_RETURN) {
var findString = document.getElementById("find-field");
if (!findString.value)
return;
if (gFindMode == FIND_NORMAL) {
var findString = document.getElementById("find-field");
if (!findString.value)
return;
if (evt.ctrlKey) {
document.getElementById("highlight").click();
return;
if (evt.ctrlKey) {
document.getElementById("highlight").click();
return;
}
if (evt.shiftKey)
findPrevious();
else
findNext();
}
else {
if (gFoundLink) {
var tmpLink = gFoundLink;
tmpLink.focus(); // In this function, gFoundLink is set null.
fireKeypressEvent(tmpLink, evt);
evt.preventDefault();
}
}
if (evt.shiftKey)
findPrevious();
else
findNext();
}
else if (evt.keyCode == KeyEvent.DOM_VK_ESCAPE) {
closeFindBar();
@ -531,22 +541,35 @@ function enableFindButtons(aEnable)
findNext.disabled = findPrev.disabled = highlight.disabled = !aEnable;
}
function updateFoundLink(res)
{
if (gFindMode != FIND_NORMAL) {
var val = document.getElementById("find-field").value;
if (res == Components.interfaces.nsITypeAheadFind.FIND_NOTFOUND || !val)
setFoundLink(null);
else
setFoundLink(getBrowser().fastFind.foundLink);
}
}
function find(val)
{
if (!val)
val = document.getElementById("find-field").value;
enableFindButtons(val);
var highlightBtn = document.getElementById("highlight");
if (highlightBtn.checked)
setHighlightTimeout();
changeSelectionColor(true);
var fastFind = getBrowser().fastFind;
var fastFind = getBrowser().fastFind;
var res = fastFind.find(val, gFindMode == FIND_LINKS);
updateFoundLink(res);
updateStatus(res, true);
if (gFindMode != FIND_NORMAL)
setFindCloseTimeout();
}
@ -566,7 +589,7 @@ function flashFindBar()
function onFindCmd()
{
gFindMode = FIND_NORMAL;
setFindMode(FIND_NORMAL);
openFindBar();
if (gFlashFindBar) {
gFlashFindBarTimeout = setInterval(flashFindBar, 500);
@ -637,26 +660,30 @@ function isFindBarVisible()
function findNext()
{
changeSelectionColor(true);
var fastFind = getBrowser().fastFind;
var res = fastFind.findNext();
updateFoundLink(res);
updateStatus(res, true);
if (gFindMode != FIND_NORMAL && isFindBarVisible())
setFindCloseTimeout();
return res;
}
function findPrevious()
{
changeSelectionColor(true);
var fastFind = getBrowser().fastFind;
var res = fastFind.findPrevious();
updateFoundLink(res);
updateStatus(res, false);
if (gFindMode != FIND_NORMAL && isFindBarVisible())
setFindCloseTimeout();
return res;
}
@ -689,5 +716,41 @@ function setFindCloseTimeout()
{
if (gQuickFindTimeout)
clearTimeout(gQuickFindTimeout);
gQuickFindTimeout = setTimeout(function() { if (gFindMode != FIND_NORMAL) closeFindBar(); }, gQuickFindTimeoutLength);
// Don't close the find toolbar while IME is composing.
if (gIsIMEComposing) {
gQuickFindTimeout = null;
return;
}
gQuickFindTimeout =
setTimeout(function() { if (gFindMode != FIND_NORMAL) closeFindBar(); },
gQuickFindTimeoutLength);
}
function onFindBarCompositionStart(evt)
{
gIsIMEComposing = true;
// Don't close the find toolbar while IME is composing.
if (gQuickFindTimeout) {
clearTimeout(gQuickFindTimeout);
gQuickFindTimeout = null;
}
}
function onFindBarCompositionEnd(evt)
{
gIsIMEComposing = false;
if (gFindMode != FIND_NORMAL && isFindBarVisible())
setFindCloseTimeout();
}
function setFindMode(mode)
{
if (mode == gFindMode)
return;
gFindMode = mode;
var fastFind = getBrowser().fastFind;
fastFind.focusLinks = (gFindMode != FIND_NORMAL);
}

Просмотреть файл

@ -60,5 +60,6 @@ interface nsITypeAheadFind : nsISupports
readonly attribute AString searchString;
attribute boolean focusLinks;
attribute boolean caseSensitive;
readonly attribute nsIDOMElement foundLink;
};

Просмотреть файл

@ -278,6 +278,7 @@ nsTypeAheadFind::FindItNow(nsIPresShell *aPresShell,
PRBool aIsFirstVisiblePreferred, PRBool aFindNext, PRUint16* aResult)
{
*aResult = FIND_NOTFOUND;
mFoundLink = nsnull;
nsCOMPtr<nsISelection> selection;
nsCOMPtr<nsISelectionController> selectionController;
nsCOMPtr<nsIPresShell> startingPresShell (do_QueryReferent(mPresShell));
@ -432,6 +433,13 @@ nsTypeAheadFind::FindItNow(nsIPresShell *aPresShell,
nsIEventStateManager *esm = presContext->EventStateManager();
PRBool isSelectionWithFocus;
esm->MoveFocusToCaret(PR_TRUE, &isSelectionWithFocus);
if (isSelectionWithFocus) {
nsCOMPtr<nsIContent> lastFocusedContent;
esm->GetLastFocusedContent(getter_AddRefs(lastFocusedContent));
nsCOMPtr<nsIDOMElement>
lastFocusedElement(do_QueryInterface(lastFocusedContent));
mFoundLink = lastFocusedElement;
}
}
*aResult = hasWrapped ? FIND_WRAPPED : FIND_FOUND;
@ -512,6 +520,15 @@ nsTypeAheadFind::GetSearchString(nsAString& aSearchString)
return NS_OK;
}
NS_IMETHODIMP
nsTypeAheadFind::GetFoundLink(nsIDOMElement** aFoundLink)
{
NS_ENSURE_ARG_POINTER(aFoundLink);
*aFoundLink = mFoundLink;
NS_IF_ADDREF(*aFoundLink);
return NS_OK;
}
NS_IMETHODIMP
nsTypeAheadFind::GetFocusLinks(PRBool* aFocusLinks)
{

Просмотреть файл

@ -120,6 +120,7 @@ protected:
PRPackedBool mLinksOnly;
PRBool mCaretBrowsingOn;
PRBool mFocusLinks;
nsCOMPtr<nsIDOMElement> mFoundLink;
PRPackedBool mLiteralTextSearchOnly;
PRPackedBool mDontTryExactMatch;
// mAllTheSame Char starts out PR_TRUE, becomes false when