Issues (282)

lib/Page.php (15 issues)

1
<?php
2
3
declare(strict_types=1);
4
/**
5
 * Page class.
6
 *
7
 * @package   YetiForcePDF\Document
8
 *
9
 * @copyright YetiForce Sp. z o.o
10
 * @license   MIT
11
 * @author    Rafal Pospiech <[email protected]>
12
 */
13
14
namespace YetiForcePDF;
15
16
use YetiForcePDF\Layout\Box;
17
use YetiForcePDF\Layout\Coordinates\Coordinates;
18
use YetiForcePDF\Layout\Dimensions\BoxDimensions;
19
use YetiForcePDF\Layout\Dimensions\Dimensions;
20
use YetiForcePDF\Layout\FooterBox;
21
use YetiForcePDF\Layout\HeaderBox;
22
use YetiForcePDF\Layout\TableFooterGroupBox;
23
use YetiForcePDF\Layout\TableHeaderGroupBox;
24
use YetiForcePDF\Layout\TableWrapperBox;
25
use YetiForcePDF\Layout\TextBox;
26
use YetiForcePDF\Layout\WatermarkBox;
27
use YetiForcePDF\Objects\Basic\StreamObject;
28
29
/**
30
 * Class Page.
31
 */
32
class Page extends \YetiForcePDF\Objects\Basic\DictionaryObject
33
{
34
	/**
35
	 * @var int
36
	 */
37
	protected $group = 0;
38
	/**
39
	 * {@inheritdoc}
40
	 */
41
	protected $dictionaryType = 'Page';
42
	/**
43
	 * Object name.
44
	 *
45
	 * @var string
46
	 */
47
	protected $name = 'Page';
48
49
	/**
50
	 * @var int page number
51
	 */
52
	protected $pageNumber = 1;
53
	/**
54
	 * @var int page count
55
	 */
56
	protected $pageCount = 1;
57
	/**
58
	 * Page resources.
59
	 *
60
	 * @var array
61
	 */
62
	protected $resources = [];
63
	/**
64
	 * Page content streams.
65
	 *
66
	 * @var StreamObject
67
	 */
68
	protected $contentStream;
69
	/**
70
	 * Portrait page orientation.
71
	 */
72
	const ORIENTATION_PORTRAIT = 'P';
73
	/**
74
	 * Landscape page orientation.
75
	 */
76
	const ORIENTATION_LANDSCAPE = 'L';
77
	/**
78
	 * After page breaking box was cut below.
79
	 */
80
	const CUT_BELOW = 1;
81
	/**
82
	 * After page breaking box was cut above.
83
	 */
84
	const CUT_ABOVE = 2;
85
	/**
86
	 * Current page format.
87
	 *
88
	 * @var string
89
	 */
90
	protected $format;
91
	/**
92
	 * Current page orientation.
93
	 *
94
	 * @var string
95
	 */
96
	protected $orientation;
97
	/**
98
	 * User unit - to calculate page dpi.
99
	 *
100
	 * @var float
101
	 */
102
	protected $userUnit = 1.0;
103
	/**
104
	 * Page margins.
105
	 *
106
	 * @var array
107
	 */
108
	protected $margins;
109
	/**
110
	 * Page dimensions.
111
	 *
112
	 * @var BoxDimensions
113
	 */
114
	protected $dimensions;
115
	/**
116
	 * Page outer dimensions.
117
	 *
118
	 * @var BoxDimensions
119
	 */
120
	protected $outerDimensions;
121
	/**
122
	 * @var Coordinates
123
	 */
124
	protected $coordinates;
125
	/**
126
	 * Don't group this 'group' names.
127
	 *
128
	 * @var string[]
129
	 */
130
	protected $doNotGroup = [];
131
	/**
132
	 * @var Box main box with content
133
	 */
134
	protected $box;
135
136
	public static $pageFormats = [
137
		// ISO 216 A Series + 2 SIS 014711 extensions
138
		'A0' => [2383.937, 3370.394], // = (  841 x 1189 ) mm  = ( 33.11 x 46.81 ) in
139
		'A1' => [1683.780, 2383.937], // = (  594 x 841  ) mm  = ( 23.39 x 33.11 ) in
140
		'A2' => [1190.551, 1683.780], // = (  420 x 594  ) mm  = ( 16.54 x 23.39 ) in
141
		'A3' => [841.890, 1190.551], // = (  297 x 420  ) mm  = ( 11.69 x 16.54 ) in
142
		'A4' => [595.276, 841.890], // = (  210 x 297  ) mm  = (  8.27 x 11.69 ) in
143
		'A5' => [419.528, 595.276], // = (  148 x 210  ) mm  = (  5.83 x 8.27  ) in
144
		'A6' => [297.638, 419.528], // = (  105 x 148  ) mm  = (  4.13 x 5.83  ) in
145
		'A7' => [209.764, 297.638], // = (   74 x 105  ) mm  = (  2.91 x 4.13  ) in
146
		'A8' => [147.402, 209.764], // = (   52 x 74   ) mm  = (  2.05 x 2.91  ) in
147
		'A9' => [104.882, 147.402], // = (   37 x 52   ) mm  = (  1.46 x 2.05  ) in
148
		'A10' => [73.701, 104.882], // = (   26 x 37   ) mm  = (  1.02 x 1.46  ) in
149
		'A11' => [51.024, 73.701], // = (   18 x 26   ) mm  = (  0.71 x 1.02  ) in
150
		'A12' => [36.850, 51.024], // = (   13 x 18   ) mm  = (  0.51 x 0.71  ) in
151
		// ISO 216 B Series + 2 SIS 014711 extensions
152
		'B0' => [2834.646, 4008.189], // = ( 1000 x 1414 ) mm  = ( 39.37 x 55.67 ) in
153
		'B1' => [2004.094, 2834.646], // = (  707 x 1000 ) mm  = ( 27.83 x 39.37 ) in
154
		'B2' => [1417.323, 2004.094], // = (  500 x 707  ) mm  = ( 19.69 x 27.83 ) in
155
		'B3' => [1000.630, 1417.323], // = (  353 x 500  ) mm  = ( 13.90 x 19.69 ) in
156
		'B4' => [708.661, 1000.630], // = (  250 x 353  ) mm  = (  9.84 x 13.90 ) in
157
		'B5' => [498.898, 708.661], // = (  176 x 250  ) mm  = (  6.93 x 9.84  ) in
158
		'B6' => [354.331, 498.898], // = (  125 x 176  ) mm  = (  4.92 x 6.93  ) in
159
		'B7' => [249.449, 354.331], // = (   88 x 125  ) mm  = (  3.46 x 4.92  ) in
160
		'B8' => [175.748, 249.449], // = (   62 x 88   ) mm  = (  2.44 x 3.46  ) in
161
		'B9' => [124.724, 175.748], // = (   44 x 62   ) mm  = (  1.73 x 2.44  ) in
162
		'B10' => [87.874, 124.724], // = (   31 x 44   ) mm  = (  1.22 x 1.73  ) in
163
		'B11' => [62.362, 87.874], // = (   22 x 31   ) mm  = (  0.87 x 1.22  ) in
164
		'B12' => [42.520, 62.362], // = (   15 x 22   ) mm  = (  0.59 x 0.87  ) in
165
		// ISO 216 C Series + 2 SIS 014711 extensions + 5 EXTENSION
166
		'C0' => [2599.370, 3676.535], // = (  917 x 1297 ) mm  = ( 36.10 x 51.06 ) in
167
		'C1' => [1836.850, 2599.370], // = (  648 x 917  ) mm  = ( 25.51 x 36.10 ) in
168
		'C2' => [1298.268, 1836.850], // = (  458 x 648  ) mm  = ( 18.03 x 25.51 ) in
169
		'C3' => [918.425, 1298.268], // = (  324 x 458  ) mm  = ( 12.76 x 18.03 ) in
170
		'C4' => [649.134, 918.425], // = (  229 x 324  ) mm  = (  9.02 x 12.76 ) in
171
		'C5' => [459.213, 649.134], // = (  162 x 229  ) mm  = (  6.38 x 9.02  ) in
172
		'C6' => [323.150, 459.213], // = (  114 x 162  ) mm  = (  4.49 x 6.38  ) in
173
		'C7' => [229.606, 323.150], // = (   81 x 114  ) mm  = (  3.19 x 4.49  ) in
174
		'C8' => [161.575, 229.606], // = (   57 x 81   ) mm  = (  2.24 x 3.19  ) in
175
		'C9' => [113.386, 161.575], // = (   40 x 57   ) mm  = (  1.57 x 2.24  ) in
176
		'C10' => [79.370, 113.386], // = (   28 x 40   ) mm  = (  1.10 x 1.57  ) in
177
		'C11' => [56.693, 79.370], // = (   20 x 28   ) mm  = (  0.79 x 1.10  ) in
178
		'C12' => [39.685, 56.693], // = (   14 x 20   ) mm  = (  0.55 x 0.79  ) in
179
		'C76' => [229.606, 459.213], // = (   81 x 162  ) mm  = (  3.19 x 6.38  ) in
180
		'DL' => [311.811, 623.622], // = (  110 x 220  ) mm  = (  4.33 x 8.66  ) in
181
		'DLE' => [323.150, 637.795], // = (  114 x 225  ) mm  = (  4.49 x 8.86  ) in
182
		'DLX' => [340.158, 666.142], // = (  120 x 235  ) mm  = (  4.72 x 9.25  ) in
183
		'DLP' => [280.630, 595.276], // = (   99 x 210  ) mm  = (  3.90 x 8.27  ) in (1/3 A4)
184
		// SIS 014711 E Series
185
		'E0' => [2491.654, 3517.795], // = (  879 x 1241 ) mm  = ( 34.61 x 48.86 ) in
186
		'E1' => [1757.480, 2491.654], // = (  620 x 879  ) mm  = ( 24.41 x 34.61 ) in
187
		'E2' => [1247.244, 1757.480], // = (  440 x 620  ) mm  = ( 17.32 x 24.41 ) in
188
		'E3' => [878.740, 1247.244], // = (  310 x 440  ) mm  = ( 12.20 x 17.32 ) in
189
		'E4' => [623.622, 878.740], // = (  220 x 310  ) mm  = (  8.66 x 12.20 ) in
190
		'E5' => [439.370, 623.622], // = (  155 x 220  ) mm  = (  6.10 x 8.66  ) in
191
		'E6' => [311.811, 439.370], // = (  110 x 155  ) mm  = (  4.33 x 6.10  ) in
192
		'E7' => [221.102, 311.811], // = (   78 x 110  ) mm  = (  3.07 x 4.33  ) in
193
		'E8' => [155.906, 221.102], // = (   55 x 78   ) mm  = (  2.17 x 3.07  ) in
194
		'E9' => [110.551, 155.906], // = (   39 x 55   ) mm  = (  1.54 x 2.17  ) in
195
		'E10' => [76.535, 110.551], // = (   27 x 39   ) mm  = (  1.06 x 1.54  ) in
196
		'E11' => [53.858, 76.535], // = (   19 x 27   ) mm  = (  0.75 x 1.06  ) in
197
		'E12' => [36.850, 53.858], // = (   13 x 19   ) mm  = (  0.51 x 0.75  ) in
198
		// SIS 014711 G Series
199
		'G0' => [2715.591, 3838.110], // = (  958 x 1354 ) mm  = ( 37.72 x 53.31 ) in
200
		'G1' => [1919.055, 2715.591], // = (  677 x 958  ) mm  = ( 26.65 x 37.72 ) in
201
		'G2' => [1357.795, 1919.055], // = (  479 x 677  ) mm  = ( 18.86 x 26.65 ) in
202
		'G3' => [958.110, 1357.795], // = (  338 x 479  ) mm  = ( 13.31 x 18.86 ) in
203
		'G4' => [677.480, 958.110], // = (  239 x 338  ) mm  = (  9.41 x 13.31 ) in
204
		'G5' => [479.055, 677.480], // = (  169 x 239  ) mm  = (  6.65 x 9.41  ) in
205
		'G6' => [337.323, 479.055], // = (  119 x 169  ) mm  = (  4.69 x 6.65  ) in
206
		'G7' => [238.110, 337.323], // = (   84 x 119  ) mm  = (  3.31 x 4.69  ) in
207
		'G8' => [167.244, 238.110], // = (   59 x 84   ) mm  = (  2.32 x 3.31  ) in
208
		'G9' => [119.055, 167.244], // = (   42 x 59   ) mm  = (  1.65 x 2.32  ) in
209
		'G10' => [82.205, 119.055], // = (   29 x 42   ) mm  = (  1.14 x 1.65  ) in
210
		'G11' => [59.528, 82.205], // = (   21 x 29   ) mm  = (  0.83 x 1.14  ) in
211
		'G12' => [39.685, 59.528], // = (   14 x 21   ) mm  = (  0.55 x 0.83  ) in
212
		// ISO Press
213
		'RA0' => [2437.795, 3458.268], // = (  860 x 1220 ) mm  = ( 33.86 x 48.03 ) in
214
		'RA1' => [1729.134, 2437.795], // = (  610 x 860  ) mm  = ( 24.02 x 33.86 ) in
215
		'RA2' => [1218.898, 1729.134], // = (  430 x 610  ) mm  = ( 16.93 x 24.02 ) in
216
		'RA3' => [864.567, 1218.898], // = (  305 x 430  ) mm  = ( 12.01 x 16.93 ) in
217
		'RA4' => [609.449, 864.567], // = (  215 x 305  ) mm  = (  8.46 x 12.01 ) in
218
		'SRA0' => [2551.181, 3628.346], // = (  900 x 1280 ) mm  = ( 35.43 x 50.39 ) in
219
		'SRA1' => [1814.173, 2551.181], // = (  640 x 900  ) mm  = ( 25.20 x 35.43 ) in
220
		'SRA2' => [1275.591, 1814.173], // = (  450 x 640  ) mm  = ( 17.72 x 25.20 ) in
221
		'SRA3' => [907.087, 1275.591], // = (  320 x 450  ) mm  = ( 12.60 x 17.72 ) in
222
		'SRA4' => [637.795, 907.087], // = (  225 x 320  ) mm  = (  8.86 x 12.60 ) in
223
		// German DIN 476
224
		'4A0' => [4767.874, 6740.787], // = ( 1682 x 2378 ) mm  = ( 66.22 x 93.62 ) in
225
		'2A0' => [3370.394, 4767.874], // = ( 1189 x 1682 ) mm  = ( 46.81 x 66.22 ) in
226
		// Variations on the ISO Standard
227
		'A2_EXTRA' => [1261.417, 1754.646], // = (  445 x 619  ) mm  = ( 17.52 x 24.37 ) in
228
		'A3+' => [932.598, 1369.134], // = (  329 x 483  ) mm  = ( 12.95 x 19.02 ) in
229
		'A3_EXTRA' => [912.756, 1261.417], // = (  322 x 445  ) mm  = ( 12.68 x 17.52 ) in
230
		'A3_SUPER' => [864.567, 1440.000], // = (  305 x 508  ) mm  = ( 12.01 x 20.00 ) in
231
		'SUPER_A3' => [864.567, 1380.472], // = (  305 x 487  ) mm  = ( 12.01 x 19.17 ) in
232
		'A4_EXTRA' => [666.142, 912.756], // = (  235 x 322  ) mm  = (  9.25 x 12.68 ) in
233
		'A4_SUPER' => [649.134, 912.756], // = (  229 x 322  ) mm  = (  9.02 x 12.68 ) in
234
		'SUPER_A4' => [643.465, 1009.134], // = (  227 x 356  ) mm  = (  8.94 x 14.02 ) in
235
		'A4_LONG' => [595.276, 986.457], // = (  210 x 348  ) mm  = (  8.27 x 13.70 ) in
236
		'F4' => [595.276, 935.433], // = (  210 x 330  ) mm  = (  8.27 x 12.99 ) in
237
		'SO_B5_EXTRA' => [572.598, 782.362], // = (  202 x 276  ) mm  = (  7.95 x 10.87 ) in
238
		'A5_EXTRA' => [490.394, 666.142], // = (  173 x 235  ) mm  = (  6.81 x 9.25  ) in
239
		// ANSI Series
240
		'ANSI_E' => [2448.000, 3168.000], // = (  864 x 1118 ) mm  = ( 34.00 x 44.00 ) in
241
		'ANSI_D' => [1584.000, 2448.000], // = (  559 x 864  ) mm  = ( 22.00 x 34.00 ) in
242
		'ANSI_C' => [1224.000, 1584.000], // = (  432 x 559  ) mm  = ( 17.00 x 22.00 ) in
243
		'ANSI_B' => [792.000, 1224.000], // = (  279 x 432  ) mm  = ( 11.00 x 17.00 ) in
244
		'ANSI_A' => [612.000, 792.000], // = (  216 x 279  ) mm  = (  8.50 x 11.00 ) in
245
		// Traditional 'Loose' North American Paper Sizes
246
		'USLEDGER' => [1224.000, 792.000], // = (  432 x 279  ) mm  = ( 17.00 x 11.00 ) in
247
		'LEDGER' => [1224.000, 792.000], // = (  432 x 279  ) mm  = ( 17.00 x 11.00 ) in
248
		'ORGANIZERK' => [792.000, 1224.000], // = (  279 x 432  ) mm  = ( 11.00 x 17.00 ) in
249
		'BIBLE' => [792.000, 1224.000], // = (  279 x 432  ) mm  = ( 11.00 x 17.00 ) in
250
		'USTABLOID' => [792.000, 1224.000], // = (  279 x 432  ) mm  = ( 11.00 x 17.00 ) in
251
		'TABLOID' => [792.000, 1224.000], // = (  279 x 432  ) mm  = ( 11.00 x 17.00 ) in
252
		'ORGANIZERM' => [612.000, 792.000], // = (  216 x 279  ) mm  = (  8.50 x 11.00 ) in
253
		'USLETTER' => [612.000, 792.000], // = (  216 x 279  ) mm  = (  8.50 x 11.00 ) in
254
		'LETTER' => [612.000, 792.000], // = (  216 x 279  ) mm  = (  8.50 x 11.00 ) in
255
		'USLEGAL' => [612.000, 1008.000], // = (  216 x 356  ) mm  = (  8.50 x 14.00 ) in
256
		'LEGAL' => [612.000, 1008.000], // = (  216 x 356  ) mm  = (  8.50 x 14.00 ) in
257
		'GOVERNMENTLETTER' => [576.000, 756.000], // = (  203 x 267  ) mm  = (  8.00 x 10.50 ) in
258
		'GLETTER' => [576.000, 756.000], // = (  203 x 267  ) mm  = (  8.00 x 10.50 ) in
259
		'JUNIORLEGAL' => [576.000, 360.000], // = (  203 x 127  ) mm  = (  8.00 x 5.00  ) in
260
		'JLEGAL' => [576.000, 360.000], // = (  203 x 127  ) mm  = (  8.00 x 5.00  ) in
261
		// Other North American Paper Sizes
262
		'QUADDEMY' => [2520.000, 3240.000], // = (  889 x 1143 ) mm  = ( 35.00 x 45.00 ) in
263
		'SUPER_B' => [936.000, 1368.000], // = (  330 x 483  ) mm  = ( 13.00 x 19.00 ) in
264
		'QUARTO' => [648.000, 792.000], // = (  229 x 279  ) mm  = (  9.00 x 11.00 ) in
265
		'GOVERNMENTLEGAL' => [612.000, 936.000], // = (  216 x 330  ) mm  = (  8.50 x 13.00 ) in
266
		'FOLIO' => [612.000, 936.000], // = (  216 x 330  ) mm  = (  8.50 x 13.00 ) in
267
		'MONARCH' => [522.000, 756.000], // = (  184 x 267  ) mm  = (  7.25 x 10.50 ) in
268
		'EXECUTIVE' => [522.000, 756.000], // = (  184 x 267  ) mm  = (  7.25 x 10.50 ) in
269
		'ORGANIZERL' => [396.000, 612.000], // = (  140 x 216  ) mm  = (  5.50 x 8.50  ) in
270
		'STATEMENT' => [396.000, 612.000], // = (  140 x 216  ) mm  = (  5.50 x 8.50  ) in
271
		'MEMO' => [396.000, 612.000], // = (  140 x 216  ) mm  = (  5.50 x 8.50  ) in
272
		'FOOLSCAP' => [595.440, 936.000], // = (  210 x 330  ) mm  = (  8.27 x 13.00 ) in
273
		'COMPACT' => [306.000, 486.000], // = (  108 x 171  ) mm  = (  4.25 x 6.75  ) in
274
		'ORGANIZERJ' => [198.000, 360.000], // = (   70 x 127  ) mm  = (  2.75 x 5.00  ) in
275
		// Canadian standard CAN 2-9.60M
276
		'P1' => [1587.402, 2437.795], // = (  560 x 860  ) mm  = ( 22.05 x 33.86 ) in
277
		'P2' => [1218.898, 1587.402], // = (  430 x 560  ) mm  = ( 16.93 x 22.05 ) in
278
		'P3' => [793.701, 1218.898], // = (  280 x 430  ) mm  = ( 11.02 x 16.93 ) in
279
		'P4' => [609.449, 793.701], // = (  215 x 280  ) mm  = (  8.46 x 11.02 ) in
280
		'P5' => [396.850, 609.449], // = (  140 x 215  ) mm  = (  5.51 x 8.46  ) in
281
		'P6' => [303.307, 396.850], // = (  107 x 140  ) mm  = (  4.21 x 5.51  ) in
282
		// North American Architectural Sizes
283
		'ARCH_E' => [2592.000, 3456.000], // = (  914 x 1219 ) mm  = ( 36.00 x 48.00 ) in
284
		'ARCH_E1' => [2160.000, 3024.000], // = (  762 x 1067 ) mm  = ( 30.00 x 42.00 ) in
285
		'ARCH_D' => [1728.000, 2592.000], // = (  610 x 914  ) mm  = ( 24.00 x 36.00 ) in
286
		'BROADSHEET' => [1296.000, 1728.000], // = (  457 x 610  ) mm  = ( 18.00 x 24.00 ) in
287
		'ARCH_C' => [1296.000, 1728.000], // = (  457 x 610  ) mm  = ( 18.00 x 24.00 ) in
288
		'ARCH_B' => [864.000, 1296.000], // = (  305 x 457  ) mm  = ( 12.00 x 18.00 ) in
289
		'ARCH_A' => [648.000, 864.000], // = (  229 x 305  ) mm  = (  9.00 x 12.00 ) in
290
		// -- North American Envelope Sizes
291
		// - Announcement Envelopes
292
		'ANNENV_A2' => [314.640, 414.000], // = (  111 x 146  ) mm  = (  4.37 x 5.75  ) in
293
		'ANNENV_A6' => [342.000, 468.000], // = (  121 x 165  ) mm  = (  4.75 x 6.50  ) in
294
		'ANNENV_A7' => [378.000, 522.000], // = (  133 x 184  ) mm  = (  5.25 x 7.25  ) in
295
		'ANNENV_A8' => [396.000, 584.640], // = (  140 x 206  ) mm  = (  5.50 x 8.12  ) in
296
		'ANNENV_A10' => [450.000, 692.640], // = (  159 x 244  ) mm  = (  6.25 x 9.62  ) in
297
		'ANNENV_SLIM' => [278.640, 638.640], // = (   98 x 225  ) mm  = (  3.87 x 8.87  ) in
298
		// - Commercial Envelopes
299
		'COMMENV_N6_1/4' => [252.000, 432.000], // = (   89 x 152  ) mm  = (  3.50 x 6.00  ) in
300
		'COMMENV_N6_3/4' => [260.640, 468.000], // = (   92 x 165  ) mm  = (  3.62 x 6.50  ) in
301
		'COMMENV_N8' => [278.640, 540.000], // = (   98 x 191  ) mm  = (  3.87 x 7.50  ) in
302
		'COMMENV_N9' => [278.640, 638.640], // = (   98 x 225  ) mm  = (  3.87 x 8.87  ) in
303
		'COMMENV_N10' => [296.640, 684.000], // = (  105 x 241  ) mm  = (  4.12 x 9.50  ) in
304
		'COMMENV_N11' => [324.000, 746.640], // = (  114 x 263  ) mm  = (  4.50 x 10.37 ) in
305
		'COMMENV_N12' => [342.000, 792.000], // = (  121 x 279  ) mm  = (  4.75 x 11.00 ) in
306
		'COMMENV_N14' => [360.000, 828.000], // = (  127 x 292  ) mm  = (  5.00 x 11.50 ) in
307
		// - Catalogue Envelopes
308
		'CATENV_N1' => [432.000, 648.000], // = (  152 x 229  ) mm  = (  6.00 x 9.00  ) in
309
		'CATENV_N1_3/4' => [468.000, 684.000], // = (  165 x 241  ) mm  = (  6.50 x 9.50  ) in
310
		'CATENV_N2' => [468.000, 720.000], // = (  165 x 254  ) mm  = (  6.50 x 10.00 ) in
311
		'CATENV_N3' => [504.000, 720.000], // = (  178 x 254  ) mm  = (  7.00 x 10.00 ) in
312
		'CATENV_N6' => [540.000, 756.000], // = (  191 x 267  ) mm  = (  7.50 x 10.50 ) in
313
		'CATENV_N7' => [576.000, 792.000], // = (  203 x 279  ) mm  = (  8.00 x 11.00 ) in
314
		'CATENV_N8' => [594.000, 810.000], // = (  210 x 286  ) mm  = (  8.25 x 11.25 ) in
315
		'CATENV_N9_1/2' => [612.000, 756.000], // = (  216 x 267  ) mm  = (  8.50 x 10.50 ) in
316
		'CATENV_N9_3/4' => [630.000, 810.000], // = (  222 x 286  ) mm  = (  8.75 x 11.25 ) in
317
		'CATENV_N10_1/2' => [648.000, 864.000], // = (  229 x 305  ) mm  = (  9.00 x 12.00 ) in
318
		'CATENV_N12_1/2' => [684.000, 900.000], // = (  241 x 318  ) mm  = (  9.50 x 12.50 ) in
319
		'CATENV_N13_1/2' => [720.000, 936.000], // = (  254 x 330  ) mm  = ( 10.00 x 13.00 ) in
320
		'CATENV_N14_1/4' => [810.000, 882.000], // = (  286 x 311  ) mm  = ( 11.25 x 12.25 ) in
321
		'CATENV_N14_1/2' => [828.000, 1044.000], // = (  292 x 368  ) mm  = ( 11.50 x 14.50 ) in
322
		// Japanese (JIS P 0138-61) Standard B-Series
323
		'JIS_B0' => [2919.685, 4127.244], // = ( 1030 x 1456 ) mm  = ( 40.55 x 57.32 ) in
324
		'JIS_B1' => [2063.622, 2919.685], // = (  728 x 1030 ) mm  = ( 28.66 x 40.55 ) in
325
		'JIS_B2' => [1459.843, 2063.622], // = (  515 x 728  ) mm  = ( 20.28 x 28.66 ) in
326
		'JIS_B3' => [1031.811, 1459.843], // = (  364 x 515  ) mm  = ( 14.33 x 20.28 ) in
327
		'JIS_B4' => [728.504, 1031.811], // = (  257 x 364  ) mm  = ( 10.12 x 14.33 ) in
328
		'JIS_B5' => [515.906, 728.504], // = (  182 x 257  ) mm  = (  7.17 x 10.12 ) in
329
		'JIS_B6' => [362.835, 515.906], // = (  128 x 182  ) mm  = (  5.04 x 7.17  ) in
330
		'JIS_B7' => [257.953, 362.835], // = (   91 x 128  ) mm  = (  3.58 x 5.04  ) in
331
		'JIS_B8' => [181.417, 257.953], // = (   64 x 91   ) mm  = (  2.52 x 3.58  ) in
332
		'JIS_B9' => [127.559, 181.417], // = (   45 x 64   ) mm  = (  1.77 x 2.52  ) in
333
		'JIS_B10' => [90.709, 127.559], // = (   32 x 45   ) mm  = (  1.26 x 1.77  ) in
334
		'JIS_B11' => [62.362, 90.709], // = (   22 x 32   ) mm  = (  0.87 x 1.26  ) in
335
		'JIS_B12' => [45.354, 62.362], // = (   16 x 22   ) mm  = (  0.63 x 0.87  ) in
336
		// PA Series
337
		'PA0' => [2381.102, 3174.803], // = (  840 x 1120 ) mm  = ( 33.07 x 44.09 ) in
338
		'PA1' => [1587.402, 2381.102], // = (  560 x 840  ) mm  = ( 22.05 x 33.07 ) in
339
		'PA2' => [1190.551, 1587.402], // = (  420 x 560  ) mm  = ( 16.54 x 22.05 ) in
340
		'PA3' => [793.701, 1190.551], // = (  280 x 420  ) mm  = ( 11.02 x 16.54 ) in
341
		'PA4' => [595.276, 793.701], // = (  210 x 280  ) mm  = (  8.27 x 11.02 ) in
342
		'PA5' => [396.850, 595.276], // = (  140 x 210  ) mm  = (  5.51 x 8.27  ) in
343
		'PA6' => [297.638, 396.850], // = (  105 x 140  ) mm  = (  4.13 x 5.51  ) in
344
		'PA7' => [198.425, 297.638], // = (   70 x 105  ) mm  = (  2.76 x 4.13  ) in
345
		'PA8' => [147.402, 198.425], // = (   52 x 70   ) mm  = (  2.05 x 2.76  ) in
346
		'PA9' => [99.213, 147.402], // = (   35 x 52   ) mm  = (  1.38 x 2.05  ) in
347
		'PA10' => [73.701, 99.213], // = (   26 x 35   ) mm  = (  1.02 x 1.38  ) in
348
		// Standard Photographic Print Sizes
349
		'PASSPORT_PHOTO' => [99.213, 127.559], // = (   35 x 45   ) mm  = (  1.38 x 1.77  ) in
350
		'E' => [233.858, 340.157], // = (   82 x 120  ) mm  = (  3.25 x 4.72  ) in
351
		'L' => [252.283, 360.000], // = (   89 x 127  ) mm  = (  3.50 x 5.00  ) in
352
		'3R' => [252.283, 360.000], // = (   89 x 127  ) mm  = (  3.50 x 5.00  ) in
353
		'KG' => [289.134, 430.866], // = (  102 x 152  ) mm  = (  4.02 x 5.98  ) in
354
		'4R' => [289.134, 430.866], // = (  102 x 152  ) mm  = (  4.02 x 5.98  ) in
355
		'4D' => [340.157, 430.866], // = (  120 x 152  ) mm  = (  4.72 x 5.98  ) in
356
		'2L' => [360.000, 504.567], // = (  127 x 178  ) mm  = (  5.00 x 7.01  ) in
357
		'5R' => [360.000, 504.567], // = (  127 x 178  ) mm  = (  5.00 x 7.01  ) in
358
		'8P' => [430.866, 575.433], // = (  152 x 203  ) mm  = (  5.98 x 7.99  ) in
359
		'6R' => [430.866, 575.433], // = (  152 x 203  ) mm  = (  5.98 x 7.99  ) in
360
		'6P' => [575.433, 720.000], // = (  203 x 254  ) mm  = (  7.99 x 10.00 ) in
361
		'8R' => [575.433, 720.000], // = (  203 x 254  ) mm  = (  7.99 x 10.00 ) in
362
		'6PW' => [575.433, 864.567], // = (  203 x 305  ) mm  = (  7.99 x 12.01 ) in
363
		'S8R' => [575.433, 864.567], // = (  203 x 305  ) mm  = (  7.99 x 12.01 ) in
364
		'4P' => [720.000, 864.567], // = (  254 x 305  ) mm  = ( 10.00 x 12.01 ) in
365
		'10R' => [720.000, 864.567], // = (  254 x 305  ) mm  = ( 10.00 x 12.01 ) in
366
		'4PW' => [720.000, 1080.000], // = (  254 x 381  ) mm  = ( 10.00 x 15.00 ) in
367
		'S10R' => [720.000, 1080.000], // = (  254 x 381  ) mm  = ( 10.00 x 15.00 ) in
368
		'11R' => [790.866, 1009.134], // = (  279 x 356  ) mm  = ( 10.98 x 14.02 ) in
369
		'S11R' => [790.866, 1224.567], // = (  279 x 432  ) mm  = ( 10.98 x 17.01 ) in
370
		'12R' => [864.567, 1080.000], // = (  305 x 381  ) mm  = ( 12.01 x 15.00 ) in
371
		'S12R' => [864.567, 1292.598], // = (  305 x 456  ) mm  = ( 12.01 x 17.95 ) in
372
		// Common Newspaper Sizes
373
		'NEWSPAPER_BROADSHEET' => [2125.984, 1700.787], // = (  750 x 600  ) mm  = ( 29.53 x 23.62 ) in
374
		'NEWSPAPER_BERLINER' => [1332.283, 892.913], // = (  470 x 315  ) mm  = ( 18.50 x 12.40 ) in
375
		'NEWSPAPER_TABLOID' => [1218.898, 793.701], // = (  430 x 280  ) mm  = ( 16.93 x 11.02 ) in
376
		'NEWSPAPER_COMPACT' => [1218.898, 793.701], // = (  430 x 280  ) mm  = ( 16.93 x 11.02 ) in
377
		// Business Cards
378
		'CREDIT_CARD' => [153.014, 242.646], // = (   54 x 86   ) mm  = (  2.13 x 3.37  ) in
379
		'BUSINESS_CARD' => [153.014, 242.646], // = (   54 x 86   ) mm  = (  2.13 x 3.37  ) in
380
		'BUSINESS_CARD_ISO7810' => [153.014, 242.646], // = (   54 x 86   ) mm  = (  2.13 x 3.37  ) in
381
		'BUSINESS_CARD_ISO216' => [147.402, 209.764], // = (   52 x 74   ) mm  = (  2.05 x 2.91  ) in
382
		'BUSINESS_CARD_IT' => [155.906, 240.945], // = (   55 x 85   ) mm  = (  2.17 x 3.35  ) in
383
		'BUSINESS_CARD_UK' => [155.906, 240.945], // = (   55 x 85   ) mm  = (  2.17 x 3.35  ) in
384
		'BUSINESS_CARD_FR' => [155.906, 240.945], // = (   55 x 85   ) mm  = (  2.17 x 3.35  ) in
385
		'BUSINESS_CARD_DE' => [155.906, 240.945], // = (   55 x 85   ) mm  = (  2.17 x 3.35  ) in
386
		'BUSINESS_CARD_ES' => [155.906, 240.945], // = (   55 x 85   ) mm  = (  2.17 x 3.35  ) in
387
		'BUSINESS_CARD_CA' => [144.567, 252.283], // = (   51 x 89   ) mm  = (  2.01 x 3.50  ) in
388
		'BUSINESS_CARD_US' => [144.567, 252.283], // = (   51 x 89   ) mm  = (  2.01 x 3.50  ) in
389
		'BUSINESS_CARD_JP' => [155.906, 257.953], // = (   55 x 91   ) mm  = (  2.17 x 3.58  ) in
390
		'BUSINESS_CARD_HK' => [153.071, 255.118], // = (   54 x 90   ) mm  = (  2.13 x 3.54  ) in
391
		'BUSINESS_CARD_AU' => [155.906, 255.118], // = (   55 x 90   ) mm  = (  2.17 x 3.54  ) in
392
		'BUSINESS_CARD_DK' => [155.906, 255.118], // = (   55 x 90   ) mm  = (  2.17 x 3.54  ) in
393
		'BUSINESS_CARD_SE' => [155.906, 255.118], // = (   55 x 90   ) mm  = (  2.17 x 3.54  ) in
394
		'BUSINESS_CARD_RU' => [141.732, 255.118], // = (   50 x 90   ) mm  = (  1.97 x 3.54  ) in
395
		'BUSINESS_CARD_CZ' => [141.732, 255.118], // = (   50 x 90   ) mm  = (  1.97 x 3.54  ) in
396
		'BUSINESS_CARD_FI' => [141.732, 255.118], // = (   50 x 90   ) mm  = (  1.97 x 3.54  ) in
397
		'BUSINESS_CARD_HU' => [141.732, 255.118], // = (   50 x 90   ) mm  = (  1.97 x 3.54  ) in
398
		'BUSINESS_CARD_IL' => [141.732, 255.118], // = (   50 x 90   ) mm  = (  1.97 x 3.54  ) in
399
		// Billboards
400
		'4SHEET' => [2880.000, 4320.000], // = ( 1016 x 1524 ) mm  = ( 40.00 x 60.00 ) in
401
		'6SHEET' => [3401.575, 5102.362], // = ( 1200 x 1800 ) mm  = ( 47.24 x 70.87 ) in
402
		'12SHEET' => [8640.000, 4320.000], // = ( 3048 x 1524 ) mm  = (120.00 x 60.00 ) in
403
		'16SHEET' => [5760.000, 8640.000], // = ( 2032 x 3048 ) mm  = ( 80.00 x 120.00) in
404
		'32SHEET' => [11520.000, 8640.000], // = ( 4064 x 3048 ) mm  = (160.00 x 120.00) in
405
		'48SHEET' => [17280.000, 8640.000], // = ( 6096 x 3048 ) mm  = (240.00 x 120.00) in
406
		'64SHEET' => [23040.000, 8640.000], // = ( 8128 x 3048 ) mm  = (320.00 x 120.00) in
407
		'96SHEET' => [34560.000, 8640.000], // = (12192 x 3048 ) mm  = (480.00 x 120.00) in
408
		// -- Old European Sizes
409
		// - Old Imperial English Sizes
410
		'EN_EMPEROR' => [3456.000, 5184.000], // = ( 1219 x 1829 ) mm  = ( 48.00 x 72.00 ) in
411
		'EN_ANTIQUARIAN' => [2232.000, 3816.000], // = (  787 x 1346 ) mm  = ( 31.00 x 53.00 ) in
412
		'EN_GRAND_EAGLE' => [2070.000, 3024.000], // = (  730 x 1067 ) mm  = ( 28.75 x 42.00 ) in
413
		'EN_DOUBLE_ELEPHANT' => [1926.000, 2880.000], // = (  679 x 1016 ) mm  = ( 26.75 x 40.00 ) in
414
		'EN_ATLAS' => [1872.000, 2448.000], // = (  660 x 864  ) mm  = ( 26.00 x 34.00 ) in
415
		'EN_COLOMBIER' => [1692.000, 2484.000], // = (  597 x 876  ) mm  = ( 23.50 x 34.50 ) in
416
		'EN_ELEPHANT' => [1656.000, 2016.000], // = (  584 x 711  ) mm  = ( 23.00 x 28.00 ) in
417
		'EN_DOUBLE_DEMY' => [1620.000, 2556.000], // = (  572 x 902  ) mm  = ( 22.50 x 35.50 ) in
418
		'EN_IMPERIAL' => [1584.000, 2160.000], // = (  559 x 762  ) mm  = ( 22.00 x 30.00 ) in
419
		'EN_PRINCESS' => [1548.000, 2016.000], // = (  546 x 711  ) mm  = ( 21.50 x 28.00 ) in
420
		'EN_CARTRIDGE' => [1512.000, 1872.000], // = (  533 x 660  ) mm  = ( 21.00 x 26.00 ) in
421
		'EN_DOUBLE_LARGE_POST' => [1512.000, 2376.000], // = (  533 x 838  ) mm  = ( 21.00 x 33.00 ) in
422
		'EN_ROYAL' => [1440.000, 1800.000], // = (  508 x 635  ) mm  = ( 20.00 x 25.00 ) in
423
		'EN_SHEET' => [1404.000, 1692.000], // = (  495 x 597  ) mm  = ( 19.50 x 23.50 ) in
424
		'EN_HALF_POST' => [1404.000, 1692.000], // = (  495 x 597  ) mm  = ( 19.50 x 23.50 ) in
425
		'EN_SUPER_ROYAL' => [1368.000, 1944.000], // = (  483 x 686  ) mm  = ( 19.00 x 27.00 ) in
426
		'EN_DOUBLE_POST' => [1368.000, 2196.000], // = (  483 x 775  ) mm  = ( 19.00 x 30.50 ) in
427
		'EN_MEDIUM' => [1260.000, 1656.000], // = (  445 x 584  ) mm  = ( 17.50 x 23.00 ) in
428
		'EN_DEMY' => [1260.000, 1620.000], // = (  445 x 572  ) mm  = ( 17.50 x 22.50 ) in
429
		'EN_LARGE_POST' => [1188.000, 1512.000], // = (  419 x 533  ) mm  = ( 16.50 x 21.00 ) in
430
		'EN_COPY_DRAUGHT' => [1152.000, 1440.000], // = (  406 x 508  ) mm  = ( 16.00 x 20.00 ) in
431
		'EN_POST' => [1116.000, 1386.000], // = (  394 x 489  ) mm  = ( 15.50 x 19.25 ) in
432
		'EN_CROWN' => [1080.000, 1440.000], // = (  381 x 508  ) mm  = ( 15.00 x 20.00 ) in
433
		'EN_PINCHED_POST' => [1062.000, 1332.000], // = (  375 x 470  ) mm  = ( 14.75 x 18.50 ) in
434
		'EN_BRIEF' => [972.000, 1152.000], // = (  343 x 406  ) mm  = ( 13.50 x 16.00 ) in
435
		'EN_FOOLSCAP' => [972.000, 1224.000], // = (  343 x 432  ) mm  = ( 13.50 x 17.00 ) in
436
		'EN_SMALL_FOOLSCAP' => [954.000, 1188.000], // = (  337 x 419  ) mm  = ( 13.25 x 16.50 ) in
437
		'EN_POTT' => [900.000, 1080.000], // = (  318 x 381  ) mm  = ( 12.50 x 15.00 ) in
438
		// - Old Imperial Belgian Sizes
439
		'BE_GRAND_AIGLE' => [1984.252, 2948.031], // = (  700 x 1040 ) mm  = ( 27.56 x 40.94 ) in
440
		'BE_COLOMBIER' => [1757.480, 2409.449], // = (  620 x 850  ) mm  = ( 24.41 x 33.46 ) in
441
		'BE_DOUBLE_CARRE' => [1757.480, 2607.874], // = (  620 x 920  ) mm  = ( 24.41 x 36.22 ) in
442
		'BE_ELEPHANT' => [1746.142, 2182.677], // = (  616 x 770  ) mm  = ( 24.25 x 30.31 ) in
443
		'BE_PETIT_AIGLE' => [1700.787, 2381.102], // = (  600 x 840  ) mm  = ( 23.62 x 33.07 ) in
444
		'BE_GRAND_JESUS' => [1559.055, 2069.291], // = (  550 x 730  ) mm  = ( 21.65 x 28.74 ) in
445
		'BE_JESUS' => [1530.709, 2069.291], // = (  540 x 730  ) mm  = ( 21.26 x 28.74 ) in
446
		'BE_RAISIN' => [1417.323, 1842.520], // = (  500 x 650  ) mm  = ( 19.69 x 25.59 ) in
447
		'BE_GRAND_MEDIAN' => [1303.937, 1714.961], // = (  460 x 605  ) mm  = ( 18.11 x 23.82 ) in
448
		'BE_DOUBLE_POSTE' => [1233.071, 1601.575], // = (  435 x 565  ) mm  = ( 17.13 x 22.24 ) in
449
		'BE_COQUILLE' => [1218.898, 1587.402], // = (  430 x 560  ) mm  = ( 16.93 x 22.05 ) in
450
		'BE_PETIT_MEDIAN' => [1176.378, 1502.362], // = (  415 x 530  ) mm  = ( 16.34 x 20.87 ) in
451
		'BE_RUCHE' => [1020.472, 1303.937], // = (  360 x 460  ) mm  = ( 14.17 x 18.11 ) in
452
		'BE_PROPATRIA' => [977.953, 1218.898], // = (  345 x 430  ) mm  = ( 13.58 x 16.93 ) in
453
		'BE_LYS' => [898.583, 1125.354], // = (  317 x 397  ) mm  = ( 12.48 x 15.63 ) in
454
		'BE_POT' => [870.236, 1088.504], // = (  307 x 384  ) mm  = ( 12.09 x 15.12 ) in
455
		'BE_ROSETTE' => [765.354, 983.622], // = (  270 x 347  ) mm  = ( 10.63 x 13.66 ) in
456
		// - Old Imperial French Sizes
457
		'FR_UNIVERS' => [2834.646, 3685.039], // = ( 1000 x 1300 ) mm  = ( 39.37 x 51.18 ) in
458
		'FR_DOUBLE_COLOMBIER' => [2551.181, 3571.654], // = (  900 x 1260 ) mm  = ( 35.43 x 49.61 ) in
459
		'FR_GRANDE_MONDE' => [2551.181, 3571.654], // = (  900 x 1260 ) mm  = ( 35.43 x 49.61 ) in
460
		'FR_DOUBLE_SOLEIL' => [2267.717, 3401.575], // = (  800 x 1200 ) mm  = ( 31.50 x 47.24 ) in
461
		'FR_DOUBLE_JESUS' => [2154.331, 3174.803], // = (  760 x 1120 ) mm  = ( 29.92 x 44.09 ) in
462
		'FR_GRAND_AIGLE' => [2125.984, 3004.724], // = (  750 x 1060 ) mm  = ( 29.53 x 41.73 ) in
463
		'FR_PETIT_AIGLE' => [1984.252, 2664.567], // = (  700 x 940  ) mm  = ( 27.56 x 37.01 ) in
464
		'FR_DOUBLE_RAISIN' => [1842.520, 2834.646], // = (  650 x 1000 ) mm  = ( 25.59 x 39.37 ) in
465
		'FR_JOURNAL' => [1842.520, 2664.567], // = (  650 x 940  ) mm  = ( 25.59 x 37.01 ) in
466
		'FR_COLOMBIER_AFFICHE' => [1785.827, 2551.181], // = (  630 x 900  ) mm  = ( 24.80 x 35.43 ) in
467
		'FR_DOUBLE_CAVALIER' => [1757.480, 2607.874], // = (  620 x 920  ) mm  = ( 24.41 x 36.22 ) in
468
		'FR_CLOCHE' => [1700.787, 2267.717], // = (  600 x 800  ) mm  = ( 23.62 x 31.50 ) in
469
		'FR_SOLEIL' => [1700.787, 2267.717], // = (  600 x 800  ) mm  = ( 23.62 x 31.50 ) in
470
		'FR_DOUBLE_CARRE' => [1587.402, 2551.181], // = (  560 x 900  ) mm  = ( 22.05 x 35.43 ) in
471
		'FR_DOUBLE_COQUILLE' => [1587.402, 2494.488], // = (  560 x 880  ) mm  = ( 22.05 x 34.65 ) in
472
		'FR_JESUS' => [1587.402, 2154.331], // = (  560 x 760  ) mm  = ( 22.05 x 29.92 ) in
473
		'FR_RAISIN' => [1417.323, 1842.520], // = (  500 x 650  ) mm  = ( 19.69 x 25.59 ) in
474
		'FR_CAVALIER' => [1303.937, 1757.480], // = (  460 x 620  ) mm  = ( 18.11 x 24.41 ) in
475
		'FR_DOUBLE_COURONNE' => [1303.937, 2040.945], // = (  460 x 720  ) mm  = ( 18.11 x 28.35 ) in
476
		'FR_CARRE' => [1275.591, 1587.402], // = (  450 x 560  ) mm  = ( 17.72 x 22.05 ) in
477
		'FR_COQUILLE' => [1247.244, 1587.402], // = (  440 x 560  ) mm  = ( 17.32 x 22.05 ) in
478
		'FR_DOUBLE_TELLIERE' => [1247.244, 1927.559], // = (  440 x 680  ) mm  = ( 17.32 x 26.77 ) in
479
		'FR_DOUBLE_CLOCHE' => [1133.858, 1700.787], // = (  400 x 600  ) mm  = ( 15.75 x 23.62 ) in
480
		'FR_DOUBLE_POT' => [1133.858, 1757.480], // = (  400 x 620  ) mm  = ( 15.75 x 24.41 ) in
481
		'FR_ECU' => [1133.858, 1474.016], // = (  400 x 520  ) mm  = ( 15.75 x 20.47 ) in
482
		'FR_COURONNE' => [1020.472, 1303.937], // = (  360 x 460  ) mm  = ( 14.17 x 18.11 ) in
483
		'FR_TELLIERE' => [963.780, 1247.244], // = (  340 x 440  ) mm  = ( 13.39 x 17.32 ) in
484
		'FR_POT' => [878.740, 1133.858], // = (  310 x 400  ) mm  = ( 12.20 x 15.75 ) in
485
	];
486
487
	/**
488
	 * Initialisation.
489
	 *
490
	 * @return $this
491
	 */
492
	public function init()
493
	{
494
		parent::init();
495
		$this->contentStream = (new \YetiForcePDF\Objects\Basic\StreamObject())
496
			->setDocument($this->document)
497
			->init();
498
		if (!$this->margins) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $this->margins of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using empty($expr) instead to make it clear that you intend to check for an array without elements.

This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent.

Consider making the comparison explicit by using empty(..) or ! empty(...) instead.

Loading history...
499
			$this->margins = $this->document->getDefaultMargins();
500
		}
501
		if (!$this->format) {
502
			$this->setFormat($this->document->getDefaultFormat());
503
		}
504
		if (!$this->orientation) {
505
			$this->setOrientation($this->document->getDefaultOrientation());
506
		}
507
		$this->document->getPagesObject()->addChild($this);
508
		$this->synchronizeFonts();
509
		return $this;
510
	}
