Chapter 4: Organizing content in tables

This is a code example of iText PDF, discover more.

10th October 2015
admin-marketing

These examples were written in the context of Chapter 4 of the book "iText in Action - Second Edition".

MyFirstTable.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class MyFirstTable {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/first_table.pdf";
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws IOException, DocumentException {
        new MyFirstTable().createPdf(RESULT);
    }
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        document.add(createFirstTable());
        // step 5
        document.close();
    }
    
    /**
     * Creates our first table
     * @return our first table
     */
    public static PdfPTable createFirstTable() {
        // a table with three columns
        PdfPTable table = new PdfPTable(3);
        // the cell object
        PdfPCell cell;
        // we add a cell with colspan 3
        cell = new PdfPCell(new Phrase("Cell with colspan 3"));
        cell.setColspan(3);
        table.addCell(cell);
        // now we add a cell with rowspan 2
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        // we add the four remaining cells with addCell()
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
}
ColumnWidths.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.Rectangle;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class ColumnWidths {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/column_widths.pdf";
    
    /**
     * Creates a PDF with five tables.
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        PdfPTable table = createTable1();
        document.add(table);
        table = createTable2();
        table.setSpacingBefore(5);
        table.setSpacingAfter(5);
        document.add(table);
        table = createTable3();
        document.add(table);
        table = createTable4();
        table.setSpacingBefore(5);
        table.setSpacingAfter(5);
        document.add(table);
        table = createTable5();
        document.add(table);
        // step 5
        document.close();
    }
    
    /**
     * Creates a table; widths are set with setWidths().
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable createTable1() throws DocumentException {
        PdfPTable table = new PdfPTable(3);
        table.setWidthPercentage(288 / 5.23f);
        table.setWidths(new int[]{2, 1, 1});
        PdfPCell cell;
        cell = new PdfPCell(new Phrase("Table 1"));
        cell.setColspan(3);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
    
    /**
     * Creates a table; widths are set with setWidths().
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable createTable2() throws DocumentException {
        PdfPTable table = new PdfPTable(3);
        table.setTotalWidth(288);
        table.setLockedWidth(true);
        table.setWidths(new float[]{2, 1, 1});
        PdfPCell cell;
        cell = new PdfPCell(new Phrase("Table 2"));
        cell.setColspan(3);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
    
    /**
     * Creates a table; widths are set in the constructor.
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable createTable3() throws DocumentException {
        PdfPTable table = new PdfPTable(new float[]{ 2, 1, 1 });
        table.setWidthPercentage(55.067f);
        PdfPCell cell;
        cell = new PdfPCell(new Phrase("Table 3"));
        cell.setColspan(3);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
    
    /**
     * Creates a table; widths are set with special setWidthPercentage() method.
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable createTable4() throws DocumentException {
        PdfPTable table = new PdfPTable(3);
        Rectangle rect = new Rectangle(523, 770);
        table.setWidthPercentage(new float[]{ 144, 72, 72 }, rect);
        PdfPCell cell;
        cell = new PdfPCell(new Phrase("Table 4"));
        cell.setColspan(3);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
    
    /**
     * Creates a table; widths are set with setTotalWidth().
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable createTable5() throws DocumentException {
        PdfPTable table = new PdfPTable(3);
        table.setTotalWidth(new float[]{ 144, 72, 72 });
        table.setLockedWidth(true);
        PdfPCell cell;
        cell = new PdfPCell(new Phrase("Table 5"));
        cell.setColspan(3);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
        cell.setRowspan(2);
        table.addCell(cell);
        table.addCell("row 1; cell 1");
        table.addCell("row 1; cell 2");
        table.addCell("row 2; cell 1");
        table.addCell("row 2; cell 2");
        return table;
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args) throws IOException, DocumentException {
        new ColumnWidths().createPdf(RESULT);
    }
}
TableAlignment.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class TableAlignment extends MyFirstTable {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/table_alignment.pdf";
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        PdfPTable table = createFirstTable();
        table.setWidthPercentage(50);
        table.setHorizontalAlignment(Element.ALIGN_LEFT);
        document.add(table);
        table.setHorizontalAlignment(Element.ALIGN_CENTER);
        document.add(table);
        table.setHorizontalAlignment(Element.ALIGN_RIGHT);
        document.add(table);
        // step 5
        document.close();
    }
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws IOException, DocumentException {
        new TableAlignment().createPdf(RESULT);
    }
}
MovieTextMode.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.SQLException;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.Country;
import com.lowagie.filmfestival.Director;
import com.lowagie.filmfestival.FilmFonts;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoToElementFactory;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class MovieTextMode {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/movie_text_mode.pdf";
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException 
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException, SQLException {
        // Create a database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");    
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        document.add(new Paragraph("Movies:"));
        List<Movie> movies = PojoFactory.getMovies(connection);
        for (Movie movie : movies) {
            PdfPTable table = new PdfPTable(2);
            table.setWidths(new int[]{1, 4});
            PdfPCell cell;
            cell = new PdfPCell(new Phrase(movie.getTitle(), FilmFonts.BOLD));
            cell.setHorizontalAlignment(Element.ALIGN_CENTER);
            cell.setColspan(2);
            table.addCell(cell);
            if (movie.getOriginalTitle() != null) {
                cell = new PdfPCell(PojoToElementFactory.getOriginalTitlePhrase(movie));
                cell.setColspan(2);
                cell.setHorizontalAlignment(Element.ALIGN_RIGHT);
                table.addCell(cell);
            }
            List<Director> directors = movie.getDirectors();
            cell = new PdfPCell(new Phrase("Directors:"));
            cell.setRowspan(directors.size());
            cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
            table.addCell(cell);
            int count = 0;
            for (Director pojo : directors) {
                cell = new PdfPCell(PojoToElementFactory.getDirectorPhrase(pojo));
                cell.setIndent(10 * count++);
                table.addCell(cell);
            }
            table.getDefaultCell().setHorizontalAlignment(Element.ALIGN_RIGHT);
            table.addCell("Year:");
            table.addCell(String.valueOf(movie.getYear()));
            table.addCell("Run length:");
            table.addCell(String.valueOf(movie.getDuration()));
            List<Country> countries = movie.getCountries();
            cell = new PdfPCell(new Phrase("Countries:"));
            cell.setRowspan(countries.size());
            cell.setVerticalAlignment(Element.ALIGN_BOTTOM);
            table.addCell(cell);
            table.getDefaultCell().setHorizontalAlignment(Element.ALIGN_CENTER);
            for (Country country : countries) {
                table.addCell(country.getCountry());
            }
            document.add(table);
        }
        // step 5
        document.close();
        // Close the database connection
        connection.close();
    }
    
    /**
     * Main method.
     *
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException 
     * @throws SQLException
     */
    public static void main(String[] args)
        throws IOException, DocumentException, SQLException {
        new MovieTextMode().createPdf(RESULT);
    }
}
Spacing.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class Spacing {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/spacing.pdf";
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws DocumentException, IOException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(RESULT));
        // step 3
        document.open();
        // step 4
        PdfPTable table = new PdfPTable(2);
        table.setWidthPercentage(100);
        Phrase p = new Phrase(
            "Dr. iText or: How I Learned to Stop Worrying " +
            "and Love the Portable Document Format.");
        PdfPCell cell = new PdfPCell(p);
        table.addCell("default leading / spacing");
        table.addCell(cell);
        table.addCell("absolute leading: 20");
        cell.setLeading(20f, 0f);
        table.addCell(cell);
        table.addCell("absolute leading: 3; relative leading: 1.2");
        cell.setLeading(3f, 1.2f);
        table.addCell(cell);
        table.addCell("absolute leading: 0; relative leading: 1.2");
        cell.setLeading(0f, 1.2f);
        table.addCell(cell);
        table.addCell("no leading at all");
        cell.setLeading(0f, 0f);
        table.addCell(cell);
        cell = new PdfPCell(new Phrase(
            "Dr. iText or: How I Learned to Stop Worrying and Love PDF"));
        table.addCell("padding 10");
        cell.setPadding(10);
        table.addCell(cell);
        table.addCell("padding 0");
        cell.setPadding(0);
        table.addCell(cell);
        table.addCell("different padding for left, right, top and bottom");
        cell.setPaddingLeft(20);
        cell.setPaddingRight(50);
        cell.setPaddingTop(0);
        cell.setPaddingBottom(5);
        table.addCell(cell);
        p = new Phrase("iText in Action Second Edition");
        table.getDefaultCell().setPadding(2);
        table.getDefaultCell().setUseAscender(false);
        table.getDefaultCell().setUseDescender(false);
        table.addCell("padding 2; no ascender, no descender");
        table.addCell(p);
        table.getDefaultCell().setUseAscender(true);
        table.getDefaultCell().setUseDescender(false);
        table.addCell("padding 2; ascender, no descender");
        table.addCell(p);
        table.getDefaultCell().setUseAscender(false);
        table.getDefaultCell().setUseDescender(true);
        table.addCell("padding 2; descender, no ascender");
        table.addCell(p);
        table.getDefaultCell().setUseAscender(true);
        table.getDefaultCell().setUseDescender(true);
        table.addCell("padding 2; ascender and descender");
        cell.setPadding(2);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        table.addCell(p);
        document.add(table);
        // step 5
        document.close();
    }
}
TableHeight.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class TableHeight extends MyFirstTable {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/table_height.pdf";
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        PdfPTable table = createFirstTable();
        document.add(new Paragraph(
            String.format("Table height before document.add(): %f",
                table.getTotalHeight())));
        document.add(new Paragraph(
            String.format("Height of the first row: %f",
                table.getRowHeight(0))));
        document.add(table);
        document.add(new Paragraph(
            String.format("Table height after document.add(): %f",
                table.getTotalHeight())));
        document.add(new Paragraph(
            String.format("Height of the first row: %f",
                table.getRowHeight(0))));
        table = createFirstTable();
        document.add(new Paragraph(
            String.format("Table height before setTotalWidth(): %f",
                table.getTotalHeight())));
        document.add(
            new Paragraph(String.format("Height of the first row: %f",
                table.getRowHeight(0))));
        table.setTotalWidth(50);
        table.setLockedWidth(true);
        document.add(
            new Paragraph(String.format("Table height after setTotalWidth(): %f",
                table.getTotalHeight())));
        document.add(new Paragraph(String.format("Height of the first row: %f",
            table.getRowHeight(0))));
        document.add(table);
        // step 5
        document.close();
    }
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */  
    public static void main(String[] args) throws IOException, DocumentException {
        new TableHeight().createPdf(RESULT);
    }
}
CellHeights.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class CellHeights {
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/cell_heights.pdf";
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args) throws DocumentException, IOException {
        // step 1
        Document document = new Document(PageSize.A5.rotate());
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(RESULT));
        // step 3
        document.open();
        // step 4
        PdfPTable table = new PdfPTable(2);
        // a long phrase
        Phrase p = new Phrase(
            "Dr. iText or: How I Learned to Stop Worrying and Love PDF.");
        PdfPCell cell = new PdfPCell(p);
        // the prhase is wrapped
        table.addCell("wrap");
        cell.setNoWrap(false);
        table.addCell(cell);
        // the phrase isn't wrapped
        table.addCell("no wrap");
        cell.setNoWrap(true);
        table.addCell(cell);
        // a long phrase with newlines
        p = new Phrase(
            "Dr. iText or:\nHow I Learned to Stop Worrying\nand Love PDF.");
        cell = new PdfPCell(p);
        // the phrase fits the fixed height
        table.addCell("fixed height (more than sufficient)");
        cell.setFixedHeight(72f);
        table.addCell(cell);
        // the phrase doesn't fit the fixed height
        table.addCell("fixed height (not sufficient)");
        cell.setFixedHeight(36f);
        table.addCell(cell);
        // The minimum height is exceeded
        table.addCell("minimum height");
        cell = new PdfPCell(new Phrase("Dr. iText"));
        cell.setMinimumHeight(36f);
        table.addCell(cell);
        // The last row is extended
        table.setExtendLastRow(true);
        table.addCell("extend last row");
        table.addCell(cell);
        document.add(table);
        // step 5
        document.close();
    }
}
RotationAndColors.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.Rectangle;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
import com.itextpdf.text.BaseColor;
 
