# Tutorial: iText by Example

## Rich Text Format

UNDER CONSTRUCTION
The RTF Package:
The RTF package is an extension of the iText package and allows iText to output Rich Text files in addition to PDF files. The majority of the iText features for PDF generation are also supported by the RTF package, with a few exceptions. There are currently two classes you can use to generate RTF documents in the RTF package. The new RtfWriter2 class and the old RtfWriter class. For details please read Creating a RTF document.
Additionally the RTF package contains a few features, that are RTF specific: Extended font support, Extended header / footer support, Table of contents support, Extended cell border support and Page number element and Using a disk cache for document generation.
Go to top of the page
Creating an RTF document:
There is no difference between generating a PDF document and a RTF document with iText.

    Document document = new Document();
    RtfWriter2.getInstance(document,
    	new FileOutputStream("testRTFdocument.rtf"));
    document.open();
    document.add(new Paragraph("Hello World!"));
    document.close();

Example: java com.lowagie.examples.rtf.HelloRtf World
Generates a simple 'Hello World' RTF file: see HelloWorld.rtf
RtfWriter2 and RtfWriter. Which one to use?
Short version: If you are starting a new project using the RTF package, use the new RtfWriter2.
The new RtfWriter2 replaces the old RtfWriter. To allow for a cleaner design and structure, the new RtfWriter2 shares no code with the old version. This means that the old extensions to the RtfWriter will not work with the new version. So as not to force anybody to upgrade their programs and still to allow everybody to incorporate bug fixes, the two writers exist in parallel.
For those who are starting a new project with iText and the RTF package, this has no consequences. They should use the new RtfWriter2, because this is where future development will happen.
For those who have already got a working program, but don't use any of the old RTF specific classes, they can simply change the writer to the new RtfWriter2.
For those who are using the old RTF specific classes the following table shows which new classes to use when upgrading.

Old extensions | New extensions
com.lowagie.text.rtf.RtfFont | com.lowagie.text.rtf.style.RtfFont
com.lowgaie.text.rtf.HeaderFooter | com.lowagie.text.rtf.headerfooter.RtfHeaderFooter
com.lowagie.text.rtf.HeaderFooters | com.lowagie.text.rtf.headerfooter.RtfHeaderFooterGroup
com.lowagie.text.rtf.RtfPageNumber | com.lowagie.text.rtf.field.RtfPageNumber
com.lowagie.text.rtf.RtfTOC | com.lowagie.text.rtf.field.RtfTableOfContents
com.lowagie.text.rtf.RtfTOCEntry | com.lowagie.text.rtf.field.RtfTOCEntry
com.lowagie.text.rtf.RtfTableCell | com.lowagie.text.rtf.table.RtfCell

Some of the new extensions have to be used in a slightly different manner now, but all functionality that was present in the old extensions is also available in the new extensions.
The old RtfWriter will continue to exist in its current form until the end of 2005 when it will be deprecated. It will finally be removed at the end of 2007. The same goes for all extensions of the old RtfWriter.
Example: java com.lowagie.examples.rtf.RtfTest
The TestSuite used to test RtfWriter2 functionality: see testNew.rtf testOld.rtf
External resources for this example: pngnow.png
Go to top of the page
Unsupported iText features:

- Watermarks
- Viewer preferences
- Encryption
- Embedded fonts
- Lists with non-bullet symbols
- Nested tables
- Images other than JPEG, PNG, BMP and WMF
- Rotated images
- Table.setSpaceInsideCell and Table.setSpaceBetweenCells
- Table.padding

Go to top of the page
Extended font support:
The base RTF package does not support embedding fonts (see unsupported iText features). To allow the RTF package to produce RTF documents with more than the built in fonts, the RtfFont class provides the facility to specify arbitrary fonts.

    RtfFont rtfFont = new RtfFont("Comic Sans MS");
    Paragraph para = new Paragraph("This is a paragraph in Comic Sans MS", rtfFont);
    document.add(para);