511
512
	/**
513
	 * Set page group.
514
	 *
515
	 * @param int $group
516
	 *
517
	 * @return $this
518
	 */
519
	public function setGroup(int $group)
520
	{
521
		$this->group = $group;
522
		return $this;
523
	}
524
525
	/**
526
	 * Get page group.
527
	 *
528
	 * @return int
529
	 */
530
	public function getGroup()
531
	{
532
		return $this->group;
533
	}
534
535
	/**
536
	 * Set page format.
537
	 *
538
	 * @param string $format
539
	 *
540
	 * @return $this
541
	 */
542
	public function setFormat(string $format)
543
	{
544
		$this->format = $format;
545
		$dimensions = self::$pageFormats[$this->format];
546
		if ('L' === $this->orientation) {
547
			$dimensions = array_reverse($dimensions);
548
		}
549
		$this->dimensions = (new Dimensions())
550
			->setDocument($this->document)
551
			->init();
552
		$this->dimensions
553
			->setWidth(Math::sub((string) $dimensions[0], Math::add((string) $this->margins['left'], (string) $this->margins['right'])))
554
			->setHeight(Math::sub((string) $dimensions[1], Math::add((string) $this->margins['top'], (string) $this->margins['bottom'])));
555
		$this->outerDimensions = (new Dimensions())
556
			->setDocument($this->document)
557
			->init();
558
		$this->outerDimensions->setWidth((string) $dimensions[0])->setHeight((string) $dimensions[1]);
559
		$this->coordinates = (new Coordinates())
560
			->setDocument($this->document)
561
			->init();
562
		$this->coordinates->setX((string) $this->margins['left'])->setY((string) $this->margins['top'])->init();
563
		return $this;
564
	}