public class RotationAndColors {
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/rotation_colors.pdf";
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws DocumentException, IOException {
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(RESULT));
        // step 3
        document.open();
        // step 4
        PdfPTable table = new PdfPTable(4);
        table.setWidths(new int[]{ 1, 3, 3, 3 });
        table.setWidthPercentage(100);
        PdfPCell cell;
        // row 1, cell 1
        cell = new PdfPCell(new Phrase("COLOR"));
        cell.setRotation(90);
        cell.setVerticalAlignment(Element.ALIGN_TOP);
        table.addCell(cell);
        // row 1, cell 2
        cell = new PdfPCell(new Phrase("red / no borders"));
        cell.setBorder(Rectangle.NO_BORDER);
        cell.setBackgroundColor(BaseColor.RED);
        table.addCell(cell);
        // row 1, cell 3
        cell = new PdfPCell(new Phrase("green / black bottom border"));
        cell.setBorder(Rectangle.BOTTOM);
        cell.setBorderColorBottom(BaseColor.BLACK);
        cell.setBorderWidthBottom(10f);
        cell.setBackgroundColor(BaseColor.GREEN);
        table.addCell(cell);
        // row 1, cell 4
        cell = new PdfPCell(new Phrase(
                "cyan / blue top border + padding"));
        cell.setBorder(Rectangle.TOP);
        cell.setUseBorderPadding(true);
        cell.setBorderWidthTop(5f);
        cell.setBorderColorTop(BaseColor.BLUE);
        cell.setBackgroundColor(BaseColor.CYAN);
        table.addCell(cell);
        // row 2, cell 1
        cell = new PdfPCell(new Phrase("GRAY"));
        cell.setRotation(90);
        cell.setVerticalAlignment(Element.ALIGN_MIDDLE);
        table.addCell(cell);
        // row 2, cell 2
        cell = new PdfPCell(new Phrase("0.6"));
        cell.setBorder(Rectangle.NO_BORDER);
        cell.setGrayFill(0.6f);
        table.addCell(cell);
        // row 2, cell 3
        cell = new PdfPCell(new Phrase("0.75"));
        cell.setBorder(Rectangle.NO_BORDER);
        cell.setGrayFill(0.75f);
        table.addCell(cell);
        // row 2, cell 4
        cell = new PdfPCell(new Phrase("0.9"));
        cell.setBorder(Rectangle.NO_BORDER);
        cell.setGrayFill(0.9f);
        table.addCell(cell);
        // row 3, cell 1
        cell = new PdfPCell(new Phrase("BORDERS"));
        cell.setRotation(90);
        cell.setVerticalAlignment(Element.ALIGN_BOTTOM);
        table.addCell(cell);
        // row 3, cell 2
        cell = new PdfPCell(new Phrase("different borders"));
        cell.setBorderWidthLeft(16f);
        cell.setBorderWidthBottom(12f);
        cell.setBorderWidthRight(8f);
        cell.setBorderWidthTop(4f);
        cell.setBorderColorLeft(BaseColor.RED);
        cell.setBorderColorBottom(BaseColor.ORANGE);
        cell.setBorderColorRight(BaseColor.YELLOW);
        cell.setBorderColorTop(BaseColor.GREEN);
        table.addCell(cell);
        // row 3, cell 3
        cell = new PdfPCell(new Phrase("with correct padding"));
        cell.setUseBorderPadding(true);
        cell.setBorderWidthLeft(16f);
        cell.setBorderWidthBottom(12f);
        cell.setBorderWidthRight(8f);
        cell.setBorderWidthTop(4f);
        cell.setBorderColorLeft(BaseColor.RED);
        cell.setBorderColorBottom(BaseColor.ORANGE);
        cell.setBorderColorRight(BaseColor.YELLOW);
        cell.setBorderColorTop(BaseColor.GREEN);
        table.addCell(cell);
        // row 3, cell 4
        cell = new PdfPCell(new Phrase("red border"));
        cell.setBorderWidth(8f);
        cell.setBorderColor(BaseColor.RED);
        table.addCell(cell);
        document.add(table);
        // step 5
        document.close();
    }
}
MovieCompositeMode.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.SQLException;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.FilmFonts;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoToElementFactory;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Image;
import com.itextpdf.text.List;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class MovieCompositeMode {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/movie_composite_mode.pdf";
    /** Path to the resources. */
    public static final String RESOURCE
        = "resources/posters/%s.jpg";
    
    /**
     * Main method.
     *
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException 
     * @throws SQLException
     */
    public static void main(String[] args)
        throws IOException, DocumentException, SQLException {
        new MovieCompositeMode().createPdf(RESULT);
    }
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException 
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException, SQLException {
        // Create a database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        document.add(new Paragraph("Movies:"));
        java.util.List<Movie> movies = PojoFactory.getMovies(connection);
        List list;
        PdfPCell cell;
        for (Movie movie : movies) {
            // a table with two columns
            PdfPTable table = new PdfPTable(new float[]{1, 7});
            table.setWidthPercentage(100);
            table.setSpacingBefore(5);
            // a cell with an image
            cell = new PdfPCell(
                Image.getInstance(String.format(RESOURCE, movie.getImdb())), true);
            cell.setBorder(PdfPCell.NO_BORDER);
            table.addCell(cell);
            cell = new PdfPCell();
            // a cell with paragraphs and lists
            Paragraph p = new Paragraph(movie.getTitle(), FilmFonts.BOLD);
            p.setAlignment(Element.ALIGN_CENTER);
            p.setSpacingBefore(5);
            p.setSpacingAfter(5);
            cell.addElement(p);
            cell.setBorder(PdfPCell.NO_BORDER);
            if (movie.getOriginalTitle() != null) {
                p = new Paragraph(movie.getOriginalTitle(), FilmFonts.ITALIC);
                p.setAlignment(Element.ALIGN_RIGHT);
                cell.addElement(p);
            }
            list = PojoToElementFactory.getDirectorList(movie);
            list.setIndentationLeft(30);
            cell.addElement(list);
            p = new Paragraph(
                String.format("Year: %d", movie.getYear()), FilmFonts.NORMAL);
            p.setIndentationLeft(15);
            p.setLeading(24);
            cell.addElement(p);
            p = new Paragraph(
                String.format("Run length: %d", movie.getDuration()), FilmFonts.NORMAL);
            p.setLeading(14);
            p.setIndentationLeft(30);
            cell.addElement(p);
            list = PojoToElementFactory.getCountryList(movie);
            list.setIndentationLeft(40);
            cell.addElement(list);
            table.addCell(cell);
            // every movie corresponds with one table
            document.add(table);
            // but the result looks like one big table
        }
        // step 4
        document.close();
        // Close the database connection
        connection.close();
    }
}
XMen.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Image;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class XMen {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/x_men.pdf";
    /** Path to the resources. */
    public static final String RESOURCE = "resources/posters/%s.jpg";
    
    /**
     * Creates a PDF with information about the movies
     * @param    filename the name of the PDF file that will be created.
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException {
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        // we'll use 4 images in this example
        Image[] img = {
                Image.getInstance(String.format(RESOURCE, "0120903")),
                Image.getInstance(String.format(RESOURCE, "0290334")),
                Image.getInstance(String.format(RESOURCE, "0376994")),
                Image.getInstance(String.format(RESOURCE, "0348150"))
        };
        // Creates a table with 6 columns
        PdfPTable table = new PdfPTable(6);
        table.setWidthPercentage(100);
        // first movie
        table.getDefaultCell().setHorizontalAlignment(Element.ALIGN_CENTER);
        table.getDefaultCell().setVerticalAlignment(Element.ALIGN_TOP);
        table.addCell("X-Men");
        // we wrap he image in a PdfPCell
        PdfPCell cell = new PdfPCell(img[0]);
        table.addCell(cell);
        // second movie
        table.getDefaultCell().setVerticalAlignment(Element.ALIGN_MIDDLE);
        table.addCell("X2");
        // we wrap the image in a PdfPCell and let iText scale it
        cell = new PdfPCell(img[1], true);
        table.addCell(cell);
        // third movie
        table.getDefaultCell().setVerticalAlignment(Element.ALIGN_BOTTOM);
        table.addCell("X-Men: The Last Stand");
        // we add the image with addCell()
        table.addCell(img[2]);
        // fourth movie
        table.addCell("Superman Returns");
        cell = new PdfPCell();
        // we add it with addElement(); it can only take 50% of the width.
        img[3].setWidthPercentage(50);
        cell.addElement(img[3]);
        table.addCell(cell);
        // we complete the table (otherwise the last row won't be rendered)
        table.completeRow();
        document.add(table);
        document.close();
    }
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args) throws IOException, DocumentException {
        new XMen().createPdf(RESULT);
    }
}
NestedTable.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
 
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class NestedTable {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/nested_table.pdf";
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws DocumentException, IOException {
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(RESULT));
        // step 3
        document.open();
        // step 4
        PdfPTable table = new PdfPTable(4);
        PdfPTable nested1 = new PdfPTable(2);
        nested1.addCell("1.1");
        nested1.addCell("1.2");
        PdfPTable nested2 = new PdfPTable(1);
        nested2.addCell("12.1");
        nested2.addCell("12.2");
        for (int k = 0; k < 16; ++k) {
            if (k == 1) {
                table.addCell(nested1);
            } else if (k == 12) {
                table.addCell(new PdfPCell(nested2));
            } else {
                table.addCell("cell " + k);
            }
        }
        document.add(table);
        // step 5
        document.close();
    }
}
NestedTables.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.Date;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.FilmFonts;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.PojoToElementFactory;
import com.lowagie.filmfestival.Screening;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Font;
import com.itextpdf.text.Image;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.html.WebColors;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
import com.itextpdf.text.BaseColor;
 
public class NestedTables {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/nested_tables.pdf";
    /** Path to the resources. */
    public static final String RESOURCE = "resources/posters/%s.jpg";
    /** Collection containing all the Images */
    public HashMap<String,Image> images = new HashMap<String,Image>();
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @throws    DocumentException 
     * @throws    IOException
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws SQLException, DocumentException, IOException {
        // create the database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        List<Date> days = PojoFactory.getDays(connection);
        for (Date day : days) {
            document.add(getTable(connection, day));
            document.newPage();
        }
        // step 5
        document.close();
        // close the database connection
        connection.close();
 
    }
 
    /**
     * Creates a table with all the screenings of a specific day.
     * The table is composed of nested tables.
     * @param connection a database connection
     * @param day a film festival day
     * @return a table
     * @throws SQLException
     * @throws DocumentException
     * @throws IOException
     */
    public PdfPTable getTable(DatabaseConnection connection, Date day)
        throws SQLException, DocumentException, IOException {
        // Create a table with only one column
        PdfPTable table = new PdfPTable(1);
        table.setWidthPercentage(100f);
        // add the cell with the date
        Font f = new Font();
        f.setColor(BaseColor.WHITE);
        PdfPCell cell = new PdfPCell(new Phrase(day.toString(), f));
        cell.setBackgroundColor(BaseColor.BLACK);
        cell.setHorizontalAlignment(Element.ALIGN_CENTER);
        table.addCell(cell);
        // add the movies as nested tables
        List<Screening> screenings = PojoFactory.getScreenings(connection, day);
        for (Screening screening : screenings) {
            table.addCell(getTable(connection, screening));
        }
        return table;
    }
 
    /**
     * Create a table with information about a movie.
     * @param connection a database connection
     * @param screening a Screening
     * @return a table
     * @throws DocumentException
     * @throws IOException
     */
    private PdfPTable getTable(DatabaseConnection connection, Screening screening)
        throws DocumentException, IOException {
        // Create a table with 4 columns
        PdfPTable table = new PdfPTable(4);
        table.setWidths(new int[]{1, 5, 10, 10});
        // Get the movie
        Movie movie = screening.getMovie();
        // A cell with the title as a nested table spanning the complete row
        PdfPCell cell = new PdfPCell();
        // nesting is done with addElement() in this example
        cell.addElement(fullTitle(screening));
        cell.setColspan(4);
        cell.setBorder(PdfPCell.NO_BORDER);
        BaseColor color
            = WebColors.getRGBColor("#" + movie.getEntry().getCategory().getColor());
        cell.setBackgroundColor(color);
        table.addCell(cell);
        // empty cell
        cell = new PdfPCell();
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        table.addCell(cell);
        // cell with the movie poster
        cell = new PdfPCell(getImage(movie.getImdb()));
        cell.setBorder(PdfPCell.NO_BORDER);
        table.addCell(cell);
        // cell with the list of directors
        cell = new PdfPCell();
        cell.addElement(PojoToElementFactory.getDirectorList(movie));
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        table.addCell(cell);
        // cell with the list of countries
        cell = new PdfPCell();
        cell.addElement(PojoToElementFactory.getCountryList(movie));
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        table.addCell(cell);
 
        return table;
    }
    
    /**
     * Create a table with the full movie title
     * @param screening a Screening object
     * @return a table
     * @throws DocumentException
     */
    private static PdfPTable fullTitle(Screening screening)
        throws DocumentException {
        PdfPTable table = new PdfPTable(3);
        table.setWidths(new int[]{3, 15, 2});
        table.setWidthPercentage(100);
        // cell 1: location and time
        PdfPCell cell = new PdfPCell();
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setBackgroundColor(BaseColor.WHITE);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        String s = String.format("%s \u2013 %2$tH:%2$tM",
            screening.getLocation(), screening.getTime().getTime());
        cell.addElement(new Paragraph(s));
        table.addCell(cell);
        // cell 2: English and original title 
        Movie movie = screening.getMovie();
        Paragraph p = new Paragraph();
        p.add(new Phrase(movie.getMovieTitle(), FilmFonts.BOLD));
        p.setLeading(16);
        if (movie.getOriginalTitle() != null) {
            p.add(new Phrase(" (" + movie.getOriginalTitle() + ")"));
        }
        cell = new PdfPCell();
        cell.addElement(p);
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        table.addCell(cell);
        // cell 3 duration
        cell = new PdfPCell();
        cell.setBorder(PdfPCell.NO_BORDER);
        cell.setBackgroundColor(BaseColor.WHITE);
        cell.setUseAscender(true);
        cell.setUseDescender(true);
        p = new Paragraph(String.format("%d'", movie.getDuration()));
        p.setAlignment(Element.ALIGN_CENTER);
        cell.addElement(p);
        table.addCell(cell);
        return table;
    }
    
    /**
     * Create an image with a movie poster.
     * @param imdb an Internet Movie Database id
     * @return an Image
     * @throws DocumentException
     * @throws IOException
     */
    public Image getImage(String imdb) throws DocumentException, IOException {
        Image img = images.get(imdb);
        if (img == null) {
            img = Image.getInstance(String.format(RESOURCE, imdb));
            img.scaleToFit(80, 72);
            images.put(imdb, img);
        }
        return img;
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args)
        throws SQLException, DocumentException, IOException {
        new NestedTables().createPdf(RESULT);
    }
}
HeaderFooter1.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.Date;
import java.sql.SQLException;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.PojoToElementFactory;
import com.lowagie.filmfestival.Screening;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Font;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
import com.itextpdf.text.BaseColor;
 
