如何在Android上获得字符串宽度?

时间:2010-09-02 18:35:47

标签: android string bounding-box

如果可能,我也希望得到身高。

7 个答案:

答案 0 :(得分:188)

您可以使用Paint对象的getTextBounds(String text, int start, int end, Rect bounds)方法。您可以使用TextView提供的绘图对象,也可以使用所需的文本外观自行构建。

使用Textview,您可以执行以下操作:

Rect bounds = new Rect();
Paint textPaint = textView.getPaint();
textPaint.getTextBounds(text, 0, text.length(), bounds);
int height = bounds.height();
int width = bounds.width();

答案 1 :(得分:68)

如果您只需要宽度,可以使用:

float width = paint.measureText(string);

http://developer.android.com/reference/android/graphics/Paint.html#measureText(java.lang.String)

答案 2 :(得分:17)

文本有两种不同的宽度度量。一个是宽度绘制的像素数,另一个是绘制文本后光标应该提前的“像素数”。

paint.measureText paint.getTextWidths 返回绘制给定字符串后光标应该前进的像素数(浮点数)。对于绘制的像素数,请使用paint.getTextBounds,如其他答案中所述。我相信这被称为字体的'Advance'。

对于某些字体,这两个测量值不同(很多),例如字体Black Chancery的字母超过其他字母(重叠) - 请参阅大写字母“L”。使用其他答案中提到的 paint.getTextBounds 来绘制像素。

答案 3 :(得分:5)

我用这种方式测量了宽度:

String str ="Hiren Patel";

Paint paint = new Paint();
paint.setTextSize(20);
Typeface typeface = Typeface.createFromAsset(getAssets(), "Helvetica.ttf");
paint.setTypeface(typeface);
paint.setColor(Color.BLACK);
paint.setStyle(Paint.Style.FILL);
Rect result = new Rect();
paint.getTextBounds(str, 0, str.length(), result);

Log.i("Text dimensions", "Width: "+result.width());

这会对你有帮助。

答案 4 :(得分:1)

您很可能想知道具有给定字体(例如,特定的Typeface,例如具有BOLD_ITALIC样式的“ sans-serif”字体家族,以及sp或px)。

您可以不使用较高级别的TextView,而是直接使用Paint对象处理单行文本,例如:

// Maybe you want to construct a (possibly static) member for repeated computations
Paint paint = new Paint();

// You can load a font family from an asset, and then pick a specific style:
//Typeface plain = Typeface.createFromAsset(assetManager, pathToFont); 
//Typeface bold = Typeface.create(plain, Typeface.DEFAULT_BOLD);
// Or just reference a system font:
paint.setTypeface(Typeface.create("sans-serif",Typeface.BOLD));

// Don't forget to specify your target font size. You can load from a resource:
//float scaledSizeInPixels = context.getResources().getDimensionPixelSize(R.dimen.mediumFontSize);
// Or just compute it fully in code:
int spSize = 18;
float scaledSizeInPixels = TypedValue.applyDimension(
            TypedValue.COMPLEX_UNIT_SP,
            spSize,
            context.getResources().getDisplayMetrics());
paint.setTextSize(scaledSizeInPixels);

// Now compute!
Rect bounds = new Rect();
String myString = "Some string to measure";
paint.getTextBounds(myString, 0, myString.length(), bounds);
Log.d(TAG, "width: " + bounds.width() + " height: " + bounds.height());

对于多行或跨行文本SpannedString),请考虑使用StaticLayout,在其中提供宽度并导出高度。有关在自定义视图中将文字测量并绘制到画布上的非常详尽的答案,请参见:https://stackoverflow.com/a/41779935/954643

同样值得一提的是,@ arberg在下面关于绘制的像素与前进宽度(“绘制给定字符串后光标应前进的像素数(浮点数)”)的回复,以防您需要处理。

答案 5 :(得分:0)

我想分享一种更好的方法(比当前接受的答案更具通用性) ,该方法使用静态类来获取绘制文本(String)的确切宽度StaticLayout

StaticLayout.getDesiredWidth(text, textPaint))

此方法比textView.getTextBounds()更准确,因为您可以计算多行TextView中单行的宽度,否则您可能不会使用TextView作为开头(例如自定义View实现。

这种方式类似于textPaint.measureText(text),但是在极少数情况下,它似乎更准确。

答案 6 :(得分:0)

simplay 我在行中添加最大字符并以最大空间挑战它并创建新行

    v_y = v_y + 30;
    String tx = "مبلغ وقدرة : "+ AmountChar+" لا غير";

    myPaint.setTextAlign(Paint.Align.RIGHT);

    int pxx = 400;
    int pxy = v_y ;
    int word_no = 1;
    int word_lng = 0;
    int max_word_lng = 45;
    int new_line = 0;
    int txt_lng = tx.length();
    int words_lng =0;
    String word_in_line = "" ;
    for (String line : tx.split(" "))
    {
        word_lng = line.length() ;
        words_lng += line.length() + 1;

        if (word_no == 1 )
        {word_in_line = line;
        word_no += 1;
        }
        else
            { word_in_line += " " + line;
            word_no += 1;
            }

        if (word_in_line.length() >= max_word_lng)
       {
           canvas.drawText(word_in_line, pxx, pxy, myPaint);
            new_line += 1;
            pxy = pxy + 30;
            word_no = 1;
            word_in_line = "";
        }
        if (txt_lng <= words_lng )
        { canvas.drawText(word_in_line, pxx, pxy, myPaint); }
    }

    v_y = pxy;