565
566
	/**
567
	 * Get format.
568
	 *
569
	 * @return string
570
	 */
571
	public function getFormat()
572
	{
573
		return $this->format;
574
	}
575
576
	/**
577
	 * Set page orientation.
578
	 *
579
	 * @param string $orientation
580
	 *
581
	 * @return \YetiForcePDF\Page
582
	 */
583
	public function setOrientation(string $orientation): self
584
	{
585
		$this->orientation = $orientation;
586
		return $this;
587
	}
588
589
	/**
590
	 * Get orientation.
591
	 *
592
	 * @return string
593
	 */
594
	public function getOrientation()
595
	{
596
		return $this->orientation;
597
	}
598
599
	/**
600
	 * Set page number.
601
	 *
602
	 * @param int $number
603
	 *
604
	 * @return $this
605
	 */
606
	public function setPageNumber(int $number)
607
	{
608
		$this->pageNumber = $number;
609
		return $this;
610
	}
611
612
	/**
613
	 * Get page number.
614
	 *
615
	 * @return int
616
	 */
617
	public function getPageNumber()
618
	{
619
		return $this->pageNumber;
620
	}
621
622
	/**
623
	 * Set page count.
624
	 *
625
	 * @param int $pageCount
626
	 *
627
	 * @return $this
628
	 */