For this to work, the correct font must be installed on the machine that is used to view the RTF document, not on the machine that creates the document. Also the given font name must match the name of the font on the viewer machine exactely.
Example: java com.lowagie.examples.rtf.RtfSpecialFont
Special fonts: see specialfont.rtf
Go to top of the page
Additional font styles:
The RtfFont provides additional font styles that only work with the RtfWriter2. To use these simply specify the desired style when constructing the RtfFont.

    RtfFont doubleStrikethroughFont = new RtfFont("Times New Roman", 12, RtfFont.STYLE_DOUBLE_STRIKETHROUGH);
    para = new Paragraph("This paragraph uses the double strikethrough style", doubleStrikethroughFont);
    document.add(para);

    RtfFont hiddenFont = new RtfFont("Times New Roman", 12, RtfFont.STYLE_HIDDEN);
    para = new Paragraph("This paragraph uses the hidden style", hiddenFont);
    document.add(para);

The supported styles are:

- STYLE_DOUBLE_STRIKETHROUGH: for a double strikethrough line.
- STYLE_SHADOW: for text with a shadow.
- STYLE_OUTLINE: for outlined text.
- STYLE_EMBOSSED: for embossed text.
- STYLE_ENGRAVED: for engraved text.
- STYLE_HIDDEN: for text that is initially hidden from user view.

Example: java com.lowagie.examples.rtf.RtfSpecialFont
Special fonts: see specialfont.rtf
Go to top of the page
Extended header / footer support:
One of the limitations of the RTF format is that only one header and footer is allowed per section. There are two ways to overcome this limitation. It is possible to

- use multiple Chapters. Every Chapter can have different headers and footers.
- use the RtfHeaderFooterGroup to have up to 3 different headers or footers per document or Chapter.

Using multiple Chapters
The first solution is very simple. Before adding the Chapter to the document, you set the headers and footers that you want to have in that Chapter.

    HeaderFooter header1 = new HeaderFooter("This is the first chapter", false);
    HeaderFooter header2 = new HeaderFooter("This is page", ".");
    Chapter chapter1 = new Chapter(new Paragraph("This is the first Chapter"), 1);
    Chapter chapter2 = new Chapter(new Paragraph("Chapter 2"), 2);
    document.setHeader(header1);
    document.add(chapter1);
    document.setHeader(header2);
    document.add(chapter2);

Using the RtfHeaderFooterGroup
The second solution is to use the RtfHeaderFooterGroup. This is slightly more complex. You will have to create a RtfHeaderFooterGroup object and then add the HeaderFooter objects to the RtfHeaderFooterGroup specifying on which pages the headers / footers should appear. The following positions are supported:

- com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_FIRST_PAGE
- com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_ALL_PAGES
- com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_LEFT_PAGES
- com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_RIGHT_PAGES

DISPLAY_ALL_PAGES and DISPLAY_LEFT_PAGES/DISPLAY_RIGHT_PAGES cannot be combined, otherwise all combinations are possible.
The first step is to create a RtfHeaderFooterGroup and then you add the HeaderFooter objects and specify where they are to appear.

    RtfHeaderFooterGroup footer = new RtfHeaderFooterGroup();
    footer.setHeaderFooter(
    	new RtfHeaderFooter(
    		new Phrase("This is the footer on the title page")),
    			com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_FIRST_PAGE);
    footer.setHeaderFooter(
    	new RtfHeaderFooter(
    		new Phrase("This is a left side page")),
    			com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_LEFT_PAGES);
    footer.setHeaderFooter(
    	new RtfHeaderFooter(
    		new Phrase("This is a right side page")),
    			com.lowagie.text.rtf.headerfooter.RtfHeaderFooter.DISPLAY_RIGHT_PAGES);
    document.setFooter(footer);

Arbitrary Elements in the header
To give the RtfWriter2 more flexibility when creating headers or footers, the com.lowagie.text.rtf.headerfooter.RtfHeaderFooter makes it possible to add any Element as a header or footer. This can be used to add tables to the header, giving improved formating capabilities.

    Table headerTable = new Table(3);
    headerTable.addCell("Document header");
    Cell pageNumberCell = new Cell();
    pageNumberCell.add(new RtfPageNumber());
    headerTable.addCell(pageNumberCell);
    headerTable.addCell("Company Name");
    HeaderFooter header = new RtfHeaderFooter(headerTable);
    document.setHeader(header);