public class HeaderFooter1 {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/header_footer_1.pdf";
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @throws    DocumentException 
     * @throws    IOException
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws SQLException, DocumentException, IOException {
        // create a database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        List<Date> days = PojoFactory.getDays(connection);
        for (Date day : days) {
            document.add(getTable(connection, day));
            document.newPage();
        }
        // step 5
        document.close();
        // close the database connection
        connection.close();
 
    }
 
    /**
     * Creates a table with screenings.
     * @param connection the database connection
     * @param day a film festival day
     * @return a table with screenings
     * @throws SQLException
     * @throws DocumentException
     * @throws IOException
     */
    public PdfPTable getTable(DatabaseConnection connection, Date day)
        throws SQLException, DocumentException, IOException {
        // Create a table with 7 columns
        PdfPTable table = new PdfPTable(new float[] { 2, 1, 2, 5, 1, 3, 2 });
        table.setWidthPercentage(100f);
        table.getDefaultCell().setUseAscender(true);
        table.getDefaultCell().setUseDescender(true);
        // Add the first header row
        Font f = new Font();
        f.setColor(BaseColor.WHITE);
        PdfPCell cell = new PdfPCell(new Phrase(day.toString(), f));
        cell.setBackgroundColor(BaseColor.BLACK);
        cell.setHorizontalAlignment(Element.ALIGN_CENTER);
        cell.setColspan(7);
        table.addCell(cell);
        // Add the second header row twice
        table.getDefaultCell().setBackgroundColor(BaseColor.LIGHT_GRAY);
        for (int i = 0; i < 2; i++) {
            table.addCell("Location");
            table.addCell("Time");
            table.addCell("Run Length");
            table.addCell("Title");
            table.addCell("Year");
            table.addCell("Directors");
            table.addCell("Countries");
        }
        table.getDefaultCell().setBackgroundColor(null);
        // There are three special rows
        table.setHeaderRows(3);
        // One of them is a footer
        table.setFooterRows(1);
        // Now let's loop over the screenings
        List<Screening> screenings = PojoFactory.getScreenings(connection, day);
        Movie movie;
        for (Screening screening : screenings) {
            movie = screening.getMovie();
            table.addCell(screening.getLocation());
            table.addCell(String.format("%1$tH:%1$tM", screening.getTime()));
            table.addCell(String.format("%d '", movie.getDuration()));
            table.addCell(movie.getMovieTitle());
            table.addCell(String.valueOf(movie.getYear()));
            cell = new PdfPCell();
            cell.setUseAscender(true);
            cell.setUseDescender(true);
            cell.addElement(PojoToElementFactory.getDirectorList(movie));
            table.addCell(cell);
            cell = new PdfPCell();
            cell.setUseAscender(true);
            cell.setUseDescender(true);
            cell.addElement(PojoToElementFactory.getCountryList(movie));
            table.addCell(cell);
        }
        return table;
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args)
        throws SQLException, DocumentException, IOException {
        new HeaderFooter1().createPdf(RESULT);
    }
}
HeaderFooter2.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.Date;
import java.sql.SQLException;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.PojoFactory;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class HeaderFooter2 extends HeaderFooter1 {
 
    /** The resulting PDF file. */
    public static final String RESULT
        = "results/part1/chapter04/header_footer_2.pdf";
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @throws    DocumentException 
     * @throws    IOException
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws SQLException, DocumentException, IOException {
        // create a database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        List<Date> days = PojoFactory.getDays(connection);
        for (Date day : days) {
            PdfPTable table = getTable(connection, day);
            table.setSplitLate(false);
            document.add(table);
            document.newPage();
        }
        // step 5
        document.close();
        // close the database connection
        connection.close();
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args)
        throws SQLException, DocumentException, IOException {
        new HeaderFooter2().createPdf(RESULT);
    }
}
MemoryTests.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.Writer;
import java.sql.SQLException;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.FilmFonts;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.PojoToElementFactory;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Font;
import com.itextpdf.text.Image;
import com.itextpdf.text.List;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.Font.FontFamily;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class MemoryTests {
 
    /** The resulting report. */
    public static final String RESULT0
       = "results/part1/chapter04/test_results.txt";
    /** A resulting PDF file. */
    public static final String RESULT1
        = "results/part1/chapter04/pdfptable_without_memory_management.pdf";
    /** A resulting PDF file. */
    public static final String RESULT2
        = "results/part1/chapter04/pdfptable_with_memory_management.pdf";
    
    private boolean test;
    private long memory_use;
    private long initial_memory_use = 0l;
    private long maximum_memory_use = 0l;
    
    /** Path to the resources. */
    public static final String RESOURCE = "resources/posters/%s.jpg";
    /** The different epochs. */
    public static final String[] EPOCH =
        { "Forties", "Fifties", "Sixties", "Seventies", "Eighties", "Nineties", "Twenty-first Century" };
    
    /** The fonts for the title. */
    public static final Font[] FONT = new Font[4];
    static {
        FONT[0] = new Font(FontFamily.HELVETICA, 24);
        FONT[1] = new Font(FontFamily.HELVETICA, 18);
        FONT[2] = new Font(FontFamily.HELVETICA, 14);
        FONT[3] = new Font(FontFamily.HELVETICA, 12, Font.BOLD);
    }
    
    /**
     * Create two PDFs, one without memory management, one with.
     * Write a report file to show the memory usage
     */
    public void createPdfs() {
        try {
            // the report file
            PrintWriter writer = new PrintWriter(new FileOutputStream(RESULT0));
            resetMaximum(writer);
            test = false;
            println(writer, RESULT1);
            // PDF without memory management
            createPdfWithPdfPTable(writer, RESULT1);
            resetMaximum(writer);
            test = true;
            println(writer, RESULT2);
            // PDF with memory management
            createPdfWithPdfPTable(writer, RESULT2);
            resetMaximum(writer);
            writer.flush();
            writer.close();
        }
        catch(Exception e) {
            e.printStackTrace();
        }
    }
 
    /**
     * Creates a PDF with a table
     * @param writer the writer to our report file
     * @param filename the PDF that will be created
     * @throws IOException
     * @throws DocumentException
     * @throws SQLException
     */
    private void createPdfWithPdfPTable(Writer writer, String filename) throws IOException, DocumentException, SQLException {
        // Create a connection to the database
        DatabaseConnection connection = new HsqldbConnection("filmfestival"); 
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        // Create a table with 2 columns
        PdfPTable table = new PdfPTable(new float[]{1, 7});
        // Mark the table as not complete
        if (test) table.setComplete(false);
        table.setWidthPercentage(100);
        java.util.List<Movie> movies = PojoFactory.getMovies(connection);
        List list;
        PdfPCell cell;
        int count = 0;
        // add information about a movie
        for (Movie movie : movies) {
            table.setSpacingBefore(5);
            // add a movie poster
            cell = new PdfPCell(Image.getInstance(String.format(RESOURCE, movie.getImdb())), true);
            cell.setBorder(PdfPCell.NO_BORDER);
            table.addCell(cell);
            // add movie information
            cell = new PdfPCell();
            Paragraph p = new Paragraph(movie.getTitle(), FilmFonts.BOLD);
            p.setAlignment(Element.ALIGN_CENTER);
            p.setSpacingBefore(5);
            p.setSpacingAfter(5);
            cell.addElement(p);
            cell.setBorder(PdfPCell.NO_BORDER);
            if (movie.getOriginalTitle() != null) {
                p = new Paragraph(movie.getOriginalTitle(), FilmFonts.ITALIC);
                p.setAlignment(Element.ALIGN_RIGHT);
                cell.addElement(p);
            }
            list = PojoToElementFactory.getDirectorList(movie);
            list.setIndentationLeft(30);
            cell.addElement(list);
            p = new Paragraph(String.format("Year: %d", movie.getYear()), FilmFonts.NORMAL);
            p.setIndentationLeft(15);
            p.setLeading(24);
            cell.addElement(p);
            p = new Paragraph(String.format("Run length: %d", movie.getDuration()), FilmFonts.NORMAL);
            p.setLeading(14);
            p.setIndentationLeft(30);
            cell.addElement(p);
            list = PojoToElementFactory.getCountryList(movie);
            list.setIndentationLeft(40);
            cell.addElement(list);
            table.addCell(cell);
            // insert a checkpoint every 10 movies
            if (count++ % 10 == 0) {
                // add the incomplete table to the document
                if (test)
                    document.add(table);
                checkpoint(writer);
            }
        }
        // Mark the table as complete
        if (test) table.setComplete(true);
        // add the table to the document
        document.add(table);
        // insert a last checkpoint
        checkpoint(writer);
        // step 5
        document.close();
    }
    
    /**
     * Writes a checkpoint to the report file.
     * @param writer the writer to our report file
     */
    private void checkpoint(Writer writer) {
        memory_use = getMemoryUse();
        maximum_memory_use = Math.max(maximum_memory_use, memory_use);
        println(writer, "memory use: ", memory_use);
    }
    
    /**
     * Resets the maximum memory that is in use
     * @param writer the writer to our report file
     */
    private void resetMaximum(Writer writer) {
        println(writer, "maximum: ", maximum_memory_use);
        println(writer, "total used: ", maximum_memory_use - initial_memory_use);
        maximum_memory_use = 0l;
        initial_memory_use = getMemoryUse();
        println(writer, "initial memory use: ", initial_memory_use);
    }
 
    /**
     * Writes a line to our report file
     * @param writer the writer to our report file
     * @param message the message to write
     */
    private void println(Writer writer, String message) {
        try {
            writer.write(message);
            writer.write("\n");
            writer.flush();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    
    /**
     * Writes a line to our report file
     * @param writer the writer to our report file
     * @param message the message to write
     * @param l a memory value
     */
    private void println(Writer writer, String message, long l) {
        try {
            writer.write(message + l);
            writer.write("\n");
            writer.flush();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    
    /**
     * Returns the current memory use.
     * 
     * @return the current memory use
     */
    private static long getMemoryUse() {
        garbageCollect();
        garbageCollect();
        long totalMemory = Runtime.getRuntime().totalMemory();
        garbageCollect();
        garbageCollect();
        long freeMemory = Runtime.getRuntime().freeMemory();
        return (totalMemory - freeMemory);
    }
    
    /**
     * Makes sure all garbage is cleared from the memory.
     */
    private static void garbageCollect() {
        try {
            System.gc();
            Thread.sleep(100);
            System.runFinalization();
            Thread.sleep(100);
            System.gc();
            Thread.sleep(100);
            System.runFinalization();
            Thread.sleep(100);
        } catch (InterruptedException ex) {
            ex.printStackTrace();
        }
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args) {
        MemoryTests tests = new MemoryTests();
        tests.createPdfs();
    }
}
PdfCalendar.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Calendar;
import java.util.GregorianCalendar;
import java.util.Locale;
import java.util.Properties;
 
import com.itextpdf.text.Chunk;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Font;
import com.itextpdf.text.Image;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Paragraph;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.pdf.BaseFont;
import com.itextpdf.text.pdf.ColumnText;
import com.itextpdf.text.pdf.PdfContentByte;
import com.itextpdf.text.pdf.PdfPCell;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
import com.itextpdf.text.BaseColor;
import com.itextpdf.text.pdf.draw.VerticalPositionMark;
 
public class PdfCalendar {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/calendar.pdf";
    /** The year for which we want to create a calendar */
    public static final int YEAR = 2011;
    /** The language code for the calendar */
    public static final String LANGUAGE = "en";
    /** Path to the resources. */
    public static final String RESOURCE = "resources/calendar/%tm.jpg";
    /** Path to the resources. */
    public static final String SPECIAL = "resources/calendar/%d.txt";
    /** Path to the resources. */
    public static final String CONTENT = "resources/calendar/content.txt";
 
    /** Collection with special days */
    public static Properties specialDays = new Properties();
    /** Collection with the description of the images */
    public static Properties content = new Properties();
 
    /** A font that is used in the calendar */
    protected Font normal;
    /** A font that is used in the calendar */
    protected Font small;
    /** A font that is used in the calendar */
    protected Font bold;
 
    /**
     * Main method.
     * @param    args    no arguments needed
     * @throws DocumentException 
     * @throws IOException
     */
    public static void main(String[] args)
        throws IOException, DocumentException {
        Locale locale = new Locale(LANGUAGE);
        new PdfCalendar().createPdf(RESULT, locale, YEAR);
    }
    
    /**
     * Initializes the fonts and collections.
     * @throws DocumentException
     * @throws IOException
     */
    public PdfCalendar() throws DocumentException, IOException {
        // fonts
        BaseFont bf_normal
            = BaseFont.createFont("c://windows/fonts/arial.ttf",
                BaseFont.WINANSI, BaseFont.EMBEDDED);
        normal = new Font(bf_normal, 16);
        small = new Font(bf_normal, 8);
        BaseFont bf_bold
            = BaseFont.createFont("c://windows/fonts/arialbd.ttf",
                BaseFont.WINANSI,BaseFont.EMBEDDED);
        bold = new Font(bf_bold, 14);
        // collections
        specialDays.load(new FileInputStream(String.format(SPECIAL, YEAR)));
        content.load(new FileInputStream(CONTENT));
    }
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @param locale Locale in case you want to create
     * a Calendar in another language
     * @param year the year for which you want to make a calendar
     * @throws    DocumentException 
     * @throws    IOException
     */
    public void createPdf(String filename, Locale locale, int year) throws IOException, DocumentException {
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter writer = PdfWriter.getInstance(document, new FileOutputStream(RESULT));
        // step 3
        document.open();
        // step 4
        PdfPTable table;
        Calendar calendar;
        PdfContentByte canvas = writer.getDirectContent();
        // Loop over the months
        for (int month = 0; month < 12; month++) {
            calendar = new GregorianCalendar(year, month, 1);
            // draw the background
            drawImageAndText(canvas, calendar);
            // create a table with 7 columns
            table = new PdfPTable(7);
            table.setTotalWidth(504);
            // add the name of the month
            table.getDefaultCell().setBackgroundColor(BaseColor.WHITE);
            table.addCell(getMonthCell(calendar, locale));
            int daysInMonth = calendar.getActualMaximum(Calendar.DAY_OF_MONTH);
            int day = 1;
            int position = 2;
            // add empty cells
            while (position != calendar.get(Calendar.DAY_OF_WEEK)) {
                position = (position % 7) + 1;
                table.addCell("");
            }
            // add cells for each day
            while (day <= daysInMonth) {
                calendar = new GregorianCalendar(year, month, day++);
                table.addCell(getDayCell(calendar, locale));
            }
            // complete the table
            table.completeRow();
            // write the table to an absolute position
            table.writeSelectedRows(0, -1, 169, table.getTotalHeight() + 18, canvas);
            document.newPage();
        }
        // step 5
        document.close();
    }
 
    /**
     * Draws the image of the month to the calendar.
     * @param canvas the direct content layer
     * @param calendar the month (to know which picture to use)
     * @throws DocumentException
     * @throws IOException
     */
    public void drawImageAndText(PdfContentByte canvas, Calendar calendar) throws DocumentException, IOException {
        // get the image
        Image img = Image.getInstance(String.format(RESOURCE, calendar));
        img.scaleToFit(PageSize.A4.getHeight(), PageSize.A4.getWidth());
        img.setAbsolutePosition(
                (PageSize.A4.getHeight() - img.getScaledWidth()) / 2,
                (PageSize.A4.getWidth() - img.getScaledHeight()) / 2);
        canvas.addImage(img);
        // add metadata
        canvas.saveState();
        canvas.setCMYKColorFill(0x00, 0x00, 0x00, 0x80);
        Phrase p = new Phrase(String.format(
                "%s - \u00a9 Katharine Osborne",
                content.getProperty(String.format("%tm.jpg", calendar))), small);
        ColumnText.showTextAligned(canvas, Element.ALIGN_LEFT, p, 5, 5, 0);
        p = new Phrase("Calendar generated using iText - example for the book iText in Action 2nd Edition", small);
        ColumnText.showTextAligned(canvas, Element.ALIGN_RIGHT, p, 839, 5, 0);
        canvas.restoreState();
    }
    
    /**
     * Creates a PdfPCell with the name of the month
     * @param calendar a date
     * @param locale a locale
     * @return a PdfPCell with rowspan 7, containing the name of the month
     */
    public PdfPCell getMonthCell(Calendar calendar, Locale locale) {
        PdfPCell cell = new PdfPCell();
        cell.setColspan(7);
        cell.setBackgroundColor(BaseColor.WHITE);
        cell.setUseDescender(true);
        Paragraph p = new Paragraph(String.format(locale, "%1$tB %1$tY", calendar), bold);
        p.setAlignment(Element.ALIGN_CENTER);
        cell.addElement(p);
        return cell;
    }
 
    /**
     * Creates a PdfPCell for a specific day
     * @param calendar a date
     * @param locale a locale
     * @return a PdfPCell
     */
    public PdfPCell getDayCell(Calendar calendar, Locale locale) {
        PdfPCell cell = new PdfPCell();
        cell.setPadding(3);
        // set the background color, based on the type of day
        if (isSunday(calendar))
            cell.setBackgroundColor(BaseColor.GRAY);
        else if (isSpecialDay(calendar))
            cell.setBackgroundColor(BaseColor.LIGHT_GRAY);
        else
            cell.setBackgroundColor(BaseColor.WHITE);
        // set the content in the language of the locale
        Chunk chunk = new Chunk(String.format(locale, "%1$ta", calendar), small);
        chunk.setTextRise(8);
        // a paragraph with the day
        Paragraph p = new Paragraph(chunk);
        // a separator
        p.add(new Chunk(new VerticalPositionMark()));
        // and the number of the day
        p.add(new Chunk(String.format(locale, "%1$te", calendar), normal));
        cell.addElement(p);
        return cell;
    }
    
    /**
     * Returns true for Sundays.
     * @param calendar a date
     * @return true for Sundays
     */
    public boolean isSunday(Calendar calendar) {
        if (calendar.get(Calendar.DAY_OF_WEEK) == Calendar.SUNDAY) {
            return true;
        }
        return false;
    }
    
    /**
     * Returns true if the date was found in a list with special days (holidays).
     * @param calendar a date
     * @return true for holidays
     */
    public boolean isSpecialDay(Calendar calendar) {
        if (calendar.get(Calendar.DAY_OF_WEEK) == Calendar.SATURDAY)
            return true;
        if (specialDays.containsKey(String.format("%1$tm%1$td", calendar)))
            return true;
        return false;
    }
}
Zhang.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.SQLException;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoFactory;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.pdf.PdfContentByte;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
 
public class Zhang {
 
    /** The resulting PDF file. */
    public static final String RESULT = "results/part1/chapter04/zhang.pdf";
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @throws    DocumentException 
     * @throws    IOException
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws IOException, DocumentException, SQLException {
        // Create a database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter writer
            = PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        // Create a table and fill it with movies
        List<Movie> movies = PojoFactory.getMovies(connection, 3);
        PdfPTable table = new PdfPTable(new float[] { 1, 5, 5, 1});
        for (Movie movie : movies) {
            table.addCell(String.valueOf(movie.getYear()));
            table.addCell(movie.getMovieTitle());
            table.addCell(movie.getOriginalTitle());
            table.addCell(String.valueOf(movie.getDuration()));
        }
        // set the total width of the table
        table.setTotalWidth(600);
        PdfContentByte canvas = writer.getDirectContent();
        // draw the first two columns on one page
        table.writeSelectedRows(0, 2, 0, -1, 236, 806, canvas);
        document.newPage();
        // draw the remaining two columns on the next page
        table.writeSelectedRows(2, -1, 0, -1, 36, 806, canvas);
        // step 5
        document.close();
        // close the database connection
        connection.close();
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args) throws IOException, DocumentException, SQLException {
        new Zhang().createPdf(RESULT);
    }
}
ColumnTable.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
 
package part1.chapter04;
 
import java.io.FileOutputStream;
import java.io.IOException;
import java.sql.Date;
import java.sql.SQLException;
import java.util.List;
 
import com.lowagie.database.DatabaseConnection;
import com.lowagie.database.HsqldbConnection;
import com.lowagie.filmfestival.Movie;
import com.lowagie.filmfestival.PojoFactory;
import com.lowagie.filmfestival.Screening;
import com.itextpdf.text.Document;
import com.itextpdf.text.DocumentException;
import com.itextpdf.text.Element;
import com.itextpdf.text.Font;
import com.itextpdf.text.PageSize;
import com.itextpdf.text.Phrase;
import com.itextpdf.text.Font.FontFamily;
import com.itextpdf.text.pdf.ColumnText;
import com.itextpdf.text.pdf.PdfPTable;
import com.itextpdf.text.pdf.PdfWriter;
import com.itextpdf.text.BaseColor;
 
public class ColumnTable {
 
    public static final String RESULT = "results/part1/chapter04/column_table.pdf";
 
    /**
     * Creates a PDF document.
     * @param filename the path to the new PDF document
     * @throws    DocumentException 
     * @throws    IOException
     * @throws    SQLException
     */
    public void createPdf(String filename)
        throws SQLException, DocumentException, IOException {
        // Create the database connection
        DatabaseConnection connection = new HsqldbConnection("filmfestival");
        // step 1
        Document document = new Document(PageSize.A4.rotate());
        // step 2
        PdfWriter writer
            = PdfWriter.getInstance(document, new FileOutputStream(filename));
        // step 3
        document.open();
        // step 4
        ColumnText column = new ColumnText(writer.getDirectContent());
        List<Date> days = PojoFactory.getDays(connection);
        // COlumn definition
        float[][] x = {
                { document.left(), document.left() + 380 },
                { document.right() - 380, document.right() }
            };
        // Loop over the festival days
        for (Date day : days) {
            // add content to the column
            column.addElement(getTable(connection, day));
            int count = 0;
            float height = 0;
            int status = ColumnText.START_COLUMN;
            // render the column as long as it has content
            while (ColumnText.hasMoreText(status)) {
                // add the top-level header to each new page
                if (count == 0) {
                    height = addHeaderTable(
                        document, day, writer.getPageNumber());
                }
                // set the dimensions of the current column
                column.setSimpleColumn(
                    x[count][0], document.bottom(),
                    x[count][1], document.top() - height - 10);
                // render as much content as possible
                status = column.go();
                // go to a new page if you've reached the last column
                if (++count > 1) {
                    count = 0;
                    document.newPage();
                }
            }
            document.newPage();
        }
        // step 5
        document.close();
        // Close the database connection
        connection.close();
    }
    
    /**
     * Add a header table to the document
     * @param document The document to which you want to add a header table
     * @param day The day that needs to be shown in the header table
     * @param page The page number that has to be shown in the header
     * @return the height of the resulting header table
     * @throws DocumentException
     */
    public float addHeaderTable(Document document, Date day, int page)
        throws DocumentException {
        PdfPTable header = new PdfPTable(3);
        header.setWidthPercentage(100);
        header.getDefaultCell().setBackgroundColor(BaseColor.BLACK);
        Font font = new Font(FontFamily.HELVETICA, 12, Font.BOLD, BaseColor.WHITE);
        Phrase p = new Phrase("Foobar Film Festival", font);
        header.addCell(p);
        header.getDefaultCell().setHorizontalAlignment(Element.ALIGN_CENTER);
        p = new Phrase(day.toString(), font);
        header.addCell(p);
        header.getDefaultCell().setHorizontalAlignment(Element.ALIGN_RIGHT);
        p = new Phrase(String.format("page %d", page), font);
        header.addCell(p);
        document.add(header);
        return header.getTotalHeight();
    }
 
    /**
     * Creates a table with movie screenings for a specific day
     * @param connection a connection to the database
     * @param day a day
     * @return a table with screenings
     * @throws SQLException
     * @throws DocumentException
     * @throws IOException
     */
    public PdfPTable getTable(DatabaseConnection connection, Date day)
        throws SQLException, DocumentException, IOException {
        PdfPTable table = new PdfPTable(new float[] { 2, 1, 2, 5, 1 });
        table.setWidthPercentage(100f);
        table.getDefaultCell().setUseAscender(true);
        table.getDefaultCell().setUseDescender(true);
        table.getDefaultCell().setBackgroundColor(BaseColor.LIGHT_GRAY);
        for (int i = 0; i < 2; i++) {
            table.addCell("Location");
            table.addCell("Time");
            table.addCell("Run Length");
            table.addCell("Title");
            table.addCell("Year");
        }
        table.getDefaultCell().setBackgroundColor(null);
        table.setHeaderRows(2);
        table.setFooterRows(1);
        List<Screening> screenings = PojoFactory.getScreenings(connection, day);
        Movie movie;
        for (Screening screening : screenings) {
            movie = screening.getMovie();
            table.addCell(screening.getLocation());
            table.addCell(String.format("%1$tH:%1$tM", screening.getTime()));
            table.addCell(String.format("%d '", movie.getDuration()));
            table.addCell(movie.getMovieTitle());
            table.addCell(String.valueOf(movie.getYear()));
        }
        return table;
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void main(String[] args)
        throws SQLException, DocumentException, IOException {
        new ColumnTable().createPdf(RESULT);
    }
}
MyFirstTable.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class MyFirstTable : IWriter {
// ===========================================================================
    public virtual void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        document.Add(CreateFirstTable());
      }
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates our first table
     * @return our first table
     */
    public static PdfPTable CreateFirstTable() {
    // a table with three columns
      PdfPTable table = new PdfPTable(3);
      // the cell object
      PdfPCell cell;
      // we add a cell with colspan 3
      cell = new PdfPCell(new Phrase("Cell with colspan 3"));
      cell.Colspan = 3;
      table.AddCell(cell);
      // now we add a cell with rowspan 2
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      // we add the four remaining cells with addCell()
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }
// ===========================================================================
  }
}
ColumnWidths.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO; 
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class ColumnWidths : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = CreateTable1();
        document.Add(table);
        table = CreateTable2();
        table.SpacingBefore = 5;
        table.SpacingAfter = 5;
        document.Add(table);
        table = CreateTable3();
        document.Add(table);
        table = CreateTable4();
        table.SpacingBefore = 5;
        table.SpacingAfter = 5;
        document.Add(table);
        table = CreateTable5();
        document.Add(table);
      }
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table; widths are set with setWidths().
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable CreateTable1() {
      PdfPTable table = new PdfPTable(3);
      table.WidthPercentage  =288 / 5.23f;
      table.SetWidths(new int[]{2, 1, 1});
      PdfPCell cell;
      cell = new PdfPCell(new Phrase("Table 1"));
      cell.Colspan = 3;
      table.AddCell(cell);
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table; widths are set with setWidths().
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable CreateTable2() {
      PdfPTable table = new PdfPTable(3);
      table.TotalWidth = 288;
      table.LockedWidth = true;
      table.SetWidths(new float[]{2, 1, 1});
      PdfPCell cell;
      cell = new PdfPCell(new Phrase("Table 2"));
      cell.Colspan = 3;
      table.AddCell(cell);
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table; widths are set in the constructor.
     * @return a PdfPTable
     * @throws DocumentException
     */
    public static PdfPTable CreateTable3() {
      PdfPTable table = new PdfPTable(new float[]{ 2, 1, 1 });
      table.WidthPercentage = 55.067f;
      PdfPCell cell;
      cell = new PdfPCell(new Phrase("Table 3"));
      cell.Colspan = 3;
      table.AddCell(cell);
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table; widths are set with special setWidthPercentage() method.
     * @return a PdfPTable
     */
    public static PdfPTable CreateTable4() {
      PdfPTable table = new PdfPTable(3);
      Rectangle rect = new Rectangle(523, 770);
      table.SetWidthPercentage(new float[]{ 144, 72, 72 }, rect);
      PdfPCell cell;
      cell = new PdfPCell(new Phrase("Table 4"));
      cell.Colspan =3;
      table.AddCell(cell);
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table; widths are set with setTotalWidth().
     * @return a PdfPTable
     */
    public static PdfPTable CreateTable5() {
      PdfPTable table = new PdfPTable(3);
      table.SetTotalWidth(new float[]{ 144, 72, 72 });
      table.LockedWidth = true;
      PdfPCell cell;
      cell = new PdfPCell(new Phrase("Table 5"));
      cell.Colspan = 3 ;
      table.AddCell(cell);
      cell = new PdfPCell(new Phrase("Cell with rowspan 2"));
      cell.Rowspan = 2;
      table.AddCell(cell);
      table.AddCell("row 1; cell 1");
      table.AddCell("row 1; cell 2");
      table.AddCell("row 2; cell 1");
      table.AddCell("row 2; cell 2");
      return table;
    }    
// ===========================================================================
  }
}
TableAlignment.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class TableAlignment : MyFirstTable {
// ===========================================================================
    public override void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = CreateFirstTable();
        table.WidthPercentage = 50;
        table.HorizontalAlignment = Element.ALIGN_LEFT;
        document.Add(table);
        table.HorizontalAlignment = Element.ALIGN_CENTER;
        document.Add(table);
        table.HorizontalAlignment = Element.ALIGN_RIGHT;
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
MovieTextMode.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using System.Linq;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class MovieTextMode : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        document.Add(new Paragraph("Movies:"));
        IEnumerable<Movie> movies = PojoFactory.GetMovies();
        foreach (Movie movie in movies) {
          PdfPTable table = new PdfPTable(2);
          table.SetWidths(new int[]{1, 4});
          PdfPCell cell;
          cell = new PdfPCell(new Phrase(movie.Title, FilmFonts.BOLD));
          cell.HorizontalAlignment = Element.ALIGN_CENTER;
          cell.Colspan = 2;
          table.AddCell(cell);
          if (!string.IsNullOrEmpty(movie.OriginalTitle)) {
            cell = new PdfPCell(PojoToElementFactory.GetOriginalTitlePhrase(movie));
            cell.Colspan = 2;
            cell.HorizontalAlignment = Element.ALIGN_RIGHT;
            table.AddCell(cell);
          }
          List<Director> directors = movie.Directors;
          cell = new PdfPCell(new Phrase("Directors:"));
          cell.Rowspan = directors.Count;
          cell.VerticalAlignment = Element.ALIGN_MIDDLE;
          table.AddCell(cell);
          int count = 0;
          foreach (Director pojo in directors) {
            cell = new PdfPCell(PojoToElementFactory.GetDirectorPhrase(pojo));
            cell.Indent = (10 * count++);
            table.AddCell(cell);
          }
          table.DefaultCell.HorizontalAlignment = Element.ALIGN_RIGHT;
          table.AddCell("Year:");
          table.AddCell(movie.Year.ToString());
          table.AddCell("Run length:");
          table.AddCell(movie.Duration.ToString());
          List<Country> countries = movie.Countries;
          cell = new PdfPCell(new Phrase("Countries:"));
          cell.Rowspan = countries.Count;
          cell.VerticalAlignment = Element.ALIGN_BOTTOM;
          table.AddCell(cell);
          table.DefaultCell.HorizontalAlignment = Element.ALIGN_CENTER;
          foreach (Country country in countries) {
            table.AddCell(country.Name);
          }
          document.Add(table);
        }        
      }
    }
// ===========================================================================
  }
}
Spacing.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class Spacing : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = new PdfPTable(2);
        table.WidthPercentage = 100;
        Phrase p = new Phrase(
          "Dr. iText or: How I Learned to Stop Worrying " +
          "and Love the Portable Document Format."
        );
        PdfPCell cell = new PdfPCell(p);
        table.AddCell("default leading / spacing");
        table.AddCell(cell);
        table.AddCell("absolute leading: 20");
        cell.SetLeading(20f, 0f);
        table.AddCell(cell);
        table.AddCell("absolute leading: 3; relative leading: 1.2");
        cell.SetLeading(3f, 1.2f);
        table.AddCell(cell);
        table.AddCell("absolute leading: 0; relative leading: 1.2");
        cell.SetLeading(0f, 1.2f);
        table.AddCell(cell);
        table.AddCell("no leading at all");
        cell.SetLeading(0f, 0f);
        table.AddCell(cell);
        cell = new PdfPCell(new Phrase(
            "Dr. iText or: How I Learned to Stop Worrying and Love PDF"));
        table.AddCell("padding 10");
        cell.Padding = 10;
        table.AddCell(cell);
        table.AddCell("padding 0");
        cell.Padding = 0;
        table.AddCell(cell);
        table.AddCell("different padding for left, right, top and bottom");
        cell.PaddingLeft = 20;
        cell.PaddingRight = 50;
        cell.PaddingTop = 0;
        cell.PaddingBottom = 5;
        table.AddCell(cell);
        p = new Phrase("iText in Action Second Edition");
        table.DefaultCell.Padding = 2;
        table.DefaultCell.UseAscender = false;
        table.DefaultCell.UseDescender = false;
        table.AddCell("padding 2; no ascender, no descender");
        table.AddCell(p);
        table.DefaultCell.UseAscender = true;
        table.DefaultCell.UseDescender = false;
        table.AddCell("padding 2; ascender, no descender");
        table.AddCell(p);
        table.DefaultCell.UseAscender = false;
        table.DefaultCell.UseDescender = true;
        table.AddCell("padding 2; descender, no ascender");
        table.AddCell(p);
        table.DefaultCell.UseAscender = true;
        table.DefaultCell.UseDescender = true;
        table.AddCell("padding 2; ascender and descender");
        cell.Padding = 2;
        cell.UseAscender = true;
        cell.UseDescender = true;
        table.AddCell(p);
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
TableHeight.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class TableHeight : MyFirstTable {
// ===========================================================================
    public override void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = CreateFirstTable();
        document.Add(new Paragraph(string.Format(
          "Table height before document.Add(): {0}",
          table.TotalHeight)
        ));
        document.Add(new Paragraph(
            string.Format("Height of the first row: {0}",
                table.GetRowHeight(0))
         ));
        document.Add(table);
        document.Add(new Paragraph(string.Format(
          "Table height after document.Add(): {0}",
          table.TotalHeight
        )));
        document.Add(new Paragraph(string.Format(
          "Height of the first row: {0}",
          table.GetRowHeight(0)
        )));
        table = CreateFirstTable();
        document.Add(new Paragraph( string.Format(
          "Table height before setTotalWidth(): {0}",
          table.TotalHeight
        )));
        document.Add(new Paragraph(string.Format(
          "Height of the first row: {0}",
          table.GetRowHeight(0)
        )));
        table.TotalWidth = 50;
        table.LockedWidth = true;
        document.Add( new Paragraph(string.Format(
          "Table height after setTotalWidth(): {0}",
          table.TotalHeight
        )));
        document.Add(new Paragraph(string.Format(
          "Height of the first row: {0}",
          table.GetRowHeight(0)
        )));
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
CellHeights.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class CellHeights : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = new PdfPTable(2);
        // a long phrase
        Phrase p = new Phrase(
          "Dr. iText or: How I Learned to Stop Worrying and Love PDF."
        );
        PdfPCell cell = new PdfPCell(p);
        // the prhase is wrapped
        table.AddCell("wrap");
        cell.NoWrap = false;
        table.AddCell(cell);
        // the phrase isn't wrapped
        table.AddCell("no wrap");
        cell.NoWrap = true;
        table.AddCell(cell);
        // a long phrase with newlines
        p = new Phrase(
            "Dr. iText or:\nHow I Learned to Stop Worrying\nand Love PDF.");
        cell = new PdfPCell(p);
        // the phrase fits the fixed height
        table.AddCell("fixed height (more than sufficient)");
        cell.FixedHeight = 72f;
        table.AddCell(cell);
        // the phrase doesn't fit the fixed height
        table.AddCell("fixed height (not sufficient)");
        cell.FixedHeight = 36f;
        table.AddCell(cell);
        // The minimum height is exceeded
        table.AddCell("minimum height");
        cell = new PdfPCell(new Phrase("Dr. iText"));
        cell.MinimumHeight = 36f;
        table.AddCell(cell);
        // The last row is extended
        table.ExtendLastRow = true;
        table.AddCell("extend last row");
        table.AddCell(cell);
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
RotationAndColors.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class RotationAndColors : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = new PdfPTable(4);
        table.SetWidths(new int[]{ 1, 3, 3, 3 });
        table.WidthPercentage = 100;
        PdfPCell cell;
        // row 1, cell 1
        cell = new PdfPCell(new Phrase("COLOR"));
        cell.Rotation = 90;
        cell.VerticalAlignment = Element.ALIGN_TOP;
        table.AddCell(cell);
        // row 1, cell 2
        cell = new PdfPCell(new Phrase("red / no borders"));
        cell.Border = Rectangle.NO_BORDER;
        cell.BackgroundColor = BaseColor.RED;
        table.AddCell(cell);
        // row 1, cell 3
        cell = new PdfPCell(new Phrase("green / black bottom border"));
        cell.Border = Rectangle.BOTTOM_BORDER;
        cell.BorderColorBottom = BaseColor.BLACK;
        cell.BorderWidthBottom = 10f;
        cell.BackgroundColor = BaseColor.GREEN;
        table.AddCell(cell);
        // row 1, cell 4
        cell = new PdfPCell(new Phrase(
          "cyan / blue top border + padding"
        ));
        cell.Border  = Rectangle.TOP_BORDER;
        cell.UseBorderPadding = true;
        cell.BorderWidthTop = 5f;
        cell.BorderColorTop = BaseColor.BLUE;
        cell.BackgroundColor = BaseColor.CYAN;
        table.AddCell(cell);
        // row 2, cell 1
        cell = new PdfPCell(new Phrase("GRAY"));
        cell.Rotation = 90;
        cell.VerticalAlignment = Element.ALIGN_MIDDLE;
        table.AddCell(cell);
        // row 2, cell 2
        cell = new PdfPCell(new Phrase("0.6"));
        cell.Border = Rectangle.NO_BORDER;
        cell.GrayFill = 0.6f;
        table.AddCell(cell);
        // row 2, cell 3
        cell = new PdfPCell(new Phrase("0.75"));
        cell.Border = Rectangle.NO_BORDER;
        cell.GrayFill = 0.75f;
        table.AddCell(cell);
        // row 2, cell 4
        cell = new PdfPCell(new Phrase("0.9"));
        cell.Border = Rectangle.NO_BORDER;
        cell.GrayFill = 0.9f;
        table.AddCell(cell);
        // row 3, cell 1
        cell = new PdfPCell(new Phrase("BORDERS"));
        cell.Rotation = 90;
        cell.VerticalAlignment = Element.ALIGN_BOTTOM;
        table.AddCell(cell);
        // row 3, cell 2
        cell = new PdfPCell(new Phrase("different borders"));
        cell.BorderWidthLeft = 16f;
        cell.BorderWidthBottom = 12f;
        cell.BorderWidthRight = 8f;
        cell.BorderWidthTop = 4f;
        cell.BorderColorLeft = BaseColor.RED;
        cell.BorderColorBottom = BaseColor.ORANGE;
        cell.BorderColorRight = BaseColor.YELLOW;
        cell.BorderColorTop = BaseColor.GREEN;
        table.AddCell(cell);
        // row 3, cell 3
        cell = new PdfPCell(new Phrase("with correct padding"));
        cell.UseBorderPadding = true;
        cell.BorderWidthLeft = 16f;
        cell.BorderWidthBottom = 12f;
        cell.BorderWidthRight = 8f;
        cell.BorderWidthTop = 4f;
        cell.BorderColorLeft = BaseColor.RED;
        cell.BorderColorBottom = BaseColor.ORANGE;
        cell.BorderColorRight = BaseColor.YELLOW;
        cell.BorderColorTop = BaseColor.GREEN;
        table.AddCell(cell);
        // row 3, cell 4
        cell = new PdfPCell(new Phrase("red border"));
        cell.BorderWidth = 8f;
        cell.BorderColor = BaseColor.RED;
        table.AddCell(cell);
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
MovieCompositeMode.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
  /*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using System.Linq;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class MovieCompositeMode : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        document.Add(new Paragraph("Movies:"));
        IEnumerable<Movie> movies = PojoFactory.GetMovies();
        List list;
        PdfPCell cell;
        string RESOURCE = Utility.ResourcePosters;
        foreach (Movie movie in movies) {
      // a table with two columns
          PdfPTable table = new PdfPTable(new float[]{1, 7});
          table.WidthPercentage = 100;
          table.SpacingBefore = 5;
          // a cell with an image
          cell = new PdfPCell(
            Image.GetInstance(Path.Combine(RESOURCE, movie.Imdb + ".jpg")),
            true
          );
          cell.Border = PdfPCell.NO_BORDER;
          table.AddCell(cell);
          cell = new PdfPCell();
          // a cell with paragraphs and lists
          Paragraph p = new Paragraph(movie.Title, FilmFonts.BOLD);
          p.Alignment = Element.ALIGN_CENTER;
          p.SpacingBefore = 5;
          p.SpacingAfter = 5;
          cell.AddElement(p);
          cell.Border = PdfPCell.NO_BORDER;
          if (!string.IsNullOrEmpty(movie.OriginalTitle)) {
            p = new Paragraph(movie.OriginalTitle, FilmFonts.ITALIC);
            p.Alignment = Element.ALIGN_RIGHT;
            cell.AddElement(p);
          }
          list = PojoToElementFactory.GetDirectorList(movie);
          list.IndentationLeft = 30;
          cell.AddElement(list);
          p = new Paragraph(
            string.Format("Year: {0}", movie.Year), 
            FilmFonts.NORMAL
          );
          p.IndentationLeft = 15;
          p.Leading = 24;
          cell.AddElement(p);
          p = new Paragraph(
            string.Format("Run length: {0}", movie.Duration), 
            FilmFonts.NORMAL
          );
          p.Leading = 14;
          p.IndentationLeft = 30;
          cell.AddElement(p);
          list = PojoToElementFactory.GetCountryList(movie);
          list.IndentationLeft = 40;
          cell.AddElement(list);
          table.AddCell(cell);
          // every movie corresponds with one table
          document.Add(table);
          // but the result looks like one big table
        }
      }
    }
// ===========================================================================
  }
}
XMen.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class XMen : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        string RESOURCE = Utility.ResourcePosters;
        // we'll use 4 images in this example
        Image[] img = {
          Image.GetInstance(Path.Combine(RESOURCE, "0120903.jpg")),
          Image.GetInstance(Path.Combine(RESOURCE, "0290334.jpg")),
          Image.GetInstance(Path.Combine(RESOURCE, "0376994.jpg")),
          Image.GetInstance(Path.Combine(RESOURCE, "0348150.jpg"))
        };
        // Creates a table with 6 columns
        PdfPTable table = new PdfPTable(6);
        table.WidthPercentage = 100;
        // first movie
        table.DefaultCell.HorizontalAlignment = Element.ALIGN_CENTER;
        table.DefaultCell.VerticalAlignment = Element.ALIGN_TOP;
        table.AddCell("X-Men");
        // we wrap he image in a PdfPCell
        PdfPCell cell = new PdfPCell(img[0]);
        table.AddCell(cell);
        // second movie
        table.DefaultCell.VerticalAlignment = Element.ALIGN_MIDDLE;
        table.AddCell("X2");
        // we wrap the image in a PdfPCell and let iText scale it
        cell = new PdfPCell(img[1], true);
        table.AddCell(cell);
        // third movie
        table.DefaultCell.VerticalAlignment = Element.ALIGN_BOTTOM;
        table.AddCell("X-Men: The Last Stand");
        // we add the image with addCell()
        table.AddCell(img[2]);
        // fourth movie
        table.AddCell("Superman Returns");
        cell = new PdfPCell();
        // we add it with addElement(); it can only take 50% of the width.
        img[3].WidthPercentage = 50;
        cell.AddElement(img[3]);
        table.AddCell(cell);
        // we complete the table (otherwise the last row won't be rendered)
        table.CompleteRow();
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
NestedTable.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using iTextSharp.text;
using iTextSharp.text.pdf;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class NestedTable : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        PdfPTable table = new PdfPTable(4);
        PdfPTable nested1 = new PdfPTable(2);
        nested1.AddCell("1.1");
        nested1.AddCell("1.2");
        PdfPTable nested2 = new PdfPTable(1);
        nested2.AddCell("12.1");
        nested2.AddCell("12.2");
        for (int k = 0; k < 16; ++k) {
          if (k == 1) {
            table.AddCell(nested1);
          } else if (k == 12) {
            table.AddCell(new PdfPCell(nested2));
          } else {
            table.AddCell("cell " + k);
          }
        }
        document.Add(table);
      }
    }
// ===========================================================================
  }
}
NestedTables.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using System.Text.RegularExpressions;
using iTextSharp.text;
using iTextSharp.text.pdf;
using iTextSharp.text.html;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class NestedTables : IWriter {
// ===========================================================================
    /** Collection containing all the Images */
    public Dictionary<String, Image> images = new Dictionary<String, Image>();
    /** Path to the resources. */
    public readonly string RESOURCE = Utility.ResourcePosters;
// ---------------------------------------------------------------------------
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        List<string> days = PojoFactory.GetDays();
        foreach (string day in days) {
          document.Add(GetTable(day));
          document.NewPage();
        }
      }
    }