629
	public function setPageCount(int $pageCount)
630
	{
631
		$this->pageCount = $pageCount;
632
		return $this;
633
	}
634
635
	/**
636
	 * Get page count.
637
	 *
638
	 * @return mixed
639
	 */
640
	public function getPageCount()
641
	{
642
		return $this->pageCount;
643
	}
644
645
	/**
646
	 * Get page margins.
647
	 *
648
	 * @return array
649
	 */
650
	public function getMargins(): array
651
	{
652
		return $this->margins;
653
	}
654
655
	/**
656
	 * Set page margins.
657
	 *
658
	 * @param float $left
659
	 * @param float $top
660
	 * @param float $right
661
	 * @param float $bottom
662
	 *
663
	 * @return $this
664
	 */
665
	public function setMargins(float $left, float $top, float $right, float $bottom)
666
	{
667
		$this->margins = [
668
			'left' => $left,
669
			'top' => $top,
670
			'right' => $right,
671
			'bottom' => $bottom,
672
			'horizontal' => $left + $right,
673
			'vertical' => $top + $bottom,
674
		];
675
		$this->setFormat($this->format);
676
		return $this;
677
	}
678
679
	/**
680
	 * Get page coordinates - content area basing on margins.
681
	 *
682
	 * @return \YetiForcePDF\Layout\Coordinates\Coordinates
683
	 */
