Package icyllis.modernui.text

# Class PrecomputedText

java.lang.Object
icyllis.modernui.text.PrecomputedText

All Implemented Interfaces:
  `Spannable`, `Spanned`, `CharSequence`

public class PrecomputedText extends Object implements Spannable
A text which has the character metrics data.

A text object that contains the character metrics data and can be used to improve the performance of text layout operations. When a PrecomputedText is created with a given `CharSequence`, it will measure the text metrics during the creation. This PrecomputedText instance can be set on `TextView` or `StaticLayout`. Since the text layout information will be included in this instance, `TextView` or `StaticLayout` will not have to recalculate this information.

Note that the `PrecomputedText` created from different parameters of the target `TextView` will be rejected internally and compute the text layout again with the current `TextView` parameters.

     An example usage is:

      static void asyncSetText(TextView textView, final String longString, Executor bgExecutor) {
          // construct precompute related parameters using the TextView that we will set the text on.
          final PrecomputedText.Params params = textView.getTextMetricsParams();
          final Reference textViewRef = new WeakReference<>(textView);
          bgExecutor.submit(() -> {
              TextView textView = textViewRef.get();
              if (textView == null) return;
              final PrecomputedText precomputedText = PrecomputedText.create(longString, params);
              textView.post(() -> {
                  TextView textView = textViewRef.get();
                  if (textView == null) return;
                  textView.setText(precomputedText);
              });
          });
      }

Note that the `PrecomputedText` created from different parameters of the target `TextView` will be rejected.

Note that any `NoCopySpan` attached to the original text won't be passed to PrecomputedText.

- ## Nested Class Summary

  Nested Classes
  Modifier and Type
  Class
  Description
  `static class`
  `PrecomputedText.ParagraphInfo`
  `static final class`
  `PrecomputedText.Params`
  The information required for building `PrecomputedText`.

  ## Nested classes/interfaces inherited from interface icyllis.modernui.text.Spannable

  `Spannable.Factory`

- ## Field Summary

  ### Fields inherited from interface icyllis.modernui.text.Spannable

  `DEFAULT_FACTORY`

  ### Fields inherited from interface icyllis.modernui.text.Spanned

  `SPAN_COMPOSING, SPAN_EXCLUSIVE_EXCLUSIVE, SPAN_EXCLUSIVE_INCLUSIVE, SPAN_INCLUSIVE_EXCLUSIVE, SPAN_INCLUSIVE_INCLUSIVE, SPAN_INTERMEDIATE, SPAN_MARK_MARK, SPAN_MARK_POINT, SPAN_PARAGRAPH, SPAN_POINT_MARK, SPAN_POINT_MARK_MASK, SPAN_POINT_POINT, SPAN_PRIORITY, SPAN_PRIORITY_SHIFT, SPAN_USER, SPAN_USER_SHIFT`

- ## Method Summary

  Modifier and Type
  Method
  Description
  `char`
  `charAt(int index)`
  `int`
  `checkResultUsable(int start, int end, TextDirectionHeuristic textDir, TextPaint paint, LineBreakConfig lbConfig)`
  Returns value if the given TextPaint gives the same result of text layout for this text.
  `static PrecomputedText`
  `create(CharSequence text, PrecomputedText.Params params)`
  Create a new `PrecomputedText` which will pre-compute text measurement and glyph positioning information.
  `static PrecomputedText.ParagraphInfo[]`
  `createMeasuredParagraphs(CharSequence text, PrecomputedText.Params params, int start, int end, boolean computeLayout)`
  `int`
  `findParaIndex(int pos)`
  `int`
  `getEnd()`
  Returns the exclusive end offset of measured region.
  `void`
  `getFontMetricsInt(int start, int end, FontMetricsInt outMetrics)`
  Retrieves the text font metrics for the given range.
  `MeasuredParagraph`
  `getMeasuredParagraph(int paraIndex)`
  `int`
  `getMemoryUsage()`
  Returns the size of PrecomputedText memory usage.
  `int`
  `getParagraphCount()`
  Returns the count of paragraphs.
  `int`
  `getParagraphEnd(int paraIndex)`
  Returns the paragraph end offset of the text.
  `PrecomputedText.ParagraphInfo[]`
  `getParagraphInfo()`
  `int`
  `getParagraphStart(int paraIndex)`
  Returns the paragraph start offset of the text.
  `PrecomputedText.Params`
  `getParams()`
  Returns the layout parameters used to measure this text.
  `int`
  `getSpanEnd(Object tag)`
  Return the end of the range of text to which the specified markup object is attached, or `-1` if the object is not attached.
  `int`
  `getSpanFlags(Object tag)`
  Return the flags that were specified when `Spannable.setSpan(java.lang.Object, int, int, int)` was used to attach the specified markup object, or `0` if the specified object has not been attached.
  `<T> List<T>`
  `getSpans(int start, int end, Class<? extends T> type, List<T> dest)`
  Query a set of the markup objects attached to the specified slice of this `CharSequence` and whose type is the specified type or a subclass of it.
  `int`
  `getSpanStart(Object tag)`
  Return the beginning of the range of text to which the specified markup object is attached, or `-1` if the object is not attached.
  `int`
  `getStart()`
  Returns the inclusive start offset of measured region.
  `CharSequence`
  `getText()`
  Return the underlying text.
  `float`
  `getWidth(int start, int end)`
  Returns text width for the given range.
  `int`
  `length()`
  `int`
  `nextSpanTransition(int start, int limit, Class<?> type)`
  Return the first offset greater than `start` where a markup object of class `type` begins or ends, or `limit` if there are no starts or ends greater than `start` but less than `limit`.
  `void`
  `removeSpan(Object what)`
  Remove the specified object from the range of text to which it was attached, if any.
  `void`
  `setSpan(Object what, int start, int end, int flags)`
  Attach the specified markup object to the range `start…end` of the text, or move the object to that range if it was already attached elsewhere.
  `CharSequence`
  `subSequence(int start, int end)`
  `String`
  `toString()`

  ### Methods inherited from class java.lang.Object

  `clone, equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait`

  ### Methods inherited from interface java.lang.CharSequence

  `chars, codePoints, isEmpty`

  ### Methods inherited from interface icyllis.modernui.text.Spannable

  `removeSpan`

  ### Methods inherited from interface icyllis.modernui.text.Spanned

  `getSpans`

