/*
- * Copyright (c) 2021 Samsung Electronics Co., Ltd.
+ * Copyright (c) 2023 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.
#include <dali-toolkit/internal/text/rendering/view-model.h>
// EXTERNAL INCLUDES
-#include <dali/devel-api/text-abstraction/font-client.h>
#include <memory.h>
// INTERNAL INCLUDES
+#include <dali-toolkit/internal/text/glyph-metrics-helper.h>
#include <dali-toolkit/internal/text/line-run.h>
namespace Dali
return mModel->GetNumberOfLines();
}
-const LineRun* const ViewModel::GetLines() const
+const LineRun* ViewModel::GetLines() const
{
return mModel->GetLines();
}
return mModel->GetNumberOfScripts();
}
-const ScriptRun* const ViewModel::GetScriptRuns() const
+const ScriptRun* ViewModel::GetScriptRuns() const
{
return mModel->GetScriptRuns();
}
+Length ViewModel::GetNumberOfCharacters() const
+{
+ return mModel->GetNumberOfCharacters();
+}
+
Length ViewModel::GetNumberOfGlyphs() const
{
if(mIsTextElided && mModel->IsTextElideEnabled())
return mModel->GetSecondMiddleIndexOfElidedGlyphs();
}
-const GlyphInfo* const ViewModel::GetGlyphs() const
+const GlyphInfo* ViewModel::GetGlyphs() const
{
if(mIsTextElided && mModel->IsTextElideEnabled())
{
return NULL;
}
-const Vector2* const ViewModel::GetLayout() const
+const Vector2* ViewModel::GetLayout() const
{
if(mIsTextElided && mModel->IsTextElideEnabled())
{
return NULL;
}
-const Vector4* const ViewModel::GetColors() const
+const Vector4* ViewModel::GetColors() const
{
return mModel->GetColors();
}
-const ColorIndex* const ViewModel::GetColorIndices() const
+const ColorIndex* ViewModel::GetColorIndices() const
{
return mModel->GetColorIndices();
}
-const Vector4* const ViewModel::GetBackgroundColors() const
+const Vector4* ViewModel::GetBackgroundColors() const
{
return mModel->GetBackgroundColors();
}
-const ColorIndex* const ViewModel::GetBackgroundColorIndices() const
+const ColorIndex* ViewModel::GetBackgroundColorIndices() const
{
return mModel->GetBackgroundColorIndices();
}
-bool const ViewModel::IsMarkupBackgroundColorSet() const
+bool ViewModel::IsMarkupBackgroundColorSet() const
{
return mModel->IsMarkupBackgroundColorSet();
}
return mModel->IsUnderlineEnabled();
}
+bool ViewModel::IsMarkupUnderlineSet() const
+{
+ return mModel->IsMarkupUnderlineSet();
+}
+
float ViewModel::GetUnderlineHeight() const
{
return mModel->GetUnderlineHeight();
}
+Text::Underline::Type ViewModel::GetUnderlineType() const
+{
+ return mModel->GetUnderlineType();
+}
+
+float ViewModel::GetDashedUnderlineWidth() const
+{
+ return mModel->GetDashedUnderlineWidth();
+}
+
+float ViewModel::GetDashedUnderlineGap() const
+{
+ return mModel->GetDashedUnderlineGap();
+}
+
Length ViewModel::GetNumberOfUnderlineRuns() const
{
return mModel->GetNumberOfUnderlineRuns();
}
-void ViewModel::GetUnderlineRuns(GlyphRun* underlineRuns, UnderlineRunIndex index, Length numberOfRuns) const
+void ViewModel::GetUnderlineRuns(UnderlinedGlyphRun* underlineRuns, UnderlineRunIndex index, Length numberOfRuns) const
{
mModel->GetUnderlineRuns(underlineRuns, index, numberOfRuns);
}
+const Vector2& ViewModel::GetOutlineOffset() const
+{
+ return mModel->GetOutlineOffset();
+}
+
const Vector4& ViewModel::GetOutlineColor() const
{
return mModel->GetOutlineColor();
return mModel->GetOutlineWidth();
}
+const float& ViewModel::GetOutlineBlurRadius() const
+{
+ return mModel->GetOutlineBlurRadius();
+}
+
const Vector4& ViewModel::GetBackgroundColor() const
{
return mModel->GetBackgroundColor();
return mModel->IsMarkupProcessorEnabled();
}
+bool ViewModel::IsSpannedTextPlaced() const
+{
+ return mModel->IsSpannedTextPlaced();
+}
+
const GlyphInfo* ViewModel::GetHyphens() const
{
return mModel->GetHyphens();
return mModel->GetHyphensCount();
}
-void ViewModel::ElideGlyphs()
+float ViewModel::GetCharacterSpacing() const
+{
+ return mModel->GetCharacterSpacing();
+}
+
+const Character* ViewModel::GetTextBuffer() const
+{
+ return mModel->GetTextBuffer();
+}
+
+const Vector<CharacterIndex>& ViewModel::GetGlyphsToCharacters() const
+{
+ return mModel->GetGlyphsToCharacters();
+}
+
+void ViewModel::ElideGlyphs(TextAbstraction::FontClient& fontClient)
{
mIsTextElided = false;
mStartIndexOfElidedGlyphs = mFirstMiddleIndexOfElidedGlyphs = mSecondMiddleIndexOfElidedGlyphs = 0;
mEndIndexOfElidedGlyphs = mModel->GetNumberOfGlyphs() - 1u;
- auto ellipsisPosition = GetEllipsisPosition();
+ auto ellipsisPosition = GetEllipsisPosition();
+ auto characterSpacing = GetCharacterSpacing();
+ const Character* textBuffer = GetTextBuffer();
+ const Vector<CharacterIndex>& glyphToCharacterMap = GetGlyphsToCharacters();
+ const CharacterIndex* glyphToCharacterMapBuffer = glyphToCharacterMap.Begin();
+ float calculatedAdvance = 0.f;
if(IsTextElideEnabled())
{
if(0u != numberOfActualLaidOutGlyphs)
{
// There are elided glyphs.
- mIsTextElided = true;
- TextAbstraction::FontClient fontClient = TextAbstraction::FontClient::Get();
+ mIsTextElided = true;
// Retrieve the whole glyphs and their positions.
const GlyphInfo* const glyphs = mModel->GetGlyphs();
firstPenSet = true;
}
- removedGlypsWidth += std::min(glyphToRemove.advance, (glyphToRemove.xBearing + glyphToRemove.width));
+ calculatedAdvance = GetCalculatedAdvance(*(textBuffer + (*(glyphToCharacterMapBuffer + indexOfEllipsis))), characterSpacing, glyphToRemove.advance);
+ removedGlypsWidth += std::min(calculatedAdvance, (glyphToRemove.xBearing + glyphToRemove.width));
// Calculate the width of the ellipsis glyph and check if it fits.
const float ellipsisGlyphWidth = ellipsisGlyph.width + ellipsisGlyph.xBearing;
// Change the 'x' and 'y' position of the ellipsis glyph.
if(position.x > firstPenX)
{
- position.x = firstPenX + removedGlypsWidth - ellipsisGlyphWidth;
+ if(isTailMode)
+ {
+ // To handle case of the mixed languages (LTR then RTL) with
+ // EllipsisPosition::END and the LayoutDirection::RIGHT_TO_LEFT
+ float nextXPositions = ellipsisLine->width;
+ if(indexOfEllipsis + 1u < numberOfGlyphs)
+ {
+ Vector2& positionOfNextGlyph = *(elidedPositionsBuffer + indexOfEllipsis + 1u);
+ nextXPositions = positionOfNextGlyph.x;
+ }
+
+ if(position.x > nextXPositions) // RTL language
+ {
+ if((indexOfEllipsis > 0u) && ((position.x - nextXPositions) > removedGlypsWidth))
+ {
+ // To handle mixed directions
+ // Re-calculates the first penX which will be used if rtl text is elided.
+ firstPenX = position.x - glyphToRemove.xBearing;
+ if(firstPenX < -ellipsisGlyph.xBearing)
+ {
+ // Avoids to exceed the bounding box when rtl text is elided.
+ firstPenX = -ellipsisGlyph.xBearing;
+ }
+ //Reset the width of removed glyphs
+ removedGlypsWidth = std::min(calculatedAdvance, (glyphToRemove.xBearing + glyphToRemove.width)) - ellipsisGlyph.xBearing;
+
+ --indexOfEllipsis;
+ continue;
+ }
+ else
+ {
+ // To handle the case of RTL language with EllipsisPosition::END
+ position.x = firstPenX + removedGlypsWidth - ellipsisGlyphWidth;
+ }
+ }
+ }
+ else
+ {
+ // To handle the case of LTR language with EllipsisPosition::START
+ position.x = firstPenX + removedGlypsWidth - ellipsisGlyphWidth;
+ }
+ }
+ else
+ {
+ if(!isTailMode)
+ {
+ // To handle case of the mixed languages (RTL then LTR) with
+ // EllipsisPosition::START and the LayoutDirection::RIGHT_TO_LEFT
+ float nextXPositions = ellipsisLine->width;
+ if(indexOfEllipsis + 1u < numberOfGlyphs)
+ {
+ Vector2& positionOfNextGlyph = *(elidedPositionsBuffer + indexOfEllipsis + 1u);
+ nextXPositions = positionOfNextGlyph.x;
+ }
+
+ if(position.x < nextXPositions) // LTR language
+ {
+ position.x = firstPenX + removedGlypsWidth - ellipsisGlyphWidth;
+
+ if((position.x + ellipsisGlyphWidth + ellipsisGlyph.xBearing) > nextXPositions)
+ {
+ position.x -= (position.x + ellipsisGlyphWidth + ellipsisGlyph.xBearing) - nextXPositions;
+ }
+ }
+ }
}
position.x += ellipsisGlyph.xBearing;
return mModel->IsStrikethroughEnabled();
}
+bool ViewModel::IsMarkupStrikethroughSet() const
+{
+ return mModel->IsMarkupStrikethroughSet();
+}
+
+Length ViewModel::GetNumberOfStrikethroughRuns() const
+{
+ return mModel->GetNumberOfStrikethroughRuns();
+}
+
+void ViewModel::GetStrikethroughRuns(StrikethroughGlyphRun* strikethroughRuns, StrikethroughRunIndex index, Length numberOfRuns) const
+{
+ mModel->GetStrikethroughRuns(strikethroughRuns, index, numberOfRuns);
+}
+
+Length ViewModel::GetNumberOfBoundedParagraphRuns() const
+{
+ return mModel->GetNumberOfBoundedParagraphRuns();
+}
+
+const Vector<BoundedParagraphRun>& ViewModel::GetBoundedParagraphRuns() const
+{
+ return mModel->GetBoundedParagraphRuns();
+}
+
+Length ViewModel::GetNumberOfCharacterSpacingGlyphRuns() const
+{
+ return mModel->GetNumberOfCharacterSpacingGlyphRuns();
+}
+
+const Vector<CharacterSpacingGlyphRun>& ViewModel::GetCharacterSpacingGlyphRuns() const
+{
+ return mModel->GetCharacterSpacingGlyphRuns();
+}
+
+const Vector<FontRun>& ViewModel::GetFontRuns() const
+{
+ return mModel->GetFontRuns();
+}
+
+const Vector<FontDescriptionRun>& ViewModel::GetFontDescriptionRuns() const
+{
+ return mModel->GetFontDescriptionRuns();
+}
+
+bool ViewModel::IsRemoveFrontInset() const
+{
+ return mModel->IsRemoveFrontInset();
+}
+
+bool ViewModel::IsRemoveBackInset() const
+{
+ return mModel->IsRemoveBackInset();
+}
+
+bool ViewModel::IsCutoutEnabled() const
+{
+ return mModel->IsCutoutEnabled();
+}
+
+const bool ViewModel::IsBackgroundWithCutoutEnabled() const
+{
+ return mModel->IsBackgroundWithCutoutEnabled();
+}
+
+const Vector4& ViewModel::GetBackgroundColorWithCutout() const
+{
+ return mModel->GetBackgroundColorWithCutout();
+}
+
+const Vector2& ViewModel::GetOffsetWithCutout() const
+{
+ return mModel->GetOffsetWithCutout();
+}
+
} // namespace Text
} // namespace Toolkit