diff options
author | thickbrick | 2010-09-23 19:39:56 +0200 |
---|---|---|
committer | thickbrick | 2010-09-25 13:28:49 +0200 |
commit | cd097fee7848f2e78c0865d0fad7d510a661aa20 (patch) | |
tree | afe1f8cca55d4c7bf60f96b4c1cf5ea46bf715ef /linden | |
parent | Make chat translator ignore non-interesting translations (empty or same as (diff) | |
download | meta-impy-cd097fee7848f2e78c0865d0fad7d510a661aa20.zip meta-impy-cd097fee7848f2e78c0865d0fad7d510a661aa20.tar.gz meta-impy-cd097fee7848f2e78c0865d0fad7d510a661aa20.tar.bz2 meta-impy-cd097fee7848f2e78c0865d0fad7d510a661aa20.tar.xz |
Fix LLTextEditor context menu translator returning "()" when nothing is selected.
New behavior is to translate the word under the mouse if nothing is selected.
Diffstat (limited to 'linden')
-rw-r--r-- | linden/indra/llui/lltexteditor.cpp | 83 | ||||
-rw-r--r-- | linden/indra/llui/lltexteditor.h | 4 |
2 files changed, 77 insertions, 10 deletions
diff --git a/linden/indra/llui/lltexteditor.cpp b/linden/indra/llui/lltexteditor.cpp index b101588..4bae155 100644 --- a/linden/indra/llui/lltexteditor.cpp +++ b/linden/indra/llui/lltexteditor.cpp | |||
@@ -105,21 +105,23 @@ bool (* LLTextEditor::mSecondlifeURLcallbackRightClick)(const std::string&) = | |||
105 | class TextChatTranslationReceiver : public LLTranslate::TranslationReceiver | 105 | class TextChatTranslationReceiver : public LLTranslate::TranslationReceiver |
106 | { | 106 | { |
107 | public : | 107 | public : |
108 | TextChatTranslationReceiver(const std::string &toLang, LLTextEditor* line): LLTranslate::TranslationReceiver("", toLang), | 108 | TextChatTranslationReceiver(const std::string &toLang, LLTextEditor* line, const S32 start, const S32 len): |
109 | m_line(line) | 109 | LLTranslate::TranslationReceiver("", toLang), |
110 | m_line(line), | ||
111 | m_position(start), | ||
112 | m_origLength(len) | ||
110 | { | 113 | { |
111 | } | 114 | } |
112 | 115 | ||
113 | static boost::intrusive_ptr<TextChatTranslationReceiver> build(const std::string &toLang,LLTextEditor* line) | 116 | static boost::intrusive_ptr<TextChatTranslationReceiver> build(const std::string &toLang,LLTextEditor* line, const S32 start, const S32 len) |
114 | { | 117 | { |
115 | return boost::intrusive_ptr<TextChatTranslationReceiver>(new TextChatTranslationReceiver(toLang,line)); | 118 | return boost::intrusive_ptr<TextChatTranslationReceiver>(new TextChatTranslationReceiver(toLang, line, start, len)); |
116 | } | 119 | } |
117 | 120 | ||
118 | protected: | 121 | protected: |
119 | void handleResponse(const std::string &translation, const std::string &detectedLanguage) | 122 | void handleResponse(const std::string &translation, const std::string &detectedLanguage) |
120 | { | 123 | { |
121 | BOOL rep = gSavedSettings.getBOOL("EmeraldTranslateReplace"); | 124 | m_line->translationReplace(translation, m_position, m_origLength); |
122 | m_line->insertText((rep?"":" (") + translation +(rep?"":")"),rep); | ||
123 | } | 125 | } |
124 | void handleFailure() | 126 | void handleFailure() |
125 | { | 127 | { |
@@ -127,6 +129,8 @@ protected: | |||
127 | } | 129 | } |
128 | private: | 130 | private: |
129 | LLTextEditor* m_line; | 131 | LLTextEditor* m_line; |
132 | S32 m_position; | ||
133 | S32 m_origLength; | ||
130 | }; | 134 | }; |
131 | 135 | ||
132 | /////////////////////////////////////////////////////////////////// | 136 | /////////////////////////////////////////////////////////////////// |
@@ -321,6 +325,8 @@ LLTextEditor::LLTextEditor( | |||
321 | mMouseDownY(0), | 325 | mMouseDownY(0), |
322 | mLastSelectionX(-1), | 326 | mLastSelectionX(-1), |
323 | mLastSelectionY(-1), | 327 | mLastSelectionY(-1), |
328 | mLastContextMenuX(-1), | ||
329 | mLastContextMenuY(-1), | ||
324 | mReflowNeeded(FALSE), | 330 | mReflowNeeded(FALSE), |
325 | mScrollNeeded(FALSE), | 331 | mScrollNeeded(FALSE), |
326 | mSpellCheckable(FALSE), | 332 | mSpellCheckable(FALSE), |
@@ -467,17 +473,36 @@ void LLTextEditor::context_copy(void* data) | |||
467 | LLTextEditor* line = (LLTextEditor*)data; | 473 | LLTextEditor* line = (LLTextEditor*)data; |
468 | if(line)line->copy(); | 474 | if(line)line->copy(); |
469 | } | 475 | } |
476 | |||
470 | void LLTextEditor::translateText(void * data) | 477 | void LLTextEditor::translateText(void * data) |
471 | { | 478 | { |
472 | SpellMenuBind* t = (SpellMenuBind*)data; | 479 | SpellMenuBind* t = (SpellMenuBind*)data; |
473 | LLTextEditor* line = t->origin; | 480 | LLTextEditor* line = t->origin; |
474 | const std::string &toLang = t->word;//LLTranslate::getTranslateLanguage(); | 481 | const std::string &toLang = t->word;//LLTranslate::getTranslateLanguage(); |
475 | LLHTTPClient::ResponderPtr result = TextChatTranslationReceiver::build(toLang,line); | ||
476 | 482 | ||
477 | S32 left_pos = llmin( line->mSelectionStart, line->mSelectionEnd ); | 483 | bool has_text = false; |
478 | S32 length = abs( line->mSelectionStart - line->mSelectionEnd ); | 484 | S32 start, length; |
479 | LLTranslate::translateMessage(result,"", toLang, line->getText().substr(left_pos, length)); | 485 | if (line->hasSelection()) |
486 | { | ||
487 | // translate selection | ||
488 | start = llmin(line->mSelectionStart, line->mSelectionEnd); | ||
489 | length = abs(line->mSelectionEnd - line->mSelectionStart); | ||
490 | has_text = length > 0; | ||
491 | } | ||
492 | else | ||
493 | { | ||
494 | // translate one word as click position | ||
495 | S32 at = line->getCursorPosFromLocalCoord(line->mLastContextMenuX, line->mLastContextMenuY, TRUE); | ||
496 | has_text = line->getWordBoundriesAt(at, &start, &length); | ||
497 | } | ||
498 | |||
499 | if (has_text) | ||
500 | { | ||
501 | LLHTTPClient::ResponderPtr result = TextChatTranslationReceiver::build(toLang, line, start, length); | ||
502 | LLTranslate::translateMessage(result,"", toLang, line->getText().substr(start, length)); | ||
503 | } | ||
480 | } | 504 | } |
505 | |||
481 | void LLTextEditor::spell_correct(void* data) | 506 | void LLTextEditor::spell_correct(void* data) |
482 | { | 507 | { |
483 | SpellMenuBind* tempBind = (SpellMenuBind*)data; | 508 | SpellMenuBind* tempBind = (SpellMenuBind*)data; |
@@ -947,6 +972,26 @@ S32 LLTextEditor::nextWordPos(S32 cursorPos) const | |||
947 | return cursorPos; | 972 | return cursorPos; |
948 | } | 973 | } |
949 | 974 | ||
975 | BOOL LLTextEditor::getWordBoundriesAt(const S32 at, S32* word_begin, S32* word_length) const | ||
976 | { | ||
977 | S32 pos = at; | ||
978 | if (isPartOfWord(mWText[pos])) | ||
979 | { | ||
980 | while ( (pos > 0) && isPartOfWord(mWText[pos - 1]) ) | ||
981 | { | ||
982 | pos--; | ||
983 | } | ||
984 | *word_begin = pos; | ||
985 | while ( (pos < getLength()) && isPartOfWord(mWText[pos]) ) | ||
986 | { | ||
987 | pos++; | ||
988 | } | ||
989 | *word_length = pos - *word_begin; | ||
990 | return TRUE; | ||
991 | } | ||
992 | return FALSE; | ||
993 | } | ||
994 | |||
950 | S32 LLTextEditor::getLineStart( S32 line ) const | 995 | S32 LLTextEditor::getLineStart( S32 line ) const |
951 | { | 996 | { |
952 | S32 num_lines = getLineCount(); | 997 | S32 num_lines = getLineCount(); |
@@ -1531,6 +1576,8 @@ BOOL LLTextEditor::handleRightMouseDown( S32 x, S32 y, MASK mask ) | |||
1531 | suggestionMenuItems.push_back(tempStruct); | 1576 | suggestionMenuItems.push_back(tempStruct); |
1532 | menu->append(suggMenuItem); | 1577 | menu->append(suggMenuItem); |
1533 | } | 1578 | } |
1579 | mLastContextMenuX = x; | ||
1580 | mLastContextMenuY = y; | ||
1534 | menu->buildDrawLabels(); | 1581 | menu->buildDrawLabels(); |
1535 | menu->updateParent(LLMenuGL::sMenuContainer); | 1582 | menu->updateParent(LLMenuGL::sMenuContainer); |
1536 | LLMenuGL::showPopup(this, menu, x, y); | 1583 | LLMenuGL::showPopup(this, menu, x, y); |
@@ -2238,6 +2285,22 @@ void LLTextEditor::spellReplace(SpellMenuBind* spellData) | |||
2238 | needsReflow(); | 2285 | needsReflow(); |
2239 | } | 2286 | } |
2240 | 2287 | ||
2288 | void LLTextEditor::translationReplace(const std::string &translation, const S32 orig_start, const S32 orig_length) | ||
2289 | { | ||
2290 | //*TODO: should probably check if the content was modified since the http query | ||
2291 | // was made, so we don't insert text in the wrong place. | ||
2292 | BOOL replace = gSavedSettings.getBOOL("EmeraldTranslateReplace"); | ||
2293 | LLWString wtext = utf8str_to_wstring(replace ? translation : " (" + translation + ")"); | ||
2294 | S32 pos = replace ? orig_start : orig_start + orig_length; | ||
2295 | if (replace) | ||
2296 | { | ||
2297 | remove(orig_start, orig_length, FALSE); | ||
2298 | } | ||
2299 | insert(pos, wtext, FALSE); | ||
2300 | setCursorPos(pos + wtext.length()); | ||
2301 | needsReflow(); | ||
2302 | } | ||
2303 | |||
2241 | // paste from clipboard | 2304 | // paste from clipboard |
2242 | void LLTextEditor::paste() | 2305 | void LLTextEditor::paste() |
2243 | { | 2306 | { |
diff --git a/linden/indra/llui/lltexteditor.h b/linden/indra/llui/lltexteditor.h index 57a6bbd..f6669c4 100644 --- a/linden/indra/llui/lltexteditor.h +++ b/linden/indra/llui/lltexteditor.h | |||
@@ -136,6 +136,7 @@ public: | |||
136 | virtual BOOL canPaste() const; | 136 | virtual BOOL canPaste() const; |
137 | 137 | ||
138 | virtual void spellReplace(SpellMenuBind* spellData); | 138 | virtual void spellReplace(SpellMenuBind* spellData); |
139 | virtual void translationReplace(const std::string &translation, const S32 orig_start, const S32 orig_length); | ||
139 | 140 | ||
140 | virtual void updatePrimary(); | 141 | virtual void updatePrimary(); |
141 | virtual void copyPrimary(); | 142 | virtual void copyPrimary(); |
@@ -352,6 +353,7 @@ public: | |||
352 | 353 | ||
353 | S32 prevWordPos(S32 cursorPos) const; | 354 | S32 prevWordPos(S32 cursorPos) const; |
354 | S32 nextWordPos(S32 cursorPos) const; | 355 | S32 nextWordPos(S32 cursorPos) const; |
356 | BOOL getWordBoundriesAt(const S32 at, S32* word_begin, S32* word_length) const; | ||
355 | 357 | ||
356 | S32 getLineCount() const { return mLineStartList.size(); } | 358 | S32 getLineCount() const { return mLineStartList.size(); } |
357 | S32 getLineStart( S32 line ) const; | 359 | S32 getLineStart( S32 line ) const; |
@@ -568,6 +570,8 @@ private: | |||
568 | 570 | ||
569 | //to keep track of what we have to remove before showing menu | 571 | //to keep track of what we have to remove before showing menu |
570 | std::vector<SpellMenuBind* > suggestionMenuItems; | 572 | std::vector<SpellMenuBind* > suggestionMenuItems; |
573 | S32 mLastContextMenuX; | ||
574 | S32 mLastContextMenuY; | ||
571 | 575 | ||
572 | line_list_t mLineStartList; | 576 | line_list_t mLineStartList; |
573 | BOOL mReflowNeeded; | 577 | BOOL mReflowNeeded; |