mirror of
https://github.com/roytam1/palemoon27.git
synced 2026-05-26 14:18:48 +00:00
import changes from `dev' branch of rmottola/Arctic-Fox:
- Bug 895274 part.145 Rename NS_SELECTION_SET to eSetSelection r=smaug (5a576f3fc7) - Bug 895274 part.146 Rename NS_MOUSE_SCROLL_START to eLegacyMouseScrollEventFirst r=smaug (a03038ca81) - Bug 895274 part.147 Rename NS_MOUSE_SCROLL to eLegacyMouseLineOrPageScroll r=smaug (a16fa072ad) - Bug 895274 part.148 Rename NS_MOUSE_PIXEL_SCROLL to eLegacyMousePixelScroll r=smaug (85810aa54b) - Bug 895274 part.150 Rename NS_QUERY_CONTENT_EVENT_START to eQueryContentEventFirst r=smaug (36b4be4c20) - Bug 895274 part.151 Rename NS_QUERY_SELECTION_AS_TRANSFERABLE to eQuerySelectionAsTransferable r=smaug (7b50da594a) - Bug 895274 part.152 Rename NS_QUERY_SELECTED_TEXT to eQuerySelectedText r=smaug (3dbd79293f) - Bug 1199224 TSFTextStore should clear mLockedContent unless it needs to wait the content to be modified asynchronously r=emk (70aed5d4c5) - Bug 895274 part.153 Rename NS_QUERY_TEXT_CONTENT to eQueryTextContent r=smaug (9d3a8acf96) - Bug 299603 part.1 IMContextWrapper should have a method to initialize a TextRange r=m_kato (cf04d9b788) - Bug 299603 part.2 IMContextWrapper::SetTextRange() should initialize the range offsets and fail if the range is collapsed r=m_kato (4c64f3f7e7) - Bug 299603 part.3 IMContextWrapper::SetTextRange() shold set the style of the range which is specified by the IME r=m_kato (02b09d3df4) - Bug 1057921 - Don't propagate text decorations through outer <svg> elements. r=dholbert (e1e489eb2b) - Bug 1186721 - Suppress line break due to soft hyphen inside ruby. r=jfkthame (15bdd20955) - Bug 1175789 Draw underline as overline when it's in vertical writing mode and the language is Japanese or Korean r=dbaron (ffdb9f3e5b) - Bug 834830 - Add nsISelectionController.SELECTION_URLSTRIKEOUT to enable striking out parts of the URL in the URL bar r=roc (73d2871c77) - Bug 1155261 - Fix computation of glyph extents and text-frame visual overflow for vertical text frames. r=smontagu (5e94c117c3) - Bug 1140486 patch 1 - Pass block frame instead of block reflow state to nsTextFrame::RecomputeOverflow. r=jfkthame (2ecd788bd1) - Bug 1140486 patch 2 - Make nsTextFrame::UpdateOverflow include the visual overflow from the text metrics by calling existing RecomputeOverflow. r=jfkthame (3452b7edfd) - Bug 299603 part.4 Some global methods in nsTextFrame.cpp should be members of nsTextFrame class r=roc (9ca79dab6f) - Bug 299603 part.5 nsTextFrame should use system foreground or background color when painting IME selections if whose style defines only one of foreground color or background color r=roc (c4843a6c98) - Bug 299603 part.6 Guess the meaning of each clause in the composition string with caret position r=m_kato (364dfcc3b2) - Bug 299603 part.7 IMContextWrapper::CreateTextRange() should convert the caret offset from offset in characters to offset in UTF-16 r=m_kato (d67b116232) - Bug 895274 part.154 Rename NS_QUERY_CARET_RECT to eQueryCaretRect r=smaug (da09b897d9) - Bug 1153634 - Weaken the assertion condition to make it match the condition before. r=roc (02ce185f35) - Bug 299603 part.8 Rename aLastDispatchedData with aCompositionString in IMContextWrapper::CreateTextRangeArray() r=m_kato (998af878dc)
This commit is contained in:
@@ -1934,13 +1934,13 @@ nsDOMWindowUtils::SendQueryContentEvent(uint32_t aType,
|
||||
EventMessage message;
|
||||
switch (aType) {
|
||||
case QUERY_SELECTED_TEXT:
|
||||
message = NS_QUERY_SELECTED_TEXT;
|
||||
message = eQuerySelectedText;
|
||||
break;
|
||||
case QUERY_TEXT_CONTENT:
|
||||
message = NS_QUERY_TEXT_CONTENT;
|
||||
message = eQueryTextContent;
|
||||
break;
|
||||
case QUERY_CARET_RECT:
|
||||
message = NS_QUERY_CARET_RECT;
|
||||
message = eQueryCaretRect;
|
||||
break;
|
||||
case QUERY_TEXT_RECT:
|
||||
message = NS_QUERY_TEXT_RECT;
|
||||
@@ -1992,10 +1992,10 @@ nsDOMWindowUtils::SendQueryContentEvent(uint32_t aType,
|
||||
InitEvent(queryEvent, &pt);
|
||||
|
||||
switch (message) {
|
||||
case NS_QUERY_TEXT_CONTENT:
|
||||
case eQueryTextContent:
|
||||
queryEvent.InitForQueryTextContent(aOffset, aLength, useNativeLineBreak);
|
||||
break;
|
||||
case NS_QUERY_CARET_RECT:
|
||||
case eQueryCaretRect:
|
||||
queryEvent.InitForQueryCaretRect(aOffset, useNativeLineBreak);
|
||||
break;
|
||||
case NS_QUERY_TEXT_RECT:
|
||||
@@ -2033,7 +2033,7 @@ nsDOMWindowUtils::SendSelectionSetEvent(uint32_t aOffset,
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
WidgetSelectionEvent selectionEvent(true, NS_SELECTION_SET, widget);
|
||||
WidgetSelectionEvent selectionEvent(true, eSetSelection, widget);
|
||||
InitEvent(selectionEvent);
|
||||
|
||||
selectionEvent.mOffset = aOffset;
|
||||
|
||||
@@ -16,7 +16,7 @@ interface nsIDOMNode;
|
||||
interface nsISelection;
|
||||
interface nsISelectionDisplay;
|
||||
|
||||
[scriptable, uuid(82c3a9df-9bd6-4da2-b561-d85a9eec5caa)]
|
||||
[scriptable, uuid(e5238312-2f50-4ec1-8e23-6337f3a67727)]
|
||||
interface nsISelectionController : nsISelectionDisplay
|
||||
{
|
||||
const short SELECTION_NONE=0;
|
||||
@@ -29,7 +29,8 @@ interface nsISelectionController : nsISelectionDisplay
|
||||
const short SELECTION_ACCESSIBILITY=64; // For accessibility API usage
|
||||
const short SELECTION_FIND=128;
|
||||
const short SELECTION_URLSECONDARY=256;
|
||||
const short NUM_SELECTIONTYPES=10;
|
||||
const short SELECTION_URLSTRIKEOUT=512;
|
||||
const short NUM_SELECTIONTYPES=11;
|
||||
|
||||
const short SELECTION_ANCHOR_REGION = 0;
|
||||
const short SELECTION_FOCUS_REGION = 1;
|
||||
|
||||
@@ -19,8 +19,9 @@ NS_INTERFACE_MAP_END
|
||||
NS_IMPL_ADDREF(nsQueryContentEventResult)
|
||||
NS_IMPL_RELEASE(nsQueryContentEventResult)
|
||||
|
||||
nsQueryContentEventResult::nsQueryContentEventResult() :
|
||||
mEventID(0), mSucceeded(false)
|
||||
nsQueryContentEventResult::nsQueryContentEventResult()
|
||||
: mEventMessage(eVoidEvent)
|
||||
, mSucceeded(false)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -54,20 +55,19 @@ nsQueryContentEventResult::GetTentativeCaretOffset(uint32_t* aOffset)
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
static bool IsRectEnabled(uint32_t aEventID)
|
||||
static bool IsRectEnabled(EventMessage aEventMessage)
|
||||
{
|
||||
return aEventID == NS_QUERY_CARET_RECT ||
|
||||
aEventID == NS_QUERY_TEXT_RECT ||
|
||||
aEventID == NS_QUERY_EDITOR_RECT ||
|
||||
aEventID == NS_QUERY_CHARACTER_AT_POINT;
|
||||
return aEventMessage == eQueryCaretRect ||
|
||||
aEventMessage == NS_QUERY_TEXT_RECT ||
|
||||
aEventMessage == NS_QUERY_EDITOR_RECT ||
|
||||
aEventMessage == NS_QUERY_CHARACTER_AT_POINT;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetReversed(bool *aReversed)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(mEventID == NS_QUERY_SELECTED_TEXT,
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(mEventMessage == eQuerySelectedText, NS_ERROR_NOT_AVAILABLE);
|
||||
*aReversed = mReversed;
|
||||
return NS_OK;
|
||||
}
|
||||
@@ -76,7 +76,7 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetLeft(int32_t *aLeft)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventID),
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventMessage),
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
*aLeft = mRect.x;
|
||||
return NS_OK;
|
||||
@@ -86,7 +86,7 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetWidth(int32_t *aWidth)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventID),
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventMessage),
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
*aWidth = mRect.width;
|
||||
return NS_OK;
|
||||
@@ -96,7 +96,7 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetTop(int32_t *aTop)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventID),
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventMessage),
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
*aTop = mRect.y;
|
||||
return NS_OK;
|
||||
@@ -106,7 +106,7 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetHeight(int32_t *aHeight)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventID),
|
||||
NS_ENSURE_TRUE(IsRectEnabled(mEventMessage),
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
*aHeight = mRect.height;
|
||||
return NS_OK;
|
||||
@@ -116,8 +116,8 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetText(nsAString &aText)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(mEventID == NS_QUERY_SELECTED_TEXT ||
|
||||
mEventID == NS_QUERY_TEXT_CONTENT,
|
||||
NS_ENSURE_TRUE(mEventMessage == eQuerySelectedText ||
|
||||
mEventMessage == eQueryTextContent,
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
aText = mString;
|
||||
return NS_OK;
|
||||
@@ -126,7 +126,7 @@ nsQueryContentEventResult::GetText(nsAString &aText)
|
||||
NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetSucceeded(bool *aSucceeded)
|
||||
{
|
||||
NS_ENSURE_TRUE(mEventID != 0, NS_ERROR_NOT_INITIALIZED);
|
||||
NS_ENSURE_TRUE(mEventMessage != eVoidEvent, NS_ERROR_NOT_INITIALIZED);
|
||||
*aSucceeded = mSucceeded;
|
||||
return NS_OK;
|
||||
}
|
||||
@@ -135,8 +135,8 @@ NS_IMETHODIMP
|
||||
nsQueryContentEventResult::GetNotFound(bool *aNotFound)
|
||||
{
|
||||
NS_ENSURE_TRUE(mSucceeded, NS_ERROR_NOT_AVAILABLE);
|
||||
NS_ENSURE_TRUE(mEventID == NS_QUERY_SELECTED_TEXT ||
|
||||
mEventID == NS_QUERY_CHARACTER_AT_POINT,
|
||||
NS_ENSURE_TRUE(mEventMessage == eQuerySelectedText ||
|
||||
mEventMessage == NS_QUERY_CHARACTER_AT_POINT,
|
||||
NS_ERROR_NOT_AVAILABLE);
|
||||
*aNotFound = (mOffset == WidgetQueryContentEvent::NOT_FOUND);
|
||||
return NS_OK;
|
||||
@@ -148,7 +148,7 @@ nsQueryContentEventResult::GetTentativeCaretOffsetNotFound(bool* aNotFound)
|
||||
if (NS_WARN_IF(!mSucceeded)) {
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
if (NS_WARN_IF(mEventID != NS_QUERY_CHARACTER_AT_POINT)) {
|
||||
if (NS_WARN_IF(mEventMessage != NS_QUERY_CHARACTER_AT_POINT)) {
|
||||
return NS_ERROR_NOT_AVAILABLE;
|
||||
}
|
||||
*aNotFound = (mTentativeCaretOffset == WidgetQueryContentEvent::NOT_FOUND);
|
||||
@@ -159,7 +159,7 @@ void
|
||||
nsQueryContentEventResult::SetEventResult(nsIWidget* aWidget,
|
||||
const WidgetQueryContentEvent &aEvent)
|
||||
{
|
||||
mEventID = aEvent.mMessage;
|
||||
mEventMessage = aEvent.mMessage;
|
||||
mSucceeded = aEvent.mSucceeded;
|
||||
mReversed = aEvent.mReply.mReversed;
|
||||
mRect = aEvent.mReply.mRect;
|
||||
@@ -167,7 +167,7 @@ nsQueryContentEventResult::SetEventResult(nsIWidget* aWidget,
|
||||
mTentativeCaretOffset = aEvent.mReply.mTentativeCaretOffset;
|
||||
mString = aEvent.mReply.mString;
|
||||
|
||||
if (!IsRectEnabled(mEventID) || !aWidget || !mSucceeded) {
|
||||
if (!IsRectEnabled(mEventMessage) || !aWidget || !mSucceeded) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ public:
|
||||
protected:
|
||||
~nsQueryContentEventResult();
|
||||
|
||||
uint32_t mEventID;
|
||||
mozilla::EventMessage mEventMessage;
|
||||
|
||||
uint32_t mOffset;
|
||||
uint32_t mTentativeCaretOffset;
|
||||
|
||||
@@ -796,11 +796,11 @@ nsresult
|
||||
ContentEventHandler::HandleQueryContentEvent(WidgetQueryContentEvent* aEvent)
|
||||
{
|
||||
switch (aEvent->mMessage) {
|
||||
case NS_QUERY_SELECTED_TEXT:
|
||||
case eQuerySelectedText:
|
||||
return OnQuerySelectedText(aEvent);
|
||||
case NS_QUERY_TEXT_CONTENT:
|
||||
case eQueryTextContent:
|
||||
return OnQueryTextContent(aEvent);
|
||||
case NS_QUERY_CARET_RECT:
|
||||
case eQueryCaretRect:
|
||||
return OnQueryCaretRect(aEvent);
|
||||
case NS_QUERY_TEXT_RECT:
|
||||
return OnQueryTextRect(aEvent);
|
||||
@@ -808,7 +808,7 @@ ContentEventHandler::HandleQueryContentEvent(WidgetQueryContentEvent* aEvent)
|
||||
return OnQueryEditorRect(aEvent);
|
||||
case NS_QUERY_CONTENT_STATE:
|
||||
return OnQueryContentState(aEvent);
|
||||
case NS_QUERY_SELECTION_AS_TRANSFERABLE:
|
||||
case eQuerySelectionAsTransferable:
|
||||
return OnQuerySelectionAsTransferable(aEvent);
|
||||
case NS_QUERY_CHARACTER_AT_POINT:
|
||||
return OnQueryCharacterAtPoint(aEvent);
|
||||
|
||||
@@ -42,11 +42,11 @@ public:
|
||||
// Handle aEvent in the current process.
|
||||
nsresult HandleQueryContentEvent(WidgetQueryContentEvent* aEvent);
|
||||
|
||||
// NS_QUERY_SELECTED_TEXT event handler
|
||||
// eQuerySelectedText event handler
|
||||
nsresult OnQuerySelectedText(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_TEXT_CONTENT event handler
|
||||
// eQueryTextContent event handler
|
||||
nsresult OnQueryTextContent(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_CARET_RECT event handler
|
||||
// eQueryCaretRect event handler
|
||||
nsresult OnQueryCaretRect(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_TEXT_RECT event handler
|
||||
nsresult OnQueryTextRect(WidgetQueryContentEvent* aEvent);
|
||||
@@ -54,7 +54,7 @@ public:
|
||||
nsresult OnQueryEditorRect(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_CONTENT_STATE event handler
|
||||
nsresult OnQueryContentState(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_SELECTION_AS_TRANSFERABLE event handler
|
||||
// eQuerySelectionAsTransferable event handler
|
||||
nsresult OnQuerySelectionAsTransferable(WidgetQueryContentEvent* aEvent);
|
||||
// NS_QUERY_CHARACTER_AT_POINT event handler
|
||||
nsresult OnQueryCharacterAtPoint(WidgetQueryContentEvent* aEvent);
|
||||
|
||||
@@ -649,11 +649,11 @@ NON_IDL_EVENT(DOMFocusOut,
|
||||
eUIEventClass)
|
||||
|
||||
NON_IDL_EVENT(DOMMouseScroll,
|
||||
NS_MOUSE_SCROLL,
|
||||
eLegacyMouseLineOrPageScroll,
|
||||
EventNameType_HTMLXUL,
|
||||
eMouseScrollEventClass)
|
||||
NON_IDL_EVENT(MozMousePixelScroll,
|
||||
NS_MOUSE_PIXEL_SCROLL,
|
||||
eLegacyMousePixelScroll,
|
||||
EventNameType_HTMLXUL,
|
||||
eMouseScrollEventClass)
|
||||
|
||||
|
||||
@@ -759,7 +759,7 @@ EventStateManager::PreHandleEvent(nsPresContext* aPresContext,
|
||||
InitLineOrPageDelta(aTargetFrame, this, wheelEvent);
|
||||
}
|
||||
break;
|
||||
case NS_SELECTION_SET:
|
||||
case eSetSelection:
|
||||
IMEStateManager::HandleSelectionEvent(aPresContext, GetFocusedContent(),
|
||||
aEvent->AsSelectionEvent());
|
||||
break;
|
||||
@@ -784,7 +784,7 @@ EventStateManager::PreHandleEvent(nsPresContext* aPresContext,
|
||||
// If the event is trusted event, set the selected text to data of
|
||||
// composition event.
|
||||
WidgetCompositionEvent* compositionEvent = aEvent->AsCompositionEvent();
|
||||
WidgetQueryContentEvent selectedText(true, NS_QUERY_SELECTED_TEXT,
|
||||
WidgetQueryContentEvent selectedText(true, eQuerySelectedText,
|
||||
compositionEvent->widget);
|
||||
HandleQueryContentEvent(&selectedText);
|
||||
NS_ASSERTION(selectedText.mSucceeded, "Failed to get selected text");
|
||||
@@ -801,9 +801,9 @@ void
|
||||
EventStateManager::HandleQueryContentEvent(WidgetQueryContentEvent* aEvent)
|
||||
{
|
||||
switch (aEvent->mMessage) {
|
||||
case NS_QUERY_SELECTED_TEXT:
|
||||
case NS_QUERY_TEXT_CONTENT:
|
||||
case NS_QUERY_CARET_RECT:
|
||||
case eQuerySelectedText:
|
||||
case eQueryTextContent:
|
||||
case eQueryCaretRect:
|
||||
case NS_QUERY_TEXT_RECT:
|
||||
case NS_QUERY_EDITOR_RECT:
|
||||
if (!IsTargetCrossProcess(aEvent)) {
|
||||
@@ -814,7 +814,7 @@ EventStateManager::HandleQueryContentEvent(WidgetQueryContentEvent* aEvent)
|
||||
return;
|
||||
// Following events have not been supported in e10s mode yet.
|
||||
case NS_QUERY_CONTENT_STATE:
|
||||
case NS_QUERY_SELECTION_AS_TRANSFERABLE:
|
||||
case eQuerySelectionAsTransferable:
|
||||
case NS_QUERY_CHARACTER_AT_POINT:
|
||||
case NS_QUERY_DOM_WIDGET_HITTEST:
|
||||
break;
|
||||
@@ -2209,8 +2209,8 @@ EventStateManager::SendLineScrollEvent(nsIFrame* aTargetFrame,
|
||||
targetContent = targetContent->GetParent();
|
||||
}
|
||||
|
||||
WidgetMouseScrollEvent event(aEvent->mFlags.mIsTrusted, NS_MOUSE_SCROLL,
|
||||
aEvent->widget);
|
||||
WidgetMouseScrollEvent event(aEvent->mFlags.mIsTrusted,
|
||||
eLegacyMouseLineOrPageScroll, aEvent->widget);
|
||||
event.mFlags.mDefaultPrevented = aState.mDefaultPrevented;
|
||||
event.mFlags.mDefaultPreventedByContent = aState.mDefaultPreventedByContent;
|
||||
event.refPoint = aEvent->refPoint;
|
||||
@@ -2249,8 +2249,8 @@ EventStateManager::SendPixelScrollEvent(nsIFrame* aTargetFrame,
|
||||
targetContent = targetContent->GetParent();
|
||||
}
|
||||
|
||||
WidgetMouseScrollEvent event(aEvent->mFlags.mIsTrusted, NS_MOUSE_PIXEL_SCROLL,
|
||||
aEvent->widget);
|
||||
WidgetMouseScrollEvent event(aEvent->mFlags.mIsTrusted,
|
||||
eLegacyMousePixelScroll, aEvent->widget);
|
||||
event.mFlags.mDefaultPrevented = aState.mDefaultPrevented;
|
||||
event.mFlags.mDefaultPreventedByContent = aState.mDefaultPreventedByContent;
|
||||
event.refPoint = aEvent->refPoint;
|
||||
@@ -3101,8 +3101,8 @@ EventStateManager::PostHandleEvent(nsPresContext* aPresContext,
|
||||
break;
|
||||
}
|
||||
case WheelPrefs::ACTION_HISTORY: {
|
||||
// If this event doesn't cause NS_MOUSE_SCROLL event or the direction
|
||||
// is oblique, don't perform history back/forward.
|
||||
// If this event doesn't cause eLegacyMouseLineOrPageScroll event or
|
||||
// the direction is oblique, don't perform history back/forward.
|
||||
int32_t intDelta = wheelEvent->GetPreferredIntDelta();
|
||||
if (!intDelta) {
|
||||
break;
|
||||
@@ -3111,8 +3111,8 @@ EventStateManager::PostHandleEvent(nsPresContext* aPresContext,
|
||||
break;
|
||||
}
|
||||
case WheelPrefs::ACTION_ZOOM: {
|
||||
// If this event doesn't cause NS_MOUSE_SCROLL event or the direction
|
||||
// is oblique, don't perform zoom in/out.
|
||||
// If this event doesn't cause eLegacyMouseLineOrPageScroll event or
|
||||
// the direction is oblique, don't perform zoom in/out.
|
||||
int32_t intDelta = wheelEvent->GetPreferredIntDelta();
|
||||
if (!intDelta) {
|
||||
break;
|
||||
|
||||
@@ -109,8 +109,8 @@ public:
|
||||
nsEventStatus* aStatus);
|
||||
|
||||
/**
|
||||
* DispatchLegacyMouseScrollEvents() dispatches NS_MOUSE_SCROLL event and
|
||||
* NS_MOUSE_PIXEL_SCROLL event for compatiblity with old Gecko.
|
||||
* DispatchLegacyMouseScrollEvents() dispatches eLegacyMouseLineOrPageScroll
|
||||
* event and eLegacyMousePixelScroll event for compatibility with old Gecko.
|
||||
*/
|
||||
void DispatchLegacyMouseScrollEvents(nsIFrame* aTargetFrame,
|
||||
WidgetWheelEvent* aEvent,
|
||||
|
||||
@@ -51,20 +51,20 @@ static const char*
|
||||
ToChar(EventMessage aEventMessage)
|
||||
{
|
||||
switch (aEventMessage) {
|
||||
case NS_QUERY_SELECTED_TEXT:
|
||||
return "NS_QUERY_SELECTED_TEXT";
|
||||
case NS_QUERY_TEXT_CONTENT:
|
||||
return "NS_QUERY_TEXT_CONTENT";
|
||||
case NS_QUERY_CARET_RECT:
|
||||
return "NS_QUERY_CARET_RECT";
|
||||
case eQuerySelectedText:
|
||||
return "eQuerySelectedText";
|
||||
case eQueryTextContent:
|
||||
return "eQueryTextContent";
|
||||
case eQueryCaretRect:
|
||||
return "eQueryCaretRect";
|
||||
case NS_QUERY_TEXT_RECT:
|
||||
return "NS_QUERY_TEXT_RECT";
|
||||
case NS_QUERY_EDITOR_RECT:
|
||||
return "NS_QUERY_EDITOR_RECT";
|
||||
case NS_QUERY_CONTENT_STATE:
|
||||
return "NS_QUERY_CONTENT_STATE";
|
||||
case NS_QUERY_SELECTION_AS_TRANSFERABLE:
|
||||
return "NS_QUERY_SELECTION_AS_TRANSFERABLE";
|
||||
case eQuerySelectionAsTransferable:
|
||||
return "eQuerySelectionAsTransferable";
|
||||
case NS_QUERY_CHARACTER_AT_POINT:
|
||||
return "NS_QUERY_CHARACTER_AT_POINT";
|
||||
case NS_QUERY_DOM_WIDGET_HITTEST:
|
||||
@@ -569,8 +569,7 @@ IMEContentObserver::HandleQueryContentEvent(WidgetQueryContentEvent* aEvent)
|
||||
|
||||
// If the instance has cache, it should use the cached selection which was
|
||||
// sent to the widget.
|
||||
if (aEvent->mMessage == NS_QUERY_SELECTED_TEXT &&
|
||||
aEvent->mUseNativeLineBreak &&
|
||||
if (aEvent->mMessage == eQuerySelectedText && aEvent->mUseNativeLineBreak &&
|
||||
mSelectionData.IsValid()) {
|
||||
aEvent->mReply.mContentsRoot = mRootContent;
|
||||
aEvent->mReply.mHasSelection = !mSelectionData.IsCollapsed();
|
||||
@@ -1109,7 +1108,7 @@ IMEContentObserver::UpdateSelectionCache()
|
||||
|
||||
// XXX Cannot we cache some information for reducing the cost to compute
|
||||
// selection offset and writing mode?
|
||||
WidgetQueryContentEvent selection(true, NS_QUERY_SELECTED_TEXT, mWidget);
|
||||
WidgetQueryContentEvent selection(true, eQuerySelectedText, mWidget);
|
||||
ContentEventHandler handler(GetPresContext());
|
||||
handler.OnQuerySelectedText(&selection);
|
||||
if (NS_WARN_IF(!selection.mSucceeded)) {
|
||||
|
||||
@@ -149,8 +149,8 @@ GetEventMessageName(EventMessage aMessage)
|
||||
return "NS_COMPOSITION_COMMIT_AS_IS";
|
||||
case NS_COMPOSITION_COMMIT:
|
||||
return "NS_COMPOSITION_COMMIT";
|
||||
case NS_SELECTION_SET:
|
||||
return "NS_SELECTION_SET";
|
||||
case eSetSelection:
|
||||
return "eSetSelection";
|
||||
default:
|
||||
return "unacceptable event message";
|
||||
}
|
||||
|
||||
@@ -415,9 +415,7 @@ TextComposition::NotityUpdateComposition(
|
||||
if (aCompositionEvent->mMessage == NS_COMPOSITION_START) {
|
||||
nsCOMPtr<nsIWidget> widget = mPresContext->GetRootWidget();
|
||||
// Update composition start offset
|
||||
WidgetQueryContentEvent selectedTextEvent(true,
|
||||
NS_QUERY_SELECTED_TEXT,
|
||||
widget);
|
||||
WidgetQueryContentEvent selectedTextEvent(true, eQuerySelectedText, widget);
|
||||
widget->DispatchEvent(&selectedTextEvent, status);
|
||||
if (selectedTextEvent.mSucceeded) {
|
||||
mCompositionStartOffset = selectedTextEvent.mReply.mOffset;
|
||||
@@ -615,8 +613,7 @@ TextComposition::CompositionEventDispatcher::Run()
|
||||
switch (mEventMessage) {
|
||||
case NS_COMPOSITION_START: {
|
||||
WidgetCompositionEvent compStart(true, NS_COMPOSITION_START, widget);
|
||||
WidgetQueryContentEvent selectedText(true, NS_QUERY_SELECTED_TEXT,
|
||||
widget);
|
||||
WidgetQueryContentEvent selectedText(true, eQuerySelectedText, widget);
|
||||
ContentEventHandler handler(presContext);
|
||||
handler.OnQuerySelectedText(&selectedText);
|
||||
NS_ASSERTION(selectedText.mSucceeded, "Failed to get selected text");
|
||||
|
||||
@@ -2458,8 +2458,8 @@ nsGenericHTMLFormElement::IsElementDisabledForEvents(EventMessage aMessage,
|
||||
case ePointerEnter:
|
||||
case ePointerLeave:
|
||||
case NS_WHEEL_WHEEL:
|
||||
case NS_MOUSE_SCROLL:
|
||||
case NS_MOUSE_PIXEL_SCROLL:
|
||||
case eLegacyMouseLineOrPageScroll:
|
||||
case eLegacyMousePixelScroll:
|
||||
return false;
|
||||
default:
|
||||
break;
|
||||
|
||||
@@ -2334,7 +2334,7 @@ TabParent::HandleQueryContentEvent(WidgetQueryContentEvent& aEvent)
|
||||
}
|
||||
switch (aEvent.mMessage) {
|
||||
case NS_QUERY_TEXT_RECT:
|
||||
case NS_QUERY_CARET_RECT:
|
||||
case eQueryCaretRect:
|
||||
case NS_QUERY_EDITOR_RECT:
|
||||
aEvent.mReply.mRect -= GetChildProcessOffset();
|
||||
break;
|
||||
|
||||
@@ -1812,7 +1812,7 @@ CocoaEventTypeForEvent(const WidgetGUIEvent& anEvent, nsIFrame* aObjectFrame)
|
||||
case eFocus:
|
||||
case eBlur:
|
||||
return NPCocoaEventFocusChanged;
|
||||
case NS_MOUSE_SCROLL:
|
||||
case eLegacyMouseLineOrPageScroll:
|
||||
return NPCocoaEventScrollWheel;
|
||||
default:
|
||||
return (NPCocoaEventType)0;
|
||||
@@ -1829,7 +1829,7 @@ TranslateToNPCocoaEvent(WidgetGUIEvent* anEvent, nsIFrame* aObjectFrame)
|
||||
if (anEvent->mMessage == eMouseMove ||
|
||||
anEvent->mMessage == eMouseDown ||
|
||||
anEvent->mMessage == eMouseUp ||
|
||||
anEvent->mMessage == NS_MOUSE_SCROLL ||
|
||||
anEvent->mMessage == eLegacyMouseLineOrPageScroll ||
|
||||
anEvent->mMessage == eMouseOver ||
|
||||
anEvent->mMessage == eMouseOut)
|
||||
{
|
||||
@@ -1871,14 +1871,14 @@ TranslateToNPCocoaEvent(WidgetGUIEvent* anEvent, nsIFrame* aObjectFrame)
|
||||
}
|
||||
break;
|
||||
}
|
||||
case NS_MOUSE_SCROLL:
|
||||
{
|
||||
case eLegacyMouseLineOrPageScroll: {
|
||||
WidgetWheelEvent* wheelEvent = anEvent->AsWheelEvent();
|
||||
if (wheelEvent) {
|
||||
cocoaEvent.data.mouse.deltaX = wheelEvent->lineOrPageDeltaX;
|
||||
cocoaEvent.data.mouse.deltaY = wheelEvent->lineOrPageDeltaY;
|
||||
} else {
|
||||
NS_WARNING("NS_MOUSE_SCROLL is not a WidgetWheelEvent? (could be, haven't checked)");
|
||||
NS_WARNING("eLegacyMouseLineOrPageScroll is not a WidgetWheelEvent? "
|
||||
"(could be, haven't checked)");
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
+12
-6
@@ -2081,8 +2081,8 @@ gfxFont::IsSpaceGlyphInvisible(gfxContext *aRefContext, gfxTextRun *aTextRun)
|
||||
GetOrCreateGlyphExtents(aTextRun->GetAppUnitsPerDevUnit());
|
||||
gfxRect glyphExtents;
|
||||
mFontEntry->mSpaceGlyphIsInvisible =
|
||||
extents->GetTightGlyphExtentsAppUnits(this, eHorizontal,
|
||||
aRefContext, GetSpaceGlyph(), &glyphExtents) &&
|
||||
extents->GetTightGlyphExtentsAppUnits(this, aRefContext,
|
||||
GetSpaceGlyph(), &glyphExtents) &&
|
||||
glyphExtents.IsEmpty();
|
||||
mFontEntry->mSpaceGlyphIsInvisibleInitialized = true;
|
||||
}
|
||||
@@ -2189,11 +2189,14 @@ gfxFont::Measure(gfxTextRun *aTextRun,
|
||||
} else {
|
||||
gfxRect glyphRect;
|
||||
if (!extents->GetTightGlyphExtentsAppUnits(this,
|
||||
orientation,
|
||||
aRefContext, glyphIndex, &glyphRect)) {
|
||||
glyphRect = gfxRect(0, metrics.mBoundingBox.Y(),
|
||||
advance, metrics.mBoundingBox.Height());
|
||||
}
|
||||
if (orientation == eVertical) {
|
||||
Swap(glyphRect.x, glyphRect.y);
|
||||
Swap(glyphRect.width, glyphRect.height);
|
||||
}
|
||||
if (isRTL) {
|
||||
glyphRect -= gfxPoint(advance, 0);
|
||||
}
|
||||
@@ -2218,13 +2221,16 @@ gfxFont::Measure(gfxTextRun *aTextRun,
|
||||
gfxRect glyphRect;
|
||||
if (glyphData->IsMissing() || !extents ||
|
||||
!extents->GetTightGlyphExtentsAppUnits(this,
|
||||
orientation,
|
||||
aRefContext, glyphIndex, &glyphRect)) {
|
||||
// We might have failed to get glyph extents due to
|
||||
// OOM or something
|
||||
glyphRect = gfxRect(0, -metrics.mAscent,
|
||||
advance, metrics.mAscent + metrics.mDescent);
|
||||
}
|
||||
if (orientation == eVertical) {
|
||||
Swap(glyphRect.x, glyphRect.y);
|
||||
Swap(glyphRect.width, glyphRect.height);
|
||||
}
|
||||
if (isRTL) {
|
||||
glyphRect -= gfxPoint(advance, 0);
|
||||
}
|
||||
@@ -3108,7 +3114,7 @@ gfxFont::GetOrCreateGlyphExtents(int32_t aAppUnitsPerDevUnit) {
|
||||
}
|
||||
|
||||
void
|
||||
gfxFont::SetupGlyphExtents(gfxContext *aContext, Orientation aOrientation,
|
||||
gfxFont::SetupGlyphExtents(gfxContext *aContext,
|
||||
uint32_t aGlyphID, bool aNeedTight,
|
||||
gfxGlyphExtents *aExtents)
|
||||
{
|
||||
@@ -3134,7 +3140,7 @@ gfxFont::SetupGlyphExtents(gfxContext *aContext, Orientation aOrientation,
|
||||
cairo_text_extents_t extents;
|
||||
cairo_glyph_extents(aContext->GetCairo(), &glyph, 1, &extents);
|
||||
|
||||
const Metrics& fontMetrics = GetMetrics(aOrientation);
|
||||
const Metrics& fontMetrics = GetMetrics(eHorizontal);
|
||||
int32_t appUnitsPerDevUnit = aExtents->GetAppUnitsPerDevUnit();
|
||||
if (!aNeedTight && extents.x_bearing >= 0 &&
|
||||
extents.y_bearing >= -fontMetrics.maxAscent &&
|
||||
|
||||
@@ -1614,8 +1614,7 @@ public:
|
||||
gfxGlyphExtents *GetOrCreateGlyphExtents(int32_t aAppUnitsPerDevUnit);
|
||||
|
||||
// You need to call SetupCairoFont on the aCR just before calling this
|
||||
virtual void SetupGlyphExtents(gfxContext *aContext,
|
||||
Orientation aOrientation, uint32_t aGlyphID,
|
||||
virtual void SetupGlyphExtents(gfxContext *aContext, uint32_t aGlyphID,
|
||||
bool aNeedTight, gfxGlyphExtents *aExtents);
|
||||
|
||||
// This is called by the default Draw() implementation above.
|
||||
|
||||
@@ -36,7 +36,6 @@ gfxGlyphExtents::~gfxGlyphExtents()
|
||||
|
||||
bool
|
||||
gfxGlyphExtents::GetTightGlyphExtentsAppUnits(gfxFont *aFont,
|
||||
gfxFont::Orientation aOrientation,
|
||||
gfxContext *aContext, uint32_t aGlyphID, gfxRect *aExtents)
|
||||
{
|
||||
HashEntry *entry = mTightGlyphExtents.GetEntry(aGlyphID);
|
||||
@@ -50,8 +49,7 @@ gfxGlyphExtents::GetTightGlyphExtentsAppUnits(gfxFont *aFont,
|
||||
#ifdef DEBUG_TEXT_RUN_STORAGE_METRICS
|
||||
++gGlyphExtentsSetupLazyTight;
|
||||
#endif
|
||||
aFont->SetupGlyphExtents(aContext, aOrientation, aGlyphID, true,
|
||||
this);
|
||||
aFont->SetupGlyphExtents(aContext, aGlyphID, true, this);
|
||||
entry = mTightGlyphExtents.GetEntry(aGlyphID);
|
||||
}
|
||||
if (!entry) {
|
||||
|
||||
@@ -63,7 +63,6 @@ public:
|
||||
// Returns true on success. Can fail on OOM or when aContext is null
|
||||
// and extents were not (successfully) prefetched.
|
||||
bool GetTightGlyphExtentsAppUnits(gfxFont *aFont,
|
||||
gfxFont::Orientation aOrientation,
|
||||
gfxContext *aContext, uint32_t aGlyphID, gfxRect *aExtents);
|
||||
|
||||
void SetContainedGlyphWidthAppUnits(uint32_t aGlyphID, uint16_t aWidth) {
|
||||
|
||||
@@ -1374,8 +1374,6 @@ gfxTextRun::FetchGlyphExtents(gfxContext *aRefContext)
|
||||
|
||||
for (j = start; j < end; ++j) {
|
||||
const gfxTextRun::CompressedGlyph *glyphData = &charGlyphs[j];
|
||||
gfxFont::Orientation orientation =
|
||||
IsVertical() ? gfxFont::eVertical : gfxFont::eHorizontal;
|
||||
if (glyphData->IsSimpleGlyph()) {
|
||||
// If we're in speed mode, don't set up glyph extents here; we'll
|
||||
// just return "optimistic" glyph bounds later
|
||||
@@ -1392,7 +1390,7 @@ gfxTextRun::FetchGlyphExtents(gfxContext *aRefContext)
|
||||
#ifdef DEBUG_TEXT_RUN_STORAGE_METRICS
|
||||
++gGlyphExtentsSetupEagerSimple;
|
||||
#endif
|
||||
font->SetupGlyphExtents(aRefContext, orientation,
|
||||
font->SetupGlyphExtents(aRefContext,
|
||||
glyphIndex, false, extents);
|
||||
}
|
||||
}
|
||||
@@ -1418,7 +1416,7 @@ gfxTextRun::FetchGlyphExtents(gfxContext *aRefContext)
|
||||
#ifdef DEBUG_TEXT_RUN_STORAGE_METRICS
|
||||
++gGlyphExtentsSetupEagerTight;
|
||||
#endif
|
||||
font->SetupGlyphExtents(aRefContext, orientation,
|
||||
font->SetupGlyphExtents(aRefContext,
|
||||
glyphIndex, true, extents);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7164,7 +7164,7 @@ PresShell::HandleEvent(nsIFrame* aFrame,
|
||||
if (presShell != this) {
|
||||
nsIFrame* frame = presShell->GetRootFrame();
|
||||
if (!frame) {
|
||||
if (aEvent->mMessage == NS_QUERY_TEXT_CONTENT ||
|
||||
if (aEvent->mMessage == eQueryTextContent ||
|
||||
aEvent->IsContentCommandEvent()) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
@@ -3019,6 +3019,7 @@ nsFrame::HandlePress(nsPresContext* aPresContext,
|
||||
if (curDetail->mType != nsISelectionController::SELECTION_SPELLCHECK &&
|
||||
curDetail->mType != nsISelectionController::SELECTION_FIND &&
|
||||
curDetail->mType != nsISelectionController::SELECTION_URLSECONDARY &&
|
||||
curDetail->mType != nsISelectionController::SELECTION_URLSTRIKEOUT &&
|
||||
curDetail->mStart <= offsets.StartOffset() &&
|
||||
offsets.EndOffset() <= curDetail->mEnd)
|
||||
{
|
||||
|
||||
@@ -3285,7 +3285,7 @@ nsLineLayout::RelativePositionFrames(PerSpanData* psd, nsOverflowAreas& aOverflo
|
||||
if (pfd->mRecomputeOverflow ||
|
||||
frame->StyleContext()->HasTextDecorationLines()) {
|
||||
nsTextFrame* f = static_cast<nsTextFrame*>(frame);
|
||||
r = f->RecomputeOverflow(*mBlockReflowState);
|
||||
r = f->RecomputeOverflow(mBlockReflowState->frame);
|
||||
}
|
||||
frame->FinishAndStoreOverflow(r, frame->GetSize());
|
||||
}
|
||||
|
||||
@@ -275,6 +275,7 @@ GetIndexFromSelectionType(SelectionType aType)
|
||||
case nsISelectionController::SELECTION_ACCESSIBILITY: return 6; break;
|
||||
case nsISelectionController::SELECTION_FIND: return 7; break;
|
||||
case nsISelectionController::SELECTION_URLSECONDARY: return 8; break;
|
||||
case nsISelectionController::SELECTION_URLSTRIKEOUT: return 9; break;
|
||||
default:
|
||||
return -1; break;
|
||||
}
|
||||
@@ -296,6 +297,7 @@ GetSelectionTypeFromIndex(int8_t aIndex)
|
||||
case 6: return nsISelectionController::SELECTION_ACCESSIBILITY; break;
|
||||
case 7: return nsISelectionController::SELECTION_FIND; break;
|
||||
case 8: return nsISelectionController::SELECTION_URLSECONDARY; break;
|
||||
case 9: return nsISelectionController::SELECTION_URLSTRIKEOUT; break;
|
||||
default:
|
||||
return nsISelectionController::SELECTION_NORMAL; break;
|
||||
}
|
||||
|
||||
+236
-153
@@ -354,6 +354,9 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
nscolor GetSystemFieldForegroundColor();
|
||||
nscolor GetSystemFieldBackgroundColor();
|
||||
|
||||
protected:
|
||||
nsTextFrame* mFrame;
|
||||
nsPresContext* mPresContext;
|
||||
@@ -373,6 +376,8 @@ protected:
|
||||
|
||||
int32_t mSufficientContrast;
|
||||
nscolor mFrameBackgroundColor;
|
||||
nscolor mSystemFieldForegroundColor;
|
||||
nscolor mSystemFieldBackgroundColor;
|
||||
|
||||
// selection colors and underline info, the colors are resolved colors if
|
||||
// mResolveColors is true (which is the default), i.e., the foreground color
|
||||
@@ -3637,6 +3642,11 @@ nsTextPaintStyle::InitCommonColors()
|
||||
nscolor defaultBgColor = mPresContext->DefaultBackgroundColor();
|
||||
mFrameBackgroundColor = NS_ComposeColors(defaultBgColor, bgColor);
|
||||
|
||||
mSystemFieldForegroundColor =
|
||||
LookAndFeel::GetColor(LookAndFeel::eColorID__moz_fieldtext);
|
||||
mSystemFieldBackgroundColor =
|
||||
LookAndFeel::GetColor(LookAndFeel::eColorID__moz_field);
|
||||
|
||||
if (bgFrame->IsThemed()) {
|
||||
// Assume a native widget has sufficient contrast always
|
||||
mSufficientContrast = 0;
|
||||
@@ -3664,6 +3674,20 @@ nsTextPaintStyle::InitCommonColors()
|
||||
mInitCommonColors = true;
|
||||
}
|
||||
|
||||
nscolor
|
||||
nsTextPaintStyle::GetSystemFieldForegroundColor()
|
||||
{
|
||||
InitCommonColors();
|
||||
return mSystemFieldForegroundColor;
|
||||
}
|
||||
|
||||
nscolor
|
||||
nsTextPaintStyle::GetSystemFieldBackgroundColor()
|
||||
{
|
||||
InitCommonColors();
|
||||
return mSystemFieldBackgroundColor;
|
||||
}
|
||||
|
||||
static Element*
|
||||
FindElementAncestorForMozSelection(nsIContent* aContent)
|
||||
{
|
||||
@@ -4830,6 +4854,18 @@ LazyGetLineBaselineOffset(nsIFrame* aChildFrame, nsBlockFrame* aBlockFrame)
|
||||
}
|
||||
}
|
||||
|
||||
static bool IsUnderlineRight(nsIFrame* aFrame)
|
||||
{
|
||||
nsIAtom* langAtom = aFrame->StyleFont()->mLanguage;
|
||||
if (!langAtom) {
|
||||
return false;
|
||||
}
|
||||
nsAtomString langStr(langAtom);
|
||||
return (StringBeginsWith(langStr, NS_LITERAL_STRING("ja")) ||
|
||||
StringBeginsWith(langStr, NS_LITERAL_STRING("ko"))) &&
|
||||
(langStr.Length() == 2 || langStr[2] == '-');
|
||||
}
|
||||
|
||||
void
|
||||
nsTextFrame::GetTextDecorations(
|
||||
nsPresContext* aPresContext,
|
||||
@@ -4928,11 +4964,19 @@ nsTextFrame::GetTextDecorations(
|
||||
color = nsLayoutUtils::GetColor(f, eCSSProperty_text_decoration_color);
|
||||
}
|
||||
|
||||
if (textDecorations & NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE) {
|
||||
bool swapUnderlineAndOverline = vertical && IsUnderlineRight(f);
|
||||
const uint8_t kUnderline =
|
||||
swapUnderlineAndOverline ? NS_STYLE_TEXT_DECORATION_LINE_OVERLINE :
|
||||
NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE;
|
||||
const uint8_t kOverline =
|
||||
swapUnderlineAndOverline ? NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE :
|
||||
NS_STYLE_TEXT_DECORATION_LINE_OVERLINE;
|
||||
|
||||
if (textDecorations & kUnderline) {
|
||||
aDecorations.mUnderlines.AppendElement(
|
||||
nsTextFrame::LineDecoration(f, baselineOffset, color, style));
|
||||
}
|
||||
if (textDecorations & NS_STYLE_TEXT_DECORATION_LINE_OVERLINE) {
|
||||
if (textDecorations & kOverline) {
|
||||
aDecorations.mOverlines.AppendElement(
|
||||
nsTextFrame::LineDecoration(f, baselineOffset, color, style));
|
||||
}
|
||||
@@ -4965,6 +5009,12 @@ nsTextFrame::GetTextDecorations(
|
||||
if (f->IsFloating() || f->IsAbsolutelyPositioned()) {
|
||||
break;
|
||||
}
|
||||
|
||||
// If we're an outer <svg> element, which is classified as an atomic
|
||||
// inline-level element, we're done.
|
||||
if (f->GetType() == nsGkAtoms::svgOuterSVGFrame) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -5175,16 +5225,16 @@ nsTextFrame::UnionAdditionalOverflow(nsPresContext* aPresContext,
|
||||
AddStateBits(TEXT_SELECTION_UNDERLINE_OVERFLOWED);
|
||||
}
|
||||
|
||||
static gfxFloat
|
||||
ComputeDescentLimitForSelectionUnderline(nsPresContext* aPresContext,
|
||||
nsTextFrame* aFrame,
|
||||
const gfxFont::Metrics& aFontMetrics)
|
||||
gfxFloat
|
||||
nsTextFrame::ComputeDescentLimitForSelectionUnderline(
|
||||
nsPresContext* aPresContext,
|
||||
const gfxFont::Metrics& aFontMetrics)
|
||||
{
|
||||
gfxFloat app = aPresContext->AppUnitsPerDevPixel();
|
||||
nscoord lineHeightApp =
|
||||
nsHTMLReflowState::CalcLineHeight(aFrame->GetContent(),
|
||||
aFrame->StyleContext(), NS_AUTOHEIGHT,
|
||||
aFrame->GetFontSizeInflation());
|
||||
nsHTMLReflowState::CalcLineHeight(GetContent(),
|
||||
StyleContext(), NS_AUTOHEIGHT,
|
||||
GetFontSizeInflation());
|
||||
gfxFloat lineHeight = gfxFloat(lineHeightApp) / app;
|
||||
if (lineHeight <= aFontMetrics.maxHeight) {
|
||||
return aFontMetrics.maxDescent;
|
||||
@@ -5196,15 +5246,18 @@ ComputeDescentLimitForSelectionUnderline(nsPresContext* aPresContext,
|
||||
// Make sure this stays in sync with DrawSelectionDecorations below
|
||||
static const SelectionType SelectionTypesWithDecorations =
|
||||
nsISelectionController::SELECTION_SPELLCHECK |
|
||||
nsISelectionController::SELECTION_URLSTRIKEOUT |
|
||||
nsISelectionController::SELECTION_IME_RAWINPUT |
|
||||
nsISelectionController::SELECTION_IME_SELECTEDRAWTEXT |
|
||||
nsISelectionController::SELECTION_IME_CONVERTEDTEXT |
|
||||
nsISelectionController::SELECTION_IME_SELECTEDCONVERTEDTEXT;
|
||||
|
||||
static gfxFloat
|
||||
ComputeSelectionUnderlineHeight(nsPresContext* aPresContext,
|
||||
const gfxFont::Metrics& aFontMetrics,
|
||||
SelectionType aSelectionType)
|
||||
/* static */
|
||||
gfxFloat
|
||||
nsTextFrame::ComputeSelectionUnderlineHeight(
|
||||
nsPresContext* aPresContext,
|
||||
const gfxFont::Metrics& aFontMetrics,
|
||||
SelectionType aSelectionType)
|
||||
{
|
||||
switch (aSelectionType) {
|
||||
case nsISelectionController::SELECTION_IME_RAWINPUT:
|
||||
@@ -5232,28 +5285,22 @@ ComputeSelectionUnderlineHeight(nsPresContext* aPresContext,
|
||||
}
|
||||
}
|
||||
|
||||
enum DecorationType {
|
||||
eNormalDecoration,
|
||||
eSelectionDecoration
|
||||
};
|
||||
|
||||
static void
|
||||
PaintDecorationLine(nsIFrame* aFrame,
|
||||
gfxContext* const aCtx,
|
||||
const gfxRect& aDirtyRect,
|
||||
nscolor aColor,
|
||||
const nscolor* aOverrideColor,
|
||||
const gfxPoint& aPt,
|
||||
gfxFloat aICoordInFrame,
|
||||
const gfxSize& aLineSize,
|
||||
gfxFloat aAscent,
|
||||
gfxFloat aOffset,
|
||||
uint8_t aDecoration,
|
||||
uint8_t aStyle,
|
||||
DecorationType aDecorationType,
|
||||
nsTextFrame::DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical,
|
||||
gfxFloat aDescentLimit = -1.0)
|
||||
void
|
||||
nsTextFrame::PaintDecorationLine(gfxContext* const aCtx,
|
||||
const gfxRect& aDirtyRect,
|
||||
nscolor aColor,
|
||||
const nscolor* aOverrideColor,
|
||||
const gfxPoint& aPt,
|
||||
gfxFloat aICoordInFrame,
|
||||
const gfxSize& aLineSize,
|
||||
gfxFloat aAscent,
|
||||
gfxFloat aOffset,
|
||||
uint8_t aDecoration,
|
||||
uint8_t aStyle,
|
||||
DecorationType aDecorationType,
|
||||
DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical,
|
||||
gfxFloat aDescentLimit /* = -1.0 */)
|
||||
{
|
||||
nscolor lineColor = aOverrideColor ? *aOverrideColor : aColor;
|
||||
if (aCallbacks) {
|
||||
@@ -5262,7 +5309,7 @@ PaintDecorationLine(nsIFrame* aFrame,
|
||||
} else {
|
||||
aCallbacks->NotifyBeforeSelectionDecorationLine(lineColor);
|
||||
}
|
||||
nsCSSRendering::DecorationLineToPath(aFrame, aCtx, aDirtyRect, lineColor,
|
||||
nsCSSRendering::DecorationLineToPath(this, aCtx, aDirtyRect, lineColor,
|
||||
aPt, aICoordInFrame, aLineSize, aAscent, aOffset, aDecoration, aStyle,
|
||||
aVertical, aDescentLimit);
|
||||
if (aDecorationType == eNormalDecoration) {
|
||||
@@ -5271,7 +5318,7 @@ PaintDecorationLine(nsIFrame* aFrame,
|
||||
aCallbacks->NotifySelectionDecorationLinePathEmitted();
|
||||
}
|
||||
} else {
|
||||
nsCSSRendering::PaintDecorationLine(aFrame, *aCtx->GetDrawTarget(),
|
||||
nsCSSRendering::PaintDecorationLine(this, *aCtx->GetDrawTarget(),
|
||||
ToRect(aDirtyRect), lineColor,
|
||||
aPt, Float(aICoordInFrame), aLineSize, aAscent, aOffset, aDecoration, aStyle,
|
||||
aVertical, aDescentLimit);
|
||||
@@ -5282,16 +5329,20 @@ PaintDecorationLine(nsIFrame* aFrame,
|
||||
* This, plus SelectionTypesWithDecorations, encapsulates all knowledge about
|
||||
* drawing text decoration for selections.
|
||||
*/
|
||||
static void DrawSelectionDecorations(gfxContext* aContext,
|
||||
const gfxRect& aDirtyRect,
|
||||
SelectionType aType,
|
||||
nsTextFrame* aFrame,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
const gfxPoint& aPt, gfxFloat aICoordInFrame, gfxFloat aWidth,
|
||||
gfxFloat aAscent, const gfxFont::Metrics& aFontMetrics,
|
||||
nsTextFrame::DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical)
|
||||
void
|
||||
nsTextFrame::DrawSelectionDecorations(gfxContext* aContext,
|
||||
const gfxRect& aDirtyRect,
|
||||
SelectionType aType,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
const gfxPoint& aPt,
|
||||
gfxFloat aICoordInFrame,
|
||||
gfxFloat aWidth,
|
||||
gfxFloat aAscent,
|
||||
const gfxFont::Metrics& aFontMetrics,
|
||||
DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical,
|
||||
uint8_t aDecoration)
|
||||
{
|
||||
gfxPoint pt(aPt);
|
||||
gfxSize size(aWidth,
|
||||
@@ -5299,7 +5350,7 @@ static void DrawSelectionDecorations(gfxContext* aContext,
|
||||
aFontMetrics, aType));
|
||||
gfxFloat descentLimit =
|
||||
ComputeDescentLimitForSelectionUnderline(aTextPaintStyle.PresContext(),
|
||||
aFrame, aFontMetrics);
|
||||
aFontMetrics);
|
||||
|
||||
float relativeSize;
|
||||
uint8_t style;
|
||||
@@ -5310,6 +5361,9 @@ static void DrawSelectionDecorations(gfxContext* aContext,
|
||||
aTextPaintStyle.GetSelectionUnderlineForPaint(index, &color,
|
||||
&relativeSize, &style);
|
||||
|
||||
gfxFloat offset = aDecoration == NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE ?
|
||||
aFontMetrics.underlineOffset : aFontMetrics.maxAscent;
|
||||
|
||||
switch (aType) {
|
||||
case nsISelectionController::SELECTION_IME_RAWINPUT:
|
||||
case nsISelectionController::SELECTION_IME_SELECTEDRAWTEXT:
|
||||
@@ -5342,13 +5396,25 @@ static void DrawSelectionDecorations(gfxContext* aContext,
|
||||
// There is no underline style definition.
|
||||
return;
|
||||
}
|
||||
if (aRangeStyle.IsUnderlineColorDefined()) {
|
||||
// If underline color is defined and that doesn't depend on the
|
||||
// foreground color, we should use the color directly.
|
||||
if (aRangeStyle.IsUnderlineColorDefined() &&
|
||||
aRangeStyle.IsForegroundColorDefined() &&
|
||||
aRangeStyle.mUnderlineColor != aRangeStyle.mForegroundColor) {
|
||||
color = aRangeStyle.mUnderlineColor;
|
||||
} else if (aRangeStyle.IsForegroundColorDefined()) {
|
||||
color = aRangeStyle.mForegroundColor;
|
||||
} else {
|
||||
NS_ASSERTION(!aRangeStyle.IsBackgroundColorDefined(),
|
||||
"Only the background color is defined");
|
||||
}
|
||||
// If foreground color or background color is defined, the both colors
|
||||
// are computed by GetSelectionTextColors(). Then, we should use its
|
||||
// foreground color always. The color should have sufficient contrast
|
||||
// with the background color.
|
||||
else if (aRangeStyle.IsForegroundColorDefined() ||
|
||||
aRangeStyle.IsBackgroundColorDefined()) {
|
||||
nscolor bg;
|
||||
GetSelectionTextColors(aType, aTextPaintStyle, aRangeStyle,
|
||||
&color, &bg);
|
||||
}
|
||||
// Otherwise, use the foreground color of the frame.
|
||||
else {
|
||||
color = aTextPaintStyle.GetTextColor();
|
||||
}
|
||||
} else if (!weDefineSelectionUnderline) {
|
||||
@@ -5362,30 +5428,37 @@ static void DrawSelectionDecorations(gfxContext* aContext,
|
||||
if (!weDefineSelectionUnderline)
|
||||
return;
|
||||
break;
|
||||
case nsISelectionController::SELECTION_URLSTRIKEOUT: {
|
||||
nscoord inflationMinFontSize =
|
||||
nsLayoutUtils::InflationMinFontSizeFor(this);
|
||||
float inflation =
|
||||
GetInflationForTextDecorations(this, inflationMinFontSize);
|
||||
const gfxFont::Metrics metrics =
|
||||
GetFirstFontMetrics(GetFontGroupForFrame(this, inflation), aVertical);
|
||||
|
||||
relativeSize = 2.0f;
|
||||
offset = metrics.strikeoutOffset + 0.5;
|
||||
aDecoration = NS_STYLE_TEXT_DECORATION_LINE_LINE_THROUGH;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
NS_WARNING("Requested selection decorations when there aren't any");
|
||||
return;
|
||||
}
|
||||
size.height *= relativeSize;
|
||||
PaintDecorationLine(aFrame, aContext, aDirtyRect, color, nullptr, pt,
|
||||
PaintDecorationLine(aContext, aDirtyRect, color, nullptr, pt,
|
||||
(aVertical ? (pt.y - aPt.y) : (pt.x - aPt.x)) + aICoordInFrame,
|
||||
size, aAscent, aFontMetrics.underlineOffset,
|
||||
NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE, style, eSelectionDecoration,
|
||||
size, aAscent, offset, aDecoration, style, eSelectionDecoration,
|
||||
aCallbacks, aVertical, descentLimit);
|
||||
}
|
||||
|
||||
/**
|
||||
* This function encapsulates all knowledge of how selections affect foreground
|
||||
* and background colors.
|
||||
* @return true if the selection affects colors, false otherwise
|
||||
* @param aForeground the foreground color to use
|
||||
* @param aBackground the background color to use, or RGBA(0,0,0,0) if no
|
||||
* background should be painted
|
||||
*/
|
||||
static bool GetSelectionTextColors(SelectionType aType,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
nscolor* aForeground, nscolor* aBackground)
|
||||
/* static */
|
||||
bool
|
||||
nsTextFrame::GetSelectionTextColors(SelectionType aType,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
nscolor* aForeground,
|
||||
nscolor* aBackground)
|
||||
{
|
||||
switch (aType) {
|
||||
case nsISelectionController::SELECTION_NORMAL:
|
||||
@@ -5402,17 +5475,28 @@ static bool GetSelectionTextColors(SelectionType aType,
|
||||
case nsISelectionController::SELECTION_IME_CONVERTEDTEXT:
|
||||
case nsISelectionController::SELECTION_IME_SELECTEDCONVERTEDTEXT:
|
||||
if (aRangeStyle.IsDefined()) {
|
||||
*aForeground = aTextPaintStyle.GetTextColor();
|
||||
*aBackground = NS_RGBA(0,0,0,0);
|
||||
if (!aRangeStyle.IsForegroundColorDefined() &&
|
||||
!aRangeStyle.IsBackgroundColorDefined()) {
|
||||
*aForeground = aTextPaintStyle.GetTextColor();
|
||||
*aBackground = NS_RGBA(0,0,0,0);
|
||||
return false;
|
||||
}
|
||||
if (aRangeStyle.IsForegroundColorDefined()) {
|
||||
*aForeground = aRangeStyle.mForegroundColor;
|
||||
}
|
||||
if (aRangeStyle.IsBackgroundColorDefined()) {
|
||||
if (aRangeStyle.IsBackgroundColorDefined()) {
|
||||
*aBackground = aRangeStyle.mBackgroundColor;
|
||||
} else {
|
||||
// If foreground color is defined but background color isn't
|
||||
// defined, we can guess that IME must expect that the background
|
||||
// color is system's default field background color.
|
||||
*aBackground = aTextPaintStyle.GetSystemFieldBackgroundColor();
|
||||
}
|
||||
} else { // aRangeStyle.IsBackgroundColorDefined() is true
|
||||
*aBackground = aRangeStyle.mBackgroundColor;
|
||||
// If background color is defined but foreground color isn't defined,
|
||||
// we can assume that IME must expect that the foreground color is
|
||||
// same as system's field text color.
|
||||
*aForeground = aTextPaintStyle.GetSystemFieldForegroundColor();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -5568,6 +5652,9 @@ AddHyphenToMetrics(nsTextFrame* aTextFrame, gfxTextRun* aBaseTextRun,
|
||||
gfxTextRun::Metrics hyphenMetrics =
|
||||
hyphenTextRun->MeasureText(0, hyphenTextRun->GetLength(),
|
||||
aBoundingBoxType, aContext, nullptr);
|
||||
if (aTextFrame->GetWritingMode().IsLineInverted()) {
|
||||
hyphenMetrics.mBoundingBox.y = -hyphenMetrics.mBoundingBox.YMost();
|
||||
}
|
||||
aMetrics->CombineWith(hyphenMetrics, aBaseTextRun->IsRightToLeft());
|
||||
}
|
||||
|
||||
@@ -5832,6 +5919,10 @@ nsTextFrame::PaintTextSelectionDecorations(gfxContext* aCtx,
|
||||
|
||||
gfxFont* firstFont = aProvider.GetFontGroup()->GetFirstValidFont();
|
||||
bool verticalRun = mTextRun->IsVertical();
|
||||
bool rightUnderline = verticalRun && IsUnderlineRight(this);
|
||||
const uint8_t kDecoration =
|
||||
rightUnderline ? NS_STYLE_TEXT_DECORATION_LINE_OVERLINE :
|
||||
NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE;
|
||||
bool useVerticalMetrics = verticalRun && mTextRun->UseCenterBaseline();
|
||||
gfxFont::Metrics
|
||||
decorationMetrics(firstFont->GetMetrics(useVerticalMetrics ?
|
||||
@@ -5875,10 +5966,10 @@ nsTextFrame::PaintTextSelectionDecorations(gfxContext* aCtx,
|
||||
}
|
||||
gfxFloat width = Abs(advance) / app;
|
||||
gfxFloat xInFrame = pt.x - (aFramePt.x / app);
|
||||
DrawSelectionDecorations(aCtx, dirtyRect, aSelectionType, this,
|
||||
DrawSelectionDecorations(aCtx, dirtyRect, aSelectionType,
|
||||
aTextPaintStyle, selectedStyle, pt, xInFrame,
|
||||
width, mAscent / app, decorationMetrics,
|
||||
aCallbacks, verticalRun);
|
||||
aCallbacks, verticalRun, kDecoration);
|
||||
}
|
||||
iterator.UpdateWithAdvance(advance);
|
||||
}
|
||||
@@ -6388,7 +6479,7 @@ nsTextFrame::DrawTextRunAndDecorations(
|
||||
decSize.height = metrics.underlineSize;
|
||||
bCoord = (frameBStart - dec.mBaselineOffset) / app;
|
||||
|
||||
PaintDecorationLine(this, aCtx, dirtyRect, dec.mColor,
|
||||
PaintDecorationLine(aCtx, dirtyRect, dec.mColor,
|
||||
aDecorationOverrideColor, decPt, 0.0, decSize, ascent,
|
||||
metrics.underlineOffset, NS_STYLE_TEXT_DECORATION_LINE_UNDERLINE,
|
||||
dec.mStyle, eNormalDecoration, aCallbacks, verticalRun);
|
||||
@@ -6409,7 +6500,7 @@ nsTextFrame::DrawTextRunAndDecorations(
|
||||
decSize.height = metrics.underlineSize;
|
||||
bCoord = (frameBStart - dec.mBaselineOffset) / app;
|
||||
|
||||
PaintDecorationLine(this, aCtx, dirtyRect, dec.mColor,
|
||||
PaintDecorationLine(aCtx, dirtyRect, dec.mColor,
|
||||
aDecorationOverrideColor, decPt, 0.0, decSize, ascent,
|
||||
metrics.maxAscent, NS_STYLE_TEXT_DECORATION_LINE_OVERLINE, dec.mStyle,
|
||||
eNormalDecoration, aCallbacks, verticalRun);
|
||||
@@ -6436,7 +6527,7 @@ nsTextFrame::DrawTextRunAndDecorations(
|
||||
decSize.height = metrics.strikeoutSize;
|
||||
bCoord = (frameBStart - dec.mBaselineOffset) / app;
|
||||
|
||||
PaintDecorationLine(this, aCtx, dirtyRect, dec.mColor,
|
||||
PaintDecorationLine(aCtx, dirtyRect, dec.mColor,
|
||||
aDecorationOverrideColor, decPt, 0.0, decSize, ascent,
|
||||
metrics.strikeoutOffset, NS_STYLE_TEXT_DECORATION_LINE_LINE_THROUGH,
|
||||
dec.mStyle, eNormalDecoration, aCallbacks, verticalRun);
|
||||
@@ -6647,7 +6738,7 @@ nsTextFrame::CombineSelectionUnderlineRect(nsPresContext* aPresContext,
|
||||
gfxFloat underlineOffset = fontGroup->GetUnderlineOffset();
|
||||
gfxFloat ascent = aPresContext->AppUnitsToGfxUnits(mAscent);
|
||||
gfxFloat descentLimit =
|
||||
ComputeDescentLimitForSelectionUnderline(aPresContext, this, metrics);
|
||||
ComputeDescentLimitForSelectionUnderline(aPresContext, metrics);
|
||||
|
||||
SelectionDetails *details = GetSelectionDetails();
|
||||
for (SelectionDetails *sd = details; sd; sd = sd->mNext) {
|
||||
@@ -7654,8 +7745,9 @@ nsTextFrame::AddInlinePrefISizeForFlow(nsRenderingContext *aRenderingContext,
|
||||
// XXXldb Shouldn't we be including the newline as part of the
|
||||
// segment that it ends rather than part of the segment that it
|
||||
// starts?
|
||||
NS_ASSERTION(preformatNewlines,
|
||||
"We can't be here unless newlines are hard breaks");
|
||||
NS_ASSERTION(preformatNewlines || preformatTabs,
|
||||
"We can't be here unless newlines are "
|
||||
"hard breaks or there are tabs");
|
||||
preformattedNewline = preformatNewlines && textRun->CharIsNewline(i);
|
||||
preformattedTab = preformatTabs && textRun->CharIsTab(i);
|
||||
if (!preformattedNewline && !preformattedTab) {
|
||||
@@ -7799,12 +7891,12 @@ nsTextFrame::ComputeTightBounds(gfxContext* aContext) const
|
||||
ComputeTransformedLength(provider),
|
||||
gfxFont::TIGHT_HINTED_OUTLINE_EXTENTS,
|
||||
aContext, &provider);
|
||||
if (GetWritingMode().IsLineInverted()) {
|
||||
metrics.mBoundingBox.y = -metrics.mBoundingBox.YMost();
|
||||
}
|
||||
// mAscent should be the same as metrics.mAscent, but it's what we use to
|
||||
// paint so that's the one we'll use.
|
||||
nsRect boundingBox = RoundOut(metrics.mBoundingBox);
|
||||
if (GetWritingMode().IsLineInverted()) {
|
||||
boundingBox.y = -boundingBox.YMost();
|
||||
}
|
||||
boundingBox += nsPoint(0, mAscent);
|
||||
if (mTextRun->IsVertical()) {
|
||||
// Swap line-relative textMetrics dimensions to physical coordinates.
|
||||
@@ -8375,7 +8467,8 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
(GetStateBits() & TEXT_IS_IN_TOKEN_MATHML);
|
||||
gfxBreakPriority breakPriority = aLineLayout.LastOptionalBreakPriority();
|
||||
gfxTextRun::SuppressBreak suppressBreak = gfxTextRun::eNoSuppressBreak;
|
||||
if (ShouldSuppressLineBreak()) {
|
||||
bool shouldSuppressLineBreak = ShouldSuppressLineBreak();
|
||||
if (shouldSuppressLineBreak) {
|
||||
suppressBreak = gfxTextRun::eSuppressAllBreaks;
|
||||
} else if (!aLineLayout.LineIsBreakable()) {
|
||||
suppressBreak = gfxTextRun::eSuppressInitialBreak;
|
||||
@@ -8398,6 +8491,10 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
textMetrics.mDescent = gfxFloat(fm->MaxDescent());
|
||||
}
|
||||
}
|
||||
if (GetWritingMode().IsLineInverted()) {
|
||||
Swap(textMetrics.mAscent, textMetrics.mDescent);
|
||||
textMetrics.mBoundingBox.y = -textMetrics.mBoundingBox.YMost();
|
||||
}
|
||||
// The "end" iterator points to the first character after the string mapped
|
||||
// by this frame. Basically, its original-string offset is offset+charsFit
|
||||
// after we've computed charsFit.
|
||||
@@ -8503,31 +8600,21 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
finalSize.BSize(wm) = 0;
|
||||
} else if (boundingBoxType != gfxFont::LOOSE_INK_EXTENTS) {
|
||||
// Use actual text metrics for floating first letter frame.
|
||||
if (wm.IsLineInverted()) {
|
||||
aMetrics.SetBlockStartAscent(NSToCoordCeil(textMetrics.mDescent));
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() +
|
||||
NSToCoordCeil(textMetrics.mAscent);
|
||||
} else {
|
||||
aMetrics.SetBlockStartAscent(NSToCoordCeil(textMetrics.mAscent));
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() +
|
||||
NSToCoordCeil(textMetrics.mDescent);
|
||||
}
|
||||
aMetrics.SetBlockStartAscent(NSToCoordCeil(textMetrics.mAscent));
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() +
|
||||
NSToCoordCeil(textMetrics.mDescent);
|
||||
} else {
|
||||
// Otherwise, ascent should contain the overline drawable area.
|
||||
// And also descent should contain the underline drawable area.
|
||||
// nsFontMetrics::GetMaxAscent/GetMaxDescent contains them.
|
||||
nsFontMetrics* fm = provider.GetFontMetrics();
|
||||
nscoord fontAscent = fm->MaxAscent();
|
||||
nscoord fontDescent = fm->MaxDescent();
|
||||
if (wm.IsLineInverted()) {
|
||||
aMetrics.SetBlockStartAscent(std::max(NSToCoordCeil(textMetrics.mDescent), fontDescent));
|
||||
nscoord descent = std::max(NSToCoordCeil(textMetrics.mAscent), fontAscent);
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() + descent;
|
||||
} else {
|
||||
aMetrics.SetBlockStartAscent(std::max(NSToCoordCeil(textMetrics.mAscent), fontAscent));
|
||||
nscoord descent = std::max(NSToCoordCeil(textMetrics.mDescent), fontDescent);
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() + descent;
|
||||
}
|
||||
nscoord fontAscent =
|
||||
wm.IsLineInverted() ? fm->MaxDescent() : fm->MaxAscent();
|
||||
nscoord fontDescent =
|
||||
wm.IsLineInverted() ? fm->MaxAscent() : fm->MaxDescent();
|
||||
aMetrics.SetBlockStartAscent(std::max(NSToCoordCeil(textMetrics.mAscent), fontAscent));
|
||||
nscoord descent = std::max(NSToCoordCeil(textMetrics.mDescent), fontDescent);
|
||||
finalSize.BSize(wm) = aMetrics.BlockStartAscent() + descent;
|
||||
}
|
||||
aMetrics.SetSize(wm, finalSize);
|
||||
|
||||
@@ -8541,14 +8628,18 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
|
||||
// Handle text that runs outside its normal bounds.
|
||||
nsRect boundingBox = RoundOut(textMetrics.mBoundingBox);
|
||||
if (wm.IsLineInverted()) {
|
||||
boundingBox.y = -boundingBox.YMost();
|
||||
}
|
||||
boundingBox += nsPoint(0, mAscent);
|
||||
if (mTextRun->IsVertical()) {
|
||||
// Swap line-relative textMetrics dimensions to physical coordinates.
|
||||
Swap(boundingBox.x, boundingBox.y);
|
||||
Swap(boundingBox.width, boundingBox.height);
|
||||
if (GetWritingMode().IsVerticalRL()) {
|
||||
boundingBox.x = -boundingBox.XMost();
|
||||
boundingBox.x += aMetrics.Width() - mAscent;
|
||||
} else {
|
||||
boundingBox.x += mAscent;
|
||||
}
|
||||
} else {
|
||||
boundingBox.y += mAscent;
|
||||
}
|
||||
aMetrics.SetOverflowAreasToDesiredBounds();
|
||||
aMetrics.VisualOverflow().UnionRect(aMetrics.VisualOverflow(), boundingBox);
|
||||
@@ -8572,36 +8663,38 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
aLineLayout.SetTrimmableISize(NSToCoordFloor(trimmableWidth));
|
||||
AddStateBits(TEXT_HAS_NONCOLLAPSED_CHARACTERS);
|
||||
}
|
||||
if (charsFit > 0 && charsFit == length &&
|
||||
textStyle->mHyphens != NS_STYLE_HYPHENS_NONE &&
|
||||
HasSoftHyphenBefore(frag, mTextRun, offset, end)) {
|
||||
bool fits =
|
||||
textMetrics.mAdvanceWidth + provider.GetHyphenWidth() <= availWidth;
|
||||
// Record a potential break after final soft hyphen
|
||||
aLineLayout.NotifyOptionalBreakPosition(this, length, fits,
|
||||
gfxBreakPriority::eNormalBreak);
|
||||
}
|
||||
bool breakAfter = forceBreakAfter;
|
||||
// length == 0 means either the text is empty or it's all collapsed away
|
||||
bool emptyTextAtStartOfLine = atStartOfLine && length == 0;
|
||||
if (!breakAfter && charsFit == length && !emptyTextAtStartOfLine &&
|
||||
transformedOffset + transformedLength == mTextRun->GetLength() &&
|
||||
!ShouldSuppressLineBreak() &&
|
||||
(mTextRun->GetFlags() & nsTextFrameUtils::TEXT_HAS_TRAILING_BREAK)) {
|
||||
// We placed all the text in the textrun and we have a break opportunity at
|
||||
// the end of the textrun. We need to record it because the following
|
||||
// content may not care about nsLineBreaker.
|
||||
|
||||
// Note that because we didn't break, we can be sure that (thanks to the
|
||||
// code up above) textMetrics.mAdvanceWidth includes the width of any
|
||||
// trailing whitespace. So we need to subtract trimmableWidth here
|
||||
// because if we did break at this point, that much width would be trimmed.
|
||||
if (textMetrics.mAdvanceWidth - trimmableWidth > availWidth) {
|
||||
breakAfter = true;
|
||||
} else {
|
||||
aLineLayout.NotifyOptionalBreakPosition(this, length, true,
|
||||
if (!shouldSuppressLineBreak) {
|
||||
if (charsFit > 0 && charsFit == length &&
|
||||
textStyle->mHyphens != NS_STYLE_HYPHENS_NONE &&
|
||||
HasSoftHyphenBefore(frag, mTextRun, offset, end)) {
|
||||
bool fits =
|
||||
textMetrics.mAdvanceWidth + provider.GetHyphenWidth() <= availWidth;
|
||||
// Record a potential break after final soft hyphen
|
||||
aLineLayout.NotifyOptionalBreakPosition(this, length, fits,
|
||||
gfxBreakPriority::eNormalBreak);
|
||||
}
|
||||
// length == 0 means either the text is empty or it's all collapsed away
|
||||
bool emptyTextAtStartOfLine = atStartOfLine && length == 0;
|
||||
if (!breakAfter && charsFit == length && !emptyTextAtStartOfLine &&
|
||||
transformedOffset + transformedLength == mTextRun->GetLength() &&
|
||||
(mTextRun->GetFlags() & nsTextFrameUtils::TEXT_HAS_TRAILING_BREAK)) {
|
||||
// We placed all the text in the textrun and we have a break opportunity
|
||||
// at the end of the textrun. We need to record it because the following
|
||||
// content may not care about nsLineBreaker.
|
||||
|
||||
// Note that because we didn't break, we can be sure that (thanks to the
|
||||
// code up above) textMetrics.mAdvanceWidth includes the width of any
|
||||
// trailing whitespace. So we need to subtract trimmableWidth here
|
||||
// because if we did break at this point, that much width would be
|
||||
// trimmed.
|
||||
if (textMetrics.mAdvanceWidth - trimmableWidth > availWidth) {
|
||||
breakAfter = true;
|
||||
} else {
|
||||
aLineLayout.NotifyOptionalBreakPosition(this, length, true,
|
||||
gfxBreakPriority::eNormalBreak);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Compute reflow status
|
||||
@@ -8650,7 +8743,7 @@ nsTextFrame::ReflowText(nsLineLayout& aLineLayout, nscoord aAvailableWidth,
|
||||
if (!textStyle->WhiteSpaceIsSignificant() &&
|
||||
(lineContainer->StyleText()->mTextAlign == NS_STYLE_TEXT_ALIGN_JUSTIFY ||
|
||||
lineContainer->StyleText()->mTextAlignLast == NS_STYLE_TEXT_ALIGN_JUSTIFY ||
|
||||
ShouldSuppressLineBreak()) &&
|
||||
shouldSuppressLineBreak) &&
|
||||
!lineContainer->IsSVGText()) {
|
||||
AddStateBits(TEXT_JUSTIFICATION_ENABLED);
|
||||
provider.ComputeJustification(offset, charsFit);
|
||||
@@ -8754,7 +8847,7 @@ nsTextFrame::TrimTrailingWhiteSpace(nsRenderingContext* aRC)
|
||||
}
|
||||
|
||||
nsOverflowAreas
|
||||
nsTextFrame::RecomputeOverflow(const nsHTMLReflowState& aBlockReflowState)
|
||||
nsTextFrame::RecomputeOverflow(nsIFrame* aBlockFrame)
|
||||
{
|
||||
nsRect bounds(nsPoint(0, 0), GetSize());
|
||||
nsOverflowAreas result(bounds, bounds);
|
||||
@@ -8772,10 +8865,10 @@ nsTextFrame::RecomputeOverflow(const nsHTMLReflowState& aBlockReflowState)
|
||||
ComputeTransformedLength(provider),
|
||||
gfxFont::LOOSE_INK_EXTENTS, nullptr,
|
||||
&provider);
|
||||
nsRect boundingBox = RoundOut(textMetrics.mBoundingBox);
|
||||
if (GetWritingMode().IsLineInverted()) {
|
||||
boundingBox.y = -boundingBox.YMost();
|
||||
textMetrics.mBoundingBox.y = -textMetrics.mBoundingBox.YMost();
|
||||
}
|
||||
nsRect boundingBox = RoundOut(textMetrics.mBoundingBox);
|
||||
boundingBox += nsPoint(0, mAscent);
|
||||
if (mTextRun->IsVertical()) {
|
||||
// Swap line-relative textMetrics dimensions to physical coordinates.
|
||||
@@ -8784,8 +8877,7 @@ nsTextFrame::RecomputeOverflow(const nsHTMLReflowState& aBlockReflowState)
|
||||
}
|
||||
nsRect &vis = result.VisualOverflow();
|
||||
vis.UnionRect(vis, boundingBox);
|
||||
UnionAdditionalOverflow(PresContext(), aBlockReflowState.frame, provider,
|
||||
&vis, true);
|
||||
UnionAdditionalOverflow(PresContext(), aBlockFrame, provider, &vis, true);
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -9159,18 +9251,9 @@ nsTextFrame::HasAnyNoncollapsedCharacters()
|
||||
bool
|
||||
nsTextFrame::UpdateOverflow()
|
||||
{
|
||||
const nsRect rect(nsPoint(0, 0), GetSize());
|
||||
nsOverflowAreas overflowAreas(rect, rect);
|
||||
|
||||
if (GetStateBits() & NS_FRAME_FIRST_REFLOW) {
|
||||
return false;
|
||||
}
|
||||
gfxSkipCharsIterator iter = EnsureTextRun(nsTextFrame::eInflated);
|
||||
if (!mTextRun) {
|
||||
return false;
|
||||
}
|
||||
PropertyProvider provider(this, iter, nsTextFrame::eInflated);
|
||||
provider.InitializeForDisplay(true);
|
||||
|
||||
nsIFrame* decorationsBlock;
|
||||
if (IsFloatingFirstLetterChild()) {
|
||||
@@ -9192,8 +9275,8 @@ nsTextFrame::UpdateOverflow()
|
||||
}
|
||||
}
|
||||
|
||||
UnionAdditionalOverflow(PresContext(), decorationsBlock, provider,
|
||||
&overflowAreas.VisualOverflow(), true);
|
||||
nsOverflowAreas overflowAreas = RecomputeOverflow(decorationsBlock);
|
||||
|
||||
return FinishAndStoreOverflow(overflowAreas, GetSize());
|
||||
}
|
||||
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#define nsTextFrame_h__
|
||||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "mozilla/EventForwards.h"
|
||||
#include "mozilla/gfx/2D.h"
|
||||
#include "nsFrame.h"
|
||||
#include "nsGenericDOMDataNode.h"
|
||||
@@ -40,6 +41,7 @@ public:
|
||||
};
|
||||
|
||||
class nsTextFrame : public nsTextFrameBase {
|
||||
typedef mozilla::TextRangeStyle TextRangeStyle;
|
||||
typedef mozilla::gfx::DrawTarget DrawTarget;
|
||||
typedef mozilla::gfx::Rect Rect;
|
||||
|
||||
@@ -281,8 +283,7 @@ public:
|
||||
TextOffsetType aOffsetType =
|
||||
TextOffsetType::OFFSETS_IN_CONTENT_TEXT) override;
|
||||
|
||||
nsOverflowAreas
|
||||
RecomputeOverflow(const nsHTMLReflowState& aBlockReflowState);
|
||||
nsOverflowAreas RecomputeOverflow(nsIFrame* aBlockFrame);
|
||||
|
||||
enum TextRunType {
|
||||
// Anything in reflow (but not intrinsic width calculation) or
|
||||
@@ -745,6 +746,74 @@ protected:
|
||||
bool CombineSelectionUnderlineRect(nsPresContext* aPresContext,
|
||||
nsRect& aRect);
|
||||
|
||||
/**
|
||||
* Utility methods to paint selection.
|
||||
*/
|
||||
void DrawSelectionDecorations(gfxContext* aContext,
|
||||
const gfxRect& aDirtyRect,
|
||||
SelectionType aType,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
const gfxPoint& aPt,
|
||||
gfxFloat aICoordInFrame,
|
||||
gfxFloat aWidth,
|
||||
gfxFloat aAscent,
|
||||
const gfxFont::Metrics& aFontMetrics,
|
||||
DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical,
|
||||
uint8_t aDecoration);
|
||||
enum DecorationType
|
||||
{
|
||||
eNormalDecoration,
|
||||
eSelectionDecoration
|
||||
};
|
||||
void PaintDecorationLine(gfxContext* const aCtx,
|
||||
const gfxRect& aDirtyRect,
|
||||
nscolor aColor,
|
||||
const nscolor* aOverrideColor,
|
||||
const gfxPoint& aPt,
|
||||
gfxFloat aICoordInFrame,
|
||||
const gfxSize& aLineSize,
|
||||
gfxFloat aAscent,
|
||||
gfxFloat aOffset,
|
||||
uint8_t aDecoration,
|
||||
uint8_t aStyle,
|
||||
DecorationType aDecorationType,
|
||||
DrawPathCallbacks* aCallbacks,
|
||||
bool aVertical,
|
||||
gfxFloat aDescentLimit = -1.0);
|
||||
/**
|
||||
* ComputeDescentLimitForSelectionUnderline() computes the most far position
|
||||
* where we can put selection underline.
|
||||
*
|
||||
* @return The maximum underline offset from the baseline (positive value
|
||||
* means that the underline can put below the baseline).
|
||||
*/
|
||||
gfxFloat ComputeDescentLimitForSelectionUnderline(
|
||||
nsPresContext* aPresContext,
|
||||
const gfxFont::Metrics& aFontMetrics);
|
||||
/**
|
||||
* This function encapsulates all knowledge of how selections affect
|
||||
* foreground and background colors.
|
||||
* @param aForeground the foreground color to use
|
||||
* @param aBackground the background color to use, or RGBA(0,0,0,0) if no
|
||||
* background should be painted
|
||||
* @return true if the selection affects colors, false otherwise
|
||||
*/
|
||||
static bool GetSelectionTextColors(SelectionType aType,
|
||||
nsTextPaintStyle& aTextPaintStyle,
|
||||
const TextRangeStyle &aRangeStyle,
|
||||
nscolor* aForeground,
|
||||
nscolor* aBackground);
|
||||
/**
|
||||
* ComputeSelectionUnderlineHeight() computes selection underline height of
|
||||
* the specified selection type from the font metrics.
|
||||
*/
|
||||
static gfxFloat ComputeSelectionUnderlineHeight(
|
||||
nsPresContext* aPresContext,
|
||||
const gfxFont::Metrics& aFontMetrics,
|
||||
SelectionType aSelectionType);
|
||||
|
||||
ContentOffsets GetCharacterOffsetAtFramePointInternal(nsPoint aPoint,
|
||||
bool aForInsertionPoint);
|
||||
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Bug 1186720 - Line break suppression with soft hyphen</title>
|
||||
</head>
|
||||
<body style="width: 1px">
|
||||
x<ruby>a</ruby>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,10 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Bug 1186720 - Line break suppression with soft hyphen</title>
|
||||
</head>
|
||||
<body style="width: 1px">
|
||||
x<ruby>a­</ruby>
|
||||
</body>
|
||||
</html>
|
||||
@@ -30,6 +30,7 @@ test-pref(dom.meta-viewport.enabled,true) test-pref(font.size.inflation.emPerLin
|
||||
== line-break-suppression-2.html line-break-suppression-2-ref.html
|
||||
== line-break-suppression-3.html line-break-suppression-3-ref.html
|
||||
== line-break-suppression-4.html line-break-suppression-4-ref.html
|
||||
== line-break-suppression-5.html line-break-suppression-5-ref.html
|
||||
== line-height-1.html line-height-1-ref.html
|
||||
== line-height-2.html line-height-2-ref.html
|
||||
== line-height-3.html line-height-3-ref.html
|
||||
|
||||
@@ -1 +1,2 @@
|
||||
pref(layout.css.ruby.enabled,true) == ruby-text-decoration-01.html ruby-text-decoration-01-ref.html
|
||||
== text-decoration-propagation-01.html text-decoration-propagation-01-ref.html
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
<!DOCTYPE html>
|
||||
<meta charset="utf-8">
|
||||
<title>CSS Test Reference</title>
|
||||
<link rel="author" title="Cameron McCormack" href="mailto:cam@mcc.id.au">
|
||||
<span>
|
||||
<svg width="400" height="100">
|
||||
<text x="10" y="30">This text must not be underlined.</text>
|
||||
</svg>
|
||||
</span>
|
||||
@@ -0,0 +1,15 @@
|
||||
<!DOCTYPE html>
|
||||
<meta charset="utf-8">
|
||||
<title>CSS Test: text-decoration shouldn't propagate through 'svg' element</title>
|
||||
<link rel="author" title="Cameron McCormack" href="mailto:cam@mcc.id.au">
|
||||
<link rel="help" href="http://www.w3.org/TR/css-text-decor-3/#line-decoration">
|
||||
<link rel="match" href="text-decoration-propagation-01-ref.html">
|
||||
<meta name="assert" content="An outer 'svg' element is an atomic inline-axis element, so text decorations must not propagate through it.">
|
||||
<style>
|
||||
span { text-decoration: underline; }
|
||||
</style>
|
||||
<span>
|
||||
<svg width="400" height="100">
|
||||
<text x="10" y="30">This text must not be underlined.</text>
|
||||
</svg>
|
||||
</span>
|
||||
@@ -0,0 +1,91 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>Bug 1175789 - underline and overline in various language</title>
|
||||
<style type="text/css">
|
||||
body {
|
||||
font-family: "Arial", "Helvetica", "sans-serif";
|
||||
}
|
||||
div {
|
||||
padding: .5em 1em;
|
||||
line-height: 2em;
|
||||
}
|
||||
.underline {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.overline {
|
||||
text-decoration: overline;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<dl>
|
||||
<dt>lang="en-US"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ja"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ko"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ja-JP"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ko-KR"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="overline">underline</span><br>
|
||||
<span class="underline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="zh"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,91 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>Bug 1175789 - underline and overline in various language</title>
|
||||
<style type="text/css">
|
||||
body {
|
||||
font-family: "Arial", "Helvetica", "sans-serif";
|
||||
}
|
||||
div {
|
||||
padding: .5em 1em;
|
||||
line-height: 2em;
|
||||
}
|
||||
.underline {
|
||||
text-decoration: underline;
|
||||
}
|
||||
.overline {
|
||||
text-decoration: overline;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<dl>
|
||||
<dt>lang="en-US"</dt>
|
||||
<dd lang="en-US">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ja"</dt>
|
||||
<dd lang="ja">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ko"</dt>
|
||||
<dd lang="ko">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ja-JP"</dt>
|
||||
<dd lang="ja-JP">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="ko-KR"</dt>
|
||||
<dd lang="ko-KR">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
<dt>lang="zh"</dt>
|
||||
<dd lang="zh">
|
||||
<div style="writing-mode: vertical-rl;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
<div style="writing-mode: vertical-lr;">
|
||||
<span class="underline">underline</span><br>
|
||||
<span class="overline">overline</span>
|
||||
</div>
|
||||
</dd>
|
||||
</dl>
|
||||
</body>
|
||||
</html>
|
||||
@@ -149,6 +149,7 @@ test-pref(dom.meta-viewport.enabled,true) test-pref(font.size.inflation.emPerLin
|
||||
== 1172774-percent-padding-3.html 1172774-percent-vertical-ref.html
|
||||
== 1172774-percent-padding-4.html 1172774-percent-vertical-ref.html
|
||||
== 1174450-intrinsic-sizing.html 1174450-intrinsic-sizing-ref.html
|
||||
== 1175789-underline-overline-1.html 1175789-underline-overline-1-ref.html
|
||||
|
||||
# Suite of tests from Gérard Talbot in bug 1079151
|
||||
include abspos/reftest.list
|
||||
|
||||
+11
-11
@@ -39,8 +39,8 @@ GetEventMessageName(EventMessage aMessage)
|
||||
return "NS_COMPOSITION_COMMIT_AS_IS";
|
||||
case NS_COMPOSITION_COMMIT:
|
||||
return "NS_COMPOSITION_COMMIT";
|
||||
case NS_SELECTION_SET:
|
||||
return "NS_SELECTION_SET";
|
||||
case eSetSelection:
|
||||
return "eSetSelection";
|
||||
default:
|
||||
return "unacceptable event message";
|
||||
}
|
||||
@@ -177,7 +177,7 @@ ContentCacheInChild::CacheSelection(nsIWidget* aWidget,
|
||||
mSelection.Clear();
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
WidgetQueryContentEvent selection(true, NS_QUERY_SELECTED_TEXT, aWidget);
|
||||
WidgetQueryContentEvent selection(true, eQuerySelectedText, aWidget);
|
||||
aWidget->DispatchEvent(&selection, status);
|
||||
if (NS_WARN_IF(!selection.mSucceeded)) {
|
||||
MOZ_LOG(sContentCacheLog, LogLevel::Error,
|
||||
@@ -219,7 +219,7 @@ ContentCacheInChild::CacheCaret(nsIWidget* aWidget,
|
||||
mCaret.mOffset = mSelection.StartOffset();
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
WidgetQueryContentEvent caretRect(true, NS_QUERY_CARET_RECT, aWidget);
|
||||
WidgetQueryContentEvent caretRect(true, eQueryCaretRect, aWidget);
|
||||
caretRect.InitForQueryCaretRect(mCaret.mOffset);
|
||||
aWidget->DispatchEvent(&caretRect, status);
|
||||
if (NS_WARN_IF(!caretRect.mSucceeded)) {
|
||||
@@ -276,7 +276,7 @@ ContentCacheInChild::CacheText(nsIWidget* aWidget,
|
||||
this, aWidget, GetNotificationName(aNotification)));
|
||||
|
||||
nsEventStatus status = nsEventStatus_eIgnore;
|
||||
WidgetQueryContentEvent queryText(true, NS_QUERY_TEXT_CONTENT, aWidget);
|
||||
WidgetQueryContentEvent queryText(true, eQueryTextContent, aWidget);
|
||||
queryText.InitForQueryTextContent(0, UINT32_MAX);
|
||||
aWidget->DispatchEvent(&queryText, status);
|
||||
if (NS_WARN_IF(!queryText.mSucceeded)) {
|
||||
@@ -516,10 +516,10 @@ ContentCacheInParent::HandleQueryContentEvent(WidgetQueryContentEvent& aEvent,
|
||||
aEvent.mReply.mFocusedWidget = aWidget;
|
||||
|
||||
switch (aEvent.mMessage) {
|
||||
case NS_QUERY_SELECTED_TEXT:
|
||||
case eQuerySelectedText:
|
||||
MOZ_LOG(sContentCacheLog, LogLevel::Info,
|
||||
("ContentCacheInParent: 0x%p HandleQueryContentEvent("
|
||||
"aEvent={ mMessage=NS_QUERY_SELECTED_TEXT }, aWidget=0x%p)",
|
||||
"aEvent={ mMessage=eQuerySelectedText }, aWidget=0x%p)",
|
||||
this, aWidget));
|
||||
if (NS_WARN_IF(!IsSelectionValid())) {
|
||||
// If content cache hasn't been initialized properly, make the query
|
||||
@@ -557,10 +557,10 @@ ContentCacheInParent::HandleQueryContentEvent(WidgetQueryContentEvent& aEvent,
|
||||
GetBoolName(aEvent.mReply.mHasSelection),
|
||||
GetWritingModeName(aEvent.mReply.mWritingMode).get()));
|
||||
break;
|
||||
case NS_QUERY_TEXT_CONTENT: {
|
||||
case eQueryTextContent: {
|
||||
MOZ_LOG(sContentCacheLog, LogLevel::Info,
|
||||
("ContentCacheInParent: 0x%p HandleQueryContentEvent("
|
||||
"aEvent={ mMessage=NS_QUERY_TEXT_CONTENT, mInput={ mOffset=%u, "
|
||||
"aEvent={ mMessage=eQueryTextContent, mInput={ mOffset=%u, "
|
||||
"mLength=%u } }, aWidget=0x%p), mText.Length()=%u",
|
||||
this, aEvent.mInput.mOffset,
|
||||
aEvent.mInput.mLength, aWidget, mText.Length()));
|
||||
@@ -638,10 +638,10 @@ ContentCacheInParent::HandleQueryContentEvent(WidgetQueryContentEvent& aEvent,
|
||||
GetWritingModeName(aEvent.mReply.mWritingMode).get(),
|
||||
GetRectText(aEvent.mReply.mRect).get()));
|
||||
break;
|
||||
case NS_QUERY_CARET_RECT:
|
||||
case eQueryCaretRect:
|
||||
MOZ_LOG(sContentCacheLog, LogLevel::Info,
|
||||
("ContentCacheInParent: 0x%p HandleQueryContentEvent("
|
||||
"aEvent={ mMessage=NS_QUERY_CARET_RECT, mInput={ mOffset=%u } }, "
|
||||
"aEvent={ mMessage=eQueryCaretRect, mInput={ mOffset=%u } }, "
|
||||
"aWidget=0x%p), mText.Length()=%u",
|
||||
this, aEvent.mInput.mOffset, aWidget, mText.Length()));
|
||||
if (NS_WARN_IF(!IsSelectionValid())) {
|
||||
|
||||
@@ -282,13 +282,13 @@ public:
|
||||
/**
|
||||
* HandleQueryContentEvent() sets content data to aEvent.mReply.
|
||||
*
|
||||
* For NS_QUERY_SELECTED_TEXT, fail if the cache doesn't contain the whole
|
||||
* For eQuerySelectedText, fail if the cache doesn't contain the whole
|
||||
* selected range. (This shouldn't happen because PuppetWidget should have
|
||||
* already sent the whole selection.)
|
||||
*
|
||||
* For NS_QUERY_TEXT_CONTENT, fail only if the cache doesn't overlap with
|
||||
* For eQueryTextContent, fail only if the cache doesn't overlap with
|
||||
* the queried range. Note the difference from above. We use
|
||||
* this behavior because a normal NS_QUERY_TEXT_CONTENT event is allowed to
|
||||
* this behavior because a normal eQueryTextContent event is allowed to
|
||||
* have out-of-bounds offsets, so that widget can request content without
|
||||
* knowing the exact length of text. It's up to widget to handle cases when
|
||||
* the returned offset/length are different from the queried offset/length.
|
||||
@@ -296,7 +296,7 @@ public:
|
||||
* For NS_QUERY_TEXT_RECT, fail if cached offset/length aren't equals to input.
|
||||
* Cocoa widget always queries selected offset, so it works on it.
|
||||
*
|
||||
* For NS_QUERY_CARET_RECT, fail if cached offset isn't equals to input
|
||||
* For eQueryCaretRect, fail if cached offset isn't equals to input
|
||||
*
|
||||
* For NS_QUERY_EDITOR_RECT, always success
|
||||
*/
|
||||
|
||||
+15
-15
@@ -123,10 +123,10 @@ NS_EVENT_MESSAGE(eXULPopupHidden, eXULEventFirst + 3)
|
||||
NS_EVENT_MESSAGE(eXULBroadcast, eXULEventFirst + 5)
|
||||
NS_EVENT_MESSAGE(eXULCommandUpdate, eXULEventFirst + 6)
|
||||
|
||||
// Scroll events
|
||||
NS_EVENT_MESSAGE(NS_MOUSE_SCROLL_START, 1600)
|
||||
NS_EVENT_MESSAGE(NS_MOUSE_SCROLL, NS_MOUSE_SCROLL_START)
|
||||
NS_EVENT_MESSAGE(NS_MOUSE_PIXEL_SCROLL, NS_MOUSE_SCROLL_START + 1)
|
||||
// Legacy mouse scroll (wheel) events
|
||||
NS_EVENT_MESSAGE(eLegacyMouseScrollEventFirst, 1600)
|
||||
NS_EVENT_MESSAGE(eLegacyMouseLineOrPageScroll, eLegacyMouseScrollEventFirst)
|
||||
NS_EVENT_MESSAGE(eLegacyMousePixelScroll, eLegacyMouseScrollEventFirst + 1)
|
||||
|
||||
NS_EVENT_MESSAGE(NS_SCROLLPORT_START, 1700)
|
||||
NS_EVENT_MESSAGE(NS_SCROLLPORT_UNDERFLOW, NS_SCROLLPORT_START)
|
||||
@@ -212,36 +212,36 @@ NS_EVENT_MESSAGE(eCut, eClipboardEventFirst + 1)
|
||||
NS_EVENT_MESSAGE(ePaste, eClipboardEventFirst + 2)
|
||||
|
||||
// Query the content information
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CONTENT_EVENT_START, 3200)
|
||||
NS_EVENT_MESSAGE(eQueryContentEventFirst, 3200)
|
||||
// Query for the selected text information, it return the selection offset,
|
||||
// selection length and selected text.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_SELECTED_TEXT, NS_QUERY_CONTENT_EVENT_START)
|
||||
NS_EVENT_MESSAGE(eQuerySelectedText, eQueryContentEventFirst)
|
||||
// Query for the text content of specified range, it returns actual lengh (if
|
||||
// the specified range is too long) and the text of the specified range.
|
||||
// Returns the entire text if requested length > actual length.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_TEXT_CONTENT, NS_QUERY_CONTENT_EVENT_START + 1)
|
||||
NS_EVENT_MESSAGE(eQueryTextContent, eQueryContentEventFirst + 1)
|
||||
// Query for the caret rect of nth insertion point. The offset of the result is
|
||||
// relative position from the top level widget.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CARET_RECT, NS_QUERY_CONTENT_EVENT_START + 3)
|
||||
NS_EVENT_MESSAGE(eQueryCaretRect, eQueryContentEventFirst + 3)
|
||||
// Query for the bounding rect of a range of characters. This works on any
|
||||
// valid character range given offset and length. Result is relative to top
|
||||
// level widget coordinates
|
||||
NS_EVENT_MESSAGE(NS_QUERY_TEXT_RECT, NS_QUERY_CONTENT_EVENT_START + 4)
|
||||
NS_EVENT_MESSAGE(NS_QUERY_TEXT_RECT, eQueryContentEventFirst + 4)
|
||||
// Query for the bounding rect of the current focused frame. Result is relative
|
||||
// to top level widget coordinates
|
||||
NS_EVENT_MESSAGE(NS_QUERY_EDITOR_RECT, NS_QUERY_CONTENT_EVENT_START + 5)
|
||||
NS_EVENT_MESSAGE(NS_QUERY_EDITOR_RECT, eQueryContentEventFirst + 5)
|
||||
// Query for the current state of the content. The particular members of
|
||||
// mReply that are set for each query content event will be valid on success.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CONTENT_STATE, NS_QUERY_CONTENT_EVENT_START + 6)
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CONTENT_STATE, eQueryContentEventFirst + 6)
|
||||
// Query for the selection in the form of a nsITransferable.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_SELECTION_AS_TRANSFERABLE, NS_QUERY_CONTENT_EVENT_START + 7)
|
||||
NS_EVENT_MESSAGE(eQuerySelectionAsTransferable, eQueryContentEventFirst + 7)
|
||||
// Query for character at a point. This returns the character offset, its
|
||||
// rect and also tentative caret point if the point is clicked. The point is
|
||||
// specified by Event::refPoint.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CHARACTER_AT_POINT, NS_QUERY_CONTENT_EVENT_START + 8)
|
||||
NS_EVENT_MESSAGE(NS_QUERY_CHARACTER_AT_POINT, eQueryContentEventFirst + 8)
|
||||
// Query if the DOM element under Event::refPoint belongs to our widget
|
||||
// or not.
|
||||
NS_EVENT_MESSAGE(NS_QUERY_DOM_WIDGET_HITTEST, NS_QUERY_CONTENT_EVENT_START + 9)
|
||||
NS_EVENT_MESSAGE(NS_QUERY_DOM_WIDGET_HITTEST, eQueryContentEventFirst + 9)
|
||||
|
||||
// Video events
|
||||
NS_EVENT_MESSAGE(eMediaEventFirst, 3300)
|
||||
@@ -295,7 +295,7 @@ NS_EVENT_MESSAGE(ePluginInputEvent, ePluginEventFirst)
|
||||
// Events to manipulate selection (WidgetSelectionEvent)
|
||||
NS_EVENT_MESSAGE(eSelectionEventFirst, 3700)
|
||||
// Clear any previous selection and set the given range as the selection
|
||||
NS_EVENT_MESSAGE(NS_SELECTION_SET, eSelectionEventFirst)
|
||||
NS_EVENT_MESSAGE(eSetSelection, eSelectionEventFirst)
|
||||
|
||||
// Events of commands for the contents
|
||||
NS_EVENT_MESSAGE(NS_CONTENT_COMMAND_EVENT_START, 3800)
|
||||
|
||||
+10
-9
@@ -399,11 +399,11 @@ public:
|
||||
}
|
||||
|
||||
// The delta value of mouse scroll event.
|
||||
// If the event message is NS_MOUSE_SCROLL, the value indicates scroll amount
|
||||
// in lines. However, if the value is nsIDOMUIEvent::SCROLL_PAGE_UP or
|
||||
// nsIDOMUIEvent::SCROLL_PAGE_DOWN, the value inducates one page scroll.
|
||||
// If the event message is NS_MOUSE_PIXEL_SCROLL, the value indicates scroll
|
||||
// amount in pixels.
|
||||
// If the event message is eLegacyMouseLineOrPageScroll, the value indicates
|
||||
// scroll amount in lines. However, if the value is
|
||||
// nsIDOMUIEvent::SCROLL_PAGE_UP or nsIDOMUIEvent::SCROLL_PAGE_DOWN, the
|
||||
// value inducates one page scroll. If the event message is
|
||||
// eLegacyMousePixelScroll, the value indicates scroll amount in pixels.
|
||||
int32_t delta;
|
||||
|
||||
// If this is true, it may cause to scroll horizontally.
|
||||
@@ -499,13 +499,14 @@ public:
|
||||
|
||||
// If device event handlers don't know when they should set lineOrPageDeltaX
|
||||
// and lineOrPageDeltaY, this is true. Otherwise, false.
|
||||
// If mIsNoLineOrPageDelta is true, ESM will generate NS_MOUSE_SCROLL events
|
||||
// when accumulated delta values reach a line height.
|
||||
// If mIsNoLineOrPageDelta is true, ESM will generate
|
||||
// eLegacyMouseLineOrPageScroll events when accumulated delta values reach
|
||||
// a line height.
|
||||
bool mIsNoLineOrPageDelta;
|
||||
|
||||
// If widget sets lineOrPageDelta, EventStateManager will dispatch
|
||||
// NS_MOUSE_SCROLL event for compatibility. Note that the delta value means
|
||||
// pages if the deltaMode is DOM_DELTA_PAGE, otherwise, lines.
|
||||
// eLegacyMouseLineOrPageScroll event for compatibility. Note that the delta
|
||||
// value means pages if the deltaMode is DOM_DELTA_PAGE, otherwise, lines.
|
||||
int32_t lineOrPageDeltaX;
|
||||
int32_t lineOrPageDeltaY;
|
||||
|
||||
|
||||
+9
-9
@@ -495,7 +495,7 @@ public:
|
||||
void InitForQueryTextContent(uint32_t aOffset, uint32_t aLength,
|
||||
bool aUseNativeLineBreak = true)
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_TEXT_CONTENT,
|
||||
NS_ASSERTION(mMessage == eQueryTextContent,
|
||||
"wrong initializer is called");
|
||||
mInput.mOffset = aOffset;
|
||||
mInput.mLength = aLength;
|
||||
@@ -505,7 +505,7 @@ public:
|
||||
void InitForQueryCaretRect(uint32_t aOffset,
|
||||
bool aUseNativeLineBreak = true)
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_CARET_RECT,
|
||||
NS_ASSERTION(mMessage == eQueryCaretRect,
|
||||
"wrong initializer is called");
|
||||
mInput.mOffset = aOffset;
|
||||
mUseNativeLineBreak = aUseNativeLineBreak;
|
||||
@@ -530,29 +530,29 @@ public:
|
||||
|
||||
void RequestFontRanges()
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_TEXT_CONTENT,
|
||||
NS_ASSERTION(mMessage == eQueryTextContent,
|
||||
"not querying text content");
|
||||
mWithFontRanges = true;
|
||||
}
|
||||
|
||||
uint32_t GetSelectionStart(void) const
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_SELECTED_TEXT,
|
||||
NS_ASSERTION(mMessage == eQuerySelectedText,
|
||||
"not querying selection");
|
||||
return mReply.mOffset + (mReply.mReversed ? mReply.mString.Length() : 0);
|
||||
}
|
||||
|
||||
uint32_t GetSelectionEnd(void) const
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_SELECTED_TEXT,
|
||||
NS_ASSERTION(mMessage == eQuerySelectedText,
|
||||
"not querying selection");
|
||||
return mReply.mOffset + (mReply.mReversed ? 0 : mReply.mString.Length());
|
||||
}
|
||||
|
||||
mozilla::WritingMode GetWritingMode(void) const
|
||||
{
|
||||
NS_ASSERTION(mMessage == NS_QUERY_SELECTED_TEXT ||
|
||||
mMessage == NS_QUERY_CARET_RECT ||
|
||||
NS_ASSERTION(mMessage == eQuerySelectedText ||
|
||||
mMessage == eQueryCaretRect ||
|
||||
mMessage == NS_QUERY_TEXT_RECT,
|
||||
"not querying selection or text rect");
|
||||
return mReply.mWritingMode;
|
||||
@@ -593,9 +593,9 @@ public:
|
||||
bool mWidgetIsHit;
|
||||
// mozilla::WritingMode value at the end (focus) of the selection
|
||||
mozilla::WritingMode mWritingMode;
|
||||
// used by NS_QUERY_SELECTION_AS_TRANSFERABLE
|
||||
// Used by eQuerySelectionAsTransferable
|
||||
nsCOMPtr<nsITransferable> mTransferable;
|
||||
// used by NS_QUERY_TEXT_CONTENT with font ranges requested
|
||||
// Used by eQueryTextContent with font ranges requested
|
||||
nsAutoTArray<mozilla::FontRange, 1> mFontRanges;
|
||||
} mReply;
|
||||
|
||||
|
||||
@@ -356,7 +356,7 @@ public:
|
||||
bool DispatchEvent(WidgetGUIEvent& aEvent);
|
||||
|
||||
/**
|
||||
* SetSelection() dispatches NS_SELECTION_SET event for the aRange.
|
||||
* SetSelection() dispatches eSetSelection event for the aRange.
|
||||
*
|
||||
* @param aRange The range which will be selected.
|
||||
* @return TRUE if setting selection is succeeded and
|
||||
|
||||
@@ -2969,7 +2969,7 @@ IMEInputHandler::ConversationIdentifier()
|
||||
nsRefPtr<IMEInputHandler> kungFuDeathGrip(this);
|
||||
|
||||
// NOTE: The size of NSInteger is same as pointer size.
|
||||
WidgetQueryContentEvent textContent(true, NS_QUERY_TEXT_CONTENT, mWidget);
|
||||
WidgetQueryContentEvent textContent(true, eQueryTextContent, mWidget);
|
||||
textContent.InitForQueryTextContent(0, 0);
|
||||
DispatchEvent(textContent);
|
||||
if (!textContent.mSucceeded) {
|
||||
@@ -3005,7 +3005,7 @@ IMEInputHandler::GetAttributedSubstringFromRange(NSRange& aRange,
|
||||
nsRefPtr<IMEInputHandler> kungFuDeathGrip(this);
|
||||
|
||||
nsAutoString str;
|
||||
WidgetQueryContentEvent textContent(true, NS_QUERY_TEXT_CONTENT, mWidget);
|
||||
WidgetQueryContentEvent textContent(true, eQueryTextContent, mWidget);
|
||||
textContent.InitForQueryTextContent(aRange.location, aRange.length);
|
||||
textContent.RequestFontRanges();
|
||||
DispatchEvent(textContent);
|
||||
@@ -3098,7 +3098,7 @@ IMEInputHandler::SelectedRange()
|
||||
|
||||
nsRefPtr<IMEInputHandler> kungFuDeathGrip(this);
|
||||
|
||||
WidgetQueryContentEvent selection(true, NS_QUERY_SELECTED_TEXT, mWidget);
|
||||
WidgetQueryContentEvent selection(true, eQuerySelectedText, mWidget);
|
||||
DispatchEvent(selection);
|
||||
|
||||
MOZ_LOG(gLog, LogLevel::Info,
|
||||
@@ -3202,7 +3202,7 @@ IMEInputHandler::FirstRectForCharacterRange(NSRange& aRange,
|
||||
}
|
||||
|
||||
if (useCaretRect) {
|
||||
WidgetQueryContentEvent caretRect(true, NS_QUERY_CARET_RECT, mWidget);
|
||||
WidgetQueryContentEvent caretRect(true, eQueryCaretRect, mWidget);
|
||||
caretRect.InitForQueryCaretRect(aRange.location);
|
||||
DispatchEvent(caretRect);
|
||||
if (!caretRect.mSucceeded) {
|
||||
@@ -3978,7 +3978,7 @@ TextInputHandlerBase::SetSelection(NSRange& aRange)
|
||||
MOZ_ASSERT(!Destroyed());
|
||||
|
||||
nsRefPtr<TextInputHandlerBase> kungFuDeathGrip(this);
|
||||
WidgetSelectionEvent selectionEvent(true, NS_SELECTION_SET, mWidget);
|
||||
WidgetSelectionEvent selectionEvent(true, eSetSelection, mWidget);
|
||||
selectionEvent.mOffset = aRange.location;
|
||||
selectionEvent.mLength = aRange.length;
|
||||
selectionEvent.mReversed = false;
|
||||
|
||||
@@ -1829,7 +1829,7 @@ nsChildView::ExecuteNativeKeyBinding(NativeKeyBindingsType aType,
|
||||
// the physical direction of the arrow.
|
||||
if (aEvent.keyCode >= nsIDOMKeyEvent::DOM_VK_LEFT &&
|
||||
aEvent.keyCode <= nsIDOMKeyEvent::DOM_VK_DOWN) {
|
||||
WidgetQueryContentEvent query(true, NS_QUERY_SELECTED_TEXT, this);
|
||||
WidgetQueryContentEvent query(true, eQuerySelectedText, this);
|
||||
DispatchWindowEvent(query);
|
||||
|
||||
if (query.mSucceeded && query.mReply.mWritingMode.IsVertical()) {
|
||||
@@ -1915,7 +1915,7 @@ NSView<mozView>* nsChildView::GetEditorView()
|
||||
// We need to get editor's view. E.g., when the focus is in the bookmark
|
||||
// dialog, the view is <panel> element of the dialog. At this time, the key
|
||||
// events are processed the parent window's view that has native focus.
|
||||
WidgetQueryContentEvent textContent(true, NS_QUERY_TEXT_CONTENT, this);
|
||||
WidgetQueryContentEvent textContent(true, eQueryTextContent, this);
|
||||
textContent.InitForQueryTextContent(0, 0);
|
||||
DispatchWindowEvent(textContent);
|
||||
if (textContent.mSucceeded && textContent.mReply.mFocusedWidget) {
|
||||
@@ -6080,8 +6080,7 @@ PanGestureTypeForEvent(NSEvent* aEvent)
|
||||
return NO;
|
||||
|
||||
// Obtain the current selection.
|
||||
WidgetQueryContentEvent event(true,
|
||||
NS_QUERY_SELECTION_AS_TRANSFERABLE,
|
||||
WidgetQueryContentEvent event(true, eQuerySelectionAsTransferable,
|
||||
mGeckoChild);
|
||||
mGeckoChild->DispatchWindowEvent(event);
|
||||
if (!event.mSucceeded || !event.mReply.mTransferable)
|
||||
|
||||
+329
-92
@@ -94,6 +94,80 @@ public:
|
||||
virtual ~GetWritingModeName() {}
|
||||
};
|
||||
|
||||
class GetTextRangeStyleText final : public nsAutoCString
|
||||
{
|
||||
public:
|
||||
explicit GetTextRangeStyleText(const TextRangeStyle& aStyle)
|
||||
{
|
||||
if (!aStyle.IsDefined()) {
|
||||
AssignLiteral("{ IsDefined()=false }");
|
||||
return;
|
||||
}
|
||||
|
||||
if (aStyle.IsLineStyleDefined()) {
|
||||
AppendLiteral("{ mLineStyle=");
|
||||
AppendLineStyle(aStyle.mLineStyle);
|
||||
if (aStyle.IsUnderlineColorDefined()) {
|
||||
AppendLiteral(", mUnderlineColor=");
|
||||
AppendColor(aStyle.mUnderlineColor);
|
||||
} else {
|
||||
AppendLiteral(", IsUnderlineColorDefined=false");
|
||||
}
|
||||
} else {
|
||||
AppendLiteral("{ IsLineStyleDefined()=false");
|
||||
}
|
||||
|
||||
if (aStyle.IsForegroundColorDefined()) {
|
||||
AppendLiteral(", mForegroundColor=");
|
||||
AppendColor(aStyle.mForegroundColor);
|
||||
} else {
|
||||
AppendLiteral(", IsForegroundColorDefined()=false");
|
||||
}
|
||||
|
||||
if (aStyle.IsBackgroundColorDefined()) {
|
||||
AppendLiteral(", mBackgroundColor=");
|
||||
AppendColor(aStyle.mBackgroundColor);
|
||||
} else {
|
||||
AppendLiteral(", IsBackgroundColorDefined()=false");
|
||||
}
|
||||
|
||||
AppendLiteral(" }");
|
||||
}
|
||||
void AppendLineStyle(uint8_t aLineStyle)
|
||||
{
|
||||
switch (aLineStyle) {
|
||||
case TextRangeStyle::LINESTYLE_NONE:
|
||||
AppendLiteral("LINESTYLE_NONE");
|
||||
break;
|
||||
case TextRangeStyle::LINESTYLE_SOLID:
|
||||
AppendLiteral("LINESTYLE_SOLID");
|
||||
break;
|
||||
case TextRangeStyle::LINESTYLE_DOTTED:
|
||||
AppendLiteral("LINESTYLE_DOTTED");
|
||||
break;
|
||||
case TextRangeStyle::LINESTYLE_DASHED:
|
||||
AppendLiteral("LINESTYLE_DASHED");
|
||||
break;
|
||||
case TextRangeStyle::LINESTYLE_DOUBLE:
|
||||
AppendLiteral("LINESTYLE_DOUBLE");
|
||||
break;
|
||||
case TextRangeStyle::LINESTYLE_WAVY:
|
||||
AppendLiteral("LINESTYLE_WAVY");
|
||||
break;
|
||||
default:
|
||||
AppendPrintf("Invalid(0x%02X)", aLineStyle);
|
||||
break;
|
||||
}
|
||||
}
|
||||
void AppendColor(nscolor aColor)
|
||||
{
|
||||
AppendPrintf("{ R=0x%02X, G=0x%02X, B=0x%02X, A=0x%02X }",
|
||||
NS_GET_R(aColor), NS_GET_G(aColor), NS_GET_B(aColor),
|
||||
NS_GET_A(aColor));
|
||||
}
|
||||
virtual ~GetTextRangeStyleText() {};
|
||||
};
|
||||
|
||||
const static bool kUseSimpleContextDefault = MOZ_WIDGET_GTK == 2;
|
||||
|
||||
/******************************************************************************
|
||||
@@ -1397,21 +1471,21 @@ IMContextWrapper::DispatchCompositionCommitEvent(
|
||||
|
||||
already_AddRefed<TextRangeArray>
|
||||
IMContextWrapper::CreateTextRangeArray(GtkIMContext* aContext,
|
||||
const nsAString& aLastDispatchedData)
|
||||
const nsAString& aCompositionString)
|
||||
{
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Info,
|
||||
("GTKIM: %p CreateTextRangeArray(aContext=%p, "
|
||||
"aLastDispatchedData=\"%s\" (Length()=%u))",
|
||||
this, aContext, NS_ConvertUTF16toUTF8(aLastDispatchedData).get(),
|
||||
aLastDispatchedData.Length()));
|
||||
"aCompositionString=\"%s\" (Length()=%u))",
|
||||
this, aContext, NS_ConvertUTF16toUTF8(aCompositionString).get(),
|
||||
aCompositionString.Length()));
|
||||
|
||||
nsRefPtr<TextRangeArray> textRangeArray = new TextRangeArray();
|
||||
|
||||
gchar *preedit_string;
|
||||
gint cursor_pos;
|
||||
gint cursor_pos_in_chars;
|
||||
PangoAttrList *feedback_list;
|
||||
gtk_im_context_get_preedit_string(aContext, &preedit_string,
|
||||
&feedback_list, &cursor_pos);
|
||||
&feedback_list, &cursor_pos_in_chars);
|
||||
if (!preedit_string || !*preedit_string) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Error,
|
||||
("GTKIM: %p CreateTextRangeArray(), FAILED, due to "
|
||||
@@ -1422,6 +1496,53 @@ IMContextWrapper::CreateTextRangeArray(GtkIMContext* aContext,
|
||||
return textRangeArray.forget();
|
||||
}
|
||||
|
||||
// Convert caret offset from offset in characters to offset in UTF-16
|
||||
// string. If we couldn't proper offset in UTF-16 string, we should
|
||||
// assume that the caret is at the end of the composition string.
|
||||
uint32_t caretOffsetInUTF16 = aCompositionString.Length();
|
||||
if (NS_WARN_IF(cursor_pos_in_chars < 0)) {
|
||||
// Note that this case is undocumented. We should assume that the
|
||||
// caret is at the end of the composition string.
|
||||
} else if (cursor_pos_in_chars == 0) {
|
||||
caretOffsetInUTF16 = 0;
|
||||
} else {
|
||||
gchar* charAfterCaret =
|
||||
g_utf8_offset_to_pointer(preedit_string, cursor_pos_in_chars);
|
||||
if (NS_WARN_IF(!charAfterCaret)) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Warning,
|
||||
("GTKIM: %p CreateTextRangeArray(), failed to get UTF-8 "
|
||||
"string before the caret (cursor_pos_in_chars=%d)",
|
||||
this, cursor_pos_in_chars));
|
||||
} else {
|
||||
glong caretOffset = 0;
|
||||
gunichar2* utf16StrBeforeCaret =
|
||||
g_utf8_to_utf16(preedit_string, charAfterCaret - preedit_string,
|
||||
nullptr, &caretOffset, nullptr);
|
||||
if (NS_WARN_IF(!utf16StrBeforeCaret) ||
|
||||
NS_WARN_IF(caretOffset < 0)) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Warning,
|
||||
("GTKIM: %p CreateTextRangeArray(), WARNING, failed to "
|
||||
"convert to UTF-16 string before the caret "
|
||||
"(cursor_pos_in_chars=%d, caretOffset=%d)",
|
||||
this, cursor_pos_in_chars, caretOffset));
|
||||
} else {
|
||||
caretOffsetInUTF16 = static_cast<uint32_t>(caretOffset);
|
||||
uint32_t compositionStringLength = aCompositionString.Length();
|
||||
if (NS_WARN_IF(caretOffsetInUTF16 > compositionStringLength)) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Warning,
|
||||
("GTKIM: %p CreateTextRangeArray(), WARNING, "
|
||||
"caretOffsetInUTF16=%u is larger than "
|
||||
"compositionStringLength=%u",
|
||||
this, caretOffsetInUTF16, compositionStringLength));
|
||||
caretOffsetInUTF16 = compositionStringLength;
|
||||
}
|
||||
}
|
||||
if (utf16StrBeforeCaret) {
|
||||
g_free(utf16StrBeforeCaret);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
PangoAttrIterator* iter;
|
||||
iter = pango_attr_list_get_iterator(feedback_list);
|
||||
if (!iter) {
|
||||
@@ -1434,93 +1555,21 @@ IMContextWrapper::CreateTextRangeArray(GtkIMContext* aContext,
|
||||
return textRangeArray.forget();
|
||||
}
|
||||
|
||||
/*
|
||||
* Depend on gtk2's implementation on XIM support.
|
||||
* In aFeedback got from gtk2, there are only three types of data:
|
||||
* PANGO_ATTR_UNDERLINE, PANGO_ATTR_FOREGROUND, PANGO_ATTR_BACKGROUND.
|
||||
* Corresponding to XIMUnderline, XIMReverse.
|
||||
* Don't take PANGO_ATTR_BACKGROUND into account, since
|
||||
* PANGO_ATTR_BACKGROUND and PANGO_ATTR_FOREGROUND are always
|
||||
* a couple.
|
||||
*/
|
||||
do {
|
||||
PangoAttribute* attrUnderline =
|
||||
pango_attr_iterator_get(iter, PANGO_ATTR_UNDERLINE);
|
||||
PangoAttribute* attrForeground =
|
||||
pango_attr_iterator_get(iter, PANGO_ATTR_FOREGROUND);
|
||||
if (!attrUnderline && !attrForeground) {
|
||||
TextRange range;
|
||||
if (!SetTextRange(iter, preedit_string, caretOffsetInUTF16, range)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// Get the range of the current attribute(s)
|
||||
gint start, end;
|
||||
pango_attr_iterator_range(iter, &start, &end);
|
||||
|
||||
TextRange range;
|
||||
// XIMReverse | XIMUnderline
|
||||
if (attrUnderline && attrForeground) {
|
||||
range.mRangeType = NS_TEXTRANGE_SELECTEDCONVERTEDTEXT;
|
||||
}
|
||||
// XIMUnderline
|
||||
else if (attrUnderline) {
|
||||
range.mRangeType = NS_TEXTRANGE_CONVERTEDTEXT;
|
||||
}
|
||||
// XIMReverse
|
||||
else if (attrForeground) {
|
||||
range.mRangeType = NS_TEXTRANGE_SELECTEDRAWTEXT;
|
||||
} else {
|
||||
range.mRangeType = NS_TEXTRANGE_RAWINPUT;
|
||||
}
|
||||
|
||||
gunichar2* uniStr = nullptr;
|
||||
if (start == 0) {
|
||||
range.mStartOffset = 0;
|
||||
} else {
|
||||
glong uniStrLen;
|
||||
uniStr = g_utf8_to_utf16(preedit_string, start,
|
||||
nullptr, &uniStrLen, nullptr);
|
||||
if (uniStr) {
|
||||
range.mStartOffset = uniStrLen;
|
||||
g_free(uniStr);
|
||||
uniStr = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
glong uniStrLen;
|
||||
uniStr = g_utf8_to_utf16(preedit_string + start, end - start,
|
||||
nullptr, &uniStrLen, nullptr);
|
||||
if (!uniStr) {
|
||||
range.mEndOffset = range.mStartOffset;
|
||||
} else {
|
||||
range.mEndOffset = range.mStartOffset + uniStrLen;
|
||||
g_free(uniStr);
|
||||
uniStr = nullptr;
|
||||
}
|
||||
|
||||
textRangeArray->AppendElement(range);
|
||||
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Debug,
|
||||
("GTKIM: %p CreateTextRangeArray(), mStartOffset=%u, "
|
||||
"mEndOffset=%u, mRangeType=%s",
|
||||
this, range.mStartOffset, range.mEndOffset,
|
||||
GetRangeTypeName(range.mRangeType)));
|
||||
} while (pango_attr_iterator_next(iter));
|
||||
|
||||
TextRange range;
|
||||
if (cursor_pos < 0) {
|
||||
range.mStartOffset = 0;
|
||||
} else if (uint32_t(cursor_pos) > aLastDispatchedData.Length()) {
|
||||
range.mStartOffset = aLastDispatchedData.Length();
|
||||
} else {
|
||||
range.mStartOffset = uint32_t(cursor_pos);
|
||||
}
|
||||
range.mEndOffset = range.mStartOffset;
|
||||
range.mStartOffset = range.mEndOffset = caretOffsetInUTF16;
|
||||
range.mRangeType = NS_TEXTRANGE_CARETPOSITION;
|
||||
textRangeArray->AppendElement(range);
|
||||
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Debug,
|
||||
("GTKIM: %p CreateTextRangeArray(), mStartOffset=%u, mEndOffset=%u, "
|
||||
"mRangeType=%s",
|
||||
("GTKIM: %p CreateTextRangeArray(), mStartOffset=%u, "
|
||||
"mEndOffset=%u, mRangeType=%s",
|
||||
this, range.mStartOffset, range.mEndOffset,
|
||||
GetRangeTypeName(range.mRangeType)));
|
||||
|
||||
@@ -1531,6 +1580,196 @@ IMContextWrapper::CreateTextRangeArray(GtkIMContext* aContext,
|
||||
return textRangeArray.forget();
|
||||
}
|
||||
|
||||
/* static */
|
||||
nscolor
|
||||
IMContextWrapper::ToNscolor(PangoAttrColor* aPangoAttrColor)
|
||||
{
|
||||
PangoColor& pangoColor = aPangoAttrColor->color;
|
||||
uint8_t r = pangoColor.red / 0x100;
|
||||
uint8_t g = pangoColor.green / 0x100;
|
||||
uint8_t b = pangoColor.blue / 0x100;
|
||||
return NS_RGB(r, g, b);
|
||||
}
|
||||
|
||||
bool
|
||||
IMContextWrapper::SetTextRange(PangoAttrIterator* aPangoAttrIter,
|
||||
const gchar* aUTF8CompositionString,
|
||||
uint32_t aUTF16CaretOffset,
|
||||
TextRange& aTextRange) const
|
||||
{
|
||||
// Set the range offsets in UTF-16 string.
|
||||
gint utf8ClauseStart, utf8ClauseEnd;
|
||||
pango_attr_iterator_range(aPangoAttrIter, &utf8ClauseStart, &utf8ClauseEnd);
|
||||
if (utf8ClauseStart == utf8ClauseEnd) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Error,
|
||||
("GTKIM: %p SetTextRange(), FAILED, due to collapsed range",
|
||||
this));
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!utf8ClauseStart) {
|
||||
aTextRange.mStartOffset = 0;
|
||||
} else {
|
||||
glong utf16PreviousClausesLength;
|
||||
gunichar2* utf16PreviousClausesString =
|
||||
g_utf8_to_utf16(aUTF8CompositionString, utf8ClauseStart, nullptr,
|
||||
&utf16PreviousClausesLength, nullptr);
|
||||
|
||||
if (NS_WARN_IF(!utf16PreviousClausesString)) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Error,
|
||||
("GTKIM: %p SetTextRange(), FAILED, due to g_utf8_to_utf16() "
|
||||
"failure (retrieving previous string of current clause)",
|
||||
this));
|
||||
return false;
|
||||
}
|
||||
|
||||
aTextRange.mStartOffset = utf16PreviousClausesLength;
|
||||
g_free(utf16PreviousClausesString);
|
||||
}
|
||||
|
||||
glong utf16CurrentClauseLength;
|
||||
gunichar2* utf16CurrentClauseString =
|
||||
g_utf8_to_utf16(aUTF8CompositionString + utf8ClauseStart,
|
||||
utf8ClauseEnd - utf8ClauseStart,
|
||||
nullptr, &utf16CurrentClauseLength, nullptr);
|
||||
|
||||
if (NS_WARN_IF(!utf16CurrentClauseString)) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Error,
|
||||
("GTKIM: %p SetTextRange(), FAILED, due to g_utf8_to_utf16() "
|
||||
"failure (retrieving current clause)",
|
||||
this));
|
||||
return false;
|
||||
}
|
||||
|
||||
aTextRange.mEndOffset = aTextRange.mStartOffset + utf16CurrentClauseLength;
|
||||
g_free(utf16CurrentClauseString);
|
||||
utf16CurrentClauseString = nullptr;
|
||||
|
||||
// Set styles
|
||||
TextRangeStyle& style = aTextRange.mRangeStyle;
|
||||
|
||||
// Underline
|
||||
PangoAttrInt* attrUnderline =
|
||||
reinterpret_cast<PangoAttrInt*>(
|
||||
pango_attr_iterator_get(aPangoAttrIter, PANGO_ATTR_UNDERLINE));
|
||||
if (attrUnderline) {
|
||||
switch (attrUnderline->value) {
|
||||
case PANGO_UNDERLINE_NONE:
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_NONE;
|
||||
break;
|
||||
case PANGO_UNDERLINE_DOUBLE:
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_DOUBLE;
|
||||
break;
|
||||
case PANGO_UNDERLINE_ERROR:
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_WAVY;
|
||||
break;
|
||||
case PANGO_UNDERLINE_SINGLE:
|
||||
case PANGO_UNDERLINE_LOW:
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_SOLID;
|
||||
break;
|
||||
default:
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Warning,
|
||||
("GTKIM: %p SetTextRange(), retrieved unknown underline "
|
||||
"style: %d",
|
||||
this, attrUnderline->value));
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_SOLID;
|
||||
break;
|
||||
}
|
||||
style.mDefinedStyles |= TextRangeStyle::DEFINED_LINESTYLE;
|
||||
|
||||
// Underline color
|
||||
PangoAttrColor* attrUnderlineColor =
|
||||
reinterpret_cast<PangoAttrColor*>(
|
||||
pango_attr_iterator_get(aPangoAttrIter,
|
||||
PANGO_ATTR_UNDERLINE_COLOR));
|
||||
if (attrUnderlineColor) {
|
||||
style.mUnderlineColor = ToNscolor(attrUnderlineColor);
|
||||
style.mDefinedStyles |= TextRangeStyle::DEFINED_UNDERLINE_COLOR;
|
||||
}
|
||||
} else {
|
||||
style.mLineStyle = TextRangeStyle::LINESTYLE_NONE;
|
||||
style.mDefinedStyles |= TextRangeStyle::DEFINED_LINESTYLE;
|
||||
}
|
||||
|
||||
// Don't set colors if they are not specified. They should be computed by
|
||||
// textframe if only one of the colors are specified.
|
||||
|
||||
// Foreground color (text color)
|
||||
PangoAttrColor* attrForeground =
|
||||
reinterpret_cast<PangoAttrColor*>(
|
||||
pango_attr_iterator_get(aPangoAttrIter, PANGO_ATTR_FOREGROUND));
|
||||
if (attrForeground) {
|
||||
style.mForegroundColor = ToNscolor(attrForeground);
|
||||
style.mDefinedStyles |= TextRangeStyle::DEFINED_FOREGROUND_COLOR;
|
||||
}
|
||||
|
||||
// Background color
|
||||
PangoAttrColor* attrBackground =
|
||||
reinterpret_cast<PangoAttrColor*>(
|
||||
pango_attr_iterator_get(aPangoAttrIter, PANGO_ATTR_BACKGROUND));
|
||||
if (attrBackground) {
|
||||
style.mBackgroundColor = ToNscolor(attrBackground);
|
||||
style.mDefinedStyles |= TextRangeStyle::DEFINED_BACKGROUND_COLOR;
|
||||
}
|
||||
|
||||
/**
|
||||
* We need to judge the meaning of the clause for a11y. Before we support
|
||||
* IME specific composition string style, we used following rules:
|
||||
*
|
||||
* 1: If attrUnderline and attrForground are specified, we assumed the
|
||||
* clause is NS_TEXTRANGE_SELECTEDCONVERTEDTEXT.
|
||||
* 2: If only attrUnderline is specified, we assumed the clause is
|
||||
* NS_TEXTRANGE_CONVERTEDTEXT.
|
||||
* 3: If only attrForground is specified, we assumed the clause is
|
||||
* NS_TEXTRANGE_SELECTEDRAWTEXT.
|
||||
* 4: If neither attrUnderline nor attrForeground is specified, we assumed
|
||||
* the clause is NS_TEXTRANGE_RAWINPUT.
|
||||
*
|
||||
* However, this rules are odd since there can be two or more selected
|
||||
* clauses. Additionally, our old rules caused that IME developers/users
|
||||
* cannot specify composition string style as they want.
|
||||
*
|
||||
* So, we shouldn't guess the meaning from its visual style.
|
||||
*/
|
||||
|
||||
if (!attrUnderline && !attrForeground && !attrBackground) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Warning,
|
||||
("GTKIM: %p SetTextRange(), FAILED, due to no attr, "
|
||||
"aTextRange= { mStartOffset=%u, mEndOffset=%u }",
|
||||
this, aTextRange.mStartOffset, aTextRange.mEndOffset));
|
||||
return false;
|
||||
}
|
||||
|
||||
// If the range covers whole of composition string and the caret is at
|
||||
// the end of the composition string, the range is probably not converted.
|
||||
if (!utf8ClauseStart &&
|
||||
utf8ClauseEnd == static_cast<gint>(strlen(aUTF8CompositionString)) &&
|
||||
aTextRange.mEndOffset == aUTF16CaretOffset) {
|
||||
aTextRange.mRangeType = NS_TEXTRANGE_RAWINPUT;
|
||||
}
|
||||
// Typically, the caret is set at the start of the selected clause.
|
||||
// So, if the caret is in the clause, we can assume that the clause is
|
||||
// selected.
|
||||
else if (aTextRange.mStartOffset <= aUTF16CaretOffset &&
|
||||
aTextRange.mEndOffset > aUTF16CaretOffset) {
|
||||
aTextRange.mRangeType = NS_TEXTRANGE_SELECTEDCONVERTEDTEXT;
|
||||
}
|
||||
// Otherwise, we should assume that the clause is converted but not
|
||||
// selected.
|
||||
else {
|
||||
aTextRange.mRangeType = NS_TEXTRANGE_CONVERTEDTEXT;
|
||||
}
|
||||
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Debug,
|
||||
("GTKIM: %p SetTextRange(), succeeded, aTextRange= { "
|
||||
"mStartOffset=%u, mEndOffset=%u, mRangeType=%s, mRangeStyle=%s }",
|
||||
this, aTextRange.mStartOffset, aTextRange.mEndOffset,
|
||||
GetRangeTypeName(aTextRange.mRangeType),
|
||||
GetTextRangeStyleText(aTextRange.mRangeStyle).get()));
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void
|
||||
IMContextWrapper::SetCursorPosition(GtkIMContext* aContext)
|
||||
{
|
||||
@@ -1571,7 +1810,7 @@ IMContextWrapper::SetCursorPosition(GtkIMContext* aContext)
|
||||
}
|
||||
|
||||
WidgetQueryContentEvent charRect(true,
|
||||
useCaret ? NS_QUERY_CARET_RECT :
|
||||
useCaret ? eQueryCaretRect :
|
||||
NS_QUERY_TEXT_RECT,
|
||||
mLastFocusedWindow);
|
||||
if (useCaret) {
|
||||
@@ -1594,7 +1833,7 @@ IMContextWrapper::SetCursorPosition(GtkIMContext* aContext)
|
||||
if (!charRect.mSucceeded) {
|
||||
MOZ_LOG(gGtkIMLog, LogLevel::Error,
|
||||
("GTKIM: %p SetCursorPosition(), FAILED, %s was failed",
|
||||
this, useCaret ? "NS_QUERY_CARET_RECT" : "NS_QUERY_TEXT_RECT"));
|
||||
this, useCaret ? "eQueryCaretRect" : "NS_QUERY_TEXT_RECT"));
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1670,8 +1909,7 @@ IMContextWrapper::GetCurrentParagraph(nsAString& aText,
|
||||
}
|
||||
|
||||
// Get all text contents of the focused editor
|
||||
WidgetQueryContentEvent queryTextContentEvent(true,
|
||||
NS_QUERY_TEXT_CONTENT,
|
||||
WidgetQueryContentEvent queryTextContentEvent(true, eQueryTextContent,
|
||||
mLastFocusedWindow);
|
||||
queryTextContentEvent.InitForQueryTextContent(0, UINT32_MAX);
|
||||
mLastFocusedWindow->DispatchEvent(&queryTextContentEvent, status);
|
||||
@@ -1767,8 +2005,7 @@ IMContextWrapper::DeleteText(GtkIMContext* aContext,
|
||||
}
|
||||
|
||||
// Get all text contents of the focused editor
|
||||
WidgetQueryContentEvent queryTextContentEvent(true,
|
||||
NS_QUERY_TEXT_CONTENT,
|
||||
WidgetQueryContentEvent queryTextContentEvent(true, eQueryTextContent,
|
||||
mLastFocusedWindow);
|
||||
queryTextContentEvent.InitForQueryTextContent(0, UINT32_MAX);
|
||||
mLastFocusedWindow->DispatchEvent(&queryTextContentEvent, status);
|
||||
@@ -1814,7 +2051,7 @@ IMContextWrapper::DeleteText(GtkIMContext* aContext,
|
||||
g_utf8_offset_to_pointer(utf8Str.get(), endInUTF8Characters);
|
||||
|
||||
// Set selection to delete
|
||||
WidgetSelectionEvent selectionEvent(true, NS_SELECTION_SET,
|
||||
WidgetSelectionEvent selectionEvent(true, eSetSelection,
|
||||
mLastFocusedWindow);
|
||||
|
||||
nsDependentCSubstring utf8StrBeforeOffset(utf8Str, 0,
|
||||
@@ -1913,7 +2150,7 @@ IMContextWrapper::EnsureToCacheSelection(nsAString* aSelectedString)
|
||||
}
|
||||
|
||||
nsEventStatus status;
|
||||
WidgetQueryContentEvent selection(true, NS_QUERY_SELECTED_TEXT,
|
||||
WidgetQueryContentEvent selection(true, eQuerySelectedText,
|
||||
mLastFocusedWindow);
|
||||
InitEvent(selection);
|
||||
mLastFocusedWindow->DispatchEvent(&selection, status);
|
||||
@@ -1962,7 +2199,7 @@ IMContextWrapper::Selection::Assign(const IMENotification& aIMENotification)
|
||||
void
|
||||
IMContextWrapper::Selection::Assign(const WidgetQueryContentEvent& aEvent)
|
||||
{
|
||||
MOZ_ASSERT(aEvent.mMessage == NS_QUERY_SELECTED_TEXT);
|
||||
MOZ_ASSERT(aEvent.mMessage == eQuerySelectedText);
|
||||
MOZ_ASSERT(aEvent.mSucceeded);
|
||||
mOffset = aEvent.mReply.mOffset;
|
||||
mLength = aEvent.mReply.mString.Length();
|
||||
|
||||
@@ -345,13 +345,34 @@ protected:
|
||||
* Generates our text range array from current composition string.
|
||||
*
|
||||
* @param aContext A GtkIMContext which is being handled.
|
||||
* @param aLastDispatchedData The data of the last compositionchange event
|
||||
* of current composition. This should be
|
||||
* mDispatchedCompositionString.
|
||||
* @param aCompositionString The data to be dispatched with
|
||||
* compositionchange event.
|
||||
*/
|
||||
already_AddRefed<TextRangeArray>
|
||||
CreateTextRangeArray(GtkIMContext* aContext,
|
||||
const nsAString& aLastDispatchedData);
|
||||
const nsAString& aCompositionString);
|
||||
|
||||
/**
|
||||
* SetTextRange() initializes aTextRange with aPangoAttrIter.
|
||||
*
|
||||
* @param aPangoAttrIter An iter which represents a clause of the
|
||||
* composition string.
|
||||
* @param aUTF8CompositionString The whole composition string (UTF-8).
|
||||
* @param aUTF16CaretOffset The caret offset in the composition
|
||||
* string encoded as UTF-16.
|
||||
* @param aTextRange The result.
|
||||
* @return true if this initializes aTextRange.
|
||||
* Otherwise, false.
|
||||
*/
|
||||
bool SetTextRange(PangoAttrIterator* aPangoAttrIter,
|
||||
const gchar* aUTF8CompositionString,
|
||||
uint32_t aUTF16CaretOffset,
|
||||
TextRange& aTextRange) const;
|
||||
|
||||
/**
|
||||
* ToNscolor() converts the PangoColor in aPangoAttrColor to nscolor.
|
||||
*/
|
||||
static nscolor ToNscolor(PangoAttrColor* aPangoAttrColor);
|
||||
|
||||
/**
|
||||
* Move the candidate window with "fake" cursor position.
|
||||
|
||||
@@ -5968,7 +5968,7 @@ nsWindow::ExecuteNativeKeyBinding(NativeKeyBindingsType aType,
|
||||
|
||||
// Check if we're targeting content with vertical writing mode,
|
||||
// and if so remap the arrow keys.
|
||||
WidgetQueryContentEvent query(true, NS_QUERY_SELECTED_TEXT, this);
|
||||
WidgetQueryContentEvent query(true, eQuerySelectedText, this);
|
||||
nsEventStatus status;
|
||||
DispatchEvent(&query, status);
|
||||
|
||||
|
||||
+10
-10
@@ -1886,12 +1886,12 @@ TestApp::TestSelection(void)
|
||||
bool succeeded = true;
|
||||
|
||||
/* If these fail the cause is probably one or more of:
|
||||
* nsTextStore::GetSelection not sending NS_QUERY_SELECTED_TEXT
|
||||
* NS_QUERY_SELECTED_TEXT not handled by ContentEventHandler
|
||||
* Bug in NS_QUERY_SELECTED_TEXT handler
|
||||
* nsTextStore::SetSelection not sending NS_SELECTION_SET
|
||||
* NS_SELECTION_SET not handled by ContentEventHandler
|
||||
* Bug in NS_SELECTION_SET handler
|
||||
* nsTextStore::GetSelection not sending eQuerySelectedText
|
||||
* eQuerySelectedText not handled by ContentEventHandler
|
||||
* Bug in eQuerySelectedText handler
|
||||
* nsTextStore::SetSelection not sending eSetSelection
|
||||
* eSetSelection not handled by ContentEventHandler
|
||||
* Bug in eSetSelection handler
|
||||
*/
|
||||
|
||||
TS_SELECTION_ACP testSel;
|
||||
@@ -1960,12 +1960,12 @@ TestApp::TestText(void)
|
||||
HRESULT hr;
|
||||
|
||||
/* If these fail the cause is probably one or more of:
|
||||
* nsTextStore::GetText not sending NS_QUERY_TEXT_CONTENT
|
||||
* NS_QUERY_TEXT_CONTENT not handled by ContentEventHandler
|
||||
* Bug in NS_QUERY_TEXT_CONTENT handler
|
||||
* nsTextStore::GetText not sending eQueryTextContent
|
||||
* eQueryTextContent not handled by ContentEventHandler
|
||||
* Bug in eQueryTextContent handler
|
||||
* nsTextStore::SetText not calling SetSelection or InsertTextAtSelection
|
||||
* Bug in SetSelection or InsertTextAtSelection
|
||||
* NS_SELECTION_SET bug or NS_COMPOSITION_* / NS_COMPOSITION_CHANGE bug
|
||||
* eSetSelection bug or NS_COMPOSITION_* / NS_COMPOSITION_CHANGE bug
|
||||
*/
|
||||
|
||||
if (!mMgr->GetFocusedStore()) {
|
||||
|
||||
@@ -1726,14 +1726,13 @@ IMMHandler::HandleDocumentFeed(nsWindow* aWindow,
|
||||
}
|
||||
|
||||
// Get all contents of the focused editor.
|
||||
WidgetQueryContentEvent textContent(true, NS_QUERY_TEXT_CONTENT, aWindow);
|
||||
WidgetQueryContentEvent textContent(true, eQueryTextContent, aWindow);
|
||||
textContent.InitForQueryTextContent(0, UINT32_MAX);
|
||||
aWindow->InitEvent(textContent, &point);
|
||||
aWindow->DispatchWindowEvent(&textContent);
|
||||
if (!textContent.mSucceeded) {
|
||||
MOZ_LOG(gIMMLog, LogLevel::Error,
|
||||
("IMM: HandleDocumentFeed, FAILED, due to NS_QUERY_TEXT_CONTENT "
|
||||
"failure"));
|
||||
("IMM: HandleDocumentFeed, FAILED, due to eQueryTextContent failure"));
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -2203,13 +2202,13 @@ IMMHandler::GetCaretRect(nsWindow* aWindow,
|
||||
return false;
|
||||
}
|
||||
|
||||
WidgetQueryContentEvent caretRect(true, NS_QUERY_CARET_RECT, aWindow);
|
||||
WidgetQueryContentEvent caretRect(true, eQueryCaretRect, aWindow);
|
||||
caretRect.InitForQueryCaretRect(selection.mOffset);
|
||||
aWindow->InitEvent(caretRect, &point);
|
||||
aWindow->DispatchWindowEvent(&caretRect);
|
||||
if (!caretRect.mSucceeded) {
|
||||
MOZ_LOG(gIMMLog, LogLevel::Info,
|
||||
("IMM: GetCaretRect, FAILED, due to NS_QUERY_CARET_RECT failure"));
|
||||
("IMM: GetCaretRect, FAILED, due to eQueryCaretRect failure"));
|
||||
return false;
|
||||
}
|
||||
aCaretRect = LayoutDevicePixel::ToUntyped(caretRect.mReply.mRect);
|
||||
@@ -2753,14 +2752,13 @@ IMMHandler::Selection::Init(nsWindow* aWindow)
|
||||
{
|
||||
Clear();
|
||||
|
||||
WidgetQueryContentEvent selection(true, NS_QUERY_SELECTED_TEXT, aWindow);
|
||||
WidgetQueryContentEvent selection(true, eQuerySelectedText, aWindow);
|
||||
nsIntPoint point(0, 0);
|
||||
aWindow->InitEvent(selection, &point);
|
||||
aWindow->DispatchWindowEvent(&selection);
|
||||
if (NS_WARN_IF(!selection.mSucceeded)) {
|
||||
MOZ_LOG(gIMMLog, LogLevel::Error,
|
||||
("IMM: Selection::Init, FAILED, due to NS_QUERY_SELECTED_TEXT "
|
||||
"failure"));
|
||||
("IMM: Selection::Init, FAILED, due to eQuerySelectedText failure"));
|
||||
return false;
|
||||
}
|
||||
// If the window is destroyed during querying selected text, we shouldn't
|
||||
|
||||
@@ -1301,7 +1301,7 @@ TSFTextStore::TSFTextStore()
|
||||
, mPendingOnSelectionChange(false)
|
||||
, mPendingOnLayoutChange(false)
|
||||
, mPendingDestroy(false)
|
||||
, mPendingClearLockedContent(false)
|
||||
, mDeferClearingLockedContent(false)
|
||||
, mNativeCaretIsCreated(false)
|
||||
, mDeferNotifyingTSF(false)
|
||||
{
|
||||
@@ -1674,11 +1674,6 @@ TSFTextStore::FlushPendingActions()
|
||||
return;
|
||||
}
|
||||
|
||||
// If dispatching event causes NOTIFY_IME_OF_COMPOSITION_UPDATE, we should
|
||||
// wait to abandon mLockedContent until it's notified because the dispatched
|
||||
// event may be handled asynchronously in e10s mode.
|
||||
mPendingClearLockedContent = !mPendingActions.Length();
|
||||
|
||||
nsRefPtr<nsWindowBase> kungFuDeathGrip(mWidget);
|
||||
for (uint32_t i = 0; i < mPendingActions.Length(); i++) {
|
||||
PendingAction& action = mPendingActions[i];
|
||||
@@ -1692,7 +1687,7 @@ TSFTextStore::FlushPendingActions()
|
||||
|
||||
if (action.mAdjustSelection) {
|
||||
// Select composition range so the new composition replaces the range
|
||||
WidgetSelectionEvent selectionSet(true, NS_SELECTION_SET, mWidget);
|
||||
WidgetSelectionEvent selectionSet(true, eSetSelection, mWidget);
|
||||
mWidget->InitEvent(selectionSet);
|
||||
selectionSet.mOffset = static_cast<uint32_t>(action.mSelectionStart);
|
||||
selectionSet.mLength = static_cast<uint32_t>(action.mSelectionLength);
|
||||
@@ -1701,7 +1696,7 @@ TSFTextStore::FlushPendingActions()
|
||||
if (!selectionSet.mSucceeded) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::FlushPendingActions() "
|
||||
"FAILED due to NS_SELECTION_SET failure", this));
|
||||
"FAILED due to eSetSelection failure", this));
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -1712,7 +1707,9 @@ TSFTextStore::FlushPendingActions()
|
||||
mWidget);
|
||||
mWidget->InitEvent(compositionStart);
|
||||
// NS_COMPOSITION_START always causes NOTIFY_IME_OF_COMPOSITION_UPDATE.
|
||||
mPendingClearLockedContent = true;
|
||||
// Therefore, we should wait to clear the locked content until it's
|
||||
// notified.
|
||||
mDeferClearingLockedContent = true;
|
||||
DispatchEvent(compositionStart);
|
||||
if (!mWidget || mWidget->Destroyed()) {
|
||||
break;
|
||||
@@ -1777,9 +1774,11 @@ TSFTextStore::FlushPendingActions()
|
||||
}
|
||||
compositionChange.mRanges = action.mRanges;
|
||||
// When the NS_COMPOSITION_CHANGE causes a DOM text event,
|
||||
// NOTIFY_IME_OF_COMPOSITION_UPDATE will be notified.
|
||||
// the IME will be notified of NOTIFY_IME_OF_COMPOSITION_UPDATE. In
|
||||
// such case, we should not clear the locked content until we notify
|
||||
// the IME of the composition update.
|
||||
if (compositionChange.CausesDOMTextEvent()) {
|
||||
mPendingClearLockedContent = true;
|
||||
mDeferClearingLockedContent = true;
|
||||
}
|
||||
DispatchEvent(compositionChange);
|
||||
// Be aware, the mWidget might already have been destroyed.
|
||||
@@ -1802,9 +1801,11 @@ TSFTextStore::FlushPendingActions()
|
||||
mWidget->InitEvent(compositionCommit);
|
||||
compositionCommit.mData = action.mData;
|
||||
// When the NS_COMPOSITION_COMMIT causes a DOM text event,
|
||||
// NOTIFY_IME_OF_COMPOSITION_UPDATE will be notified.
|
||||
// the IME will be notified of NOTIFY_IME_OF_COMPOSITION_UPDATE. In
|
||||
// such case, we should not clear the locked content until we notify
|
||||
// the IME of the composition update.
|
||||
if (compositionCommit.CausesDOMTextEvent()) {
|
||||
mPendingClearLockedContent = true;
|
||||
mDeferClearingLockedContent = true;
|
||||
}
|
||||
DispatchEvent(compositionCommit);
|
||||
if (!mWidget || mWidget->Destroyed()) {
|
||||
@@ -1812,15 +1813,15 @@ TSFTextStore::FlushPendingActions()
|
||||
}
|
||||
break;
|
||||
}
|
||||
case PendingAction::SELECTION_SET: {
|
||||
case PendingAction::SET_SELECTION: {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Debug,
|
||||
("TSF: 0x%p TSFTextStore::FlushPendingActions() "
|
||||
"flushing SELECTION_SET={ mSelectionStart=%d, "
|
||||
"flushing SET_SELECTION={ mSelectionStart=%d, "
|
||||
"mSelectionLength=%d, mSelectionReversed=%s }",
|
||||
this, action.mSelectionStart, action.mSelectionLength,
|
||||
GetBoolName(action.mSelectionReversed)));
|
||||
|
||||
WidgetSelectionEvent selectionSet(true, NS_SELECTION_SET, mWidget);
|
||||
WidgetSelectionEvent selectionSet(true, eSetSelection, mWidget);
|
||||
selectionSet.mOffset =
|
||||
static_cast<uint32_t>(action.mSelectionStart);
|
||||
selectionSet.mLength =
|
||||
@@ -1868,9 +1869,11 @@ TSFTextStore::MaybeFlushPendingNotifications()
|
||||
return;
|
||||
}
|
||||
|
||||
if (mPendingClearLockedContent) {
|
||||
mPendingClearLockedContent = false;
|
||||
if (!mDeferClearingLockedContent && mLockedContent.IsInitialized()) {
|
||||
mLockedContent.Clear();
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Debug,
|
||||
("TSF: 0x%p TSFTextStore::MaybeFlushPendingNotifications(), "
|
||||
"mLockedContent is cleared", this));
|
||||
}
|
||||
|
||||
if (mPendingOnLayoutChange) {
|
||||
@@ -1997,12 +2000,21 @@ TSFTextStore::LockedContent()
|
||||
// This should be called when the document is locked or the content hasn't
|
||||
// been abandoned yet.
|
||||
if (NS_WARN_IF(!IsReadLocked() && !mLockedContent.IsInitialized())) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::LockedContent(), FAILED, due to "
|
||||
"called wrong timing, IsReadLocked()=%s, "
|
||||
"mLockedContent.IsInitialized()=%s",
|
||||
this, GetBoolName(IsReadLocked()),
|
||||
GetBoolName(mLockedContent.IsInitialized())));
|
||||
mLockedContent.Clear();
|
||||
return mLockedContent;
|
||||
}
|
||||
|
||||
Selection& currentSel = CurrentSelection();
|
||||
if (currentSel.IsDirty()) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::LockedContent(), FAILED, due to "
|
||||
"CurrentSelection() failure", this));
|
||||
mLockedContent.Clear();
|
||||
return mLockedContent;
|
||||
}
|
||||
@@ -2010,19 +2022,31 @@ TSFTextStore::LockedContent()
|
||||
if (!mLockedContent.IsInitialized()) {
|
||||
nsAutoString text;
|
||||
if (NS_WARN_IF(!GetCurrentText(text))) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::LockedContent(), FAILED, due to "
|
||||
"GetCurrentText() failure", this));
|
||||
mLockedContent.Clear();
|
||||
return mLockedContent;
|
||||
}
|
||||
|
||||
mLockedContent.Init(text);
|
||||
// Basically, the locked content should be cleared after the document is
|
||||
// unlocked. However, in e10s mode, content will be modified
|
||||
// asynchronously. In such case, mDeferClearingLockedContent may be
|
||||
// true even after the document is unlocked.
|
||||
mDeferClearingLockedContent = false;
|
||||
}
|
||||
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Debug,
|
||||
("TSF: 0x%p TSFTextStore::LockedContent(): "
|
||||
"mLockedContent={ mText.Length()=%d, mLastCompositionString=\"%s\", "
|
||||
"mLockedContent={ mText=\"%s\" (Length()=%u), "
|
||||
"mLastCompositionString=\"%s\" (Length()=%u), "
|
||||
"mMinTextModifiedOffset=%u }",
|
||||
this, mLockedContent.Text().Length(),
|
||||
this, mLockedContent.Text().Length() <= 20 ?
|
||||
NS_ConvertUTF16toUTF8(mLockedContent.Text()).get() : "<omitted>",
|
||||
mLockedContent.Text().Length(),
|
||||
NS_ConvertUTF16toUTF8(mLockedContent.LastCompositionString()).get(),
|
||||
mLockedContent.LastCompositionString().Length(),
|
||||
mLockedContent.MinTextModifiedOffset()));
|
||||
|
||||
return mLockedContent;
|
||||
@@ -2038,11 +2062,18 @@ TSFTextStore::GetCurrentText(nsAString& aTextContent)
|
||||
|
||||
MOZ_ASSERT(mWidget && !mWidget->Destroyed());
|
||||
|
||||
WidgetQueryContentEvent queryText(true, NS_QUERY_TEXT_CONTENT, mWidget);
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Debug,
|
||||
("TSF: 0x%p TSFTextStore::GetCurrentText(): "
|
||||
"retrieving text from the content...", this));
|
||||
|
||||
WidgetQueryContentEvent queryText(true, eQueryTextContent, mWidget);
|
||||
queryText.InitForQueryTextContent(0, UINT32_MAX);
|
||||
mWidget->InitEvent(queryText);
|
||||
DispatchEvent(queryText);
|
||||
if (NS_WARN_IF(!queryText.mSucceeded)) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::GetCurrentText(), FAILED, due to "
|
||||
"eQueryTextContent failure", this));
|
||||
aTextContent.Truncate();
|
||||
return false;
|
||||
}
|
||||
@@ -2061,8 +2092,7 @@ TSFTextStore::CurrentSelection()
|
||||
MOZ_CRASH();
|
||||
}
|
||||
|
||||
WidgetQueryContentEvent querySelection(true, NS_QUERY_SELECTED_TEXT,
|
||||
mWidget);
|
||||
WidgetQueryContentEvent querySelection(true, eQuerySelectedText, mWidget);
|
||||
mWidget->InitEvent(querySelection);
|
||||
DispatchEvent(querySelection);
|
||||
NS_ENSURE_TRUE(querySelection.mSucceeded, mSelection);
|
||||
@@ -2664,7 +2694,7 @@ TSFTextStore::SetSelectionInternal(const TS_SELECTION_ACP* pSelection,
|
||||
|
||||
CompleteLastActionIfStillIncomplete();
|
||||
PendingAction* action = mPendingActions.AppendElement();
|
||||
action->mType = PendingAction::SELECTION_SET;
|
||||
action->mType = PendingAction::SET_SELECTION;
|
||||
action->mSelectionStart = pSelection->acpStart;
|
||||
action->mSelectionLength = pSelection->acpEnd - pSelection->acpStart;
|
||||
action->mSelectionReversed = (pSelection->style.ase == TS_AE_START);
|
||||
@@ -4676,7 +4706,9 @@ TSFTextStore::OnUpdateCompositionInternal()
|
||||
"mDeferNotifyingTSF=%s",
|
||||
this, GetBoolName(mDeferNotifyingTSF)));
|
||||
|
||||
mPendingClearLockedContent = true;
|
||||
// Now, all sent composition events are handled by the content even in
|
||||
// e10s mode.
|
||||
mDeferClearingLockedContent = false;
|
||||
mDeferNotifyingTSF = false;
|
||||
MaybeFlushPendingNotifications();
|
||||
return NS_OK;
|
||||
@@ -4779,14 +4811,14 @@ TSFTextStore::CreateNativeCaret()
|
||||
// collapsed, is it OK?
|
||||
uint32_t caretOffset = currentSel.MaxOffset();
|
||||
|
||||
WidgetQueryContentEvent queryCaretRect(true, NS_QUERY_CARET_RECT, mWidget);
|
||||
WidgetQueryContentEvent queryCaretRect(true, eQueryCaretRect, mWidget);
|
||||
queryCaretRect.InitForQueryCaretRect(caretOffset);
|
||||
mWidget->InitEvent(queryCaretRect);
|
||||
DispatchEvent(queryCaretRect);
|
||||
if (!queryCaretRect.mSucceeded) {
|
||||
MOZ_LOG(sTextStoreLog, LogLevel::Error,
|
||||
("TSF: 0x%p TSFTextStore::CreateNativeCaret() FAILED due to "
|
||||
"NS_QUERY_CARET_RECT failure (offset=%d)", this, caretOffset));
|
||||
"eQueryCaretRect failure (offset=%d)", this, caretOffset));
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -511,7 +511,7 @@ protected:
|
||||
COMPOSITION_START,
|
||||
COMPOSITION_UPDATE,
|
||||
COMPOSITION_END,
|
||||
SELECTION_SET
|
||||
SET_SELECTION
|
||||
};
|
||||
ActionType mType;
|
||||
// For compositionstart and selectionset
|
||||
@@ -793,9 +793,9 @@ protected:
|
||||
// During the documet is locked, we shouldn't destroy the instance.
|
||||
// If this is true, the instance will be destroyed after unlocked.
|
||||
bool mPendingDestroy;
|
||||
// If this is true, MaybeFlushPendingNotifications() will clear the
|
||||
// If this is false, MaybeFlushPendingNotifications() will clear the
|
||||
// mLockedContent.
|
||||
bool mPendingClearLockedContent;
|
||||
bool mDeferClearingLockedContent;
|
||||
// While there is native caret, this is true. Otherwise, false.
|
||||
bool mNativeCaretIsCreated;
|
||||
// While the instance is dispatching events, the event may not be handled
|
||||
|
||||
Reference in New Issue
Block a user