// ---------------------------------------------------------------------------   
    /**
     * Creates a table with all the screenings of a specific day.
     * The table is composed of nested tables.
     * @param day a film festival day
     * @return a table
     */
    public PdfPTable GetTable(string day) {
      // Create a table with only one column
      PdfPTable table = new PdfPTable(1);
      table.WidthPercentage = 100f;
      // add the cell with the date
      Font f = new Font();
      f.Color = BaseColor.WHITE;
      PdfPCell cell = new PdfPCell(new Phrase(day, f));
      cell.BackgroundColor = BaseColor.BLACK;
      cell.HorizontalAlignment = Element.ALIGN_CENTER;
      table.AddCell(cell);
      // add the movies as nested tables
      List<Screening> screenings = PojoFactory.GetScreenings(day);
      foreach (Screening screening in screenings) {
        table.AddCell(GetTable(screening));
      }
      return table;
    }
// ---------------------------------------------------------------------------   
    /**
     * Create a table with information about a movie.
     * @param screening a Screening
     * @return a table
     */
    private PdfPTable GetTable(Screening screening) {
      // Create a table with 4 columns
      PdfPTable table = new PdfPTable(4);
      table.SetWidths(new int[]{1, 5, 10, 10});
      // Get the movie
      Movie movie = screening.movie;
      // A cell with the title as a nested table spanning the complete row
      PdfPCell cell = new PdfPCell();
      // nesting is done with addElement() in this example
      cell.AddElement(FullTitle(screening));
      cell.Colspan = 4;
      cell.Border = PdfPCell.NO_BORDER;
      BaseColor color = WebColors.GetRGBColor(
        "#" + movie.entry.category.color
      );
      cell.BackgroundColor = color;
      table.AddCell(cell);
      // empty cell
      cell = new PdfPCell();
      cell.Border = PdfPCell.NO_BORDER;
      cell.UseAscender = true;
      cell.UseDescender = true;
      table.AddCell(cell);
      // cell with the movie poster
      cell = new PdfPCell(GetImage(movie.Imdb));
      cell.Border = PdfPCell.NO_BORDER;
      table.AddCell(cell);
      // cell with the list of directors
      cell = new PdfPCell();
      cell.AddElement(PojoToElementFactory.GetDirectorList(movie));
      cell.Border = PdfPCell.NO_BORDER;
      cell.UseAscender = true;
      cell.UseDescender = true;
      table.AddCell(cell);
      // cell with the list of countries
      cell = new PdfPCell();
      cell.AddElement(PojoToElementFactory.GetCountryList(movie));
      cell.Border = PdfPCell.NO_BORDER;
      cell.UseAscender =  true;
      cell.UseDescender = true;
      table.AddCell(cell);
      return table;
    }
