summaryrefslogtreecommitdiff
path: root/indra
diff options
context:
space:
mode:
authormaksymsproductengine <maksymsproductengine@lindenlab.com>2014-05-07 18:42:24 +0300
committermaksymsproductengine <maksymsproductengine@lindenlab.com>2014-05-07 18:42:24 +0300
commit8b86130f25a780b7dc623c6f7ff7a9cb6cf22ea1 (patch)
tree88eb3344998377aea30f28a144dc6847ccd8ed4b /indra
parentb36458a98fb3aeb63d2aca5e3249c7aa508192c8 (diff)
MAINT-3967 FIXED Up arrow key does not move the cursor up in chat field.
Diffstat (limited to 'indra')
-rwxr-xr-xindra/llui/lltextbase.cpp29
-rwxr-xr-xindra/llui/lltextbase.h1
-rwxr-xr-xindra/llui/lltexteditor.cpp56
3 files changed, 79 insertions, 7 deletions
diff --git a/indra/llui/lltextbase.cpp b/indra/llui/lltextbase.cpp
index 62edbadb07..183d6481c3 100755
--- a/indra/llui/lltextbase.cpp
+++ b/indra/llui/lltextbase.cpp
@@ -225,7 +225,8 @@ LLTextBase::LLTextBase(const LLTextBase::Params &p)
mParseHighlights(p.parse_highlights),
mBGVisible(p.bg_visible),
mScroller(NULL),
- mStyleDirty(true)
+ mStyleDirty(true),
+ mDrawRightmostCursor(false)
{
if(p.allow_scroll)
{
@@ -1510,6 +1511,11 @@ void LLTextBase::reflow()
// find and erase line info structs starting at start_index and going to end of document
if (!mLineInfoList.empty())
{
+ if (mDrawRightmostCursor)
+ {
+ start_index--;
+ }
+
// find first element whose end comes after start_index
line_list_t::iterator iter = std::upper_bound(mLineInfoList.begin(), mLineInfoList.end(), start_index, line_end_compare());
line_start_index = iter->mDocIndexStart;
@@ -1698,6 +1704,11 @@ S32 LLTextBase::getLineNumFromDocIndex( S32 doc_index, bool include_wordwrap) co
}
else
{
+ if (mDrawRightmostCursor)
+ {
+ doc_index--;
+ }
+
line_list_t::const_iterator iter = std::upper_bound(mLineInfoList.begin(), mLineInfoList.end(), doc_index, line_end_compare());
if (include_wordwrap)
{
@@ -1726,6 +1737,11 @@ S32 LLTextBase::getLineOffsetFromDocIndex( S32 startpos, bool include_wordwrap)
}
else
{
+ if (mDrawRightmostCursor)
+ {
+ startpos--;
+ }
+
line_list_t::const_iterator iter = std::upper_bound(mLineInfoList.begin(), mLineInfoList.end(), startpos, line_end_compare());
return startpos - iter->mDocIndexStart;
}
@@ -2445,7 +2461,7 @@ S32 LLTextBase::getDocIndexFromLocalCoord( S32 local_x, S32 local_y, BOOL round,
}
else if (hit_past_end_of_line && segmentp->getEnd() >= line_iter->mDocIndexEnd)
{
- if (getLineNumFromDocIndex(line_iter->mDocIndexEnd - 1) == line_iter->mLineNum)
+ if (getLineNumFromDocIndex(line_iter->mDocIndexEnd - 1) == line_iter->mLineNum && !mDrawRightmostCursor)
{
// if segment wraps to the next line we should step one char back
// to compensate for the space char between words
@@ -2478,8 +2494,13 @@ LLRect LLTextBase::getDocRectFromDocIndex(S32 pos) const
// clamp pos to valid values
pos = llclamp(pos, 0, mLineInfoList.back().mDocIndexEnd - 1);
- // find line that contains cursor
- line_list_t::const_iterator line_iter = std::upper_bound(mLineInfoList.begin(), mLineInfoList.end(), pos, line_end_compare());
+ S32 corrected_pos = pos;
+ if (mDrawRightmostCursor && pos > 0)
+ {
+ corrected_pos--;
+ }
+
+ line_list_t::const_iterator line_iter = std::upper_bound(mLineInfoList.begin(), mLineInfoList.end(), corrected_pos, line_end_compare());
doc_rect.mLeft = line_iter->mRect.mLeft;
doc_rect.mBottom = line_iter->mRect.mBottom;
diff --git a/indra/llui/lltextbase.h b/indra/llui/lltextbase.h
index d1f66b6cfe..51ab81bf29 100755
--- a/indra/llui/lltextbase.h
+++ b/indra/llui/lltextbase.h
@@ -606,6 +606,7 @@ protected:
// cursor
S32 mCursorPos; // I-beam is just after the mCursorPos-th character.
+ bool mDrawRightmostCursor; // When cursor is on the rightmost position on the line
S32 mDesiredXPixel; // X pixel position where the user wants the cursor to be
LLFrameTimer mCursorBlinkTimer; // timer that controls cursor blinking
diff --git a/indra/llui/lltexteditor.cpp b/indra/llui/lltexteditor.cpp
index fbd742f615..6bb13516bf 100755
--- a/indra/llui/lltexteditor.cpp
+++ b/indra/llui/lltexteditor.cpp
@@ -1135,8 +1135,14 @@ void LLTextEditor::addChar(llwchar wc)
setCursorPos(new_cursor_pos);
}
}
-}
+ if (mCursorPos > 0)
+ {
+ LLRect current_cursor_rect = getDocRectFromDocIndex(mCursorPos);
+ LLRect prev_cursor_rect = getDocRectFromDocIndex(mCursorPos - 1);
+ mDrawRightmostCursor = current_cursor_rect.mBottom < prev_cursor_rect.mBottom;
+ }
+}
void LLTextEditor::addLineBreakChar(BOOL group_together)
{
@@ -1282,6 +1288,12 @@ BOOL LLTextEditor::handleNavigationKey(const KEY key, const MASK mask)
break;
case KEY_HOME:
+ if(mDrawRightmostCursor && mCursorPos > 0)
+ {
+ mCursorPos--;
+ mDrawRightmostCursor = false;
+ }
+
startOfLine();
break;
@@ -1296,6 +1308,14 @@ BOOL LLTextEditor::handleNavigationKey(const KEY key, const MASK mask)
case KEY_END:
endOfLine();
+ if (!mDrawRightmostCursor)
+ {
+ mDrawRightmostCursor = true;
+ if (mCursorPos + 1 < getLength())
+ {
+ setCursorPos(mCursorPos + 1);
+ }
+ }
break;
case KEY_LEFT:
@@ -1307,7 +1327,18 @@ BOOL LLTextEditor::handleNavigationKey(const KEY key, const MASK mask)
{
if( 0 < mCursorPos )
{
- setCursorPos(mCursorPos - 1);
+ LLRect current_cursor_rect = getDocRectFromDocIndex(mCursorPos);
+ LLRect next_cursor_rect = getDocRectFromDocIndex(mCursorPos - 1);
+
+ if (current_cursor_rect.mBottom < next_cursor_rect.mBottom)
+ {
+ mDrawRightmostCursor = true;
+ }
+ else
+ {
+ mDrawRightmostCursor = false;
+ setCursorPos(mCursorPos - 1);
+ }
}
else
{
@@ -1325,7 +1356,26 @@ BOOL LLTextEditor::handleNavigationKey(const KEY key, const MASK mask)
{
if( mCursorPos < getLength() )
{
- setCursorPos(mCursorPos + 1);
+ LLRect current_cursor_rect = getDocRectFromDocIndex(mCursorPos);
+ LLRect next_cursor_rect = getDocRectFromDocIndex(mCursorPos + 1);
+
+ if (current_cursor_rect.mBottom > next_cursor_rect.mBottom)
+ {
+ if (mDrawRightmostCursor)
+ {
+ mDrawRightmostCursor = false;
+ }
+ else
+ {
+ mDrawRightmostCursor = true;
+ setCursorPos(mCursorPos + 1);
+ }
+ }
+ else
+ {
+ mDrawRightmostCursor = false;
+ setCursorPos(mCursorPos + 1);
+ }
}
else
{