From 8d70765e9e608bda15d8e04720687f3a0ddc0e81 Mon Sep 17 00:00:00 2001 From: sarajammal Date: Sun, 25 Sep 2022 18:26:12 +0300 Subject: [PATCH] Add GetLineBoundingRectangle API. Calculate the line size and position: - X, the left starting point of the line. - Y, the left top point of the line. - Width. - Height. Function prototype: GetLineBoundingRectangle(ModelPtr model, uint32_t lineIndex); Add new API to TextGeometry. Reference patches: https://review.tizen.org/gerrit/c/platform/core/uifw/dali-toolkit/+/266891 Change-Id: I742a44bd406bc13d1c3ec35bce3049b467d21962 --- automated-tests/src/dali-toolkit/CMakeLists.txt | 1 + .../src/dali-toolkit/test-text-geometry-utils.cpp | 8 + .../src/dali-toolkit/test-text-geometry-utils.h | 1 + .../src/dali-toolkit/utc-Dali-TextGeometry.cpp | 331 +++++++++++++++++++++ dali-toolkit/devel-api/file.list | 2 + .../devel-api/text/text-geometry-devel.cpp | 56 ++++ dali-toolkit/devel-api/text/text-geometry-devel.h | 73 +++++ .../controls/text-controls/text-editor-impl.cpp | 5 + .../controls/text-controls/text-editor-impl.h | 9 + .../controls/text-controls/text-field-impl.cpp | 5 + .../controls/text-controls/text-field-impl.h | 9 + .../controls/text-controls/text-label-impl.cpp | 5 + .../controls/text-controls/text-label-impl.h | 9 + .../internal/text/controller/text-controller.cpp | 6 +- .../internal/text/controller/text-controller.h | 9 + dali-toolkit/internal/text/line-run.h | 8 + dali-toolkit/internal/text/text-geometry.cpp | 65 ++++ dali-toolkit/internal/text/text-geometry.h | 32 +- 18 files changed, 632 insertions(+), 2 deletions(-) create mode 100644 automated-tests/src/dali-toolkit/utc-Dali-TextGeometry.cpp create mode 100644 dali-toolkit/devel-api/text/text-geometry-devel.cpp create mode 100644 dali-toolkit/devel-api/text/text-geometry-devel.h diff --git a/automated-tests/src/dali-toolkit/CMakeLists.txt b/automated-tests/src/dali-toolkit/CMakeLists.txt index 7076e8a..2cdf4c8 100755 --- a/automated-tests/src/dali-toolkit/CMakeLists.txt +++ b/automated-tests/src/dali-toolkit/CMakeLists.txt @@ -42,6 +42,7 @@ SET(TC_SOURCES utc-Dali-TableView.cpp utc-Dali-TextEditor.cpp utc-Dali-TextField.cpp + utc-Dali-TextGeometry.cpp utc-Dali-TextLabel.cpp utc-Dali-TextSelectionPopup.cpp utc-Dali-TextSelectionPopupMirroringLTR.cpp diff --git a/automated-tests/src/dali-toolkit/test-text-geometry-utils.cpp b/automated-tests/src/dali-toolkit/test-text-geometry-utils.cpp index b2f0411..6ca87ad 100644 --- a/automated-tests/src/dali-toolkit/test-text-geometry-utils.cpp +++ b/automated-tests/src/dali-toolkit/test-text-geometry-utils.cpp @@ -34,4 +34,12 @@ void CheckGeometryResult(Vector positionsList, Vector sizeList } } +void CheckRectGeometryResult(Rect<> rectGeometry, Rect<> expectedRectGeometry) +{ + DALI_TEST_EQUALS((float)rectGeometry.x, (float)expectedRectGeometry.x, TEST_LOCATION); + DALI_TEST_EQUALS((float)rectGeometry.y, (float)expectedRectGeometry.y, TEST_LOCATION); + DALI_TEST_EQUALS((float)rectGeometry.width, (float)expectedRectGeometry.width, TEST_LOCATION); + DALI_TEST_EQUALS((float)rectGeometry.height, (float)expectedRectGeometry.height, TEST_LOCATION); +} + } \ No newline at end of file diff --git a/automated-tests/src/dali-toolkit/test-text-geometry-utils.h b/automated-tests/src/dali-toolkit/test-text-geometry-utils.h index 4aa2a33..41050eb 100644 --- a/automated-tests/src/dali-toolkit/test-text-geometry-utils.h +++ b/automated-tests/src/dali-toolkit/test-text-geometry-utils.h @@ -27,6 +27,7 @@ namespace TestTextGeometryUtils { void CheckGeometryResult(Vector positionsList, Vector sizeList, Vector expectedPositions, Vector expectedSizes); +void CheckRectGeometryResult(Rect<> rectGeometry, Rect<> expectedRectGeometry); } #endif // TOOLKIT_TEXT_GEOMETRY_UTILS_H diff --git a/automated-tests/src/dali-toolkit/utc-Dali-TextGeometry.cpp b/automated-tests/src/dali-toolkit/utc-Dali-TextGeometry.cpp new file mode 100644 index 0000000..34f8d1e --- /dev/null +++ b/automated-tests/src/dali-toolkit/utc-Dali-TextGeometry.cpp @@ -0,0 +1,331 @@ + + +/* + * Copyright (c) 2022 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "test-text-geometry-utils.h" + +using namespace Dali; +using namespace Toolkit; +using namespace Text; + +void dali_textgeometry_startup(void) +{ + test_return_value = TET_UNDEF; +} + +void dali_textgeometry_cleanup(void) +{ + test_return_value = TET_PASS; +} + +int UtcDaliTextGeometryGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + float lineSpacing = -20.f; + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(DevelTextLabel::Property::LINE_SPACING, lineSpacing); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 16, 420, 16}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryGetLineBoundingRectangleEditor(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryGetLineBoundingRectangleEditor"); + + TextEditor editor = TextEditor::New(); + DALI_TEST_CHECK(editor); + + application.GetScene().Add(editor); + + editor.SetProperty(Actor::Property::SIZE, Vector2(160.0f, 250.f)); + editor.SetProperty(TextEditor::Property::POINT_SIZE, 10.f); + editor.SetProperty(TextEditor::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(editor, 0); + + Rect<> expectedLineGeometry = {0, 0, 91, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryGetLineBoundingRectangleField(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryGetLineBoundingRectangleField"); + + TextField field = TextField::New(); + DALI_TEST_CHECK(field); + + application.GetScene().Add(field); + + field.SetProperty(Actor::Property::ANCHOR_POINT, AnchorPoint::CENTER); + field.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 350.f)); + field.SetProperty(TextField::Property::POINT_SIZE, 10.f); + field.SetProperty(TextField::Property::TEXT, "مرحبا بالعالم"); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(field, 0); + + Rect<> expectedLineGeometry = {0, 0, 163, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryEmptyTextGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryEmptyTextGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::TEXT, ""); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 0); + + Rect<> expectedLineGeometry = {0, 0, 0, 0}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryLineSpacingPositiveGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryLineSpacingPositiveGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + float lineSpacing = 20.f; + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(DevelTextLabel::Property::LINE_SPACING, lineSpacing); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 56, 420, 56}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryWithVerticalLineAlignmentTopGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryWithVerticalLineAlignmentTopGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(Toolkit::TextLabel::Property::VERTICAL_ALIGNMENT, "TOP"); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 36, 420, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryWithVerticalLineAlignmentBottomGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryWithVerticalLineAlignmentBottomGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(Toolkit::TextLabel::Property::VERTICAL_ALIGNMENT, "BOTTOM"); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 36, 420, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} +int UtcDaliTextGeometryWithEllipsisMiddleGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryWithEllipsisMiddleGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(TextLabel::Property::ELLIPSIS, true); + label.SetProperty(DevelTextLabel::Property::ELLIPSIS_POSITION, DevelText::EllipsisPosition::MIDDLE); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 36, 420, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryWithEllipsisStartGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryWithEllipsisStartGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(TextLabel::Property::ELLIPSIS, true); + label.SetProperty(DevelTextLabel::Property::ELLIPSIS_POSITION, DevelText::EllipsisPosition::START); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 36, 420, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + +int UtcDaliTextGeometryWithEllipsisEndGetLineBoundingRectangleLabel(void) +{ + ToolkitTestApplication application; + tet_infoline("UtcDaliTextGeometryWithEllipsisEndGetLineBoundingRectangleLabel"); + + TextLabel label = TextLabel::New(); + DALI_TEST_CHECK(label); + + application.GetScene().Add(label); + + label.SetProperty(Actor::Property::SIZE, Vector2(450.0f, 300.f)); + label.SetProperty(TextLabel::Property::POINT_SIZE, 10.f); + label.SetProperty(TextLabel::Property::MULTI_LINE, true); + label.SetProperty(TextLabel::Property::ELLIPSIS, true); + label.SetProperty(DevelTextLabel::Property::ELLIPSIS_POSITION, DevelText::EllipsisPosition::END); + label.SetProperty(TextLabel::Property::TEXT, "Lorem ipsum dolor sit amet, \n consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."); + + application.SendNotification(); + application.Render(); + + Rect<> lineGeometry = TextGeometry::GetLineBoundingRectangle(label, 1); + + Rect<> expectedLineGeometry = {0, 36, 420, 36}; + + TestTextGeometryUtils::CheckRectGeometryResult(lineGeometry, expectedLineGeometry); + + END_TEST; +} + + diff --git a/dali-toolkit/devel-api/file.list b/dali-toolkit/devel-api/file.list index b501c9c..e520bd4 100755 --- a/dali-toolkit/devel-api/file.list +++ b/dali-toolkit/devel-api/file.list @@ -71,6 +71,7 @@ SET( devel_api_src_files ${devel_api_src_dir}/visual-factory/visual-base.cpp ${devel_api_src_dir}/controls/gaussian-blur-view/gaussian-blur-view.cpp ${devel_api_src_dir}/drag-drop-detector/drag-and-drop-detector.cpp + ${devel_api_src_dir}/text/text-geometry-devel.cpp ) # Add devel header files here @@ -231,6 +232,7 @@ SET( devel_api_text_header_files ${devel_api_src_dir}/text/bitmap-font.h ${devel_api_src_dir}/text/text-utils-devel.h ${devel_api_src_dir}/text/rendering-backend.h + ${devel_api_src_dir}/text/text-geometry-devel.h ) SET( devel_api_tool_bar_header_files diff --git a/dali-toolkit/devel-api/text/text-geometry-devel.cpp b/dali-toolkit/devel-api/text/text-geometry-devel.cpp new file mode 100644 index 0000000..1afc773 --- /dev/null +++ b/dali-toolkit/devel-api/text/text-geometry-devel.cpp @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2022 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +// CLASS HEADER +#include + +// INTERNAL INCLUDES +#include +#include +#include + +namespace Dali +{ +namespace Toolkit +{ +namespace Text +{ +namespace TextGeometry +{ + +Rect GetLineBoundingRectangle(TextEditor editor, const uint32_t lineIndex) +{ + return GetImpl(editor).GetLineBoundingRectangle(lineIndex); +} + +Rect GetLineBoundingRectangle(TextLabel label, const uint32_t lineIndex) +{ + return GetImpl(label).GetLineBoundingRectangle(lineIndex); +} + +Rect GetLineBoundingRectangle(TextField field, const uint32_t lineIndex) +{ + return GetImpl(field).GetLineBoundingRectangle(lineIndex); +} + +} //namespace TextGeometry + +} // namespace Text + +} // namespace Toolkit + +} // namespace Dali diff --git a/dali-toolkit/devel-api/text/text-geometry-devel.h b/dali-toolkit/devel-api/text/text-geometry-devel.h new file mode 100644 index 0000000..b63f337 --- /dev/null +++ b/dali-toolkit/devel-api/text/text-geometry-devel.h @@ -0,0 +1,73 @@ +#ifndef DALI_TOOLKIT_TEXT_GEOMETRY_DEVEL_H +#define DALI_TOOLKIT_TEXT_GEOMETRY_DEVEL_H + +/* + * Copyright (c) 2022 Samsung Electronics Co., Ltd. + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + * + */ + +//INTERNAL INCLUDES +#include +#include +#include + +namespace Dali +{ +namespace Toolkit +{ +namespace Text +{ +namespace TextGeometry +{ + + /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] editor the editor controller that contains the line. + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + DALI_TOOLKIT_API Rect GetLineBoundingRectangle(TextEditor editor, const uint32_t lineIndex); + + /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] label the label controller that contains the line. + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + DALI_TOOLKIT_API Rect GetLineBoundingRectangle(TextLabel label, const uint32_t lineIndex); + + /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] field the field controller that contains the line. + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + DALI_TOOLKIT_API Rect GetLineBoundingRectangle(TextField field, const uint32_t lineIndex); + +} // namespace TextGeometry + +} // namespace Text + +} // namespace Toolkit + +} // namespace Dali + +#endif //DALI_TOOLKIT_TEXT_GEOMETRY_DEVEL_H diff --git a/dali-toolkit/internal/controls/text-controls/text-editor-impl.cpp b/dali-toolkit/internal/controls/text-controls/text-editor-impl.cpp index 7d0f2fe..890b22c 100644 --- a/dali-toolkit/internal/controls/text-controls/text-editor-impl.cpp +++ b/dali-toolkit/internal/controls/text-controls/text-editor-impl.cpp @@ -364,6 +364,11 @@ Vector TextEditor::GetTextPosition(const uint32_t startIndex, const uin return mController->GetTextPosition(startIndex, endIndex); } +Rect TextEditor::GetLineBoundingRectangle(const uint32_t lineIndex) const +{ + return mController->GetLineBoundingRectangle(lineIndex); +} + string TextEditor::GetSelectedText() const { string selectedText = ""; diff --git a/dali-toolkit/internal/controls/text-controls/text-editor-impl.h b/dali-toolkit/internal/controls/text-controls/text-editor-impl.h index aaa58f7..0ad18a9 100644 --- a/dali-toolkit/internal/controls/text-controls/text-editor-impl.h +++ b/dali-toolkit/internal/controls/text-controls/text-editor-impl.h @@ -358,6 +358,15 @@ public: Vector GetTextPosition(const uint32_t startIndex, const uint32_t endIndex) const; /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + Rect GetLineBoundingRectangle(const uint32_t lineIndex) const; + + /** * @copydoc Text::SelectableControlInterface::GetSelectedText() */ string GetSelectedText() const override; diff --git a/dali-toolkit/internal/controls/text-controls/text-field-impl.cpp b/dali-toolkit/internal/controls/text-controls/text-field-impl.cpp index 15ea363..76d68df 100644 --- a/dali-toolkit/internal/controls/text-controls/text-field-impl.cpp +++ b/dali-toolkit/internal/controls/text-controls/text-field-impl.cpp @@ -1205,6 +1205,11 @@ Vector TextField::GetTextPosition(const uint32_t startIndex, const uint return mController->GetTextPosition(startIndex, endIndex); } +Rect TextField::GetLineBoundingRectangle(const uint32_t lineIndex) const +{ + return mController->GetLineBoundingRectangle(lineIndex); +} + std::string TextField::TextFieldAccessible::GetName() const { if(IsHiddenInput()) diff --git a/dali-toolkit/internal/controls/text-controls/text-field-impl.h b/dali-toolkit/internal/controls/text-controls/text-field-impl.h index bed947d..8e8a01a 100644 --- a/dali-toolkit/internal/controls/text-controls/text-field-impl.h +++ b/dali-toolkit/internal/controls/text-controls/text-field-impl.h @@ -367,6 +367,15 @@ public: */ Vector GetTextPosition(const uint32_t startIndex, const uint32_t endIndex) const; + /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + Rect GetLineBoundingRectangle(const uint32_t lineIndex) const; + private: // Implementation /** * @copydoc Dali::Toolkit::Text::Controller::(InputMethodContext& inputMethodContext, const InputMethodContext::EventData& inputMethodContextEvent) diff --git a/dali-toolkit/internal/controls/text-controls/text-label-impl.cpp b/dali-toolkit/internal/controls/text-controls/text-label-impl.cpp index d9e413f..cec3d0c 100644 --- a/dali-toolkit/internal/controls/text-controls/text-label-impl.cpp +++ b/dali-toolkit/internal/controls/text-controls/text-label-impl.cpp @@ -1236,6 +1236,11 @@ Vector TextLabel::GetTextPosition(const uint32_t startIndex, const uint return mController->GetTextPosition(startIndex, endIndex); } +Rect TextLabel::GetLineBoundingRectangle(const uint32_t lineIndex) const +{ + return mController->GetLineBoundingRectangle(lineIndex); +} + std::string TextLabel::TextLabelAccessible::GetNameRaw() const { return GetWholeText(); diff --git a/dali-toolkit/internal/controls/text-controls/text-label-impl.h b/dali-toolkit/internal/controls/text-controls/text-label-impl.h index 31167d8..000b6f0 100644 --- a/dali-toolkit/internal/controls/text-controls/text-label-impl.h +++ b/dali-toolkit/internal/controls/text-controls/text-label-impl.h @@ -125,6 +125,15 @@ public: */ Vector GetTextPosition(const uint32_t startIndex, const uint32_t endIndex) const; + /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + Rect GetLineBoundingRectangle(const uint32_t lineIndex) const; + private: // From Control /** * @copydoc Control::OnInitialize() diff --git a/dali-toolkit/internal/text/controller/text-controller.cpp b/dali-toolkit/internal/text/controller/text-controller.cpp index b3b55b1..5362804 100644 --- a/dali-toolkit/internal/text/controller/text-controller.cpp +++ b/dali-toolkit/internal/text/controller/text-controller.cpp @@ -38,7 +38,6 @@ #include #include #include - namespace { #if defined(DEBUG_ENABLED) @@ -1416,6 +1415,11 @@ Vector Controller::GetTextPosition(CharacterIndex startIndex, Character return positionsList; } +Rect Controller::GetLineBoundingRectangle(const uint32_t lineIndex) +{ + return GetLineBoundingRect(mImpl->mModel, lineIndex); +} + Rect<> Controller::GetTextBoundingRectangle(CharacterIndex startIndex, CharacterIndex endIndex) { Vector sizeList; diff --git a/dali-toolkit/internal/text/controller/text-controller.h b/dali-toolkit/internal/text/controller/text-controller.h index 09305d2..25185ad 100644 --- a/dali-toolkit/internal/text/controller/text-controller.h +++ b/dali-toolkit/internal/text/controller/text-controller.h @@ -1733,6 +1733,15 @@ public: // Queries & retrieves. Vector GetTextPosition(CharacterIndex startIndex, CharacterIndex endIndex); /** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ + Rect GetLineBoundingRectangle(const uint32_t lineIndex); + + /** * @brief Gets the bounding box of a specific text range. * * @param[in] startIndex start index of the text requested to get bounding box to. diff --git a/dali-toolkit/internal/text/line-run.h b/dali-toolkit/internal/text/line-run.h index c0bb095..ac2e29d 100644 --- a/dali-toolkit/internal/text/line-run.h +++ b/dali-toolkit/internal/text/line-run.h @@ -56,6 +56,14 @@ struct LineRun */ float GetLineHeight(const LineRun lineRun, bool isLastLine); +/** + * @brief Get the line width for the specified line run. + * + * @param[in] lineRun The line runs to get the width for. + * @return the width of the line. + */ +float GetLineWidth(const LineRun& lineRun); + } // namespace Text } // namespace Toolkit diff --git a/dali-toolkit/internal/text/text-geometry.cpp b/dali-toolkit/internal/text/text-geometry.cpp index 1efae75..09d2c92 100644 --- a/dali-toolkit/internal/text/text-geometry.cpp +++ b/dali-toolkit/internal/text/text-geometry.cpp @@ -23,6 +23,8 @@ // INTERNAL INCLUDES #include +#include +#include using namespace Dali; @@ -268,6 +270,69 @@ void GetTextGeometry(ModelPtr textModel, CharacterIndex startIndex, CharacterInd positionsList.PushBack(blockPos); } +float GetLineLeft(const LineRun& lineRun) +{ + return lineRun.alignmentOffset; +} + +float GetLineTop(const Vector& lines, const LineRun& lineRun) +{ + float lineTop = 0; + const int numberOfLines = (int)lines.Count(); + + int currentLineIndex = 0; + Vector::ConstIterator endIt = (&lineRun); + for(Vector::Iterator it = lines.Begin(); + it != endIt; + ++it, ++currentLineIndex) + { + LineRun& line = *it; + bool isLastLine = (currentLineIndex + 1) == numberOfLines; + lineTop += GetLineHeight(line, isLastLine); + } + + return lineTop; +} + +float GetLineWidth(const LineRun& lineRun) +{ + return lineRun.width; +} + +Rect GetLineBoundingRect(ModelPtr textModel, const uint32_t lineIndex) +{ + + if(textModel->mVisualModel == nullptr) + { + return {0, 0, 0, 0}; + } + + Length numberOfLines = textModel->mVisualModel->GetTotalNumberOfLines(); + + if(lineIndex >= numberOfLines) + { + return {0, 0, 0, 0}; + } + + const Vector& lines = textModel->mVisualModel->mLines; + const LineRun& lineRun = lines[lineIndex]; + bool isFirstLine = lineIndex == 0; + bool isLastLine = (lineIndex + 1) == numberOfLines; + + // Calculate the Left(lineX) = X position. + float lineX = GetLineLeft(lineRun) + textModel->mScrollPosition.x; + + // Calculate the Top(lineY) = PreviousHeights. + // If the line is the first line of the text; its top = 0. + float lineY = (isFirstLine ? 0 : GetLineTop(lines, lineRun)) + textModel->mScrollPosition.y; + + // The rectangle contains the width and height: + float lineWidth = GetLineWidth(lineRun); + float lineHeight = GetLineHeight(lineRun, isLastLine); + + return {lineX, lineY, lineWidth, lineHeight}; +} + } // namespace Text } // namespace Toolkit diff --git a/dali-toolkit/internal/text/text-geometry.h b/dali-toolkit/internal/text/text-geometry.h index fb118f0..c783d9b 100644 --- a/dali-toolkit/internal/text/text-geometry.h +++ b/dali-toolkit/internal/text/text-geometry.h @@ -18,9 +18,11 @@ * */ +// EXTERNAL INCLUDES +#include + // INTERNAL INCLUDES #include - namespace Dali { namespace Toolkit @@ -40,6 +42,34 @@ namespace Text */ void GetTextGeometry(ModelPtr textModel, CharacterIndex startIndex, CharacterIndex endIndex, Vector& sizesList, Vector& positionsList); +/** + * @brief Get the line bounding rectangle. + * if the requested index is out of range or the line is not yet rendered, a rect of {0, 0, 0, 0} is returned. + * + * @param[in] textModel text model containing line info. + * @param[in] lineIndex line index to which we want to calculate the geometry for. + * @return bounding rectangle. + */ +Rect GetLineBoundingRect(ModelPtr textModel, const uint32_t lineIndex); + +/** + * @brief Get the left point of the line (x). + * + * @param[in] lineRun the requested line. + * @return x point of the line. + */ +float GetLineLeft(const LineRun& lineRun); + +/** + * @brief Get the top point of the line (y). + * if the requested line id the first; the top = 0, else the top = the heights of the previouse lines. + * + * @param[in] lines the lines in the text controller. + * @param[in] lineRun the requested line. + * @return y point of the line. + */ +float GetLineTop(const Vector& lines, const LineRun& lineRun); + } // namespace Text } // namespace Toolkit -- 2.7.4