// ---------------------------------------------------------------------------       
    /**
     * Create a table with the full movie title
     * @param screening a Screening object
     * @return a table
     */
    private static PdfPTable FullTitle(Screening screening) {
      PdfPTable table = new PdfPTable(3);
      table.SetWidths(new int[]{3, 15, 2});
      table.WidthPercentage = 100;
      // cell 1: location and time
      PdfPCell cell = new PdfPCell();
      cell.Border = PdfPCell.NO_BORDER;
      cell.BackgroundColor = BaseColor.WHITE;
      cell.UseAscender = true;
      cell.UseDescender = true;
      String s = string.Format(
        // "{0} \u2013 %2$tH:%2$tM",
        "{0} \u2013 {1}",
        screening.Location, 
        screening.Time.Substring(0, 5)
        // screening.Time().getTime()
      );
      cell.AddElement(new Paragraph(s));
      table.AddCell(cell);
      // cell 2: English and original title 
      Movie movie = screening.movie;
      Paragraph p = new Paragraph();
      p.Add(new Phrase(movie.MovieTitle, FilmFonts.BOLD));
      p.Leading = 16;
      if (!string.IsNullOrEmpty(movie.OriginalTitle)) {
        p.Add(new Phrase(" (" + movie.OriginalTitle + ")"));
      }
      cell = new PdfPCell();
      cell.AddElement(p);
      cell.Border = PdfPCell.NO_BORDER;
      cell.UseAscender = true;
      cell.UseDescender = true;
      table.AddCell(cell);
      // cell 3 duration
      cell = new PdfPCell();
      cell.Border = PdfPCell.NO_BORDER;
      cell.BackgroundColor = BaseColor.WHITE;
      cell.UseAscender = true;
      cell.UseDescender = true;
      // p = new Paragraph(String.format("%d'", movie.getDuration()));
      p = new Paragraph(movie.Duration.ToString() + "'");
      p.Alignment = Element.ALIGN_CENTER;
      cell.AddElement(p);
      table.AddCell(cell);
      return table;
    }
