From c8073b1370ab872ad2b2d6aee2ef25af6d5339eb Mon Sep 17 00:00:00 2001 From: "Jinho, Lee" Date: Sat, 10 Jun 2017 01:32:56 +0900 Subject: [PATCH] Fixed an error adding duplicate primary position.y MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit In the target, characters with different glyph heights (ex: Korean, English: "안녕하세요, hello") are written in same text field when the character is deleted by one character, the position of the TextField continuously goes down. Change-Id: Ic44d79992eec67ae7ddec9e302c95877f90f2580 --- .../src/dali-toolkit/utc-Dali-TextEditor.cpp | 64 ++++++++++++++++++++++ .../internal/text/cursor-helper-functions.cpp | 4 +- .../internal/text/cursor-helper-functions.h | 2 + .../internal/text/decorator/text-decorator.cpp | 16 +++++- .../internal/text/decorator/text-decorator.h | 18 ++++++ .../internal/text/text-controller-impl.cpp | 15 ++++- 6 files changed, 116 insertions(+), 3 deletions(-) diff --git a/automated-tests/src/dali-toolkit/utc-Dali-TextEditor.cpp b/automated-tests/src/dali-toolkit/utc-Dali-TextEditor.cpp index c143510..053c79c 100644 --- a/automated-tests/src/dali-toolkit/utc-Dali-TextEditor.cpp +++ b/automated-tests/src/dali-toolkit/utc-Dali-TextEditor.cpp @@ -1801,6 +1801,70 @@ int utcDaliTextEditorEvent05(void) END_TEST; } +int utcDaliTextEditorEvent06(void) +{ + ToolkitTestApplication application; + tet_infoline(" utcDaliTextEditorEvent06"); + + // Checks if the highlight actor is created. + + TextEditor editor = TextEditor::New(); + DALI_TEST_CHECK( editor ); + + Stage::GetCurrent().Add( editor ); + + editor.SetProperty( TextEditor::Property::TEXT, "Hello\nworld\nHello world" ); + editor.SetProperty( TextEditor::Property::POINT_SIZE, 10.f ); + editor.SetSize( 100.f, 50.f ); + editor.SetParentOrigin( ParentOrigin::TOP_LEFT ); + editor.SetAnchorPoint( AnchorPoint::TOP_LEFT ); + + // Avoid a crash when core load gl resources. + application.GetGlAbstraction().SetCheckFramebufferStatusResult( GL_FRAMEBUFFER_COMPLETE ); + + // Render and notify + application.SendNotification(); + application.Render(); + + // Tap on the text editor + application.ProcessEvent( GenerateTap( Gesture::Possible, 1u, 1u, Vector2( 3.f, 25.0f ) ) ); + application.ProcessEvent( GenerateTap( Gesture::Started, 1u, 1u, Vector2( 3.f, 25.0f ) ) ); + + // Render and notify + application.SendNotification(); + application.Render(); + + // Move to seconds line of the text. + application.ProcessEvent( GenerateKey( "", "", DALI_KEY_CURSOR_DOWN, 0, 0, Integration::KeyEvent::Down, DEFAULT_DEVICE_NAME, DevelKeyEvent::DeviceClass::NONE ) ); + + // Render and notify + application.SendNotification(); + application.Render(); + + float layoutHeight = editor.GetHeightForWidth( 100.f ); + + + // Add another script characters ( glyph height is defferent ) + application.ProcessEvent( GenerateKey( "d", "ㅁ", KEY_D_CODE, 0, 0, Integration::KeyEvent::Down, DEFAULT_DEVICE_NAME, DevelKeyEvent::DeviceClass::NONE ) ); + application.ProcessEvent( GenerateKey( "d", "ኢ", KEY_D_CODE, 0, 0, Integration::KeyEvent::Down, DEFAULT_DEVICE_NAME, DevelKeyEvent::DeviceClass::NONE ) ); + + // Delete characters + application.ProcessEvent( GenerateKey( "", "", DALI_KEY_BACKSPACE, 0, 0, Integration::KeyEvent::Down, DEFAULT_DEVICE_NAME, DevelKeyEvent::DeviceClass::NONE ) ); + application.ProcessEvent( GenerateKey( "", "", DALI_KEY_BACKSPACE, 0, 0, Integration::KeyEvent::Down, DEFAULT_DEVICE_NAME, DevelKeyEvent::DeviceClass::NONE ) ); + + DALI_TEST_EQUALS( layoutHeight, editor.GetHeightForWidth( 100.f ), TEST_LOCATION ); + + // Render and notify + application.SendNotification(); + application.Render(); + + DALI_TEST_EQUALS( "Hello\nworld\nHello world", editor.GetProperty( TextEditor::Property::TEXT ), TEST_LOCATION ); + + + + END_TEST; +} + int utcDaliTextEditorHandles(void) { ToolkitTestApplication application; diff --git a/dali-toolkit/internal/text/cursor-helper-functions.cpp b/dali-toolkit/internal/text/cursor-helper-functions.cpp index b847996..04a1af3 100644 --- a/dali-toolkit/internal/text/cursor-helper-functions.cpp +++ b/dali-toolkit/internal/text/cursor-helper-functions.cpp @@ -668,9 +668,11 @@ void GetCursorPosition( VisualModelPtr visualModel, // Set the primary cursor's height. cursorInfo.primaryCursorHeight = cursorInfo.isSecondaryCursor ? 0.5f * glyphMetrics.fontHeight : glyphMetrics.fontHeight; + + cursorInfo.glyphOffset = line.ascender - glyphMetrics.ascender; // Set the primary cursor's position. cursorInfo.primaryPosition.x = -glyphMetrics.xBearing + primaryPosition.x + glyphAdvance; - cursorInfo.primaryPosition.y = cursorInfo.lineOffset + line.ascender - glyphMetrics.ascender; + cursorInfo.primaryPosition.y = cursorInfo.lineOffset + cursorInfo.glyphOffset; // Transform the cursor info from line's coords to text's coords. cursorInfo.primaryPosition.x += line.alignmentOffset; diff --git a/dali-toolkit/internal/text/cursor-helper-functions.h b/dali-toolkit/internal/text/cursor-helper-functions.h index f62165b..34a5f7b 100644 --- a/dali-toolkit/internal/text/cursor-helper-functions.h +++ b/dali-toolkit/internal/text/cursor-helper-functions.h @@ -50,6 +50,7 @@ struct CursorInfo : primaryPosition(), secondaryPosition(), lineOffset( 0.f ), + glyphOffset( 0.f ), lineHeight( 0.f ), primaryCursorHeight( 0.f ), secondaryCursorHeight( 0.f ), @@ -62,6 +63,7 @@ struct CursorInfo Vector2 primaryPosition; ///< The primary cursor's position (in text's coords). Vector2 secondaryPosition; ///< The secondary cursor's position (in text's coords). float lineOffset; ///< The vertical offset where the line containing the cursor starts. + float glyphOffset; ///< The difference of line ascender and glyph ascender. float lineHeight; ///< The height of the line where the cursor is placed. float primaryCursorHeight; ///< The primary cursor's height. float secondaryCursorHeight; ///< The secondary cursor's height. diff --git a/dali-toolkit/internal/text/decorator/text-decorator.cpp b/dali-toolkit/internal/text/decorator/text-decorator.cpp index da49940..e9e0b1a 100644 --- a/dali-toolkit/internal/text/decorator/text-decorator.cpp +++ b/dali-toolkit/internal/text/decorator/text-decorator.cpp @@ -164,7 +164,8 @@ struct Decorator::Impl : public ConnectionTracker : color( Dali::Color::BLACK ), position(), cursorHeight( 0.0f ), - lineHeight( 0.0f ) + lineHeight( 0.0f ), + glyphOffset( 0.0f ) { } @@ -172,6 +173,7 @@ struct Decorator::Impl : public ConnectionTracker Vector2 position; float cursorHeight; float lineHeight; + float glyphOffset; }; struct HandleImpl @@ -2006,6 +2008,18 @@ const Vector2& Decorator::GetPosition( Cursor cursor ) const return mImpl->mCursor[cursor].position; } +void Decorator::SetGlyphOffset( Cursor cursor, float glyphOffset ) +{ + Impl::CursorImpl& cursorImpl = mImpl->mCursor[cursor]; + + cursorImpl.glyphOffset = glyphOffset; +} + +const float Decorator::GetGlyphOffset( Cursor cursor) const +{ + return mImpl->mCursor[cursor].glyphOffset; +} + void Decorator::SetCursorColor( Cursor cursor, const Dali::Vector4& color ) { mImpl->mCursor[cursor].color = color; diff --git a/dali-toolkit/internal/text/decorator/text-decorator.h b/dali-toolkit/internal/text/decorator/text-decorator.h index 6e7c727..8cff322 100644 --- a/dali-toolkit/internal/text/decorator/text-decorator.h +++ b/dali-toolkit/internal/text/decorator/text-decorator.h @@ -243,6 +243,24 @@ public: */ const Vector2& GetPosition( Cursor cursor ) const; + + /** + * @brief Sets the glyph offset of a cursor. + * + * @param[in] cursor The cursor to set. + * @param[in] glyphoffset The difference of line ascender and glyph ascender. + */ + void SetGlyphOffset( Cursor cursor, float glyphOffset ); + + /** + * @brief Retrieves the glyph offset of a cursor. + * + * @param[in] cursor The cursor to get. + * + * @return The glyph offset. glyph offset means difference of line ascender and glyph ascender. + */ + const float GetGlyphOffset( Cursor cursor ) const; + /** * @brief Sets the color for a cursor. * diff --git a/dali-toolkit/internal/text/text-controller-impl.cpp b/dali-toolkit/internal/text/text-controller-impl.cpp index f119650..58893d4 100644 --- a/dali-toolkit/internal/text/text-controller-impl.cpp +++ b/dali-toolkit/internal/text/text-controller-impl.cpp @@ -2695,6 +2695,8 @@ void Controller::Impl::UpdateCursorPosition( const CursorInfo& cursorInfo ) const Vector2 cursorPosition = cursorInfo.primaryPosition + mModel->mScrollPosition; + mEventData->mDecorator->SetGlyphOffset( PRIMARY_CURSOR, cursorInfo.glyphOffset ); + // Sets the cursor position. mEventData->mDecorator->SetPosition( PRIMARY_CURSOR, cursorPosition.x, @@ -2845,9 +2847,20 @@ void Controller::Impl::ScrollTextToMatchCursor( const CursorInfo& cursorInfo ) // Get the current cursor position in decorator coords. const Vector2& currentCursorPosition = mEventData->mDecorator->GetPosition( PRIMARY_CURSOR ); + const LineIndex lineIndex = mModel->mVisualModel->GetLineOfCharacter( mEventData->mPrimaryCursorPosition ); + + + // Calculate the offset to match the cursor position before the character was deleted. mModel->mScrollPosition.x = currentCursorPosition.x - cursorInfo.primaryPosition.x; - mModel->mScrollPosition.y = currentCursorPosition.y - cursorInfo.lineOffset; + + //If text control has more than two lines and current line index is not last, calculate scrollpositionY + if( mModel->mVisualModel->mLines.Count() > 1u && lineIndex != mModel->mVisualModel->mLines.Count() -1u ) + { + const float currentCursorGlyphOffset = mEventData->mDecorator->GetGlyphOffset( PRIMARY_CURSOR ); + mModel->mScrollPosition.y = currentCursorPosition.y - cursorInfo.lineOffset - currentCursorGlyphOffset; + } + ClampHorizontalScroll( mModel->mVisualModel->GetLayoutSize() ); ClampVerticalScroll( mModel->mVisualModel->GetLayoutSize() ); -- 2.7.4