- ## Method Details

  - ### create

    public static PrecomputedText create(@NonNull CharSequence text, @NonNull PrecomputedText.Params params)
    Create a new `PrecomputedText` which will pre-compute text measurement and glyph positioning information.

    This can be expensive, so computing this on a background thread before your text will be presented can save work on the UI thread.

    Note that any `NoCopySpan` attached to the text won't be passed to the created PrecomputedText.

    Parameters:
      `text` - the text to be measured
      `params` - parameters that define how text will be precomputed
    Returns:
      A `PrecomputedText`

  - ### createMeasuredParagraphs

    @Internal public static PrecomputedText.ParagraphInfo[] createMeasuredParagraphs(@NonNull CharSequence text, @NonNull PrecomputedText.Params params, @IntRange(from=0L) int start, @IntRange(from=0L) int end, boolean computeLayout)

  - ### getText

    @Internal @NonNull public CharSequence getText()
    Return the underlying text.

  - ### getStart

    @Internal @IntRange(from=0L) public int getStart()
    Returns the inclusive start offset of measured region.

  - ### getEnd

    @Internal @IntRange(from=0L) public int getEnd()
    Returns the exclusive end offset of measured region.

  - ### getParams

    @NonNull public PrecomputedText.Params getParams()
    Returns the layout parameters used to measure this text.

  - ### getParagraphCount

    @IntRange(from=0L) public int getParagraphCount()
    Returns the count of paragraphs.

  - ### getParagraphStart

    @IntRange(from=0L) public int getParagraphStart(@IntRange(from=0L) int paraIndex)
    Returns the paragraph start offset of the text.

  - ### getParagraphEnd

    @IntRange(from=0L) public int getParagraphEnd(@IntRange(from=0L) int paraIndex)
    Returns the paragraph end offset of the text.

  - ### getMeasuredParagraph

    @Internal @NonNull public MeasuredParagraph getMeasuredParagraph(@IntRange(from=0L) int paraIndex)

  - ### getParagraphInfo

    @Internal @NonNull public PrecomputedText.ParagraphInfo[] getParagraphInfo()

  - ### checkResultUsable

    @Internal public int checkResultUsable(@IntRange(from=0L) int start, @IntRange(from=0L) int end, @NonNull TextDirectionHeuristic textDir, @NonNull TextPaint paint, @NonNull LineBreakConfig lbConfig)
    Returns value if the given TextPaint gives the same result of text layout for this text.

  - ### findParaIndex

    @Internal public int findParaIndex(@IntRange(from=0L) int pos)

  - ### getWidth

    @FloatRange(from=0.0) public float getWidth(@IntRange(from=0L) int start, @IntRange(from=0L) int end)
    Returns text width for the given range. Both `start` and `end` offset need to be in the same paragraph, otherwise IllegalArgumentException will be thrown.
    Parameters:
      `start` - the inclusive start offset in the text
      `end` - the exclusive end offset in the text
    Returns:
      the text width
    Throws:
      `IllegalArgumentException` - if start and end offset are in the different paragraph.

  - ### getFontMetricsInt

    public void getFontMetricsInt(@IntRange(from=0L) int start, @IntRange(from=0L) int end, @NonNull FontMetricsInt outMetrics)
    Retrieves the text font metrics for the given range. Both `start` and `end` offset need to be in the same paragraph, otherwise IllegalArgumentException will be thrown.
    Parameters:
      `start` - the inclusive start offset in the text
      `end` - the exclusive end offset in the text
      `outMetrics` - the output font metrics
    Throws:
      `IllegalArgumentException` - if start and end offset are in the different paragraph.

  - ### getMemoryUsage

    @Internal public int getMemoryUsage()
    Returns the size of PrecomputedText memory usage.

    Note that this is not guaranteed to be accurate. Must be used only for testing purposes.

  - ### setSpan

    public void setSpan(@NonNull Object what, int start, int end, int flags)
    Description copied from interface: `Spannable`
    Attach the specified markup object to the range `start…end` of the text, or move the object to that range if it was already attached elsewhere. See `Spanned` for an explanation of what the flags mean. The object can be one that has meaning only within your application, or it can be one that the text system will use to affect text display or behavior. Some noteworthy ones are the subclasses of `CharacterStyle` and `ParagraphStyle`, and `TextWatcher` and `SpanWatcher`.
    Specified by:
      `setSpan` in interface `Spannable`
    Parameters:
      `what` - the markup object
      `start` - the start char index of the span
      `end` - the end char index of the span
      `flags` - the flags of the span
    Throws:
      `IllegalArgumentException` - if `MetricAffectingSpan` is specified.

  - ### removeSpan

    public void removeSpan(@NonNull Object what)
    Description copied from interface: `Spannable`
    Remove the specified object from the range of text to which it was attached, if any.
    It is OK to remove an object that was never attached in the first place.
    Specified by:
      `removeSpan` in interface `Spannable`
    Parameters:
      `what` - markup object to remove
    Throws:
      `IllegalArgumentException` - if `MetricAffectingSpan` is specified.

  - ### getSpans

    @NonNull public <T> List<T> getSpans(int start, int end, @Nullable Class<? extends T> type, @Nullable List<T> dest)
    Description copied from interface: `Spanned`
    Query a set of the markup objects attached to the specified slice of this `CharSequence` and whose type is the specified type or a subclass of it.
    Specify `null` or `Object.class` for the type if you want all the objects regardless of type.

    If `dest` list is non-null, it will be filled with the method results and returned as-is. Otherwise, a new (and possibly- unmodifiable) list will be created with method results and returned. The return list can be empty if there is no match.

    Specified by:
      `getSpans` in interface `Spanned`
    Parameters:
      `start` - start char index of the slice
      `end` - end char index of the slice
      `type` - markup class
      `dest` - the list that receives method results
    Returns:
      the list of results

  - ### getSpanStart

    public int getSpanStart(@NonNull Object tag)
    Description copied from interface: `Spanned`
    Return the beginning of the range of text to which the specified markup object is attached, or `-1` if the object is not attached.
    Specified by:
      `getSpanStart` in interface `Spanned`
    Parameters:
      `tag` - markup object
    Returns:
      the start char index

  - ### getSpanEnd

    public int getSpanEnd(@NonNull Object tag)
    Description copied from interface: `Spanned`
    Return the end of the range of text to which the specified markup object is attached, or `-1` if the object is not attached.
    Specified by:
      `getSpanEnd` in interface `Spanned`
    Parameters:
      `tag` - markup object
    Returns:
      the end char index

  - ### getSpanFlags

    public int getSpanFlags(@NonNull Object tag)
    Description copied from interface: `Spanned`
    Return the flags that were specified when `Spannable.setSpan(java.lang.Object, int, int, int)` was used to attach the specified markup object, or `0` if the specified object has not been attached.
    Specified by:
      `getSpanFlags` in interface `Spanned`
    Parameters:
      `tag` - markup object
    Returns:
      the flags

  - ### nextSpanTransition

    public int nextSpanTransition(int start, int limit, @Nullable Class<?> type)
    Description copied from interface: `Spanned`
    Return the first offset greater than `start` where a markup object of class `type` begins or ends, or `limit` if there are no starts or ends greater than `start` but less than `limit`. Specify `null` or `Object.class` for the type if you want every transition regardless of type.
    Specified by:
      `nextSpanTransition` in interface `Spanned`
    Parameters:
      `start` - start char index of the slice
      `limit` - end char index of the slice
      `type` - the markup type
    Returns:
      transition point

  - ### length

    public int length()
    Specified by:
      `length` in interface `CharSequence`

  - ### charAt

    public char charAt(int index)
    Specified by:
      `charAt` in interface `CharSequence`

  - ### subSequence

    public CharSequence subSequence(int start, int end)
    Specified by:
      `subSequence` in interface `CharSequence`

  - ### toString

    public String toString()
    Specified by:
      `toString` in interface `CharSequence`
    Overrides:
      `toString` in class `Object`