// ---------------------------------------------------------------------------       
    /**
     * Create an image with a movie poster.
     * @param imdb an Internet Movie Database id
     * @return an Image
     * @throws DocumentException
     * @throws IOException
     */
    public Image GetImage(String imdb) {
      if ( images.ContainsKey(imdb) ) {
        return images[imdb];
      }
      else {
        Image img = Image.GetInstance(Path.Combine(RESOURCE, imdb + ".jpg"));
        img.ScaleToFit(80, 72);
        images.Add(imdb, img);
        return img;
      }
    } 
// ===========================================================================
  }
}
HeaderFooter1.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class HeaderFooter1 : IWriter {
// ===========================================================================
    public virtual void Write(Stream stream) {
      // step 1
      using (Document document = new Document(PageSize.A4.Rotate())) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        List<string> days = PojoFactory.GetDays();
        foreach (string day in days) {
          document.Add(GetTable(day));
          document.NewPage();
        }
      }
    }
// ---------------------------------------------------------------------------    
    /**
     * Creates a table with screenings.
     * @param day a film festival day
     * @return a table with screenings
     */
    public PdfPTable GetTable(string day) {
    // Create a table with 7 columns
      PdfPTable table = new PdfPTable(new float[] { 2, 1, 2, 5, 1, 3, 2 });
      table.WidthPercentage = 100f;
      table.DefaultCell.UseAscender = true;
      table.DefaultCell.UseDescender = true;
      // Add the first header row
      Font f = new Font();
      f.Color = BaseColor.WHITE;
      PdfPCell cell = new PdfPCell(new Phrase(day, f));
      cell.BackgroundColor = BaseColor.BLACK;
      cell.HorizontalAlignment = Element.ALIGN_CENTER;
      cell.Colspan = 7;
      table.AddCell(cell);
      // Add the second header row twice
      table.DefaultCell.BackgroundColor = BaseColor.LIGHT_GRAY;
      for (int i = 0; i < 2; i++) {
        table.AddCell("Location");
        table.AddCell("Time");
        table.AddCell("Run Length");
        table.AddCell("Title");
        table.AddCell("Year");
        table.AddCell("Directors");
        table.AddCell("Countries");
      }
      table.DefaultCell.BackgroundColor = null;
      // There are three special rows
      table.HeaderRows = 3;
      // One of them is a footer
      table.FooterRows = 1;
      // Now let's loop over the screenings
      List<Screening> screenings = PojoFactory.GetScreenings(day);
      Movie movie;
      foreach (Screening screening in screenings) {
        movie = screening.movie;
        table.AddCell(screening.Location);
        table.AddCell(screening.Time.Substring(0, 5));
        table.AddCell(movie.Duration.ToString() + " '");
        table.AddCell(movie.MovieTitle);
        table.AddCell(movie.Year.ToString());
        cell = new PdfPCell();
        cell.UseAscender = true;
        cell.UseDescender = true;
        cell.AddElement(PojoToElementFactory.GetDirectorList(movie));
        table.AddCell(cell);
        cell = new PdfPCell();
        cell.UseAscender = true;
        cell.UseDescender = true;
        cell.AddElement(PojoToElementFactory.GetCountryList(movie));
        table.AddCell(cell);
      }
      return table;
    }    
