Example usage for android.widget TextView getMaxWidth

List of usage examples for android.widget TextView getMaxWidth

Introduction

In this page you can find the example usage for android.widget TextView getMaxWidth.

Prototype

public int getMaxWidth() 

Source Link

Document

Returns the maximum width of TextView in terms of pixels or -1 if the maximum width was set using #setMaxEms(int) or #setEms(int) .

Usage

From source file:cn.dreamtobe.emoji.ellipsize.helper.SpanEllipsizeEndHelper.java

@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
private static String getMaxWidthKey(CharSequence targetText, TextView textView) {
    String key = String.format("%s@%d@%d", targetText, textView.getMaxWidth(), (int) textView.getTextSize());
    if (targetText instanceof SpannableString) {
        Object[] spans = ((SpannableString) targetText).getSpans(0, targetText.length(), Object.class);
        for (Object span : spans) {
            key += ((SpannableString) targetText).getSpanStart(span);
            key += ((SpannableString) targetText).getSpanEnd(span);
        }//from   w  ww.ja v  a2  s.  co  m
    }

    return key;
}

From source file:cn.dreamtobe.emoji.ellipsize.helper.SpanEllipsizeEndHelper.java

@TargetApi(Build.VERSION_CODES.JELLY_BEAN)
public static CharSequence matchMaxWidth(SpannableString targetText, TextView textView) {
    if (targetText.length() <= 0) {
        return targetText;
    }/*  ww  w. j  av a 2 s  .co m*/

    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
        return targetText;
    }

    if (textView == null) {
        return targetText;
    }

    final int maxWidth = textView.getMaxWidth();

    if (maxWidth <= 0 || maxWidth >= Integer.MAX_VALUE) {
        return targetText;
    }

    if (textView.getEllipsize() != TextUtils.TruncateAt.END) {
        return targetText;
    }

    //TODO Multi-lines support
    if (textView.getMaxLines() != 1) {
        return targetText;
    }

    final String maxWidthKey = getMaxWidthKey(targetText, textView);
    SpannableString tmpText = SPAN_MAXWIDTH_CACHE.get(maxWidthKey);
    if (tmpText != null) {
        removeClickableSpan(tmpText);
        return tmpText;
    }

    TextPaint textPaint = textView.getPaint();
    if (textPaint == null) {
        return targetText;
    }

    final int totalWidth = (int) textPaint.measureText(targetText, 0, targetText.length());
    if (totalWidth <= maxWidth) {
        return targetText;
    }

    final long startTime = System.currentTimeMillis();
    // deal maxwitdh

    final int dotWidth = (int) textPaint.measureText("...");

    tmpText = targetText;

    int start = 0;
    int end = targetText.length();

    // targetX is maxWidth - "...".length
    int targetX = maxWidth - dotWidth;

    //dichotomy: get x most touch targetX
    int middle = targetText.length();
    int x = 0;
    while (start <= end) {
        // tx = targetX, tl = targetLength

        // width:  0           x
        // length: 0         middle           end
        //         -------------|-------------
        middle = (start + end) / 2;

        int emojiDraW = 0;
        int emojiStrW = 0;

        int emojiExcursion = 1;

        final Object[] tmpSpans = tmpText.getSpans(0, middle, Object.class);
        if (tmpSpans != null) {
            for (Object tmpSpan : tmpSpans) {
                final int tmpStart = tmpText.getSpanStart(tmpSpan);
                final int tmpEnd = tmpText.getSpanEnd(tmpSpan);

                //middle in (tmpStart, tmpEnd)
                if (tmpStart < middle && tmpEnd > middle) {
                    middle = tmpEnd;
                    emojiExcursion = tmpEnd - tmpStart;
                }
            }

            // TextPaint#measure do not attention span, so adjust by ourselves
            for (Object tmpSpan : tmpSpans) {
                final int tmpStart = tmpText.getSpanStart(tmpSpan);
                final int tmpEnd = tmpText.getSpanEnd(tmpSpan);

                // TODO support other span
                if (tmpStart < middle && tmpSpan instanceof ImageSpan) {
                    emojiDraW += ((ImageSpan) tmpSpan).getDrawable().getBounds().width();
                    emojiStrW += textPaint.measureText(tmpText, tmpStart, tmpEnd);
                }
            }

        }

        x = (int) textPaint.measureText(tmpText, 0, middle);
        x = x - emojiStrW + emojiDraW;

        //            x = (int) (textPaint.measureText(pureStr, 0, pureStr.length()) + emojiWidth);

        //            Log.d(TAG, String.format("targetX: %d, currentX: %d, currentLength: %d, totalLength: %d, emojiStrW[%d], emojiDraW[%d]", targetX, x, middle, targetText.length(), emojiStrW, emojiDraW));

        if (x > targetX) {
            // width:  0       tx        x
            // length: start   tl      middle         end
            //             ----|---------|-------------
            // TO:     start   |       *end
            //             ----|--------|--------------
            end = middle - emojiExcursion;
        } else if (x < targetX) {
            // width:  0               x       tx
            // length: start         middle    tl     end
            //           --------------|-------|------
            // TO:                      *start  |       end
            //           ---------------|------|------
            start = middle + 1;
        } else {
            break;
        }
    }

    // adjust x larger targetX
    while (x > targetX && middle > 0) {
        x = (int) textPaint.measureText(tmpText, 0, --middle);
    }

    // adjust x middle emoji span
    final Object[] ajustSpans = tmpText.getSpans(0, tmpText.length(), Object.class);
    for (Object adjustSpan : ajustSpans) {
        final int adjustStart = tmpText.getSpanStart(adjustSpan);
        final int adjustEnd = tmpText.getSpanEnd(adjustSpan);

        //[adjustStart, adjustEnd)
        if (middle >= adjustStart && middle < adjustEnd) {
            middle = adjustStart - 1;
            break;
        }
    }

    // finnal middle

    // sub sequence [0, middle + 1) & remove [middle +1, length] spans
    tmpText = (SpannableString) tmpText.subSequence(0, middle + 1);
    //        Log.d(TAG, String.format("sub Sequence[0, %d), [%s] to [%s]", middle + 1, targetText, tmpText));

    // add ...
    final SpannableString maxWidthSS = new SpannableString(tmpText + "...");

    final Object[] maxWidthSpans = tmpText.getSpans(0, tmpText.length(), Object.class);
    if (maxWidthSpans != null) {
        for (Object maxWidthSpan : maxWidthSpans) {
            final int mwSpanStart = tmpText.getSpanStart(maxWidthSpan);
            final int mwSpanEnd = tmpText.getSpanEnd(maxWidthSpan);
            final int mwSpanFlag = tmpText.getSpanFlags(maxWidth);

            maxWidthSS.setSpan(maxWidthSpan, mwSpanStart, mwSpanEnd, mwSpanFlag);
        }
    }

    targetText = maxWidthSS;

    SPAN_MAXWIDTH_CACHE.put(maxWidthKey, targetText);
    Log.d(TAG, String.format("deal maxWidth %d", System.currentTimeMillis() - startTime));

    return targetText;
}