java iText ColumnText设置矩形中的文本大小
我想将文本添加到一个矩形中(x,y,w,h)。文本应该适合矩形的大小(意味着它有一个最大大小,但它仍然包含在矩形中)
我试图根据BaseFont.getWidthPoint()
来测量文本大小。问题是最终的文本大小不能适应矩形。看起来是这样的:
以下是我的尝试:
PdfContentByte cb = writer.getDirectContent();
cb.saveState();
ColumnText ct = new ColumnText(writer.getDirectContent());
Font font = new Font(BaseFont.createFont());
int rectWidth = 80;
float maxFontSize = getMaxFontSize(BaseFont.createFont(), "text", rectWidth );
font.setSize(maxFontSize);
ct.setText(new Phrase("test", font));
ct.setSimpleColumn(10, 10, rectWidth , 70);
ct.go();
// draw the rect
cb.setColorStroke(BaseColor.BLUE);
cb.rectangle(10, 10, rectWidth , 70);
cb.stroke();
cb.restoreState();
// get max font size base on rect width
private static float getMaxFontSize(BaseFont bf, String text, int width){
float measureWidth = 1;
float fontSize = 0.1f;
float oldSize = 0.1f;
while(measureWidth < width){
measureWidth = bf.getWidthPoint(text, fontSize);
oldSize = fontSize;
fontSize += 0.1f;
}
return oldSize;
}
你能告诉我哪里错了吗
另一个问题,我想测量宽度和高度,文本完全包含在矩形中,并且具有最大字体大小。有没有办法做到这一点
更新:以下是适用于我的完整源代码:
private static float getMaxFontSize(BaseFont bf, String text, int width, int height){
// avoid infinite loop when text is empty
if(TextUtils.isEmpty(text)){
return 0.0f;
}
float fontSize = 0.1f;
while(bf.getWidthPoint(text, fontSize) < width){
fontSize += 0.1f;
}
float maxHeight = measureHeight(bf, text, fontSize);
while(maxHeight > height){
fontSize -= 0.1f;
maxHeight = measureHeight(bf, text, fontSize);
};
return fontSize;
}
public static float measureHeight(BaseFont baseFont, String text, float fontSize)
{
float ascend = baseFont.getAscentPoint(text, fontSize);
float descend = baseFont.getDescentPoint(text, fontSize);
return ascend - descend;
}
# 1 楼答案
我花了相当长的时间来实现这样的功能,使用二进制搜索方法来查找适合矩形的字体大小。今天我在iText中偶然发现了一个有趣的方法
这是iText{}中的一种新方法
在我的iText版本中,它是静态的。 请参阅详细信息:http://developers.itextpdf.com/reference/com.itextpdf.text.pdf.ColumnText
# 2 楼答案
这里有两个bug,都在
measureWidth >= width
-换句话说,当您退出while
循环时,measureWidth
对于矩形来说已经太大了李>fontSize++
,这意味着在你用fontSize
来计算measureWidth
之后,你在增加它。当您确实抽出时间返回它时,它比您刚才测试的值多出一个。因此,该方法的返回值将比您测试的最后一个值(由于第1点,该值已经太大)多一个李># 3 楼答案
主要问题
主要问题是在
ct.setSimpleColumn
中使用了错误的参数:与后面的
cb.rectangle
调用不同方法{}有参数{}({}和{}是宽度和高度)方法{}有参数{}(ll是左下和ur是右上)。因此,您的
ct.setSimpleColumn
应该如下所示:枝节问题
除主要问题外,您的结果字体大小过大0.1;本质上,这是@David已经指出的一个错误
getMaxFontSize
方法中的主循环如下:这基本上会导致
oldSize
(最终返回)成为第一个不适合的字体大小。您可以通过使用更好的方法是只计算字符串宽度一次,而不使用循环,例如
(此方法使用整数算术。如果坚持精确拟合,请切换到浮点或双精度算术。)