// ===========================================================================
  }
}
HeaderFooter2.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class HeaderFooter2 : HeaderFooter1 {
// ===========================================================================
    public override void Write(Stream stream) {
      // step 1
      using (Document document = new Document(PageSize.A4.Rotate())) {
        // step 2
        PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        List<string> days = PojoFactory.GetDays();
        foreach (string day in days) {
          PdfPTable table = GetTable(day);
          table.SplitLate = false;
          document.Add(table);
          document.NewPage();
        }
      }
    }
// ===========================================================================
  }
}
MemoryTests.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Threading;
using Ionic.Zip;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class MemoryTests : IWriter {
 
    /** The resulting report. */
    public readonly String RESULT0 = "test_results.txt";
 
    /** A resulting PDF file. */
    public readonly String RESULT1
        = "pdfptable_without_memory_management.pdf";
    /** A resulting PDF file. */
    public readonly String RESULT2
        = "pdfptable_with_memory_management.pdf";
    
    private bool test;
    private long memory_use;
    private long initial_memory_use = 0l;
    private long maximum_memory_use = 0l;
    
    /** Path to the resources. */
    public readonly String RESOURCE = Utility.ResourceDirectory+"/posters/{0}.jpg";
    /** The different epochs. */
    public readonly String[] EPOCH = new [] { "Forties", "Fifties", "Sixties", "Seventies", "Eighties", "Nineties", "Twenty-first Century" };
    
    /** The fonts for the title. */
    public readonly Font[] FONT  = new []
    {
        new Font(Font.FontFamily.HELVETICA, 24),
        new Font(Font.FontFamily.HELVETICA, 18),
        new Font(Font.FontFamily.HELVETICA, 14),
        new Font(Font.FontFamily.HELVETICA, 12, Font.BOLD)
    };
    
    
    /**
     * Creates a PDF with a table
     * @param writer the writer to our report file
     * @param filename the PDF that will be created
     * @throws IOException
     * @throws DocumentException
     * @throws SQLException
     */
    private void CreatePdfWithPdfPTable(StreamWriter writer, Stream doc) {
        // Create a connection to the database
        //DatabaseConnection connection = new HsqldbConnection("filmfestival"); 
        // step 1
        Document document = new Document();
        // step 2
        PdfWriter.GetInstance(document, doc);
        // step 3
        document.Open();
        // step 4
        // Create a table with 2 columns
        PdfPTable table = new PdfPTable(new float[]{1, 7});
        // Mark the table as not complete
        if (test) table.Complete = false;
        table.WidthPercentage = 100;
        IEnumerable<Movie> movies = PojoFactory.GetMovies();
        List list;
        PdfPCell cell;
        int count = 0;
        // add information about a movie
        foreach (Movie movie in movies) {
            table.SpacingBefore = 5;
            // add a movie poster
            cell = new PdfPCell(Image.GetInstance(String.Format(RESOURCE, movie.Imdb)), true);
            cell.Border = PdfPCell.NO_BORDER;
            table.AddCell(cell);
            // add movie information
            cell = new PdfPCell();
            Paragraph p = new Paragraph(movie.Title, FilmFonts.BOLD);
            p.Alignment = Element.ALIGN_CENTER;
            p.SpacingBefore = 5;
            p.SpacingAfter = 5;
            cell.AddElement(p);
            cell.Border = PdfPCell.NO_BORDER;
            if (movie.OriginalTitle != null) {
                p = new Paragraph(movie.OriginalTitle, FilmFonts.ITALIC);
                p.Alignment = Element.ALIGN_RIGHT;
                cell.AddElement(p);
            }
            list = PojoToElementFactory.GetDirectorList(movie);
            list.IndentationLeft = 30;
            cell.AddElement(list);
            p = new Paragraph(String.Format("Year: %d", movie.Year), FilmFonts.NORMAL);
            p.IndentationLeft = 15;
            p.Leading = 24;
            cell.AddElement(p);
            p = new Paragraph(String.Format("Run length: %d", movie.Duration), FilmFonts.NORMAL);
            p.Leading = 14;
            p.IndentationLeft = 30;
            cell.AddElement(p);
            list = PojoToElementFactory.GetCountryList(movie);
            list.IndentationLeft = 40;
            cell.AddElement(list);
            table.AddCell(cell);
            // insert a checkpoint every 10 movies
            if (count++ % 10 == 0) {
                // add the incomplete table to the document
                if (test)
                    document.Add(table);
                Checkpoint(writer);
            }
        }
        // Mark the table as complete
        if (test) table.Complete = true;
        // add the table to the document
        document.Add(table);
        // insert a last checkpoint
        Checkpoint(writer);
        // step 5
        document.Close();
    }
    
    /**
     * Writes a checkpoint to the report file.
     * @param writer the writer to our report file
     */
    private void Checkpoint(StreamWriter writer) {
        memory_use = GetMemoryUse();
        maximum_memory_use = Math.Max(maximum_memory_use, memory_use);
        Println(writer, "memory use: ", memory_use);
    }
    
    /**
     * Resets the maximum memory that is in use
     * @param writer the writer to our report file
     */
    private void ResetMaximum(StreamWriter writer) {
        Println(writer, "maximum: ", maximum_memory_use);
        Println(writer, "total used: ", maximum_memory_use - initial_memory_use);
        maximum_memory_use = 0l;
        GarbageCollect();
        initial_memory_use = GetMemoryUse();
        Println(writer, "initial memory use: ", initial_memory_use);
    }
 
    /**
     * Writes a line to our report file
     * @param writer the writer to our report file
     * @param message the message to write
     */
    private void Println(StreamWriter writer, String message) {
        try {
            writer.WriteLine(message);
            writer.WriteLine("\n");
            writer.Flush();
        } catch (IOException e) {
            Console.WriteLine(e.StackTrace);
        }
    }
    
    /**
     * Writes a line to our report file
     * @param writer the writer to our report file
     * @param message the message to write
     * @param l a memory value
     */
    private void Println(StreamWriter writer, String message, long l) {
        try {
            writer.WriteLine(message + l);
            writer.WriteLine("\n");
            writer.Flush();
        } catch (IOException e) {
            Console.WriteLine(e.StackTrace);
        }
    }
    
    /**
     * Returns the current memory use.
     * 
     * @return the current memory use
     */
    private static long GetMemoryUse() {
        return (GC.GetTotalMemory(true));
    }
    
    /**
     * Makes sure all garbage is cleared from the memory.
     */
    private static void GarbageCollect() {
        try {
            GC.Collect();
            Thread.Sleep(200);
            GC.WaitForPendingFinalizers();
            Thread.Sleep(200);
            GC.Collect();
            Thread.Sleep(200);
            GC.WaitForPendingFinalizers();
            Thread.Sleep(200);
        } catch (Exception ex) {
            Console.WriteLine(ex.StackTrace);
        }
    }
 
    /**
     * Main method.
     * @param args no arguments needed
     * @throws DocumentException 
     * @throws IOException
     * @throws SQLException
     */
    public static void Main(String[] args) {
        
    }
// ===========================================================================
    public void Write(Stream stream) {
        try
        {
            using (ZipFile zip = new ZipFile())
            {
                using (MemoryStream resultStream = new MemoryStream())
                {
                    using (StreamWriter sw = new StreamWriter(resultStream))
                    {
                        ResetMaximum(sw);
                        using (MemoryStream ms = new MemoryStream())
                        {
                            // step 1
                            test = false;
                            Println(sw, RESULT1);
                            // PDF without memory management
                            CreatePdfWithPdfPTable(sw, ms);
                            ResetMaximum(sw);
                            zip.AddEntry(RESULT1, ms.ToArray());
                        }
                        using (MemoryStream ms = new MemoryStream())
                        {
                            // step 2
                            test = true;
                            Println(sw, RESULT2);
                            // PDF with memory management
                            CreatePdfWithPdfPTable(sw, ms);
                            ResetMaximum(sw);
                            zip.AddEntry(RESULT2, ms.ToArray());
                        }
                        // step 3
                        zip.AddEntry(RESULT0, resultStream.ToArray());
                    }
                }
                zip.Save(stream);
            }
        }
        catch(Exception ex)
        {
            Console.WriteLine(ex.StackTrace);
        }
    }
// ===========================================================================
  }
}
PdfCalendar.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Globalization;
using System.util;
using iTextSharp.text;
using iTextSharp.text.pdf;
using iTextSharp.text.pdf.draw;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class PdfCalendar : IWriter {
// ===========================================================================
    /** The year for which we want to create a calendar */
    public const int YEAR = 2011;
    /** The language code for the calendar
     * change this to set culture-specific info
    */
    public const string LANGUAGE = "en";
    /** Path to the resources. */
    public readonly string RESOURCE = Utility.ResourceCalendar;
    /** resources file. */
    public const string CONTENT = "content.txt";
 
    public Properties specialDays = new Properties();
    /** Collection with the description of the images */
    public Properties content = new Properties();
 
    /** A font that is used in the calendar */
    protected Font normal;
    /** A font that is used in the calendar */
    protected Font small;
    /** A font that is used in the calendar */
    protected Font bold;
// ---------------------------------------------------------------------------
    /**
     * Initializes the fonts and collections.
     */
    public PdfCalendar() {
      // fonts
    BaseFont bf_normal = BaseFont.CreateFont(
      "c://windows/fonts/arial.ttf",
        BaseFont.WINANSI, 
        BaseFont.EMBEDDED
      );
      normal = new Font(bf_normal, 16);
      small = new Font(bf_normal, 8);
      BaseFont bf_bold = BaseFont.CreateFont(
        "c://windows/fonts/arialbd.ttf",
        BaseFont.WINANSI,
        BaseFont.EMBEDDED
      );
      bold = new Font(bf_bold, 14);
      // collections
      string year_file = Path.Combine(
        Utility.ResourceCalendar, string.Format("{0}.txt", YEAR)
      );
      if (!File.Exists(year_file)) { 
        throw new ArgumentException(year_file + " NOT FOUND!");
      }
      string content_file = Path.Combine(Utility.ResourceCalendar, CONTENT);
      if (!File.Exists(content_file)) {
        throw new ArgumentException(year_file + " NOT FOUND!");
      }
      using (FileStream fs = new FileStream(
        year_file, FileMode.Open, FileAccess.Read
      ) ) {
        specialDays.Load(fs);
      }
      using (FileStream fs = new FileStream(
        content_file, FileMode.Open, FileAccess.Read
      ) ) {
        content.Load(fs);
      }      
    }
// ---------------------------------------------------------------------------
    /**
     * Creates a PDF document.
     */
    public virtual void Write(Stream stream) {
      // step 1
      using (Document document = new Document(PageSize.A4.Rotate())) {
        // step 2
        PdfWriter writer = PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        // "en" => System.Globalization.GregorianCalendar 
        Calendar calendar = new CultureInfo(LANGUAGE, false).Calendar;
        PdfContentByte canvas = writer.DirectContent;
        // Loop over the months
        for (int month = 0; month < 12; month++) {
          int current_month = month + 1;
          DateTime dt = new DateTime(YEAR, current_month, 1, calendar);
          // draw the background
          DrawImageAndText(canvas, dt);
          // create a table with 7 columns
          PdfPTable table = new PdfPTable(7);
          table.TotalWidth = 504;
          // add the name of the month
          table.DefaultCell.BackgroundColor = BaseColor.WHITE;
          table.AddCell(GetMonthCell(dt));
          int daysInMonth = DateTime.DaysInMonth(YEAR, dt.Month);
          int day = 1;
          // add empty cells
          // SUNDAY; Java => 1, .NET => 0
          int position = 0;
          while (position++ != (int) dt.DayOfWeek) {
            table.AddCell("");
          }
          // add cells for each day
          while (day <= daysInMonth) {
            dt = new DateTime(YEAR, current_month, day++, calendar);
            table.AddCell(GetDayCell(dt));
          }
          // complete the table
          table.CompleteRow();
          // write the table to an absolute position
          table.WriteSelectedRows(0, -1, 169, table.TotalHeight + 18, canvas);
          document.NewPage();
        }
      }
    }
// ---------------------------------------------------------------------------
    /**
     * Draws the image of the month to the calendar.
     * @param canvas the direct content layer
     * @param dt the DateTime (to know which picture to use)
     */
    public void DrawImageAndText(PdfContentByte canvas, DateTime dt) {
      string MM = dt.ToString("MM");
      // get the image
      Image img = Image.GetInstance(Path.Combine(
        RESOURCE, MM + ".jpg"
      ));
      img.ScaleToFit(PageSize.A4.Height, PageSize.A4.Width);
      img.SetAbsolutePosition(
        (PageSize.A4.Height - img.ScaledWidth) / 2,
        (PageSize.A4.Width - img.ScaledHeight) / 2
      );
      canvas.AddImage(img);
      // add metadata
      canvas.SaveState();
      canvas.SetCMYKColorFill(0x00, 0x00, 0x00, 0x80);
      Phrase p = new Phrase(string.Format(
          "{0} - \u00a9 Katharine Osborne",
          content[string.Format("{0}.jpg", dt.ToString("MM"))]
        ),
        small
      );
      ColumnText.ShowTextAligned(canvas, Element.ALIGN_LEFT, p, 5, 5, 0);
      p = new Phrase(
        "Calendar generated using iText - example for the book iText in Action 2nd Edition", 
        small
      );
      ColumnText.ShowTextAligned(canvas, Element.ALIGN_RIGHT, p, 839, 5, 0);
      canvas.RestoreState();
    }
// ---------------------------------------------------------------------------   
    /**
     * Creates a PdfPCell with the name of the month
     * @param dt a DateTime
     * @return a PdfPCell with rowspan 7, containing the name of the month
     */
    public PdfPCell GetMonthCell(DateTime dt) {
      PdfPCell cell = new PdfPCell();
      cell.Colspan = 7;
      cell.BackgroundColor = BaseColor.WHITE;
      cell.UseDescender = true;
      Paragraph p = new Paragraph(dt.ToString("MMMM yyyy"), bold);
      p.Alignment = Element.ALIGN_CENTER;
      cell.AddElement(p);
      return cell;
    }
//// ---------------------------------------------------------------------------   
//    /**
//     * Creates a PdfPCell for a specific day
//     * @param dt a DateTime
//     * @return a PdfPCell
//     */
    public PdfPCell GetDayCell(DateTime dt) {
      PdfPCell cell = new PdfPCell();
      cell.Padding = 3;
      // set the background color, based on the type of day
      cell.BackgroundColor = IsSunday(dt)
        ? BaseColor.GRAY
        : IsSpecialDay(dt)
          ? BaseColor.LIGHT_GRAY
          : BaseColor.WHITE
      ;
      // set the content in the language of the locale
      Chunk chunk = new Chunk(dt.ToString("ddd"), small);
      chunk.SetTextRise(8);
      // a paragraph with the day
      Paragraph p = new Paragraph(chunk);
      // a separator
      p.Add(new Chunk(new VerticalPositionMark()));
      // and the number of the day
      p.Add(new Chunk(dt.ToString("%d"), normal));
      cell.AddElement(p);
      return cell;
    }
// ---------------------------------------------------------------------------       
    /**
     * Returns true for Sundays.
     * @param dt a DateTime
     * @return true for Sundays
     */
    public bool IsSunday(DateTime dt) {
      return dt.DayOfWeek == DayOfWeek.Sunday ? true : false;
    }
//// ---------------------------------------------------------------------------       
//    /**
//     * Returns true if the date was found in a list with special days (holidays).
//     * @param calendar a date
//     * @return true for holidays
//     */
    public bool IsSpecialDay(DateTime dt) {
      return dt.DayOfWeek == DayOfWeek.Saturday
        ? true
        : specialDays.ContainsKey(dt.ToString("MMdd"))
          ? true
          : false
      ;
    }    
// ===========================================================================
  }
}
Zhang.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using System.Linq;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class Zhang : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document()) {
        // step 2
        PdfWriter writer = PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        // Create a table and fill it with movies
        IEnumerable<Movie> movies = PojoFactory.GetMovies(3);
        PdfPTable table = new PdfPTable(new float[] { 1, 5, 5, 1});
        foreach (Movie movie in movies) {
          table.AddCell(movie.Year.ToString());
          table.AddCell(movie.MovieTitle);
          table.AddCell(movie.OriginalTitle);
          table.AddCell(movie.Duration.ToString());
        }
        // set the total width of the table
        table.TotalWidth = 600;
        PdfContentByte canvas = writer.DirectContent;
        // draw the first three columns on one page
        table.WriteSelectedRows(0, 2, 0, -1, 236, 806, canvas);
        document.NewPage();
        // draw the next three columns on the next page
        table.WriteSelectedRows(2, -1, 0, -1, 36, 806, canvas);
      }
    }