Example: java com.lowagie.examples.rtf.RtfWithHeadersFooters
Headers/footers and page numbers: see headerfooter.rtf
Go to top of the page
Table of contents support:
The RtfWriter2 also supports the creation of a table of contents and the addition of entries into that table of contents. There is one limitation and that is that the actual table of contents will have to be generated by the RTF viewer application, because iText does not know how to render RTF documents and can therefore not calculate the correct page numbers. When creating the RtfTableOfContents it is necessary to specify the text that is displayed before the field is updated by the viewer.
Adding a table of contents
You can add the actual table of contents anywhere in the document. Simply create an instance of com.lowagie.text.rtf.toc.RtfTableOfContents and add it to a paragraph. The constructor takes the default string to display and the font to use as parameters.

    Paragraph para = new Paragraph();
    para.add(new RtfTableOfContents(
    	"RIGHT CLICK AND HERE AND SELECT \"UPDATE FIELD\" TO UPDATE.",
    	new Font()));
    doc.add(para);

Adding entries to the table of contents
You can add entries to the table of contents before or after you've added the actual table of contents. It's as simple as adding an instance of RtfTOCEntry to the document.

    RtfTOCEntry tocEntry =
    	new RtfTOCEntry("Manually added TOC entry", new Font());
    document.add(tocEntry);

The second possibility is to let the RtfWriter2 automatically add RtfTOCEntrys for every Chapter you add.

    writer2.setAutogenerateTOCEntries(true);

Example: java com.lowagie.examples.rtf.RtfTOCandCellborders
Table of contents and cell borders: see toc.rtf
Go to top of the page
Extended cell border support:
The RtfWriter2 also provides support for using special border styles with table cells. To use this feature you add RtfCell objects to the Table instead of Cells.

    RtfCell cellDotted = new RtfCell("Dotted border");
    cellDotted.setBorders(new RtfBorderGroup(
    	Rectangle.BOX, RtfBorder.BORDER_DOTTED, 1, new Color(0, 0, 0)));
    RtfCell cellEmbossed = new RtfCell("Embossed border");
    cellEmbossed.setBorders(
    	new RtfBorderGroup(
    		Rectangle.BOX, RtfBorder.BORDER_EMBOSS, 1, new Color(0, 0, 0)));
    			    RtfCell cellNoBorder = new RtfCell("No border")
    cellNoBorder.setBorders(new RtfBorderGroup());

    table.addCell(cellDotted);
    table.addCell(cellEmbossed);
    table.addCell(cellNoBorder);

The RtfCell supports a long list of border styles. Please consult the javadoc documentation for an exhaustive list.
Example: java com.lowagie.examples.rtf.RtfTOCandCellborders
Table of contents and cell borders: see toc.rtf
Go to top of the page
Page number element:
The RtfPageNumber class allows you to add the number of the current page at any position in the document. The primary use is in headers or footers with special formatting.

    Table headerTable = new Table(3);
    headerTable.addCell("Document header");
    Cell pageNumberCell = new Cell();
    pageNumberCell.add(new RtfPageNumber());
    headerTable.addCell(pageNumberCell);
    headerTable.addCell("Company Name");
    HeaderFooter header = new RtfHeaderFooter(headerTable);
    document.setHeader(header);

Example: java com.lowagie.examples.rtf.RtfWithHeadersFooters
Headers/footers and page numbers: see headerfooter.rtf
.
Go to top of the page
Using a Disk Cache for document generation:
The RtfWriter2 differs in one more way from PdfWriter and that is that due to the way the rtf format works, the document data has to be cached and can only be written to the final file after the complete document has been generated. For very large documents and those containing big images, this results in huge memory requirements.
To solve this problem the RtfWriter2 supports caching the document data on disk in a temporary file. To activate disk caching insert the following code directly after creating the RtfWriter2.

    writer2.setDataCacheStyle(com.lowagie.text.rtf.document.output.RtfDataCache.CACHE_DISK);

Go to top of the page
Amazon books:
amazon.co.uk-link