684
	public function getCoordinates()
685
	{
686
		return $this->coordinates;
687
	}
688
689
	/**
690
	 * Set main box for the page.
691
	 *
692
	 * @param Box $box
693
	 *
694
	 * @return $this
695
	 */
696
	public function setBox(Box $box)
697
	{
698
		$this->box = $box;
699
		return $this;
700
	}
701
702
	/**
703
	 * Get main box for the page.
704
	 *
705
	 * @return Box
706
	 */
707
	public function getBox()
708
	{
709
		return $this->box;
710
	}
711
712
	/**
713
	 * Set user unit (scale of the DPI $userUnit * 72).
714
	 *
715
	 * @param float $userUnit
716
	 *
717
	 * @return \YetiForcePDF\Page
718
	 */
719
	public function setUserUnit(float $userUnit): self
720
	{
721
		$this->userUnit = $userUnit;
722
		return $this;
723
	}
724
725
	/**
726
	 * Add page resource.
727
	 *
728
	 * @param string                          $groupName
729
	 * @param string                          $resourceName
730
	 * @param \YetiForcePDF\Objects\PdfObject $resource
731
	 *
732
	 * @return \YetiForcePDF\Page
733
	 */
734
	public function addResource(string $groupName, string $resourceName, Objects\PdfObject $resource): self