// ===========================================================================
  }
}
ColumnTable.cs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
/*
 * This class is part of the book "iText in Action - 2nd Edition"
 * written by Bruno Lowagie (ISBN: 9781935182610)
 * For more info, go to: http://itextpdf.com/examples/
 * This example only works with the AGPL version of iText.
 */
using System;
using System.IO;
using System.Collections.Generic;
using iTextSharp.text;
using iTextSharp.text.pdf;
using kuujinbo.iTextInAction2Ed.Intro_1_2;
 
namespace kuujinbo.iTextInAction2Ed.Chapter04 {
  public class ColumnTable : IWriter {
// ===========================================================================
    public void Write(Stream stream) {
      // step 1
      using (Document document = new Document(PageSize.A4.Rotate())) {
        // step 2
        PdfWriter writer = PdfWriter.GetInstance(document, stream);
        // step 3
        document.Open();
        // step 4
        ColumnText column = new ColumnText(writer.DirectContent);
        List<string> days = PojoFactory.GetDays();
        // COlumn definition
        float[][] x = {
          new float[] { document.Left, document.Left + 380 },
          new float[] { document.Right - 380, document.Right }
        };
        // Loop over the festival days
        foreach (string day in days) {
        // add content to the column
          column.AddElement(GetTable(day));
          int count = 0;
          float height = 0;
          // iText-ONLY, 'Initial value of the status' => 0
          // iTextSharp **DOES NOT** include this member variable
          // int status = ColumnText.START_COLUMN;
          int status = 0;
          // render the column as long as it has content
          while (ColumnText.HasMoreText(status)) {
          // add the top-level header to each new page
            if (count == 0) {
              height = AddHeaderTable(document, day, writer.PageNumber);
            }
            // set the dimensions of the current column
            column.SetSimpleColumn(
              x[count][0], document.Bottom,
              x[count][1], document.Top - height - 10
            );
            // render as much content as possible
            status = column.Go();
            // go to a new page if you've reached the last column
            if (++count > 1) {
              count = 0;
              document.NewPage();
            }
          }
          document.NewPage();
        }
      }
    }
// ---------------------------------------------------------------------------    
    /**
     * Add a header table to the document
     * @param document The document to which you want to add a header table
     * @param day The day that needs to be shown in the header table
     * @param page The page number that has to be shown in the header
     * @return the height of the resulting header table
     */
    public float AddHeaderTable(Document document, string day, int page) {
      PdfPTable header = new PdfPTable(3);
      header.WidthPercentage = 100;
      header.DefaultCell.BackgroundColor = BaseColor.BLACK;
      Font font = new Font(Font.FontFamily.HELVETICA, 12, Font.BOLD, BaseColor.WHITE);
      Phrase p = new Phrase("Foobar Film Festival", font);
      header.AddCell(p);
      header.DefaultCell.HorizontalAlignment = Element.ALIGN_CENTER;
      p = new Phrase(day, font);
      header.AddCell(p);
      header.DefaultCell.HorizontalAlignment = Element.ALIGN_RIGHT;
      p = new Phrase(string.Format("page {0}", page), font);
      header.AddCell(p);
      document.Add(header);
      return header.TotalHeight;
    }
// ---------------------------------------------------------------------------
    /**
     * Creates a table with movie screenings for a specific day
     * @param connection a connection to the database
     * @param day a day
     * @return a table with screenings
     */
    public PdfPTable GetTable(string day) {
      PdfPTable table = new PdfPTable(new float[] { 2, 1, 2, 5, 1 });
      table.WidthPercentage = 100f;
      table.DefaultCell.UseAscender = true;
      table.DefaultCell.UseDescender = true;
      table.DefaultCell.BackgroundColor = BaseColor.LIGHT_GRAY;
      for (int i = 0; i < 2; i++) {
        table.AddCell("Location");
        table.AddCell("Time");
        table.AddCell("Run Length");
        table.AddCell("Title");
        table.AddCell("Year");
      }
      table.DefaultCell.BackgroundColor = null;
      table.HeaderRows = 2;
      table.FooterRows = 1;
      List<Screening> screenings = PojoFactory.GetScreenings(day);
      Movie movie;
      foreach (Screening screening in screenings) {
        movie = screening.movie;
        table.AddCell(screening.Location);
        table.AddCell(screening.Time.Substring(0, 5));
        table.AddCell(movie.Duration.ToString());
        table.AddCell(movie.MovieTitle);
        table.AddCell(movie.Year.ToString());
      }
      return table;
    }    
// ===========================================================================
  }
}


Contact

Still have questions? 

We're happy to answer your questions. Reach out to us and we'll get back to you shortly.

Contact us
Stay updated

Join 11,000+ subscribers and become an iText PDF expert by staying up to date with our new products, updates, tips, technical solutions and happenings.

Subscribe Now