How to fit a String inside a rectangle?

Tags: ColumnTextmeasure textiText 5

I'm trying to add some strings, images and tables into my pdf file (there have to be several pages) but when I try to use ColumnText (I use this because I want to place strings at absolute positions), I encounter a problem. When the column height is not sufficient to add the content of the strings, the content is incomplete. How can I avoid that content gets lost?

Here's the related code :

PdfContentByte cb = writer.getDirectContent();
Image imageust = Image.getInstance(imageUrl);
Image imageAlt = imageAlt = Image.getInstance(imageUrlAlt);
imageust.setAbsolutePosition(0f,
    document.getPageSize().getHeight() - imageust.getHeight()-10);
imageAlt.setAbsolutePosition(0f, 10f);
document.add(imageust);
document.add(imageAlt);
// now draw a line below the headline
cb.setLineWidth(1f); 
cb.moveTo(0, 200);
cb.lineTo(200, 200);
cb.stroke();
// first define a standard font for our text
Font helvetica8BoldBlue = FontFactory.getFont(FontFactory.HELVETICA,16);
// create a column object
ColumnText ct = new ColumnText(cb);
// define the text to print in the column
Phrase myText = new Phrase("Very Very Long String!!!" , helvetica8BoldBlue);
ct.setSimpleColumn(myText, 60, 750,
    /* width*/document.getPageSize().getWidth() - 40, 100,
    20, Element.ALIGN_LEFT);
ct.go();
Posted on StackOverflow on Nov 23, 2012 by Adnan Bal

There are three options:

  1. Either you provide a bigger rectangle, so that the content fits inside,
  2. or you reduce the content (e.g. smaller font, less text),...
  3. or you keep the size of the rectangle, keep the font size, etc... but add the content that doesn't fit on the next page.

How do you know if the content doesn't fit?

You can add the content in simulation mode first, and test if all the content was 'consumed':

int status = ct.go(true);
boolean fits = !ColumnText.hasMoreText(status);

Based on the value of fits, you can decide to change the size of the rectangle or the content.

If you can distribute the content over different pages, you don't need simulation mode, you just need to insert a document.newPage();

ColumnText ct = new ColumnText(cb);
ct.setSimpleColumn(rect);
int status = ct.go();
while (ColumnText.hasMoreText(status)) {
    document.newPage();
    ct.setSimpleColumn(rect);
    status = ct.go();
}

In this example rect contains the coordinates of the rectangle.