735
	{
736
		if (!isset($this->resources[$groupName])) {
737
			$this->resources[$groupName] = [];
738
		}
739
		$this->resources[$groupName][$resourceName] = $resource;
740
		if (!$resourceName) {
741
			$this->doNotGroup[] = $groupName;
742
		}
743
		return $this;
744
	}
745
746
	/**
747
	 * Get resource.
748
	 *
749
	 * @param string $groupName
750
	 * @param string $resourceName
751
	 *
752
	 * @return \YetiForcePDF\Objects\PdfObject|null
753
	 */
754
	public function getResource(string $groupName, string $resourceName)
755
	{
756
		if (!empty($this->resources[$groupName][$resourceName])) {
757
			return $this->resources[$groupName][$resourceName];
758
		}
759
		return null;
760
	}
761
762
	/**
763
	 * Synchronize fonts with document fonts.
764
	 */
765
	public function synchronizeFonts()
766
	{
767
		// add all existing fonts
768
		foreach ($this->document->getAllFontInstances() as $fontInstance) {
769
			$fontNumber = $fontInstance->getNumber();
770
			if (!$this->getResource('Font', $fontNumber)) {
771
				$this->addResource('Font', $fontNumber, $fontInstance->getType0Font());
772
			}
773
		}
774
	}
775
776
	/**
777
	 * Get page content stream.
778
	 *
779
	 * @return \YetiForcePDF\Objects\Basic\StreamObject
780
	 */
781
	public function getContentStream(): StreamObject
782
	{
783
		return $this->contentStream;
784
	}
785
786
	/**
787
	 * Get page dimensions.
788
	 *
789
	 * @return \YetiForcePDF\Layout\Dimensions\Dimensions
790
	 */
791
	public function getDimensions(): Dimensions
792
	{
793
		return $this->dimensions;
794
	}
795
796
	/**
797
	 * Get page dimensions.
798
	 *
799
	 * @return \YetiForcePDF\Layout\Dimensions\Dimensions
800
	 */
801
	public function getOuterDimensions(): Dimensions
802
	{
803
		return $this->outerDimensions;
804
	}
805
806
	/**
807
	 * Layout header.
808
	 *
809
	 * @param HeaderBox $header
810
	 *
811
	 * @return $this
812
	 */
813
	protected function layoutHeader(HeaderBox $header)
814
	{
815
		$header = $header->cloneWithChildren();
816
		$box = $this->getBox();
817
		if (!$box->hasChildren()) {
818
			return $this;
819
		}
820
		$box->insertBefore($header, $box->getFirstChild());
0 ignored issues
show
It seems like $box->getFirstChild() can also be of type null; however, parameter $before of YetiForcePDF\Layout\Box::insertBefore() does only seem to accept YetiForcePDF\Layout\Box, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

820
		$box->insertBefore($header, /** @scrutinizer ignore-type */ $box->getFirstChild());
Loading history...
821
		$outerWidth = $this->getOuterDimensions()->getWidth();
822
		$outerHeight = $this->getOuterDimensions()->getHeight();
823
		$header->getDimensions()->resetWidth()->resetHeight();
824
		$this->getDimensions()->setWidth($outerWidth);
825
		$this->getBox()->getDimensions()->setWidth($outerWidth);
826
		$this->getDimensions()->setHeight($outerHeight);
827
		$this->getBox()->getDimensions()->setWidth($outerHeight);
828
		$header->getDimensions()->setWidth($outerWidth);
829
		$header->setDisplayable(true);
830
		$header->layout();
831
		return $this;
832
	}
833
834
	/**
835
	 * Layout footer.
836
	 *
837
	 * @param FooterBox $footer
838
	 *
839
	 * @return $this
840
	 */
841
	protected function layoutFooter(FooterBox $footer)
842
	{
843
		$footer = $footer->cloneWithChildren();
844
		$box = $this->getBox();
845
		if (!$box->hasChildren()) {
846
			return $this;
847
		}
848
		$box->insertBefore($footer, $box->getFirstChild());
0 ignored issues
show
It seems like $box->getFirstChild() can also be of type null; however, parameter $before of YetiForcePDF\Layout\Box::insertBefore() does only seem to accept YetiForcePDF\Layout\Box, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

848
		$box->insertBefore($footer, /** @scrutinizer ignore-type */ $box->getFirstChild());
Loading history...
849
		$outerWidth = $this->getOuterDimensions()->getWidth();
850
		$outerHeight = $this->getOuterDimensions()->getHeight();
851
		$footer->getDimensions()->resetWidth()->resetHeight();
852
		$this->getDimensions()->setWidth($outerWidth);
853
		$this->getBox()->getDimensions()->setWidth($outerWidth);
854
		$this->getDimensions()->setHeight($outerHeight);
855
		$this->getBox()->getDimensions()->setWidth($outerHeight);
856
		$footer->getDimensions()->setWidth($outerWidth);
857
		$footer->setDisplayable(true);
858
		$footer->layout();
859
		return $this;
860
	}
861
862
	/**
863
	 * Layout watermark.
864
	 *
865
	 * @param WatermarkBox $watermark
866
	 *
867
	 * @return $this
868
	 */
869
	protected function layoutWatermark(WatermarkBox $watermark)
870
	{
871
		$watermark = $watermark->cloneWithChildren();
872
		$box = $this->getBox();
873
		if (!$box->hasChildren()) {
874
			return $this;
875
		}
876
		$box->insertBefore($watermark, $box->getFirstChild());
0 ignored issues
show
It seems like $box->getFirstChild() can also be of type null; however, parameter $before of YetiForcePDF\Layout\Box::insertBefore() does only seem to accept YetiForcePDF\Layout\Box, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

876
		$box->insertBefore($watermark, /** @scrutinizer ignore-type */ $box->getFirstChild());
Loading history...
877
		$outerWidth = $this->getOuterDimensions()->getWidth();
878
		$outerHeight = $this->getOuterDimensions()->getHeight();
879
		$watermark->getDimensions()->resetWidth()->resetHeight();
880
		$this->getDimensions()->setWidth($outerWidth);
881
		$this->getBox()->getDimensions()->setWidth($outerWidth);
882
		$this->getDimensions()->setHeight($outerHeight);
883
		$this->getBox()->getDimensions()->setWidth($outerHeight);
884
		$watermark->getDimensions()->setWidth($outerWidth);
885
		$watermark->setDisplayable(true);
886
		$watermark->layout();
887
		return $this;
888
	}
889
890
	/**
891
	 * Set up absolute positioned boxes like header,footer, watermark.
892
	 *
893
	 * @return $this
894
	 */
895
	public function setUpAbsoluteBoxes()
896
	{
897
		$this->document->setCurrentPage($this);
898
		$this->getBox()->getOffset()->setLeft('0');
899
		$this->getBox()->getOffset()->setTop('0');
900
		$this->getBox()->getCoordinates()->setX('0');
901
		$this->getBox()->getCoordinates()->setY('0');
902
		$this->setMargins(0, 0, 0, 0);
903
		$box = $this->getBox();
904
		$headers = $box->getBoxesByType('HeaderBox');
905
		if (!empty($headers)) {
906
			$header = $headers[0];
907
			$headerClone = $header->getParent()->removeChild($header)->cloneWithChildren();
908
			$header->clearChildren();
909
			$this->document->setHeader($headerClone);
910
			$this->layoutHeader($headerClone);
911
		} elseif ($this->document->getHeader()) {
912
			$this->layoutHeader($this->document->getHeader());
913
		}
914
		$footers = $box->getBoxesByType('FooterBox');
915
		if (!empty($footers)) {
916
			$footer = $footers[0];
917
			$footerClone = $footer->getParent()->removeChild($footer)->cloneWithChildren();
918
			$footer->clearChildren();
919
			$this->document->setFooter($footerClone);
920
			$this->layoutFooter($footerClone);
921
		} elseif ($this->document->getFooter()) {
922
			$this->layoutFooter($this->document->getFooter());
923
		}
924
		$watermarks = $box->getBoxesByType('WatermarkBox');
925
		if (!empty($watermarks)) {
926
			$watermark = $watermarks[0];
927
			$watermarkClone = $watermark->getParent()->removeChild($watermark)->cloneWithChildren();
928
			$watermark->clearChildren();
929
			$this->document->setWatermark($watermarkClone);
930
			$this->layoutWatermark($watermarkClone);
931
		} elseif ($this->document->getWatermark()) {
932
			$this->layoutWatermark($this->document->getWatermark());
933
		}
934
		return $this;
935
	}
