Completed
Pull Request — master (#1559)
by Adrien
09:36
created

PageSetup::setPageOrder()   A

Complexity

Conditions 4
Paths 2

Size

Total Lines 7
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 20

Importance

Changes 0
Metric Value
cc 4
eloc 3
c 0
b 0
f 0
nc 2
nop 1
dl 0
loc 7
ccs 0
cts 4
cp 0
crap 20
rs 10
1
<?php
2
3
namespace PhpOffice\PhpSpreadsheet\Worksheet;
4
5
use PhpOffice\PhpSpreadsheet\Cell\Coordinate;
6
use PhpOffice\PhpSpreadsheet\Exception as PhpSpreadsheetException;
7
8
/**
9
 * <code>
10
 * Paper size taken from Office Open XML Part 4 - Markup Language Reference, page 1988:.
11
 *
12
 * 1 = Letter paper (8.5 in. by 11 in.)
13
 * 2 = Letter small paper (8.5 in. by 11 in.)
14
 * 3 = Tabloid paper (11 in. by 17 in.)
15
 * 4 = Ledger paper (17 in. by 11 in.)
16
 * 5 = Legal paper (8.5 in. by 14 in.)
17
 * 6 = Statement paper (5.5 in. by 8.5 in.)
18
 * 7 = Executive paper (7.25 in. by 10.5 in.)
19
 * 8 = A3 paper (297 mm by 420 mm)
20
 * 9 = A4 paper (210 mm by 297 mm)
21
 * 10 = A4 small paper (210 mm by 297 mm)
22
 * 11 = A5 paper (148 mm by 210 mm)
23
 * 12 = B4 paper (250 mm by 353 mm)
24
 * 13 = B5 paper (176 mm by 250 mm)
25
 * 14 = Folio paper (8.5 in. by 13 in.)
26
 * 15 = Quarto paper (215 mm by 275 mm)
27
 * 16 = Standard paper (10 in. by 14 in.)
28
 * 17 = Standard paper (11 in. by 17 in.)
29
 * 18 = Note paper (8.5 in. by 11 in.)
30
 * 19 = #9 envelope (3.875 in. by 8.875 in.)
31
 * 20 = #10 envelope (4.125 in. by 9.5 in.)
32
 * 21 = #11 envelope (4.5 in. by 10.375 in.)
33
 * 22 = #12 envelope (4.75 in. by 11 in.)
34
 * 23 = #14 envelope (5 in. by 11.5 in.)
35
 * 24 = C paper (17 in. by 22 in.)
36
 * 25 = D paper (22 in. by 34 in.)
37
 * 26 = E paper (34 in. by 44 in.)
38
 * 27 = DL envelope (110 mm by 220 mm)
39
 * 28 = C5 envelope (162 mm by 229 mm)
40
 * 29 = C3 envelope (324 mm by 458 mm)
41
 * 30 = C4 envelope (229 mm by 324 mm)
42
 * 31 = C6 envelope (114 mm by 162 mm)
43
 * 32 = C65 envelope (114 mm by 229 mm)
44
 * 33 = B4 envelope (250 mm by 353 mm)
45
 * 34 = B5 envelope (176 mm by 250 mm)
46
 * 35 = B6 envelope (176 mm by 125 mm)
47
 * 36 = Italy envelope (110 mm by 230 mm)
48
 * 37 = Monarch envelope (3.875 in. by 7.5 in.).
49
 * 38 = 6 3/4 envelope (3.625 in. by 6.5 in.)
50
 * 39 = US standard fanfold (14.875 in. by 11 in.)
51
 * 40 = German standard fanfold (8.5 in. by 12 in.)
52
 * 41 = German legal fanfold (8.5 in. by 13 in.)
53
 * 42 = ISO B4 (250 mm by 353 mm)
54
 * 43 = Japanese double postcard (200 mm by 148 mm)
55
 * 44 = Standard paper (9 in. by 11 in.)
56
 * 45 = Standard paper (10 in. by 11 in.)
57
 * 46 = Standard paper (15 in. by 11 in.)
58
 * 47 = Invite envelope (220 mm by 220 mm)
59
 * 50 = Letter extra paper (9.275 in. by 12 in.)
60
 * 51 = Legal extra paper (9.275 in. by 15 in.)
61
 * 52 = Tabloid extra paper (11.69 in. by 18 in.)
62
 * 53 = A4 extra paper (236 mm by 322 mm)
63
 * 54 = Letter transverse paper (8.275 in. by 11 in.)
64
 * 55 = A4 transverse paper (210 mm by 297 mm)
65
 * 56 = Letter extra transverse paper (9.275 in. by 12 in.)
66
 * 57 = SuperA/SuperA/A4 paper (227 mm by 356 mm)
67
 * 58 = SuperB/SuperB/A3 paper (305 mm by 487 mm)
68
 * 59 = Letter plus paper (8.5 in. by 12.69 in.)
69
 * 60 = A4 plus paper (210 mm by 330 mm)
70
 * 61 = A5 transverse paper (148 mm by 210 mm)
71
 * 62 = JIS B5 transverse paper (182 mm by 257 mm)
72
 * 63 = A3 extra paper (322 mm by 445 mm)
73
 * 64 = A5 extra paper (174 mm by 235 mm)
74
 * 65 = ISO B5 extra paper (201 mm by 276 mm)
75
 * 66 = A2 paper (420 mm by 594 mm)
76
 * 67 = A3 transverse paper (297 mm by 420 mm)
77
 * 68 = A3 extra transverse paper (322 mm by 445 mm)
78
 * </code>
79
 */
80
class PageSetup
81
{
82
    // Paper size
83
    const PAPERSIZE_LETTER = 1;
84
    const PAPERSIZE_LETTER_SMALL = 2;
85
    const PAPERSIZE_TABLOID = 3;
86
    const PAPERSIZE_LEDGER = 4;
87
    const PAPERSIZE_LEGAL = 5;
88
    const PAPERSIZE_STATEMENT = 6;
89
    const PAPERSIZE_EXECUTIVE = 7;
90
    const PAPERSIZE_A3 = 8;
91
    const PAPERSIZE_A4 = 9;
92
    const PAPERSIZE_A4_SMALL = 10;
93
    const PAPERSIZE_A5 = 11;
94
    const PAPERSIZE_B4 = 12;
95
    const PAPERSIZE_B5 = 13;
96
    const PAPERSIZE_FOLIO = 14;
97
    const PAPERSIZE_QUARTO = 15;
98
    const PAPERSIZE_STANDARD_1 = 16;
99
    const PAPERSIZE_STANDARD_2 = 17;
100
    const PAPERSIZE_NOTE = 18;
101
    const PAPERSIZE_NO9_ENVELOPE = 19;
102
    const PAPERSIZE_NO10_ENVELOPE = 20;
103
    const PAPERSIZE_NO11_ENVELOPE = 21;
104
    const PAPERSIZE_NO12_ENVELOPE = 22;
105
    const PAPERSIZE_NO14_ENVELOPE = 23;
106
    const PAPERSIZE_C = 24;
107
    const PAPERSIZE_D = 25;
108
    const PAPERSIZE_E = 26;
109
    const PAPERSIZE_DL_ENVELOPE = 27;
110
    const PAPERSIZE_C5_ENVELOPE = 28;
111
    const PAPERSIZE_C3_ENVELOPE = 29;
112
    const PAPERSIZE_C4_ENVELOPE = 30;
113
    const PAPERSIZE_C6_ENVELOPE = 31;
114
    const PAPERSIZE_C65_ENVELOPE = 32;
115
    const PAPERSIZE_B4_ENVELOPE = 33;
116
    const PAPERSIZE_B5_ENVELOPE = 34;
117
    const PAPERSIZE_B6_ENVELOPE = 35;
118
    const PAPERSIZE_ITALY_ENVELOPE = 36;
119
    const PAPERSIZE_MONARCH_ENVELOPE = 37;
120
    const PAPERSIZE_6_3_4_ENVELOPE = 38;
121
    const PAPERSIZE_US_STANDARD_FANFOLD = 39;
122
    const PAPERSIZE_GERMAN_STANDARD_FANFOLD = 40;
123
    const PAPERSIZE_GERMAN_LEGAL_FANFOLD = 41;
124
    const PAPERSIZE_ISO_B4 = 42;
125
    const PAPERSIZE_JAPANESE_DOUBLE_POSTCARD = 43;
126
    const PAPERSIZE_STANDARD_PAPER_1 = 44;
127
    const PAPERSIZE_STANDARD_PAPER_2 = 45;
128
    const PAPERSIZE_STANDARD_PAPER_3 = 46;
129
    const PAPERSIZE_INVITE_ENVELOPE = 47;
130
    const PAPERSIZE_LETTER_EXTRA_PAPER = 48;
131
    const PAPERSIZE_LEGAL_EXTRA_PAPER = 49;
132
    const PAPERSIZE_TABLOID_EXTRA_PAPER = 50;
133
    const PAPERSIZE_A4_EXTRA_PAPER = 51;
134
    const PAPERSIZE_LETTER_TRANSVERSE_PAPER = 52;
135
    const PAPERSIZE_A4_TRANSVERSE_PAPER = 53;
136
    const PAPERSIZE_LETTER_EXTRA_TRANSVERSE_PAPER = 54;
137
    const PAPERSIZE_SUPERA_SUPERA_A4_PAPER = 55;
138
    const PAPERSIZE_SUPERB_SUPERB_A3_PAPER = 56;
139
    const PAPERSIZE_LETTER_PLUS_PAPER = 57;
140
    const PAPERSIZE_A4_PLUS_PAPER = 58;
141
    const PAPERSIZE_A5_TRANSVERSE_PAPER = 59;
142
    const PAPERSIZE_JIS_B5_TRANSVERSE_PAPER = 60;
143
    const PAPERSIZE_A3_EXTRA_PAPER = 61;
144
    const PAPERSIZE_A5_EXTRA_PAPER = 62;
145
    const PAPERSIZE_ISO_B5_EXTRA_PAPER = 63;
146
    const PAPERSIZE_A2_PAPER = 64;
147
    const PAPERSIZE_A3_TRANSVERSE_PAPER = 65;
148
    const PAPERSIZE_A3_EXTRA_TRANSVERSE_PAPER = 66;
149
150
    // Page orientation
151
    const ORIENTATION_DEFAULT = 'default';
152
    const ORIENTATION_LANDSCAPE = 'landscape';
153
    const ORIENTATION_PORTRAIT = 'portrait';
154
155
    // Print Range Set Method
156
    const SETPRINTRANGE_OVERWRITE = 'O';
157
    const SETPRINTRANGE_INSERT = 'I';
158
159
    const PAGEORDER_OVER_THEN_DOWN = 'overThenDown';
160
    const PAGEORDER_DOWN_THEN_OVER = 'downThenOver';
161
162
    /**
163
     * Paper size.
164
     *
165
     * @var int
166
     */
167
    private $paperSize = self::PAPERSIZE_LETTER;
168
169
    /**
170
     * Orientation.
171
     *
172
     * @var string
173
     */
174
    private $orientation = self::ORIENTATION_DEFAULT;
175
176
    /**
177
     * Scale (Print Scale).
178
     *
179
     * Print scaling. Valid values range from 10 to 400
180
     * This setting is overridden when fitToWidth and/or fitToHeight are in use
181
     *
182
     * @var null|int
183
     */
184
    private $scale = 100;
185
186
    /**
187
     * Fit To Page
188
     * Whether scale or fitToWith / fitToHeight applies.
189
     *
190
     * @var bool
191
     */
192
    private $fitToPage = false;
193
194
    /**
195
     * Fit To Height
196
     * Number of vertical pages to fit on.
197
     *
198
     * @var null|int
199
     */
200
    private $fitToHeight = 1;
201
202
    /**
203
     * Fit To Width
204
     * Number of horizontal pages to fit on.
205
     *
206
     * @var null|int
207
     */
208
    private $fitToWidth = 1;
209
210
    /**
211
     * Columns to repeat at left.
212
     *
213
     * @var array Containing start column and end column, empty array if option unset
214
     */
215
    private $columnsToRepeatAtLeft = ['', ''];
216
217
    /**
218
     * Rows to repeat at top.
219
     *
220
     * @var array Containing start row number and end row number, empty array if option unset
221
     */
222
    private $rowsToRepeatAtTop = [0, 0];
223
224
    /**
225
     * Center page horizontally.
226
     *
227
     * @var bool
228
     */
229
    private $horizontalCentered = false;
230
231
    /**
232
     * Center page vertically.
233
     *
234
     * @var bool
235
     */
236
    private $verticalCentered = false;
237
238
    /**
239
     * Print area.
240
     *
241
     * @var string
242
     */
243
    private $printArea;
244
245
    /**
246
     * First page number.
247
     *
248
     * @var int
249
     */
250
    private $firstPageNumber;
251
252
    private $pageOrder = self::PAGEORDER_DOWN_THEN_OVER;
253
254
    /**
255
     * Create a new PageSetup.
256 359
     */
257
    public function __construct()
258 359
    {
259
    }
260
261
    /**
262
     * Get Paper Size.
263
     *
264
     * @return int
265 127
     */
266
    public function getPaperSize()
267 127
    {
268
        return $this->paperSize;
269
    }
270
271
    /**
272
     * Set Paper Size.
273
     *
274
     * @param int $pValue see self::PAPERSIZE_*
275
     *
276
     * @return $this
277 99
     */
278
    public function setPaperSize($pValue)
279 99
    {
280
        $this->paperSize = $pValue;
281 99
282
        return $this;
283
    }
284
285
    /**
286
     * Get Orientation.
287
     *
288
     * @return string
289 126
     */
290
    public function getOrientation()
291 126
    {
292
        return $this->orientation;
293
    }
294
295
    /**
296
     * Set Orientation.
297
     *
298
     * @param string $pValue see self::ORIENTATION_*
299
     *
300
     * @return $this
301 103
     */
302
    public function setOrientation($pValue)
303 103
    {
304
        $this->orientation = $pValue;
305 103
306
        return $this;
307
    }
308
309
    /**
310
     * Get Scale.
311
     *
312
     * @return null|int
313 120
     */
314
    public function getScale()
315 120
    {
316
        return $this->scale;
317
    }
318
319
    /**
320
     * Set Scale.
321
     * Print scaling. Valid values range from 10 to 400
322
     * This setting is overridden when fitToWidth and/or fitToHeight are in use.
323
     *
324
     * @param null|int $pValue
325
     * @param bool $pUpdate Update fitToPage so scaling applies rather than fitToHeight / fitToWidth
326
     *
327
     * @return $this
328 80
     */
329
    public function setScale($pValue, $pUpdate = true)
330
    {
331
        // Microsoft Office Excel 2007 only allows setting a scale between 10 and 400 via the user interface,
332 80
        // but it is apparently still able to handle any scale >= 0, where 0 results in 100
333 80
        if (($pValue >= 0) || $pValue === null) {
334 80
            $this->scale = $pValue;
335 80
            if ($pUpdate) {
336
                $this->fitToPage = false;
337
            }
338
        } else {
339
            throw new PhpSpreadsheetException('Scale must not be negative');
340
        }
341 80
342
        return $this;
343
    }
344
345
    /**
346
     * Get Fit To Page.
347
     *
348
     * @return bool
349 120
     */
350
    public function getFitToPage()
351 120
    {
352
        return $this->fitToPage;
353
    }
354
355
    /**
356
     * Set Fit To Page.
357
     *
358
     * @param bool $pValue
359
     *
360
     * @return $this
361 28
     */
362
    public function setFitToPage($pValue)
363 28
    {
364
        $this->fitToPage = $pValue;
365 28
366
        return $this;
367
    }
368
369
    /**
370
     * Get Fit To Height.
371
     *
372
     * @return null|int
373 120
     */
374
    public function getFitToHeight()
375 120
    {
376
        return $this->fitToHeight;
377
    }
378
379
    /**
380
     * Set Fit To Height.
381
     *
382
     * @param null|int $pValue
383
     * @param bool $pUpdate Update fitToPage so it applies rather than scaling
384
     *
385
     * @return $this
386 80
     */
387
    public function setFitToHeight($pValue, $pUpdate = true)
388 80
    {
389 80
        $this->fitToHeight = $pValue;
390
        if ($pUpdate) {
391
            $this->fitToPage = true;
392
        }
393 80
394
        return $this;
395
    }
396
397
    /**
398
     * Get Fit To Width.
399
     *
400
     * @return null|int
401 120
     */
402
    public function getFitToWidth()
403 120
    {
404
        return $this->fitToWidth;
405
    }
406
407
    /**
408
     * Set Fit To Width.
409
     *
410
     * @param null|int $pValue
411
     * @param bool $pUpdate Update fitToPage so it applies rather than scaling
412
     *
413
     * @return $this
414 80
     */
415
    public function setFitToWidth($pValue, $pUpdate = true)
416 80
    {
417 80
        $this->fitToWidth = $pValue;
418
        if ($pUpdate) {
419
            $this->fitToPage = true;
420
        }
421 80
422
        return $this;
423
    }
424
425
    /**
426
     * Is Columns to repeat at left set?
427
     *
428
     * @return bool
429 120
     */
430
    public function isColumnsToRepeatAtLeftSet()
431 120
    {
432 120
        if (is_array($this->columnsToRepeatAtLeft)) {
0 ignored issues
show
introduced by
The condition is_array($this->columnsToRepeatAtLeft) is always true.
Loading history...
433
            if ($this->columnsToRepeatAtLeft[0] != '' && $this->columnsToRepeatAtLeft[1] != '') {
434
                return true;
435
            }
436
        }
437 120
438
        return false;
439
    }
440
441
    /**
442
     * Get Columns to repeat at left.
443
     *
444
     * @return array Containing start column and end column, empty array if option unset
445
     */
446
    public function getColumnsToRepeatAtLeft()
447
    {
448
        return $this->columnsToRepeatAtLeft;
449
    }
450
451
    /**
452
     * Set Columns to repeat at left.
453
     *
454
     * @param array $pValue Containing start column and end column, empty array if option unset
455
     *
456
     * @return $this
457
     */
458
    public function setColumnsToRepeatAtLeft(array $pValue)
459
    {
460
        $this->columnsToRepeatAtLeft = $pValue;
461
462
        return $this;
463
    }
464
465
    /**
466
     * Set Columns to repeat at left by start and end.
467
     *
468
     * @param string $pStart eg: 'A'
469
     * @param string $pEnd eg: 'B'
470
     *
471
     * @return $this
472
     */
473
    public function setColumnsToRepeatAtLeftByStartAndEnd($pStart, $pEnd)
474
    {
475
        $this->columnsToRepeatAtLeft = [$pStart, $pEnd];
476
477
        return $this;
478
    }
479
480
    /**
481
     * Is Rows to repeat at top set?
482
     *
483
     * @return bool
484 136
     */
485
    public function isRowsToRepeatAtTopSet()
486 136
    {
487 136
        if (is_array($this->rowsToRepeatAtTop)) {
0 ignored issues
show
introduced by
The condition is_array($this->rowsToRepeatAtTop) is always true.
Loading history...
488 1
            if ($this->rowsToRepeatAtTop[0] != 0 && $this->rowsToRepeatAtTop[1] != 0) {
489
                return true;
490
            }
491
        }
492 135
493
        return false;
494
    }
495
496
    /**
497
     * Get Rows to repeat at top.
498
     *
499
     * @return array Containing start column and end column, empty array if option unset
500 1
     */
501
    public function getRowsToRepeatAtTop()
502 1
    {
503
        return $this->rowsToRepeatAtTop;
504
    }
505
506
    /**
507
     * Set Rows to repeat at top.
508
     *
509
     * @param array $pValue Containing start column and end column, empty array if option unset
510
     *
511
     * @return $this
512 1
     */
513
    public function setRowsToRepeatAtTop(array $pValue)
514 1
    {
515
        $this->rowsToRepeatAtTop = $pValue;
516 1
517
        return $this;
518
    }
519
520
    /**
521
     * Set Rows to repeat at top by start and end.
522
     *
523
     * @param int $pStart eg: 1
524
     * @param int $pEnd eg: 1
525
     *
526
     * @return $this
527 1
     */
528
    public function setRowsToRepeatAtTopByStartAndEnd($pStart, $pEnd)
529 1
    {
530
        $this->rowsToRepeatAtTop = [$pStart, $pEnd];
531 1
532
        return $this;
533
    }
534
535
    /**
536
     * Get center page horizontally.
537
     *
538
     * @return bool
539 120
     */
540
    public function getHorizontalCentered()
541 120
    {
542
        return $this->horizontalCentered;
543
    }
544
545
    /**
546
     * Set center page horizontally.
547
     *
548
     * @param bool $value
549
     *
550
     * @return $this
551 29
     */
552
    public function setHorizontalCentered($value)
553 29
    {
554
        $this->horizontalCentered = $value;
555 29
556
        return $this;
557
    }
558
559
    /**
560
     * Get center page vertically.
561
     *
562
     * @return bool
563 120
     */
564
    public function getVerticalCentered()
565 120
    {
566
        return $this->verticalCentered;
567
    }
568
569
    /**
570
     * Set center page vertically.
571
     *
572
     * @param bool $value
573
     *
574
     * @return $this
575 29
     */
576
    public function setVerticalCentered($value)
577 29
    {
578
        $this->verticalCentered = $value;
579 29
580
        return $this;
581
    }
582
583
    /**
584
     * Get print area.
585
     *
586
     * @param int $index Identifier for a specific print area range if several ranges have been set
587
     *                            Default behaviour, or a index value of 0, will return all ranges as a comma-separated string
588
     *                            Otherwise, the specific range identified by the value of $index will be returned
589
     *                            Print areas are numbered from 1
590
     *
591
     * @return string
592 2
     */
593
    public function getPrintArea($index = 0)
594 2
    {
595 2
        if ($index == 0) {
596
            return $this->printArea;
597
        }
598
        $printAreas = explode(',', $this->printArea);
599
        if (isset($printAreas[$index - 1])) {
600
            return $printAreas[$index - 1];
601
        }
602
603
        throw new PhpSpreadsheetException('Requested Print Area does not exist');
604
    }
605
606
    /**
607
     * Is print area set?
608
     *
609
     * @param int $index Identifier for a specific print area range if several ranges have been set
610
     *                            Default behaviour, or an index value of 0, will identify whether any print range is set
611
     *                            Otherwise, existence of the range identified by the value of $index will be returned
612
     *                            Print areas are numbered from 1
613
     *
614
     * @return bool
615 136
     */
616
    public function isPrintAreaSet($index = 0)
617 136
    {
618 136
        if ($index == 0) {
619
            return $this->printArea !== null;
620
        }
621
        $printAreas = explode(',', $this->printArea);
622
623
        return isset($printAreas[$index - 1]);
624
    }
625
626
    /**
627
     * Clear a print area.
628
     *
629
     * @param int $index Identifier for a specific print area range if several ranges have been set
630
     *                            Default behaviour, or an index value of 0, will clear all print ranges that are set
631
     *                            Otherwise, the range identified by the value of $index will be removed from the series
632
     *                            Print areas are numbered from 1
633
     *
634
     * @return $this
635
     */
636
    public function clearPrintArea($index = 0)
637
    {
638
        if ($index == 0) {
639
            $this->printArea = null;
640
        } else {
641
            $printAreas = explode(',', $this->printArea);
642
            if (isset($printAreas[$index - 1])) {
643
                unset($printAreas[$index - 1]);
644
                $this->printArea = implode(',', $printAreas);
645
            }
646
        }
647
648
        return $this;
649
    }
650
651
    /**
652
     * Set print area. e.g. 'A1:D10' or 'A1:D10,G5:M20'.
653
     *
654
     * @param string $value
655
     * @param int $index Identifier for a specific print area range allowing several ranges to be set
656
     *                            When the method is "O"verwrite, then a positive integer index will overwrite that indexed
657
     *                                entry in the print areas list; a negative index value will identify which entry to
658
     *                                overwrite working bacward through the print area to the list, with the last entry as -1.
659
     *                                Specifying an index value of 0, will overwrite <b>all</b> existing print ranges.
660
     *                            When the method is "I"nsert, then a positive index will insert after that indexed entry in
661
     *                                the print areas list, while a negative index will insert before the indexed entry.
662
     *                                Specifying an index value of 0, will always append the new print range at the end of the
663
     *                                list.
664
     *                            Print areas are numbered from 1
665
     * @param string $method Determines the method used when setting multiple print areas
666
     *                            Default behaviour, or the "O" method, overwrites existing print area
667
     *                            The "I" method, inserts the new print area before any specified index, or at the end of the list
668
     *
669
     * @return $this
670 2
     */
671
    public function setPrintArea($value, $index = 0, $method = self::SETPRINTRANGE_OVERWRITE)
672 2
    {
673
        if (strpos($value, '!') !== false) {
674 2
            throw new PhpSpreadsheetException('Cell coordinate must not specify a worksheet.');
675
        } elseif (strpos($value, ':') === false) {
676 2
            throw new PhpSpreadsheetException('Cell coordinate must be a range of cells.');
677
        } elseif (strpos($value, '$') !== false) {
678
            throw new PhpSpreadsheetException('Cell coordinate must not be absolute.');
679 2
        }
680
        $value = strtoupper($value);
681 2
682 2
        if ($method == self::SETPRINTRANGE_OVERWRITE) {
683 2
            if ($index == 0) {
684
                $this->printArea = $value;
685
            } else {
686
                $printAreas = explode(',', $this->printArea);
687
                if ($index < 0) {
688
                    $index = count($printAreas) - abs($index) + 1;
689
                }
690
                if (($index <= 0) || ($index > count($printAreas))) {
691
                    throw new PhpSpreadsheetException('Invalid index for setting print range.');
692
                }
693 2
                $printAreas[$index - 1] = $value;
694
                $this->printArea = implode(',', $printAreas);
695
            }
696
        } elseif ($method == self::SETPRINTRANGE_INSERT) {
697
            if ($index == 0) {
698
                $this->printArea .= ($this->printArea == '') ? $value : ',' . $value;
699
            } else {
700
                $printAreas = explode(',', $this->printArea);
701
                if ($index < 0) {
702
                    $index = abs($index) - 1;
703
                }
704
                if ($index > count($printAreas)) {
705
                    throw new PhpSpreadsheetException('Invalid index for setting print range.');
706
                }
707
                $printAreas = array_merge(array_slice($printAreas, 0, $index), [$value], array_slice($printAreas, $index));
2 ignored issues
show
Bug introduced by
It seems like $index can also be of type double; however, parameter $length of array_slice() does only seem to accept integer, 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

707
                $printAreas = array_merge(array_slice($printAreas, 0, /** @scrutinizer ignore-type */ $index), [$value], array_slice($printAreas, $index));
Loading history...
Bug introduced by
It seems like $index can also be of type double; however, parameter $offset of array_slice() does only seem to accept integer, 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

707
                $printAreas = array_merge(array_slice($printAreas, 0, $index), [$value], array_slice($printAreas, /** @scrutinizer ignore-type */ $index));
Loading history...
708
                $this->printArea = implode(',', $printAreas);
709
            }
710
        } else {
711
            throw new PhpSpreadsheetException('Invalid method for setting print range.');
712
        }
713 2
714
        return $this;
715
    }
716
717
    /**
718
     * Add a new print area (e.g. 'A1:D10' or 'A1:D10,G5:M20') to the list of print areas.
719
     *
720
     * @param string $value
721
     * @param int $index Identifier for a specific print area range allowing several ranges to be set
722
     *                            A positive index will insert after that indexed entry in the print areas list, while a
723
     *                                negative index will insert before the indexed entry.
724
     *                                Specifying an index value of 0, will always append the new print range at the end of the
725
     *                                list.
726
     *                            Print areas are numbered from 1
727
     *
728
     * @return $this
729
     */
730
    public function addPrintArea($value, $index = -1)
731
    {
732
        return $this->setPrintArea($value, $index, self::SETPRINTRANGE_INSERT);
733
    }
734
735
    /**
736
     * Set print area.
737
     *
738
     * @param int $column1 Column 1
739
     * @param int $row1 Row 1
740
     * @param int $column2 Column 2
741
     * @param int $row2 Row 2
742
     * @param int $index Identifier for a specific print area range allowing several ranges to be set
743
     *                                When the method is "O"verwrite, then a positive integer index will overwrite that indexed
744
     *                                    entry in the print areas list; a negative index value will identify which entry to
745
     *                                    overwrite working backward through the print area to the list, with the last entry as -1.
746
     *                                    Specifying an index value of 0, will overwrite <b>all</b> existing print ranges.
747
     *                                When the method is "I"nsert, then a positive index will insert after that indexed entry in
748
     *                                    the print areas list, while a negative index will insert before the indexed entry.
749
     *                                    Specifying an index value of 0, will always append the new print range at the end of the
750
     *                                    list.
751
     *                                Print areas are numbered from 1
752
     * @param string $method Determines the method used when setting multiple print areas
753
     *                                Default behaviour, or the "O" method, overwrites existing print area
754
     *                                The "I" method, inserts the new print area before any specified index, or at the end of the list
755
     *
756
     * @return $this
757
     */
758
    public function setPrintAreaByColumnAndRow($column1, $row1, $column2, $row2, $index = 0, $method = self::SETPRINTRANGE_OVERWRITE)
759
    {
760
        return $this->setPrintArea(
761
            Coordinate::stringFromColumnIndex($column1) . $row1 . ':' . Coordinate::stringFromColumnIndex($column2) . $row2,
762
            $index,
763
            $method
764
        );
765
    }
766
767
    /**
768
     * Add a new print area to the list of print areas.
769
     *
770
     * @param int $column1 Start Column for the print area
771
     * @param int $row1 Start Row for the print area
772
     * @param int $column2 End Column for the print area
773
     * @param int $row2 End Row for the print area
774
     * @param int $index Identifier for a specific print area range allowing several ranges to be set
775
     *                                A positive index will insert after that indexed entry in the print areas list, while a
776
     *                                    negative index will insert before the indexed entry.
777
     *                                    Specifying an index value of 0, will always append the new print range at the end of the
778
     *                                    list.
779
     *                                Print areas are numbered from 1
780
     *
781
     * @return $this
782
     */
783
    public function addPrintAreaByColumnAndRow($column1, $row1, $column2, $row2, $index = -1)
784
    {
785
        return $this->setPrintArea(
786
            Coordinate::stringFromColumnIndex($column1) . $row1 . ':' . Coordinate::stringFromColumnIndex($column2) . $row2,
787
            $index,
788
            self::SETPRINTRANGE_INSERT
789
        );
790
    }
791
792
    /**
793
     * Get first page number.
794
     *
795
     * @return int
796 106
     */
797
    public function getFirstPageNumber()
798 106
    {
799
        return $this->firstPageNumber;
800
    }
801
802
    /**
803
     * Set first page number.
804
     *
805
     * @param int $value
806
     *
807
     * @return $this
808
     */
809
    public function setFirstPageNumber($value)
810
    {
811
        $this->firstPageNumber = $value;
812
813
        return $this;
814
    }
815
816
    /**
817
     * Reset first page number.
818
     *
819
     * @return $this
820
     */
821
    public function resetFirstPageNumber()
822
    {
823
        return $this->setFirstPageNumber(null);
824
    }
825
826
    public function getPageOrder(): string
827
    {
828
        return $this->pageOrder;
829
    }
830
831
    public function setPageOrder(?string $pageOrder): self
832
    {
833
        if ($pageOrder === null || $pageOrder === self::PAGEORDER_DOWN_THEN_OVER || $pageOrder === self::PAGEORDER_OVER_THEN_DOWN) {
834
            $this->pageOrder = $pageOrder ?? self::PAGEORDER_DOWN_THEN_OVER;
835
        }
836
837
        return $this;
838
    }
839
840
    /**
841
     * Implement PHP __clone to create a deep clone, not just a shallow copy.
842
     */
843
    public function __clone()
844
    {
845
        $vars = get_object_vars($this);
846
        foreach ($vars as $key => $value) {
847
            if (is_object($value)) {
848
                $this->$key = clone $value;
849
            } else {
850
                $this->$key = $value;
851
            }
852
        }
853
    }
854
}
855