936
937
	/**
938
	 * Get boxes that are laid out after specified y position of the current page.
939
	 *
940
	 * @param string $yPos
941
	 *
942
	 * @return Box[]
943
	 */
944
	public function getRootChildsAfterY(string $yPos)
945
	{
946
		$boxes = [];
947
		$box = $this->getBox();
948
		$endY = $box->getCoordinates()->getEndY();
949
		if (Math::comp($endY, $yPos) <= 0) {
950
			return $boxes;
951
		}
952
		foreach ($box->getChildren() as $childBox) {
953
			if (Math::comp($childBox->getCoordinates()->getEndY(), $yPos) > 0) {
954
				$boxes[] = $childBox;
955
			}
956
		}
957
		return $boxes;
958
	}
959
960
	/**
961
	 * Cut box above specified position.
962
	 *
963
	 * @param Box    $child
964
	 * @param string $yPos
965
	 *
966
	 * @return $this
967
	 */
968
	public function cutAbove(Box $child, string $yPos)
969
	{
970
		$height = Math::sub($child->getCoordinates()->getEndY(), $yPos);
971
		$child->getDimensions()->setHeight($height);
972
		$child->getStyle()
973
			->setRule('border-top-width', '0')
974
			->setRule('padding-top', '0')
975
			->setRule('margin-top', '0');
976
		$child->setCut(static::CUT_ABOVE);
977
		return $this;
978
	}
979
980
	/**
981
	 * Cut box below specified position.
982
	 *
983
	 * @param Box    $child
984
	 * @param string $yPos
985
	 *
986
	 * @return $this
987
	 */
988
	public function cutBelow(Box $child, string $yPos)
989
	{
990
		if ($child instanceof TextBox) {
991
			$child->setRenderable(false);
992
			return $this;
993
		}
994
		$height = Math::sub($yPos, $child->getCoordinates()->getY());
995
		$child->getDimensions()->setHeight($height);
996
		$child->getStyle()
997
			->setRule('border-bottom-width', '0')
998
			->setRule('margin-bottom', '0')
999
			->setRule('padding-bottom', '0');
1000
		$child->setCut(static::CUT_BELOW);
1001
		return $this;
1002
	}
1003
1004
	/**
1005
	 * Cut box.
1006
	 *
1007
	 * @param Box    $box
1008
	 * @param string $yPos
1009
	 * @param Box    $cloned
1010
	 *
1011
	 * @return Box
1012
	 */
1013
	public function cutBox(Box $box, string $yPos, Box $cloned)
1014
	{
1015
		foreach ($box->getChildren() as $child) {
1016
			if (!$child->isForMeasurement() || !$child->isRenderable()) {
1017
				continue;
1018
			}
1019
			$childCoords = $child->getCoordinates();
1020
			if (Math::comp($childCoords->getEndY(), $yPos) >= 0) {
1021
				$childBoxes = $this->cloneAndDivideChildrenAfterY($yPos, [$child]);
1022
				foreach ($childBoxes as $childBox) {
1023
					$cloned->appendChild($childBox);
1024
				}
1025
			}
1026
			if (Math::comp($childCoords->getY(), $yPos) >= 0) {
1027
				$child->setRenderable(false)->setForMeasurement(false);
1028
			}
1029
		}
1030
		if (Math::comp($box->getCoordinates()->getY(), $yPos) < 0 && Math::comp($box->getCoordinates()->getEndY(), $yPos) > 0) {
1031
			$this->cutBelow($box, $yPos);
1032
			$this->cutAbove($cloned, $yPos);
1033
		} elseif (Math::comp($box->getCoordinates()->getY(), $yPos) >= 0) {
1034
			$box->setRenderable(false)->setForMeasurement(false);
1035
		}
1036
		return $cloned;
1037
	}
1038
1039
	/**
1040
	 * Group boxes by parent.
1041
	 *
1042
	 * @param Box[]|null $boxes
1043
	 * @param string     $yPos
1044
	 *
1045
	 * @return Box[]|null cloned boxes
1046
	 */
1047
	public function cloneAndDivideChildrenAfterY(string $yPos, array $boxes = null)
1048
	{
1049
		if (null === $boxes) {
1050
			$boxes = [];
1051
			foreach ($this->getBox()->getChildren() as $child) {
1052
				if (Math::comp($child->getCoordinates()->getEndY(), $yPos) >= 0) {
1053
					$boxes[] = $child;
1054
				}
1055
			}
1056
		}
1057
		if (empty($boxes)) {
1058
			return null;
1059
		}
1060
		$clonedBoxes = [];
1061
		foreach ($boxes as $box) {
1062
			$cloned = $box->clone();
1063
			$cloned->clearChildren();
1064
			$boxCoords = $box->getCoordinates();
1065
			if ($box instanceof TableWrapperBox && Math::comp($boxCoords->getY(), $yPos) <= 0 && Math::comp($boxCoords->getEndY(), $yPos) > 0) {
1066
				$cloned = $this->divideTable($box, $yPos, $cloned);
1067
			} else {
1068
				$cloned = $this->cutBox($box, $yPos, $cloned);
1069
			}
1070
			$clonedBoxes[] = $cloned;
1071
		}
1072
		return $clonedBoxes;
1073
	}
1074
1075
	/**
1076
	 * Treat table like div? - just cut.
1077
	 *
1078
	 * @param TableWrapperBox $tableWrapperBox
1079
	 * @param string          $yPos
1080
	 *
1081
	 * @return bool
1082
	 */
1083
	public function treatTableLikeDiv(TableWrapperBox $tableWrapperBox, string $yPos)
0 ignored issues
show
The parameter $yPos is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

1083
	public function treatTableLikeDiv(TableWrapperBox $tableWrapperBox, /** @scrutinizer ignore-unused */ string $yPos)

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
1084
	{
1085
		$cells = $tableWrapperBox->getBoxesByType('TableCellBox');
1086
		foreach ($cells as $cell) {
1087
			if (Math::comp($cell->getDimensions()->getHeight(), $this->getDimensions()->getHeight()) > 0) {
0 ignored issues
show
It seems like $this->getDimensions()->getHeight() can also be of type null; however, parameter $right of YetiForcePDF\Math::comp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1087
			if (Math::comp($cell->getDimensions()->getHeight(), /** @scrutinizer ignore-type */ $this->getDimensions()->getHeight()) > 0) {
Loading history...
1088
				return true;
1089
			}
1090
		}
1091
		return false;
1092
	}
1093
1094
	/**
1095
	 * Divide overflowed table.
1096
	 *
1097
	 * @param Box    $tableChild
1098
	 * @param string $yPos
1099
	 * @param Box    $cloned
1100
	 *
1101
	 * @return TableWrapperBox
1102
	 */
1103
	protected function divideTable(Box $tableChild, string $yPos, Box $cloned)
1104
	{
1105
		$tableWrapperBox = $tableChild->getClosestByType('TableWrapperBox');
1106
		if ($this->treatTableLikeDiv($tableWrapperBox, $yPos)) {
1107
			return $this->cutBox($tableWrapperBox, $yPos, $cloned);
1108
		}
1109
		$pageEnd = Math::add($this->getDimensions()->getHeight(), (string) $this->margins['top']);
0 ignored issues
show
It seems like $this->getDimensions()->getHeight() can also be of type null; however, parameter $numbers of YetiForcePDF\Math::add() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1109
		$pageEnd = Math::add(/** @scrutinizer ignore-type */ $this->getDimensions()->getHeight(), (string) $this->margins['top']);
Loading history...
1110
		if (Math::comp($tableWrapperBox->getCoordinates()->getY(), $pageEnd) >= 0) {
1111
			// if table is below page do nothing - it will be moved to the next page and then again checked
1112
			return $tableWrapperBox;
1113
		}
1114
		$newTableWrapperBox = $tableWrapperBox->clone();
1115
		$newTableWrapperBox->getStyle()->setBox($newTableWrapperBox);
1116
		$newTableWrapperBox->clearChildren();
1117
		$tableBox = $tableWrapperBox->getFirstChild();
1118
		$newTableBox = $tableBox->clone();
1119
		$newTableBox->getStyle()->setBox($newTableBox);
1120
		$newTableBox->clearChildren();
1121
		$newTableWrapperBox->appendChild($newTableBox);
0 ignored issues
show
It seems like $newTableBox can also be of type null; however, parameter $box of YetiForcePDF\Layout\Box::appendChild() does only seem to accept YetiForcePDF\Layout\Box, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1121
		$newTableWrapperBox->appendChild(/** @scrutinizer ignore-type */ $newTableBox);
Loading history...
1122
		$clonedFooters = $tableWrapperBox->getBoxesByType('TableFooterGroupBox', 'TableWrapperBox');
1123
		if (!empty($clonedFooters)) {
1124
			$clonedFooter = $clonedFooters[0]->getParent()->removeChild($clonedFooters[0])->cloneWithChildren();
1125
		}
1126
		$headers = $tableWrapperBox->getBoxesByType('TableHeaderGroupBox', 'TableWrapperBox');
1127
		if (!empty($headers)) {
1128
			$newTableBox->appendChild($headers[0]->cloneWithChildren());
1129
		}
1130
		// clone row groups and rows
1131
		foreach ($tableWrapperBox->getFirstChild()->getChildren() as $tableRowGroup) {
1132
			if (Math::comp($tableRowGroup->getCoordinates()->getEndY(), $pageEnd) < 0) {
1133
				continue;
1134
			}
1135
			$moveRowGroup = $tableRowGroup->clone();
1136
			$moveRowGroup->clearChildren();
1137
			foreach ($tableRowGroup->getChildren() as $rowIndex => $row) {
1138
				if (!$tableRowGroup instanceof TableFooterGroupBox && !$tableRowGroup instanceof TableHeaderGroupBox) {
1139
					$moveRow = false;
1140
					foreach ($row->getChildren() as $column) {
1141
						if (Math::comp($column->getCoordinates()->getEndY(), $pageEnd) >= 0) {
1142
							$moveRow = true;
1143
							break;
1144
						}
1145
					}
1146
					if ($moveRow) {
1147
						if ($row->getRowSpanUp() > 0) {
0 ignored issues
show
The method getRowSpanUp() does not exist on YetiForcePDF\Layout\Box. It seems like you code against a sub-type of YetiForcePDF\Layout\Box such as YetiForcePDF\Layout\TableRowBox or YetiForcePDF\Layout\TableColumnBox. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

1147
						if ($row->/** @scrutinizer ignore-call */ getRowSpanUp() > 0) {
Loading history...
1148
							$move = [];
1149
							// copy spanned rows too
1150
							for ($i = $row->getRowSpanUp(); $i > 0; --$i) {
1151
								$spannedRowIndex = $rowIndex - $i;
1152
								$move[] = $tableRowGroup->getChildren()[$spannedRowIndex];
1153
							}
1154
							// copy all next rows
1155
							$rows = $tableRowGroup->getChildren();
1156
							for ($i = $rowIndex, $len = \count($rows); $i < $len; ++$i) {
1157
								$nextRow = $rows[$i];
1158
								$move[] = $nextRow;
1159
							}
1160
							foreach ($move as $mr) {
1161
								$moveRowGroup->appendChild($mr->getParent()->removeChild($mr));
1162
							}
1163
							break;
1164
						}
1165
						$moveRowGroup->appendChild($row->getParent()->removeChild($row));
1166
					}
1167
				}
1168
			}
1169
			$newTableBox->appendChild($moveRowGroup);
1170
		}
1171
		if (isset($clonedFooter)) {
1172
			$newTableBox->appendChild($clonedFooter);
1173
		}
1174
		//remove empty rows
1175
		$tableBox->removeEmptyRows();
0 ignored issues
show
The method removeEmptyRows() does not exist on YetiForcePDF\Layout\Box. It seems like you code against a sub-type of YetiForcePDF\Layout\Box such as YetiForcePDF\Layout\TableBox. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

1175
		$tableBox->/** @scrutinizer ignore-call */ 
1176
             removeEmptyRows();
Loading history...
1176
		// remove original table if it was moved with all the content
1177
		$removeSource = !$tableBox->hasChildren() || !$tableBox->containContent();
1178
		$removeSource = $removeSource || ($tableBox->getFirstChild() instanceof TableHeaderGroupBox && 1 === \count($tableBox->getChildren()));
1179
		if ($removeSource) {
1180
			$tableWrapperBox->setDisplayable(false)->setRenderable(false)->setForMeasurement(false);
1181
		}
1182
		return $newTableWrapperBox;
1183
	}
1184
1185
	/**
1186
	 * Clone current page.
1187
	 *
1188
	 * @throws \InvalidArgumentException
1189
	 *
1190
	 * @return Page
1191
	 */
1192
	public function cloneCurrentPage()
1193
	{
1194
		$newPage = clone $this;
1195
		$newPage->setId($this->document->getActualId());
1196
		$newPage->setPageNumber($this->getPageNumber() + 1);
1197
		$newPage->contentStream = (new \YetiForcePDF\Objects\Basic\StreamObject())
1198
			->setDocument($this->document)
1199
			->init();
1200
		$newPage->document->getPagesObject()->addChild($newPage, $this);
1201
		$this->document->addPage($this->format, $this->orientation, $newPage, $this);
1202
		$this->document->addObject($newPage, $this);
1203
		return $newPage;
1204
	}
1205
1206
	/**
1207
	 * Break page after specified box.
1208
	 *
1209
	 * @param Box $box
1210
	 *
1211
	 * @return $this
1212
	 */
1213
	public function breakAfter(Box $box)
1214
	{
1215
		$box = $box->getFirstRootChild();
1216
		if ($box->getParent()->getLastChild() === $box) {
1217
			return $this;
1218
		}
1219
		$contentBoxes = [];
1220
		$break = false;
1221
		foreach ($box->getParent()->getChildren() as $child) {
1222
			if ($child === $box) {
1223
				$break = true;
1224
			}
1225
			if ($break && $child !== $box) {
1226
				$contentBoxes[] = $child;
1227
			}
1228
		}
1229
		$haveContent = false;
1230
		foreach ($contentBoxes as $contentBox) {
1231
			if ($contentBox->containContent()) {
1232
				$haveContent = true;
1233
				break;
1234
			}
1235
		}
1236
		if (!$haveContent) {
1237
			return $this;
1238
		}
1239
		$newPage = $this->cloneCurrentPage();
1240
		$newBox = $newPage->getBox()->clone();
1241
		$newBox->clearChildren();
1242
		$newPage->setBox($newBox);
1243
		$break = false;
1244
		foreach ($box->getParent()->getChildren() as $child) {
1245
			if ($child === $box) {
1246
				$break = true;
1247
			}
1248
			if ($break && $child !== $box) {
1249
				$newBox->appendChild($child->getParent()->removeChild($child));
1250
			}
1251
		}
1252
		$newBox->layout(true);
0 ignored issues
show
The method layout() does not exist on YetiForcePDF\Layout\Box. It seems like you code against a sub-type of YetiForcePDF\Layout\Box such as YetiForcePDF\Layout\BlockBox. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

1252
		$newBox->/** @scrutinizer ignore-call */ 
1253
           layout(true);
Loading history...
1253
		$this->document->setCurrentPage($newPage);
1254
		unset($contentBoxes);
1255
		return $this;
1256
	}
1257
1258
	/**
1259
	 * Break overflow of the current page.
1260
	 *
1261
	 * @param int $level Is used to stop infinite loop if something goes wrong
1262
	 *
1263
	 * @return $this
1264
	 */
1265
	public function breakOverflow(int $level = 0)
1266
	{
1267
		$atYPos = Math::add($this->getDimensions()->getHeight(), (string) $this->margins['top']);
0 ignored issues
show
It seems like $this->getDimensions()->getHeight() can also be of type null; however, parameter $numbers of YetiForcePDF\Math::add() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1267
		$atYPos = Math::add(/** @scrutinizer ignore-type */ $this->getDimensions()->getHeight(), (string) $this->margins['top']);
Loading history...
1268
		$clonedBoxes = $this->cloneAndDivideChildrenAfterY($atYPos);
1269
		if (empty($clonedBoxes)) {
1270
			return $this;
1271
		}
1272
		$newPage = $this->cloneCurrentPage();
1273
		$newBox = $newPage->getBox();
1274
		$newBox->clearChildren();
1275
		foreach ($clonedBoxes as $clonedBox) {
1276
			$newBox->appendChild($clonedBox->getParent()->removeChild($clonedBox));
1277
		}
1278
		$this->getBox()->getStyle()->fixDomTree();
1279
		$this->getBox()->measureHeight(true)->measureOffset(true)->alignText()->measurePosition(true);
0 ignored issues
show
The method measureHeight() does not exist on YetiForcePDF\Layout\Box. It seems like you code against a sub-type of said class. However, the method does not exist in YetiForcePDF\Layout\ElementBox. Are you sure you never get one of those? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

1279
		$this->getBox()->/** @scrutinizer ignore-call */ measureHeight(true)->measureOffset(true)->alignText()->measurePosition(true);
Loading history...
1280
		$newBox->layout(true);
1281
		$newBox->getStyle()->fixDomTree();
1282
		$this->document->setCurrentPage($newPage);
1283
		if (Math::comp($newBox->getDimensions()->getHeight(), $this->getDimensions()->getHeight()) > 0 && $level < 1024) {
0 ignored issues
show
It seems like $this->getDimensions()->getHeight() can also be of type null; however, parameter $right of YetiForcePDF\Math::comp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1283
		if (Math::comp($newBox->getDimensions()->getHeight(), /** @scrutinizer ignore-type */ $this->getDimensions()->getHeight()) > 0 && $level < 1024) {
Loading history...
It seems like $newBox->getDimensions()->getHeight() can also be of type null; however, parameter $left of YetiForcePDF\Math::comp() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

1283
		if (Math::comp(/** @scrutinizer ignore-type */ $newBox->getDimensions()->getHeight(), $this->getDimensions()->getHeight()) > 0 && $level < 1024) {
Loading history...
1284
			$newPage->breakOverflow(++$level);
1285
		}
1286
		unset($clonedBoxes);
1287
		return $this;
1288
	}
1289
1290
	/**
1291
	 * Layout page resources.
1292
	 *
1293
	 * @return string
1294
	 */
1295
	public function renderResources(): string
1296
	{
1297
		$rendered = [
1298
			'  /Resources <<',
1299
		];
1300
		foreach ($this->resources as $groupName => $resourceGroup) {
1301
			if (!\in_array($groupName, $this->doNotGroup)) {
1302
				$rendered[] = "    /$groupName <<";
1303
				foreach ($resourceGroup as $resourceName => $resourceObject) {
1304
					$rendered[] = "      /$resourceName " . $resourceObject->getReference();
1305
				}
1306
				$rendered[] = '    >>';
1307
			} else {
1308
				$str = "    /$groupName ";
1309
				foreach ($resourceGroup as $resourceName => $resourceObject) {
1310
					$str .= $resourceObject->getReference();
1311
				}
1312
				$rendered[] = $str;
1313
			}
1314
		}
1315
		$rendered[] = '  >>';
1316
		return implode("\n", $rendered);
1317
	}
1318
1319
	/**
1320
	 * {@inheritdoc}
1321
	 */
1322
	public function render(): string
1323
	{
1324
		$dimensions = $this->getOuterDimensions();
1325
		return implode("\n", [
1326
			$this->getRawId() . ' obj',
1327
			'<<',
1328
			'  /Type /Page',
1329
			'  /Parent ' . $this->parent->getReference(),
1330
			'  /MediaBox [0 0 ' . $dimensions->getWidth() . ' ' . $dimensions->getHeight() . ']',
1331
			'  /BleedBox [' . $this->margins['left'] . ' ' . $this->margins['top'] . ' ' . $dimensions->getWidth() . ' ' . $dimensions->getHeight() . ']',
1332
			'  /UserUnit ' . $this->userUnit,
1333
			'  /Rotate 0',
1334
			$this->renderResources(),
1335
			'  /Contents ' . $this->contentStream->getReference(),
1336
			'>>',
1337
			'endobj',
1338
		]);
1339
	}
1340
1341
	public function __clone()
1342
	{
1343
		$this->box = clone $this->box->cloneWithChildren();
1344
		$this->coordinates = clone $this->coordinates;
1345
		$this->coordinates->setBox($this->box);
1346
		$this->contentStream = clone $this->contentStream;
1347
		$this->dimensions = clone $this->dimensions;
1348
		$this->outerDimensions = clone $this->dimensions;
1349
		$currentResources = $this->resources;
1350
		$this->resources = [];
1351
		foreach ($currentResources as $groupName => $resources) {
1352
			foreach ($resources as $resourceName => $resource) {
1353
				$this->resources[$groupName][$resourceName] = clone $resource;
1354
			}
1355
		}
1356
	}
1357
}
1358