Completed
Pull Request — develop (#207)
by Franck
14:46 queued 07:07
created

PptSlides::writeShapeGroup()   C

Complexity

Conditions 8
Paths 8

Size

Total Lines 80
Code Lines 46

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 39
CRAP Score 8.1515

Importance

Changes 2
Bugs 0 Features 0
Metric Value
c 2
b 0
f 0
dl 0
loc 80
ccs 39
cts 45
cp 0.8667
rs 6.0132
cc 8
eloc 46
nc 8
nop 3
crap 8.1515

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace PhpOffice\PhpPresentation\Writer\PowerPoint2007;
4
5
use PhpOffice\Common\Drawing as CommonDrawing;
6
use PhpOffice\Common\Text;
7
use PhpOffice\Common\XMLWriter;
8
use PhpOffice\PhpPresentation\Shape\AbstractDrawing;
9
use PhpOffice\PhpPresentation\Shape\Chart as ShapeChart;
10
use PhpOffice\PhpPresentation\Shape\Comment;
11
use PhpOffice\PhpPresentation\Shape\Drawing as ShapeDrawing;
12
use PhpOffice\PhpPresentation\Shape\Group;
13
use PhpOffice\PhpPresentation\Shape\Line;
14
use PhpOffice\PhpPresentation\Shape\Media;
15
use PhpOffice\PhpPresentation\Shape\RichText;
16
use PhpOffice\PhpPresentation\Shape\RichText\BreakElement;
17
use PhpOffice\PhpPresentation\Shape\RichText\Run;
18
use PhpOffice\PhpPresentation\Shape\RichText\TextElement;
19
use PhpOffice\PhpPresentation\Shape\Table as ShapeTable;
20
use PhpOffice\PhpPresentation\Slide;
21
use PhpOffice\PhpPresentation\Slide\Background\Image;
22
use PhpOffice\PhpPresentation\Slide\Note;
23
use PhpOffice\PhpPresentation\Slide\Transition;
24
use PhpOffice\PhpPresentation\Style\Alignment;
25
use PhpOffice\PhpPresentation\Style\Bullet;
26
use PhpOffice\PhpPresentation\Style\Border;
27
use PhpOffice\PhpPresentation\Style\Shadow;
28
use PhpOffice\PhpPresentation\Writer\PowerPoint2007\LayoutPack\PackDefault;
29
30
class PptSlides extends AbstractDecoratorWriter
31
{
32
    /**
33
     * Add slides (drawings, ...) and slide relationships (drawings, ...)
34
     * @return \PhpOffice\Common\Adapter\Zip\ZipInterface
35
     */
36
    public function render()
37 94
    {
38
        foreach ($this->oPresentation->getAllSlides() as $idx => $oSlide) {
0 ignored issues
show
Coding Style introduced by
Blank line found at start of control structure
Loading history...
39 94
40
            $this->oZip->addFromString('ppt/slides/_rels/slide' . ($idx + 1) . '.xml.rels', $this->writeSlideRelationships($oSlide));
41 94
            $this->oZip->addFromString('ppt/slides/slide' . ($idx + 1) . '.xml', $this->writeSlide($oSlide));
42 94
43
            // Add note slide
44
            if ($oSlide->getNote()->getShapeCollection()->count() > 0) {
45 94
                $this->oZip->addFromString('ppt/notesSlides/notesSlide' . ($idx + 1) . '.xml', $this->writeNote($oSlide->getNote()));
0 ignored issues
show
Bug introduced by
It seems like $oSlide->getNote() can be null; however, writeNote() does not accept null, maybe add an additional type check?

Unless you are absolutely sure that the expression can never be null because of other conditions, we strongly recommend to add an additional type check to your code:

/** @return stdClass|null */
function mayReturnNull() { }

function doesNotAcceptNull(stdClass $x) { }

// With potential error.
function withoutCheck() {
    $x = mayReturnNull();
    doesNotAcceptNull($x); // Potential error here.
}

// Safe - Alternative 1
function withCheck1() {
    $x = mayReturnNull();
    if ( ! $x instanceof stdClass) {
        throw new \LogicException('$x must be defined.');
    }
    doesNotAcceptNull($x);
}

// Safe - Alternative 2
function withCheck2() {
    $x = mayReturnNull();
    if ($x instanceof stdClass) {
        doesNotAcceptNull($x);
    }
}
Loading history...
46 1
            }
47 1
48
            // Add background image slide
49
            $oBkgImage = $oSlide->getBackground();
50 94
            if ($oBkgImage instanceof Image) {
51 94
                $this->oZip->addFromString('ppt/media/'.$oBkgImage->getIndexedFilename($idx), file_get_contents($oBkgImage->getPath()));
52
            }
53
        }
54 94
55
        return $this->oZip;
56 94
    }
57
58
    /**
59
     * Write slide relationships to XML format
60
     *
61
     * @param  \PhpOffice\PhpPresentation\Slide $pSlide
62
     * @return string              XML Output
63
     * @throws \Exception
64
     */
65
    protected function writeSlideRelationships(Slide $pSlide)
66 94
    {
67
        //@todo Group all getShapeCollection()->getIterator
68
69
        // Create XML writer
70
        $objWriter = new XMLWriter(XMLWriter::STORAGE_MEMORY);
71 94
72
        // XML header
73
        $objWriter->startDocument('1.0', 'UTF-8', 'yes');
74 94
75
        // Relationships
76
        $objWriter->startElement('Relationships');
77 94
        $objWriter->writeAttribute('xmlns', 'http://schemas.openxmlformats.org/package/2006/relationships');
78 94
79
        // Starting relation id
80
        $relId = 1;
81 94
        $idxSlide = $pSlide->getParent()->getIndex($pSlide);
82 94
83
        // Write slideLayout relationship
84
        $oLayoutPack  = new PackDefault();
85 94
        $layoutId = $oLayoutPack->findlayoutId($pSlide->getSlideLayout(), $pSlide->getSlideMasterId());
86 94
87
        $this->writeRelationship($objWriter, $relId++, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slideLayout', '../slideLayouts/slideLayout' . $layoutId . '.xml');
88 94
89
        // Write drawing relationships?
90
        if ($pSlide->getShapeCollection()->count() > 0) {
91 94
            // Loop trough images and write relationships
92
            $iterator = $pSlide->getShapeCollection()->getIterator();
93 70
            while ($iterator->valid()) {
94 70
                if ($iterator->current() instanceof ShapeDrawing\AbstractDrawingAdapter) {
95 70
                    // Write relationship for image drawing
96
                    $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/image', '../media/' . $iterator->current()->getIndexedFilename());
97 8
                    $iterator->current()->relationId = 'rId' . $relId;
98
                    ++$relId;
99 8
                } elseif ($iterator->current() instanceof ShapeChart) {
100
                    // Write relationship for chart drawing
101 8
                    $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/chart', '../charts/' . $iterator->current()->getIndexedFilename());
102 70
103
                    $iterator->current()->relationId = 'rId' . $relId;
104 24
105
                    ++$relId;
106 24
                } elseif ($iterator->current() instanceof Group) {
107
                    $iterator2 = $iterator->current()->getShapeCollection()->getIterator();
108 24
                    while ($iterator2->valid()) {
109 62
                        if ($iterator->current() instanceof ShapeDrawing\AbstractDrawingAdapter) {
110 1
                            // Write relationship for image drawing
111 1
                            $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/image', '../media/' . $iterator2->current()->getIndexedFilename());
112 1
                            $iterator2->current()->relationId = 'rId' . $relId;
113
114
                            ++$relId;
115
                        } elseif ($iterator2->current() instanceof ShapeChart) {
116
                            // Write relationship for chart drawing
117
                            $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/chart', '../charts/' . $iterator2->current()->getIndexedFilename());
118
                            $iterator2->current()->relationId = 'rId' . $relId;
119 1
120
                            ++$relId;
121
                        }
122
                        $iterator2->next();
123
                    }
124
                }
125
126
                $iterator->next();
127 1
            }
128 1
        }
129 1
130
        // Write background relationships?
131 70
        $oBackground = $pSlide->getBackground();
132 70
        if ($oBackground instanceof Image) {
133 70
            $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/image', '../media/' . $oBackground->getIndexedFilename($idxSlide));
134
            $oBackground->relationId = 'rId' . $relId;
135
            ++$relId;
136 94
        }
137 94
138
        // Write hyperlink relationships?
139
        if ($pSlide->getShapeCollection()->count() > 0) {
140
            // Loop trough hyperlinks and write relationships
141
            $iterator = $pSlide->getShapeCollection()->getIterator();
142
            while ($iterator->valid()) {
143
                // Hyperlink on shape
144 94
                if ($iterator->current()->hasHyperlink()) {
145
                    // Write relationship for hyperlink
146 70
                    $hyperlink               = $iterator->current()->getHyperlink();
147 70
                    $hyperlink->relationId = 'rId' . $relId;
148
149 70
                    if (!$hyperlink->isInternal()) {
150
                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
151 2
                    } else {
152 2
                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
153
                    }
154 2
155 2
                    ++$relId;
156 2
                }
157
158
                // Hyperlink on rich text run
159
                if ($iterator->current() instanceof RichText) {
160 2
                    foreach ($iterator->current()->getParagraphs() as $paragraph) {
161 2
                        foreach ($paragraph->getRichTextElements() as $element) {
162
                            if ($element instanceof Run || $element instanceof RunTextElement) {
0 ignored issues
show
Bug introduced by
The class PhpOffice\PhpPresentatio...oint2007\RunTextElement does not exist. Did you forget a USE statement, or did you not list all dependencies?

This error could be the result of:

1. Missing dependencies

PHP Analyzer uses your composer.json file (if available) to determine the dependencies of your project and to determine all the available classes and functions. It expects the composer.json to be in the root folder of your repository.

Are you sure this class is defined by one of your dependencies, or did you maybe not list a dependency in either the require or require-dev section?

2. Missing use statement

PHP does not complain about undefined classes in ìnstanceof checks. For example, the following PHP code will work perfectly fine:

if ($x instanceof DoesNotExist) {
    // Do something.
}

If you have not tested against this specific condition, such errors might go unnoticed.

Loading history...
163
                                if ($element->hasHyperlink()) {
164 70
                                    // Write relationship for hyperlink
165 21
                                    $hyperlink               = $element->getHyperlink();
166 21
                                    $hyperlink->relationId = 'rId' . $relId;
167 17
168 16
                                    if (!$hyperlink->isInternal()) {
169
                                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
170 2
                                    } else {
171 2
                                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
172
                                    }
173 2
174 1
                                    ++$relId;
175 1
                                }
176 1
                            }
177
                        }
178
                    }
179 2
                }
180 2
181 16
                // Hyperlink in table
182 21
                if ($iterator->current() instanceof ShapeTable) {
183 21
                    // Rows
184 21
                    $countRows = count($iterator->current()->getRows());
185
                    for ($row = 0; $row < $countRows; $row++) {
186
                        // Cells in rows
187 70
                        $countCells = count($iterator->current()->getRow($row)->getCells());
188
                        for ($cell = 0; $cell < $countCells; $cell++) {
189 9
                            $currentCell = $iterator->current()->getRow($row)->getCell($cell);
190 9
                            // Paragraphs in cell
191
                            foreach ($currentCell->getParagraphs() as $paragraph) {
192 9
                                // RichText in paragraph
193 9
                                foreach ($paragraph->getRichTextElements() as $element) {
194 9
                                    // Run or Text in RichText
195
                                    if ($element instanceof Run || $element instanceof TextElement) {
196 9
                                        if ($element->hasHyperlink()) {
197
                                            // Write relationship for hyperlink
198 9
                                            $hyperlink               = $element->getHyperlink();
199
                                            $hyperlink->relationId = 'rId' . $relId;
200 9
201 9
                                            if (!$hyperlink->isInternal()) {
202
                                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
203 1
                                            } else {
204 1
                                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
205
                                            }
206 1
207 1
                                            ++$relId;
208 1
                                        }
209
                                    }
210
                                }
211
                            }
212 1
                        }
213 1
                    }
214 9
                }
215 9
216 9
                if ($iterator->current() instanceof Group) {
217 9
                    $iterator2 = $pSlide->getShapeCollection()->getIterator();
218 9
                    while ($iterator2->valid()) {
219 9
                        // Hyperlink on shape
220
                        if ($iterator2->current()->hasHyperlink()) {
221 70
                            // Write relationship for hyperlink
222 1
                            $hyperlink             = $iterator2->current()->getHyperlink();
223 1
                            $hyperlink->relationId = 'rId' . $relId;
224
225 1
                            if (!$hyperlink->isInternal()) {
226
                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
227
                            } else {
228
                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
229
                            }
230
231
                            ++$relId;
232
                        }
233
234
                        // Hyperlink on rich text run
235
                        if ($iterator2->current() instanceof RichText) {
236
                            foreach ($iterator2->current()->getParagraphs() as $paragraph) {
237
                                foreach ($paragraph->getRichTextElements() as $element) {
238
                                    if ($element instanceof Run || $element instanceof TextElement) {
239
                                        if ($element->hasHyperlink()) {
240 1
                                            // Write relationship for hyperlink
241
                                            $hyperlink              = $element->getHyperlink();
242
                                            $hyperlink->relationId = 'rId' . $relId;
243
244
                                            if (!$hyperlink->isInternal()) {
245
                                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
246
                                            } else {
247
                                                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
248
                                            }
249
250
                                            ++$relId;
251
                                        }
252
                                    }
253
                                }
254
                            }
255
                        }
256
257
                        // Hyperlink in table
258
                        if ($iterator2->current() instanceof ShapeTable) {
259
                            // Rows
260
                            $countRows = count($iterator2->current()->getRows());
261
                            for ($row = 0; $row < $countRows; $row++) {
262
                                // Cells in rows
263 1
                                $countCells = count($iterator2->current()->getRow($row)->getCells());
264
                                for ($cell = 0; $cell < $countCells; $cell++) {
265
                                    $currentCell = $iterator2->current()->getRow($row)->getCell($cell);
266
                                    // Paragraphs in cell
267
                                    foreach ($currentCell->getParagraphs() as $paragraph) {
268
                                        // RichText in paragraph
269
                                        foreach ($paragraph->getRichTextElements() as $element) {
270
                                            // Run or Text in RichText
271
                                            if ($element instanceof Run || $element instanceof TextElement) {
272
                                                if ($element->hasHyperlink()) {
273
                                                    // Write relationship for hyperlink
274
                                                    $hyperlink               = $element->getHyperlink();
275
                                                    $hyperlink->relationId = 'rId' . $relId;
276
277
                                                    if (!$hyperlink->isInternal()) {
278
                                                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink', $hyperlink->getUrl(), 'External');
279
                                                    } else {
280
                                                        $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/slide', 'slide' . $hyperlink->getSlideNumber() . '.xml');
281
                                                    }
282
283
                                                    ++$relId;
284
                                                }
285
                                            }
286
                                        }
287
                                    }
288
                                }
289
                            }
290
                        }
291
292
                        $iterator2->next();
293
                    }
294
0 ignored issues
show
Coding Style introduced by
Blank line found at end of control structure
Loading history...
295
                }
296
297 1
                $iterator->next();
298 1
            }
299
        }
300 1
301
        // Write comment relationships
302 70
        if ($pSlide->getShapeCollection()->count() > 0) {
303 70
            $hasSlideComment = false;
304 70
305
            // Loop trough images and write relationships
306
            $iterator = $pSlide->getShapeCollection()->getIterator();
307 94
            while ($iterator->valid()) {
308 70
                if ($iterator->current() instanceof Comment) {
309
                    $hasSlideComment = true;
310
                    break;
311 70
                } elseif ($iterator->current() instanceof Group) {
312 70
                    $iterator2 = $iterator->current()->getShapeCollection()->getIterator();
313 70
                    while ($iterator2->valid()) {
314 6
                        if ($iterator2->current() instanceof Comment) {
315 6
                            $hasSlideComment = true;
316 64
                            break 2;
317 1
                        }
318 1
                        $iterator2->next();
319 1
                    }
320 1
                }
321 1
322
                $iterator->next();
323
            }
324
325
            if ($hasSlideComment) {
326
                $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/comments', '../comments/comment'.($idxSlide + 1).'.xml');
327 63
                ++$relId;
328 63
            }
329
        }
330 70
331 7
        if ($pSlide->getNote()->getShapeCollection()->count() > 0) {
332 7
            $this->writeRelationship($objWriter, $relId, 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/notesSlide', '../notesSlides/notesSlide'.($idxSlide + 1).'.xml');
333 7
        }
334 70
335
        $objWriter->endElement();
336 94
337 1
        // Return
338 1
        return $objWriter->getData();
339
    }
340 94
341
    /**
342
     * Write slide to XML format
343 94
     *
344
     * @param  \PhpOffice\PhpPresentation\Slide $pSlide
345
     * @return string              XML Output
346
     * @throws \Exception
347
     */
348
    public function writeSlide(Slide $pSlide)
349
    {
350
        // Create XML writer
351
        $objWriter = new XMLWriter(XMLWriter::STORAGE_MEMORY);
352
353 94
        // XML header
354
        $objWriter->startDocument('1.0', 'UTF-8', 'yes');
355
356 94
        // p:sld
357
        $objWriter->startElement('p:sld');
358
        $objWriter->writeAttribute('xmlns:a', 'http://schemas.openxmlformats.org/drawingml/2006/main');
359 94
        $objWriter->writeAttribute('xmlns:r', 'http://schemas.openxmlformats.org/officeDocument/2006/relationships');
360
        $objWriter->writeAttribute('xmlns:p', 'http://schemas.openxmlformats.org/presentationml/2006/main');
361
        $objWriter->writeAttributeIf(!$pSlide->isVisible(), 'show', 0);
362 94
363 94
        // p:sld\p:cSld
364 94
        $objWriter->startElement('p:cSld');
365 94
366 94
        // Background
367
        if ($pSlide->getBackground() instanceof Slide\AbstractBackground) {
368
            $oBackground = $pSlide->getBackground();
369 94
            // p:bg
370
            $objWriter->startElement('p:bg');
371
372 94
            // p:bgPr
373
            $objWriter->startElement('p:bgPr');
374
375
            if ($oBackground instanceof Slide\Background\Color) {
376
                // a:solidFill
377
                $objWriter->startElement('a:solidFill');
378
379
                $this->writeColor($objWriter, $oBackground->getColor());
380
381
                // > a:solidFill
382
                $objWriter->endElement();
383
            }
384
385
            if ($oBackground instanceof Slide\Background\Image) {
386
                // a:blipFill
387
                $objWriter->startElement('a:blipFill');
388
389
                // a:blip
390
                $objWriter->startElement('a:blip');
391
                $objWriter->writeAttribute('r:embed', $oBackground->relationId);
392
393
                // > a:blipFill
394
                $objWriter->endElement();
395
396
                // a:stretch
397
                $objWriter->startElement('a:stretch');
398
399
                // a:fillRect
400
                $objWriter->writeElement('a:fillRect');
401
402
                // > a:stretch
403
                $objWriter->endElement();
404
405
                // > a:blipFill
406
                $objWriter->endElement();
407
            }
408
409
            // > p:bgPr
410
            $objWriter->endElement();
411
412
            // > p:bg
413
            $objWriter->endElement();
414
        }
415
416
        // p:spTree
417
        $objWriter->startElement('p:spTree');
418
419
        // p:nvGrpSpPr
420
        $objWriter->startElement('p:nvGrpSpPr');
421
422 94
        // p:cNvPr
423
        $objWriter->startElement('p:cNvPr');
424
        $objWriter->writeAttribute('id', '1');
425 94
        $objWriter->writeAttribute('name', '');
426
        $objWriter->endElement();
427
428 94
        // p:cNvGrpSpPr
429 94
        $objWriter->writeElement('p:cNvGrpSpPr', null);
430 94
431 94
        // p:nvPr
432
        $objWriter->writeElement('p:nvPr', null);
433
434 94
        $objWriter->endElement();
435
436
        // p:grpSpPr
437 94
        $objWriter->startElement('p:grpSpPr');
438
439 94
        // a:xfrm
440
        $objWriter->startElement('a:xfrm');
441
442 94
        // a:off
443
        $objWriter->startElement('a:off');
444
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($pSlide->getOffsetX()));
445 94
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($pSlide->getOffsetY()));
446
        $objWriter->endElement(); // a:off
447
448 94
        // a:ext
449 94
        $objWriter->startElement('a:ext');
450 94
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($pSlide->getExtentX()));
451 94
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($pSlide->getExtentY()));
452
        $objWriter->endElement(); // a:ext
453
454 94
        // a:chOff
455 94
        $objWriter->startElement('a:chOff');
456 94
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($pSlide->getOffsetX()));
457 94
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($pSlide->getOffsetY()));
458
        $objWriter->endElement(); // a:chOff
459
460 94
        // a:chExt
461 94
        $objWriter->startElement('a:chExt');
462 94
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($pSlide->getExtentX()));
463 94
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($pSlide->getExtentY()));
464
        $objWriter->endElement(); // a:chExt
465
466 94
        $objWriter->endElement();
467 94
468 94
        $objWriter->endElement();
469 94
470
        // Loop shapes
471 94
        $shapeId = 0;
472
        $shapes  = $pSlide->getShapeCollection();
473 94
        foreach ($shapes as $shape) {
474
            // Increment $shapeId
475
            ++$shapeId;
476 94
477 94
            // Check type
478 94
            if ($shape instanceof RichText) {
479
                $this->writeShapeText($objWriter, $shape, $shapeId);
480 70
            } elseif ($shape instanceof ShapeTable) {
481
                $this->writeShapeTable($objWriter, $shape, $shapeId);
482
            } elseif ($shape instanceof Line) {
483 70
                $this->writeShapeLine($objWriter, $shape, $shapeId);
484 21
            } elseif ($shape instanceof ShapeChart) {
485 70
                $this->writeShapeChart($objWriter, $shape, $shapeId);
486 9
            } elseif ($shape instanceof ShapeDrawing\AbstractDrawingAdapter) {
487 49
                $this->writeShapeDrawing($objWriter, $shape, $shapeId);
488 1
            } elseif ($shape instanceof Group) {
489 40
                $this->writeShapeGroup($objWriter, $shape, $shapeId);
490 24
            }
491 39
        }
492 8
493 15
        // TODO
494 1
        $objWriter->endElement();
495 1
496 94
        $objWriter->endElement();
497
498
        // p:clrMapOvr
499 94
        $objWriter->startElement('p:clrMapOvr');
500
501 94
        // a:masterClrMapping
502
        $objWriter->writeElement('a:masterClrMapping', null);
503
504 94
        $objWriter->endElement();
505
506
        if (!is_null($pSlide->getTransition())) {
507 94
            $this->writeTransition($objWriter, $pSlide->getTransition());
508
        }
509 94
510
        $objWriter->endElement();
511 94
512 1
        // Return
513 1
        return $objWriter->getData();
514
    }
515 94
516
    /**
517
     * Write group
518 94
     *
519
     * @param \PhpOffice\Common\XMLWriter $objWriter XML Writer
520
     * @param \PhpOffice\PhpPresentation\Shape\Group $group
521
     * @param  int $shapeId
522
     */
523
    protected function writeShapeGroup(XMLWriter $objWriter, Group $group, &$shapeId)
524
    {
525
        // p:grpSp
526
        $objWriter->startElement('p:grpSp');
527
528 1
        // p:nvGrpSpPr
529
        $objWriter->startElement('p:nvGrpSpPr');
530
531 1
        // p:cNvPr
532
        $objWriter->startElement('p:cNvPr');
533
        $objWriter->writeAttribute('name', 'Group '.$shapeId++);
534 1
        $objWriter->writeAttribute('id', $shapeId);
535
        $objWriter->endElement(); // p:cNvPr
536
        // NOTE: Re: $shapeId This seems to be how PowerPoint 2010 does business.
537 1
538 1
        // p:cNvGrpSpPr
539 1
        $objWriter->writeElement('p:cNvGrpSpPr', null);
540 1
541
        // p:nvPr
542
        $objWriter->writeElement('p:nvPr', null);
543
544 1
        $objWriter->endElement(); // p:nvGrpSpPr
545
546
        // p:grpSpPr
547 1
        $objWriter->startElement('p:grpSpPr');
548
549 1
        // a:xfrm
550
        $objWriter->startElement('a:xfrm');
551
552 1
        // a:off
553
        $objWriter->startElement('a:off');
554
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($group->getOffsetX()));
555 1
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($group->getOffsetY()));
556
        $objWriter->endElement(); // a:off
557
558 1
        // a:ext
559 1
        $objWriter->startElement('a:ext');
560 1
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($group->getExtentX()));
561 1
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($group->getExtentY()));
562
        $objWriter->endElement(); // a:ext
563
564 1
        // a:chOff
565 1
        $objWriter->startElement('a:chOff');
566 1
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($group->getOffsetX()));
567 1
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($group->getOffsetY()));
568
        $objWriter->endElement(); // a:chOff
569
570 1
        // a:chExt
571 1
        $objWriter->startElement('a:chExt');
572 1
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($group->getExtentX()));
573 1
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($group->getExtentY()));
574
        $objWriter->endElement(); // a:chExt
575
576 1
        $objWriter->endElement(); // a:xfrm
577 1
578 1
        $objWriter->endElement(); // p:grpSpPr
579 1
580
        $shapes  = $group->getShapeCollection();
581 1
        foreach ($shapes as $shape) {
582
            // Increment $shapeId
583 1
            ++$shapeId;
584
585 1
            // Check type
586 1
            if ($shape instanceof RichText) {
587
                $this->writeShapeText($objWriter, $shape, $shapeId);
588 1
            } elseif ($shape instanceof ShapeTable) {
589
                $this->writeShapeTable($objWriter, $shape, $shapeId);
590
            } elseif ($shape instanceof Line) {
591 1
                $this->writeShapeLine($objWriter, $shape, $shapeId);
592
            } elseif ($shape instanceof ShapeChart) {
593 1
                $this->writeShapeChart($objWriter, $shape, $shapeId);
594
            } elseif ($shape instanceof ShapeDrawing\AbstractDrawingAdapter) {
595 1
                $this->writeShapeDrawing($objWriter, $shape, $shapeId);
596
            } elseif ($shape instanceof Group) {
597 1
                $this->writeShapeGroup($objWriter, $shape, $shapeId);
598
            }
599 1
        }
600
601 1
        $objWriter->endElement(); // p:grpSp
602
    }
603
604 1
    /**
605
     * Write chart
606 1
     *
607 1
     * @param \PhpOffice\Common\XMLWriter $objWriter XML Writer
608
     * @param \PhpOffice\PhpPresentation\Shape\Chart $shape
609
     * @param  int $shapeId
610
     */
611
    protected function writeShapeChart(XMLWriter $objWriter, ShapeChart $shape, $shapeId)
612
    {
613
        // p:graphicFrame
614
        $objWriter->startElement('p:graphicFrame');
615
616 24
        // p:nvGraphicFramePr
617
        $objWriter->startElement('p:nvGraphicFramePr');
618
619 24
        // p:cNvPr
620
        $objWriter->startElement('p:cNvPr');
621
        $objWriter->writeAttribute('id', $shapeId);
622 24
        $objWriter->writeAttribute('name', $shape->getName());
623
        $objWriter->writeAttribute('descr', $shape->getDescription());
624
        $objWriter->endElement();
625 24
626 24
        // p:cNvGraphicFramePr
627 24
        $objWriter->writeElement('p:cNvGraphicFramePr', null);
628 24
629 24
        // p:nvPr
630
        $objWriter->writeElement('p:nvPr', null);
631
632 24
        $objWriter->endElement();
633
634
        // p:xfrm
635 24
        $objWriter->startElement('p:xfrm');
636
        $objWriter->writeAttribute('rot', CommonDrawing::degreesToAngle($shape->getRotation()));
637 24
638
        // a:off
639
        $objWriter->startElement('a:off');
640 24
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
641 24
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
642
        $objWriter->endElement();
643
644 24
        // a:ext
645 24
        $objWriter->startElement('a:ext');
646 24
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
647 24
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
648
        $objWriter->endElement();
649
650 24
        $objWriter->endElement();
651 24
652 24
        // a:graphic
653 24
        $objWriter->startElement('a:graphic');
654
655 24
        // a:graphicData
656
        $objWriter->startElement('a:graphicData');
657
        $objWriter->writeAttribute('uri', 'http://schemas.openxmlformats.org/drawingml/2006/chart');
658 24
659
        // c:chart
660
        $objWriter->startElement('c:chart');
661 24
        $objWriter->writeAttribute('xmlns:c', 'http://schemas.openxmlformats.org/drawingml/2006/chart');
662 24
        $objWriter->writeAttribute('xmlns:r', 'http://schemas.openxmlformats.org/officeDocument/2006/relationships');
663
        $objWriter->writeAttribute('r:id', $shape->relationId);
664
        $objWriter->endElement();
665 24
666 24
        $objWriter->endElement();
667 24
668 24
        $objWriter->endElement();
669 24
670
        $objWriter->endElement();
671 24
    }
672
673 24
    /**
674
     * Write pic
675 24
     *
676 24
     * @param  \PhpOffice\Common\XMLWriter  $objWriter XML Writer
677
     * @param  \PhpOffice\PhpPresentation\Shape\Drawing\AbstractDrawingAdapter $shape
678
     * @param  int $shapeId
679
     * @throws \Exception
680
     */
681
    protected function writeShapeDrawing(XMLWriter $objWriter, ShapeDrawing\AbstractDrawingAdapter $shape, $shapeId)
682
    {
683
        // p:pic
684
        $objWriter->startElement('p:pic');
685
686 8
        // p:nvPicPr
687
        $objWriter->startElement('p:nvPicPr');
688
689 8
        // p:cNvPr
690
        $objWriter->startElement('p:cNvPr');
691
        $objWriter->writeAttribute('id', $shapeId);
692 8
        $objWriter->writeAttribute('name', $shape->getName());
693
        $objWriter->writeAttribute('descr', $shape->getDescription());
694
695 8
        // a:hlinkClick
696 8
        if ($shape->hasHyperlink()) {
697 8
            $this->writeHyperlink($objWriter, $shape);
698 8
        }
699
700
        $objWriter->endElement();
701 8
702 1
        // p:cNvPicPr
703 1
        $objWriter->startElement('p:cNvPicPr');
704
705 8
        // a:picLocks
706
        $objWriter->startElement('a:picLocks');
707
        $objWriter->writeAttribute('noChangeAspect', '1');
708 8
        $objWriter->endElement();
709
710
        $objWriter->endElement();
711 8
712 8
        // p:nvPr
713 8
        $objWriter->startElement('p:nvPr');
714
        /**
715 8
         * @link : https://github.com/stefslon/exportToPPTX/blob/master/exportToPPTX.m#L2128
716
         */
717
        if ($shape instanceof Media) {
718 8
            // p:nvPr > a:videoFile
719
            $objWriter->startElement('a:videoFile');
720
            $objWriter->writeAttribute('r:link', $shape->relationId);
721
            $objWriter->endElement();
722 8
            // p:nvPr > p:extLst
723
            $objWriter->startElement('p:extLst');
724 1
            // p:nvPr > p:extLst > p:ext
725 1
            $objWriter->startElement('p:ext');
726 1
            $objWriter->writeAttribute('uri', '{DAA4B4D4-6D71-4841-9C94-3DE7FCFB9230}');
727
            // p:nvPr > p:extLst > p:ext > p14:media
728 1
            $objWriter->startElement('p14:media');
729
            $objWriter->writeAttribute('r:embed', $shape->relationId);
730 1
            $objWriter->writeAttribute('xmlns:p14', 'http://schemas.microsoft.com/office/powerpoint/2010/main');
731 1
            // p:nvPr > p:extLst > p:ext > ##p14:media
732
            $objWriter->endElement();
733 1
            // p:nvPr > p:extLst > ##p:ext
734 1
            $objWriter->endElement();
735 1
            // p:nvPr > ##p:extLst
736
            $objWriter->endElement();
737 1
        }
738
        // ##p:nvPr
739 1
        $objWriter->endElement();
740
        $objWriter->endElement();
741 1
742 1
        // p:blipFill
743
        $objWriter->startElement('p:blipFill');
744 8
745 8
        // a:blip
746
        $objWriter->startElement('a:blip');
747
        $objWriter->writeAttribute('r:embed', $shape->relationId);
748 8
        $objWriter->endElement();
749
750
        // a:stretch
751 8
        $objWriter->startElement('a:stretch');
752 8
        $objWriter->writeElement('a:fillRect', null);
753 8
        $objWriter->endElement();
754
755
        $objWriter->endElement();
756 8
757 8
        // p:spPr
758 8
        $objWriter->startElement('p:spPr');
759
        // a:xfrm
760 8
        $objWriter->startElement('a:xfrm');
761
        $objWriter->writeAttribute('rot', CommonDrawing::degreesToAngle($shape->getRotation()));
762
763 8
        // a:off
764
        $objWriter->startElement('a:off');
765 8
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
766 8
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
767
        $objWriter->endElement();
768
769 8
        // a:ext
770 8
        $objWriter->startElement('a:ext');
771 8
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
772 8
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
773
        $objWriter->endElement();
774
775 8
        $objWriter->endElement();
776 8
777 8
        // a:prstGeom
778 8
        $objWriter->startElement('a:prstGeom');
779
        $objWriter->writeAttribute('prst', 'rect');
780 8
781
        // a:avLst
782
        $objWriter->writeElement('a:avLst', null);
783 8
784 8
        $objWriter->endElement();
785
786
        $this->writeBorder($objWriter, $shape->getBorder(), '');
787 8
788
        $this->writeShadow($objWriter, $shape->getShadow());
789 8
790
        $objWriter->endElement();
791 8
792 1
        $objWriter->endElement();
793 1
    }
794
795 8
    /**
796 1
     * Write txt
797 1
     *
798
     * @param  \PhpOffice\Common\XMLWriter $objWriter XML Writer
799 8
     * @param  \PhpOffice\PhpPresentation\Shape\RichText   $shape
800
     * @param  int                            $shapeId
801 8
     * @throws \Exception
802 8
     */
803
    protected function writeShapeText(XMLWriter $objWriter, RichText $shape, $shapeId)
804
    {
805
        // p:sp
806
        $objWriter->startElement('p:sp');
807
808
        // p:sp\p:nvSpPr
809
        $objWriter->startElement('p:nvSpPr');
810
811
        // p:sp\p:nvSpPr\p:cNvPr
812 21
        $objWriter->startElement('p:cNvPr');
813
        $objWriter->writeAttribute('id', $shapeId);
814
        $objWriter->writeAttribute('name', '');
815 21
816
        // Hyperlink
817
        if ($shape->hasHyperlink()) {
818 21
            $this->writeHyperlink($objWriter, $shape);
819
        }
820
        // > p:sp\p:nvSpPr
821 21
        $objWriter->endElement();
822 21
823 21
        // p:sp\p:cNvSpPr
824
        $objWriter->startElement('p:cNvSpPr');
825
        $objWriter->writeAttribute('txBox', '1');
826 21
        $objWriter->endElement();
827 1
        // p:sp\p:cNvSpPr\p:nvPr
828 1
        $objWriter->writeElement('p:nvPr', null);
829
        // > p:sp\p:cNvSpPr
830 21
        $objWriter->endElement();
831
832
        // p:sp\p:spPr
833 21
        $objWriter->startElement('p:spPr');
834 21
835 21
        // p:sp\p:spPr\a:xfrm
836
        $objWriter->startElement('a:xfrm');
837 21
        $objWriter->writeAttribute('rot', CommonDrawing::degreesToAngle($shape->getRotation()));
838
839 21
        // p:sp\p:spPr\a:xfrm\a:off
840
        $objWriter->startElement('a:off');
841
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
842 21
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
843
        $objWriter->endElement();
844
845 21
        // p:sp\p:spPr\a:xfrm\a:ext
846 21
        $objWriter->startElement('a:ext');
847
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
848
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
849 21
        $objWriter->endElement();
850 21
851 21
        // > p:sp\p:spPr\a:xfrm
852 21
        $objWriter->endElement();
853
854
        // p:sp\p:spPr\a:prstGeom
855 21
        $objWriter->startElement('a:prstGeom');
856 21
        $objWriter->writeAttribute('prst', 'rect');
857 21
        $objWriter->endElement();
858 21
859
        if ($shape->getFill()) {
860
            $this->writeFill($objWriter, $shape->getFill());
861 21
        }
862
        $this->writeBorder($objWriter, $shape->getBorder(), '');
863
        $this->writeShadow($objWriter, $shape->getShadow());
864 21
865 21
        // > p:sp\p:spPr
866 21
        $objWriter->endElement();
867
868 21
        // p:txBody
869 21
        $objWriter->startElement('p:txBody');
870 21
871 21
        // a:bodyPr
872
        //@link :http://msdn.microsoft.com/en-us/library/documentformat.openxml.drawing.bodyproperties%28v=office.14%29.aspx
873
        $objWriter->startElement('a:bodyPr');
874 21
        $verticalAlign = $shape->getActiveParagraph()->getAlignment()->getVertical();
875 1
        if ($verticalAlign != Alignment::VERTICAL_BASE && $verticalAlign != Alignment::VERTICAL_AUTO) {
876 1
            $objWriter->writeAttribute('anchor', $verticalAlign);
877
        }
878 21
        if ($shape->getWrap() != RichText::WRAP_SQUARE) {
879
            $objWriter->writeAttribute('wrap', $shape->getWrap());
880
        }
881 21
        $objWriter->writeAttribute('rtlCol', '0');
882
883
        if ($shape->getHorizontalOverflow() != RichText::OVERFLOW_OVERFLOW) {
884
            $objWriter->writeAttribute('horzOverflow', $shape->getHorizontalOverflow());
885 21
        }
886 21
        if ($shape->getVerticalOverflow() != RichText::OVERFLOW_OVERFLOW) {
887 21
            $objWriter->writeAttribute('vertOverflow', $shape->getVerticalOverflow());
888 3
        }
889 3
890 21
        if ($shape->isUpright()) {
891
            $objWriter->writeAttribute('upright', '1');
892
        }
893 21
        if ($shape->isVertical()) {
894
            $objWriter->writeAttribute('vert', 'vert');
895 21
        }
896
897
        $objWriter->writeAttribute('bIns', CommonDrawing::pixelsToEmu($shape->getInsetBottom()));
898 21
        $objWriter->writeAttribute('lIns', CommonDrawing::pixelsToEmu($shape->getInsetLeft()));
899
        $objWriter->writeAttribute('rIns', CommonDrawing::pixelsToEmu($shape->getInsetRight()));
900
        $objWriter->writeAttribute('tIns', CommonDrawing::pixelsToEmu($shape->getInsetTop()));
901
902 21
        if ($shape->getColumns() <> 1) {
903 1
            $objWriter->writeAttribute('numCol', $shape->getColumns());
904 1
        }
905 21
906 1
        // a:spAutoFit
907 1
        $objWriter->startElement('a:' . $shape->getAutoFit());
908
        if ($shape->getAutoFit() == RichText::AUTOFIT_NORMAL) {
909 21
            if (!is_null($shape->getFontScale())) {
910 21
                $objWriter->writeAttribute('fontScale', (int)($shape->getFontScale() * 1000));
911 21
            }
912 21
            if (!is_null($shape->getLineSpaceReduction())) {
913
                $objWriter->writeAttribute('lnSpcReduction', (int)($shape->getLineSpaceReduction() * 1000));
914 21
            }
915
        }
916
917
        $objWriter->endElement();
918
919 21
        $objWriter->endElement();
920 21
921 1
        // a:lstStyle
922 1
        $objWriter->writeElement('a:lstStyle', null);
923 1
924 1
        // Write paragraphs
925 1
        $this->writeParagraphs($objWriter, $shape->getParagraphs());
926 1
927 1
        $objWriter->endElement();
928
929 21
        $objWriter->endElement();
930
    }
931 21
932
    /**
933
     * Write table
934 21
     *
935
     * @param  \PhpOffice\Common\XMLWriter $objWriter XML Writer
936
     * @param  \PhpOffice\PhpPresentation\Shape\Table      $shape
937 21
     * @param  int                            $shapeId
938
     * @throws \Exception
939 21
     */
940
    protected function writeShapeTable(XMLWriter $objWriter, ShapeTable $shape, $shapeId)
941 21
    {
942 21
        // p:graphicFrame
943
        $objWriter->startElement('p:graphicFrame');
944
945
        // p:nvGraphicFramePr
946
        $objWriter->startElement('p:nvGraphicFramePr');
947
948
        // p:cNvPr
949
        $objWriter->startElement('p:cNvPr');
950
        $objWriter->writeAttribute('id', $shapeId);
951
        $objWriter->writeAttribute('name', $shape->getName());
952 9
        $objWriter->writeAttribute('descr', $shape->getDescription());
953
954
        $objWriter->endElement();
955 9
956
        // p:cNvGraphicFramePr
957
        $objWriter->startElement('p:cNvGraphicFramePr');
958 9
959
        // a:graphicFrameLocks
960
        $objWriter->startElement('a:graphicFrameLocks');
961 9
        $objWriter->writeAttribute('noGrp', '1');
962 9
        $objWriter->endElement();
963 9
964 9
        $objWriter->endElement();
965
966 9
        // p:nvPr
967
        $objWriter->writeElement('p:nvPr', null);
968
969 9
        $objWriter->endElement();
970
971
        // p:xfrm
972 9
        $objWriter->startElement('p:xfrm');
973 9
974 9
        // a:off
975
        $objWriter->startElement('a:off');
976 9
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
977
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
978
        $objWriter->endElement();
979 9
980
        // a:ext
981 9
        $objWriter->startElement('a:ext');
982
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
983
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
984 9
        $objWriter->endElement();
985
986
        $objWriter->endElement();
987 9
988 9
        // a:graphic
989 9
        $objWriter->startElement('a:graphic');
990 9
991
        // a:graphicData
992
        $objWriter->startElement('a:graphicData');
993 9
        $objWriter->writeAttribute('uri', 'http://schemas.openxmlformats.org/drawingml/2006/table');
994 9
995 9
        // a:tbl
996 9
        $objWriter->startElement('a:tbl');
997
998 9
        // a:tblPr
999
        $objWriter->startElement('a:tblPr');
1000
        $objWriter->writeAttribute('firstRow', '1');
1001 9
        $objWriter->writeAttribute('bandRow', '1');
1002
1003
        $objWriter->endElement();
1004 9
1005 9
        // a:tblGrid
1006
        $objWriter->startElement('a:tblGrid');
1007
1008 9
        // Write cell widths
1009
        $countCells = count($shape->getRow(0)->getCells());
1010
        for ($cell = 0; $cell < $countCells; $cell++) {
1011 9
            // a:gridCol
1012 9
            $objWriter->startElement('a:gridCol');
1013 9
1014
            // Calculate column width
1015 9
            $width = $shape->getRow(0)->getCell($cell)->getWidth();
1016
            if ($width == 0) {
1017
                $colCount   = count($shape->getRow(0)->getCells());
1018 9
                $totalWidth = $shape->getWidth();
1019
                $width      = $totalWidth / $colCount;
1020
            }
1021 9
1022 9
            $objWriter->writeAttribute('w', CommonDrawing::pixelsToEmu($width));
1023
            $objWriter->endElement();
1024 9
        }
1025
1026
        $objWriter->endElement();
1027 9
1028 9
        // Colspan / rowspan containers
1029 9
        $colSpan = array();
1030 9
        $rowSpan = array();
1031 9
1032 9
        // Default border style
1033
        $defaultBorder = new Border();
1034 9
1035 9
        // Write rows
1036 9
        $countRows = count($shape->getRows());
1037
        for ($row = 0; $row < $countRows; $row++) {
1038 9
            // a:tr
1039
            $objWriter->startElement('a:tr');
1040
            $objWriter->writeAttribute('h', CommonDrawing::pixelsToEmu($shape->getRow($row)->getHeight()));
1041 9
1042 9
            // Write cells
1043
            $countCells = count($shape->getRow($row)->getCells());
1044
            for ($cell = 0; $cell < $countCells; $cell++) {
1045 9
                // Current cell
1046
                $currentCell = $shape->getRow($row)->getCell($cell);
1047
1048 9
                // Next cell right
1049 9
                $nextCellRight = $shape->getRow($row)->getCell($cell + 1, true);
1050
1051 9
                // Next cell below
1052 9
                $nextRowBelow  = $shape->getRow($row + 1, true);
1053
                $nextCellBelow = null;
1054
                if ($nextRowBelow != null) {
1055 9
                    $nextCellBelow = $nextRowBelow->getCell($cell, true);
1056 9
                }
1057
1058 9
                // a:tc
1059
                $objWriter->startElement('a:tc');
1060
                // Colspan
1061 9
                if ($currentCell->getColSpan() > 1) {
1062
                    $objWriter->writeAttribute('gridSpan', $currentCell->getColSpan());
1063
                    $colSpan[$row] = $currentCell->getColSpan() - 1;
1064 9
                } elseif (isset($colSpan[$row]) && $colSpan[$row] > 0) {
1065 9
                    $colSpan[$row]--;
1066 9
                    $objWriter->writeAttribute('hMerge', '1');
1067 2
                }
1068 2
1069
                // Rowspan
1070
                if ($currentCell->getRowSpan() > 1) {
1071 9
                    $objWriter->writeAttribute('rowSpan', $currentCell->getRowSpan());
1072
                    $rowSpan[$cell] = $currentCell->getRowSpan() - 1;
1073 9
                } elseif (isset($rowSpan[$cell]) && $rowSpan[$cell] > 0) {
1074 1
                    $rowSpan[$cell]--;
1075 1
                    $objWriter->writeAttribute('vMerge', '1');
1076 9
                }
1077 1
1078 1
                // a:txBody
1079 1
                $objWriter->startElement('a:txBody');
1080
1081
                // a:bodyPr
1082 9
                $objWriter->startElement('a:bodyPr');
1083 1
                $objWriter->writeAttribute('wrap', 'square');
1084 1
                $objWriter->writeAttribute('rtlCol', '0');
1085 9
1086 1
                // a:spAutoFit
1087 1
                $objWriter->writeElement('a:spAutoFit', null);
1088 1
1089
                $objWriter->endElement();
1090
1091 9
                // a:lstStyle
1092
                $objWriter->writeElement('a:lstStyle', null);
1093
1094 9
                // Write paragraphs
1095 9
                $this->writeParagraphs($objWriter, $currentCell->getParagraphs());
1096 9
1097
                $objWriter->endElement();
1098
1099 9
                // a:tcPr
1100
                $objWriter->startElement('a:tcPr');
1101 9
                // Alignment (horizontal)
1102
                $firstParagraph  = $currentCell->getParagraph(0);
1103
                $verticalAlign = $firstParagraph->getAlignment()->getVertical();
1104 9
                if ($verticalAlign != Alignment::VERTICAL_BASE && $verticalAlign != Alignment::VERTICAL_AUTO) {
1105
                    $objWriter->writeAttribute('anchor', $verticalAlign);
1106
                }
1107 9
1108
                // Determine borders
1109 9
                $borderLeft         = $currentCell->getBorders()->getLeft();
1110
                $borderRight        = $currentCell->getBorders()->getRight();
1111
                $borderTop          = $currentCell->getBorders()->getTop();
1112 9
                $borderBottom       = $currentCell->getBorders()->getBottom();
1113
                $borderDiagonalDown = $currentCell->getBorders()->getDiagonalDown();
1114 9
                $borderDiagonalUp   = $currentCell->getBorders()->getDiagonalUp();
1115 9
1116 9
                // Fix PowerPoint implementation
1117 1
                if (!is_null($nextCellRight) && $nextCellRight->getBorders()->getRight()->getHashCode() != $defaultBorder->getHashCode()) {
1118 1
                    $borderRight = $nextCellRight->getBorders()->getLeft();
1119
                }
1120
                if (!is_null($nextCellBelow) && $nextCellBelow->getBorders()->getBottom()->getHashCode() != $defaultBorder->getHashCode()) {
1121 9
                    $borderBottom = $nextCellBelow->getBorders()->getTop();
1122 9
                }
1123 9
1124 9
                // Write borders
1125 9
                $this->writeBorder($objWriter, $borderLeft, 'L');
1126 9
                $this->writeBorder($objWriter, $borderRight, 'R');
1127
                $this->writeBorder($objWriter, $borderTop, 'T');
1128
                $this->writeBorder($objWriter, $borderBottom, 'B');
1129 9
                $this->writeBorder($objWriter, $borderDiagonalDown, 'TlToBr');
1130 1
                $this->writeBorder($objWriter, $borderDiagonalUp, 'BlToTr');
1131 1
1132 9
                // Fill
1133 1
                $this->writeFill($objWriter, $currentCell->getFill());
1134 1
1135
                $objWriter->endElement();
1136
1137 9
                $objWriter->endElement();
1138 9
            }
1139 9
1140 9
            $objWriter->endElement();
1141 9
        }
1142 9
1143
        $objWriter->endElement();
1144
1145 9
        $objWriter->endElement();
1146
1147 9
        $objWriter->endElement();
1148
1149 9
        $objWriter->endElement();
1150 9
    }
1151
1152 9
    /**
1153 9
     * Write paragraphs
1154
     *
1155 9
     * @param  \PhpOffice\Common\XMLWriter           $objWriter  XML Writer
1156
     * @param  \PhpOffice\PhpPresentation\Shape\RichText\Paragraph[] $paragraphs
1157 9
     * @throws \Exception
1158
     */
1159 9
    protected function writeParagraphs(XMLWriter $objWriter, $paragraphs)
1160
    {
1161 9
        // Loop trough paragraphs
1162 9
        foreach ($paragraphs as $paragraph) {
1163
            // a:p
1164
            $objWriter->startElement('a:p');
1165
1166
            // a:pPr
1167
            $objWriter->startElement('a:pPr');
1168
            $objWriter->writeAttribute('algn', $paragraph->getAlignment()->getHorizontal());
1169
            $objWriter->writeAttribute('fontAlgn', $paragraph->getAlignment()->getVertical());
1170
            $objWriter->writeAttribute('marL', CommonDrawing::pixelsToEmu($paragraph->getAlignment()->getMarginLeft()));
1171 31
            $objWriter->writeAttribute('marR', CommonDrawing::pixelsToEmu($paragraph->getAlignment()->getMarginRight()));
1172
            $objWriter->writeAttribute('indent', CommonDrawing::pixelsToEmu($paragraph->getAlignment()->getIndent()));
1173
            $objWriter->writeAttribute('lvl', $paragraph->getAlignment()->getLevel());
1174 31
1175
            // Bullet type specified?
1176 31
            if ($paragraph->getBulletStyle()->getBulletType() != Bullet::TYPE_NONE) {
1177
                // a:buFont
1178
                $objWriter->startElement('a:buFont');
1179 31
                $objWriter->writeAttribute('typeface', $paragraph->getBulletStyle()->getBulletFont());
1180 31
                $objWriter->endElement();
1181 31
1182 31
                if ($paragraph->getBulletStyle()->getBulletType() == Bullet::TYPE_BULLET) {
1183 31
                    // a:buChar
1184 31
                    $objWriter->startElement('a:buChar');
1185 31
                    $objWriter->writeAttribute('char', $paragraph->getBulletStyle()->getBulletChar());
1186
                    $objWriter->endElement();
1187
                } elseif ($paragraph->getBulletStyle()->getBulletType() == Bullet::TYPE_NUMERIC) {
1188 31
                    // a:buAutoNum
1189
                    $objWriter->startElement('a:buAutoNum');
1190 2
                    $objWriter->writeAttribute('type', $paragraph->getBulletStyle()->getBulletNumericStyle());
1191 2
                    if ($paragraph->getBulletStyle()->getBulletNumericStartAt() != 1) {
1192 2
                        $objWriter->writeAttribute('startAt', $paragraph->getBulletStyle()->getBulletNumericStartAt());
1193
                    }
1194 2
                    $objWriter->endElement();
1195
                }
1196 1
            }
1197 1
1198 1
            $objWriter->endElement();
1199 2
1200
            // Loop trough rich text elements
1201 1
            $elements = $paragraph->getRichTextElements();
1202 1
            foreach ($elements as $element) {
1203 1
                if ($element instanceof BreakElement) {
1204 1
                    // a:br
1205 1
                    $objWriter->writeElement('a:br', null);
1206 1
                } elseif ($element instanceof Run || $element instanceof TextElement) {
1207 1
                    // a:r
1208 2
                    $objWriter->startElement('a:r');
1209
1210 31
                    // a:rPr
1211
                    if ($element instanceof Run) {
1212
                        // a:rPr
1213 31
                        $objWriter->startElement('a:rPr');
1214 31
1215 27
                        // Lang
1216
                        $objWriter->writeAttribute('lang', ($element->getLanguage() ? $element->getLanguage() : 'en-US'));
1217 1
1218 27
                        // Bold
1219
                        $objWriter->writeAttribute('b', ($element->getFont()->isBold() ? '1' : '0'));
1220 26
1221
                        // Italic
1222
                        $objWriter->writeAttribute('i', ($element->getFont()->isItalic() ? '1' : '0'));
1223 26
1224
                        // Strikethrough
1225 26
                        $objWriter->writeAttribute('strike', ($element->getFont()->isStrikethrough() ? 'sngStrike' : 'noStrike'));
1226
1227
                        // Size
1228 26
                        $objWriter->writeAttribute('sz', ($element->getFont()->getSize() * 100));
1229
1230
                        // Underline
1231 26
                        $objWriter->writeAttribute('u', $element->getFont()->getUnderline());
1232
1233
                        // Superscript / subscript
1234 26
                        if ($element->getFont()->isSuperScript() || $element->getFont()->isSubScript()) {
1235
                            if ($element->getFont()->isSuperScript()) {
1236
                                $objWriter->writeAttribute('baseline', '30000');
1237 26
                            } elseif ($element->getFont()->isSubScript()) {
1238
                                $objWriter->writeAttribute('baseline', '-25000');
1239
                            }
1240 26
                        }
1241
1242
                        // Color - a:solidFill
1243 26
                        $objWriter->startElement('a:solidFill');
1244
1245
                        $this->writeColor($objWriter, $element->getFont()->getColor());
1246 26
1247 2
                        $objWriter->endElement();
1248 1
1249 2
                        // Font - a:latin
1250 1
                        $objWriter->startElement('a:latin');
1251 1
                        $objWriter->writeAttribute('typeface', $element->getFont()->getName());
1252 2
                        $objWriter->endElement();
1253
1254
                        // a:hlinkClick
1255 26
                        if ($element->hasHyperlink()) {
1256
                            $this->writeHyperlink($objWriter, $element);
1257 26
                        }
1258
1259 26
                        $objWriter->endElement();
1260
                    }
1261
1262 26
                    // t
1263 26
                    $objWriter->startElement('a:t');
1264 26
                    $objWriter->writeCData(Text::controlCharacterPHP2OOXML($element->getText()));
1265
                    $objWriter->endElement();
1266
1267 26
                    $objWriter->endElement();
1268 3
                }
1269 3
            }
1270
1271 26
            $objWriter->endElement();
1272 26
        }
1273
    }
1274
1275 26
    /**
1276 26
     * Write Line Shape
1277 26
     *
1278
     * @param  \PhpOffice\Common\XMLWriter $objWriter XML Writer
1279 26
     * @param \PhpOffice\PhpPresentation\Shape\Line $shape
1280 26
     * @param  int $shapeId
1281 31
     */
1282
    protected function writeShapeLine(XMLWriter $objWriter, Line $shape, $shapeId)
1283 31
    {
1284 31
        // p:sp
1285 31
        $objWriter->startElement('p:cxnSp');
1286
1287
        // p:nvSpPr
1288
        $objWriter->startElement('p:nvCxnSpPr');
1289
1290
        // p:cNvPr
1291
        $objWriter->startElement('p:cNvPr');
1292
        $objWriter->writeAttribute('id', $shapeId);
1293
        $objWriter->writeAttribute('name', '');
1294 1
1295
        $objWriter->endElement();
1296
1297 1
        // p:cNvCxnSpPr
1298
        $objWriter->writeElement('p:cNvCxnSpPr', null);
1299
1300 1
        // p:nvPr
1301
        $objWriter->writeElement('p:nvPr', null);
1302
1303 1
        $objWriter->endElement();
1304 1
1305 1
        // p:spPr
1306
        $objWriter->startElement('p:spPr');
1307 1
1308
        // a:xfrm
1309
        $objWriter->startElement('a:xfrm');
1310 1
1311
        if ($shape->getWidth() >= 0 && $shape->getHeight() >= 0) {
1312
            // a:off
1313 1
            $objWriter->startElement('a:off');
1314
            $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
1315 1
            $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
1316
            $objWriter->endElement();
1317
1318 1
            // a:ext
1319
            $objWriter->startElement('a:ext');
1320
            $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
1321 1
            $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
1322
            $objWriter->endElement();
1323 1
        } elseif ($shape->getWidth() < 0 && $shape->getHeight() < 0) {
1324
            // a:off
1325 1
            $objWriter->startElement('a:off');
1326 1
            $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX() + $shape->getWidth()));
1327 1
            $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY() + $shape->getHeight()));
1328 1
            $objWriter->endElement();
1329
1330
            // a:ext
1331 1
            $objWriter->startElement('a:ext');
1332 1
            $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu(-$shape->getWidth()));
1333 1
            $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu(-$shape->getHeight()));
1334 1
            $objWriter->endElement();
1335 1
        } elseif ($shape->getHeight() < 0) {
1336
            $objWriter->writeAttribute('flipV', 1);
1337 1
1338 1
            // a:off
1339 1
            $objWriter->startElement('a:off');
1340 1
            $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX()));
1341
            $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY() + $shape->getHeight()));
1342
            $objWriter->endElement();
1343 1
1344 1
            // a:ext
1345 1
            $objWriter->startElement('a:ext');
1346 1
            $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($shape->getWidth()));
1347 1
            $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu(-$shape->getHeight()));
1348 1
            $objWriter->endElement();
1349
        } elseif ($shape->getWidth() < 0) {
1350
            $objWriter->writeAttribute('flipV', 1);
1351 1
1352 1
            // a:off
1353 1
            $objWriter->startElement('a:off');
1354 1
            $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($shape->getOffsetX() + $shape->getWidth()));
1355
            $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($shape->getOffsetY()));
1356
            $objWriter->endElement();
1357 1
1358 1
            // a:ext
1359 1
            $objWriter->startElement('a:ext');
1360 1
            $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu(-$shape->getWidth()));
1361 1
            $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($shape->getHeight()));
1362 1
            $objWriter->endElement();
1363
        }
1364
1365 1
        $objWriter->endElement();
1366 1
1367 1
        // a:prstGeom
1368 1
        $objWriter->startElement('a:prstGeom');
1369
        $objWriter->writeAttribute('prst', 'line');
1370
        $objWriter->endElement();
1371 1
1372 1
        if ($shape->getBorder()->getLineStyle() != Border::LINE_NONE) {
1373 1
            $this->writeBorder($objWriter, $shape->getBorder(), '');
1374 1
        }
1375 1
1376
        $objWriter->endElement();
1377 1
1378
        $objWriter->endElement();
1379
    }
1380 1
1381 1
    /**
1382 1
     * Write Shadow
1383
     * @param XMLWriter $objWriter
1384 1
     * @param Shadow $oShadow
1385 1
     */
1386 1
    protected function writeShadow(XMLWriter $objWriter, $oShadow)
1387
    {
1388 1
        if (!($oShadow instanceof Shadow)) {
1389
            return;
1390 1
        }
1391 1
1392
        if (!$oShadow->isVisible()) {
1393
            return;
1394
        }
1395
1396
        // a:effectLst
1397
        $objWriter->startElement('a:effectLst');
1398 2
1399
        // a:outerShdw
1400
        $objWriter->startElement('a:outerShdw');
1401 2
        $objWriter->writeAttribute('blurRad', CommonDrawing::pixelsToEmu($oShadow->getBlurRadius()));
1402
        $objWriter->writeAttribute('dist', CommonDrawing::pixelsToEmu($oShadow->getDistance()));
1403
        $objWriter->writeAttribute('dir', CommonDrawing::degreesToAngle($oShadow->getDirection()));
1404 2
        $objWriter->writeAttribute('algn', $oShadow->getAlignment());
1405 2
        $objWriter->writeAttribute('rotWithShape', '0');
1406 2
1407 2
        $this->writeColor($objWriter, $oShadow->getColor(), $oShadow->getAlpha());
1408 2
1409 2
        $objWriter->endElement();
1410
1411 2
        $objWriter->endElement();
1412
    }
1413 2
1414
    /**
1415 2
     * Write hyperlink
1416 2
     *
1417
     * @param \PhpOffice\Common\XMLWriter                               $objWriter XML Writer
1418
     * @param \PhpOffice\PhpPresentation\AbstractShape|\PhpOffice\PhpPresentation\Shape\RichText\TextElement $shape
1419
     */
1420
    protected function writeHyperlink(XMLWriter $objWriter, $shape)
1421
    {
1422
        // a:hlinkClick
1423
        $objWriter->startElement('a:hlinkClick');
1424 5
        $objWriter->writeAttribute('r:id', $shape->getHyperlink()->relationId);
1425
        $objWriter->writeAttribute('tooltip', $shape->getHyperlink()->getTooltip());
1426
        if ($shape->getHyperlink()->isInternal()) {
1427 5
            $objWriter->writeAttribute('action', $shape->getHyperlink()->getUrl());
1428 5
        }
1429 5
        $objWriter->endElement();
1430 5
    }
1431 1
1432 1
    /**
1433 5
     * Write Note Slide
1434 5
     * @param Note $pNote
1435
     * @throws \Exception
1436
     * @return  string
1437
     */
1438
    protected function writeNote(Note $pNote)
1439
    {
1440
        // Create XML writer
1441
        $objWriter = new XMLWriter(XMLWriter::STORAGE_MEMORY);
1442 1
1443
        // XML header
1444
        $objWriter->startDocument('1.0', 'UTF-8', 'yes');
1445 1
1446
        // p:notes
1447
        $objWriter->startElement('p:notes');
1448 1
        $objWriter->writeAttribute('xmlns:a', 'http://schemas.openxmlformats.org/drawingml/2006/main');
1449
        $objWriter->writeAttribute('xmlns:p', 'http://schemas.openxmlformats.org/presentationml/2006/main');
1450
        $objWriter->writeAttribute('xmlns:r', 'http://schemas.openxmlformats.org/officeDocument/2006/relationships');
1451 1
1452 1
        // p:notes/p:cSld
1453 1
        $objWriter->startElement('p:cSld');
1454 1
1455
        // p:notes/p:cSld/p:spTree
1456
        $objWriter->startElement('p:spTree');
1457 1
1458
        // p:notes/p:cSld/p:spTree/p:nvGrpSpPr
1459
        $objWriter->startElement('p:nvGrpSpPr');
1460 1
1461
        // p:notes/p:cSld/p:spTree/p:nvGrpSpPr/p:cNvPr
1462
        $objWriter->startElement('p:cNvPr');
1463 1
        $objWriter->writeAttribute('id', '1');
1464
        $objWriter->writeAttribute('name', '');
1465
        $objWriter->endElement();
1466 1
1467 1
        // p:notes/p:cSld/p:spTree/p:nvGrpSpPr/p:cNvGrpSpPr
1468 1
        $objWriter->writeElement('p:cNvGrpSpPr', null);
1469 1
1470
        // p:notes/p:cSld/p:spTree/p:nvGrpSpPr/p:nvPr
1471
        $objWriter->writeElement('p:nvPr', null);
1472 1
1473
        // p:notes/p:cSld/p:spTree/p:nvGrpSpPr
1474
        $objWriter->endElement();
1475 1
1476
        // p:notes/p:cSld/p:spTree/p:grpSpPr
1477
        $objWriter->startElement('p:grpSpPr');
1478 1
1479
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm
1480
        $objWriter->startElement('a:xfrm');
1481 1
1482
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm/a:off
1483
        $objWriter->startElement('a:off');
1484 1
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($pNote->getOffsetX()));
1485
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($pNote->getOffsetY()));
1486
        $objWriter->endElement(); // a:off
1487 1
1488 1
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm/a:ext
1489 1
        $objWriter->startElement('a:ext');
1490 1
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($pNote->getExtentX()));
1491
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($pNote->getExtentY()));
1492
        $objWriter->endElement(); // a:ext
1493 1
1494 1
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm/a:chOff
1495 1
        $objWriter->startElement('a:chOff');
1496 1
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($pNote->getOffsetX()));
1497
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu($pNote->getOffsetY()));
1498
        $objWriter->endElement(); // a:chOff
1499 1
1500 1
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm/a:chExt
1501 1
        $objWriter->startElement('a:chExt');
1502 1
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu($pNote->getExtentX()));
1503
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu($pNote->getExtentY()));
1504
        $objWriter->endElement(); // a:chExt
1505 1
1506 1
        // p:notes/p:cSld/p:spTree/p:grpSpPr/a:xfrm
1507 1
        $objWriter->endElement();
1508 1
1509
        // p:notes/p:cSld/p:spTree/p:grpSpPr
1510
        $objWriter->endElement();
1511 1
1512
        // p:notes/p:cSld/p:spTree/p:sp[1]
1513
        $objWriter->startElement('p:sp');
1514 1
1515
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr
1516
        $objWriter->startElement('p:nvSpPr');
1517 1
1518
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:cNvPr
1519
        $objWriter->startElement('p:cNvPr');
1520 1
        $objWriter->writeAttribute('id', '2');
1521
        $objWriter->writeAttribute('name', 'Slide Image Placeholder 1');
1522
        $objWriter->endElement();
1523 1
1524 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:cNvSpPr
1525 1
        $objWriter->startElement('p:cNvSpPr');
1526 1
1527
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:cNvSpPr/a:spLocks
1528
        $objWriter->startElement('a:spLocks');
1529 1
        $objWriter->writeAttribute('noGrp', '1');
1530
        $objWriter->writeAttribute('noRot', '1');
1531
        $objWriter->writeAttribute('noChangeAspect', '1');
1532 1
        $objWriter->endElement();
1533 1
1534 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:cNvSpPr
1535 1
        $objWriter->endElement();
1536 1
1537
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:nvPr
1538
        $objWriter->startElement('p:nvPr');
1539 1
1540
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:nvPr/p:ph
1541
        $objWriter->startElement('p:ph');
1542 1
        $objWriter->writeAttribute('type', 'sldImg');
1543
        $objWriter->endElement();
1544
1545 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr/p:nvPr
1546 1
        $objWriter->endElement();
1547 1
1548
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:nvSpPr
1549
        $objWriter->endElement();
1550 1
1551
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr
1552
        $objWriter->startElement('p:spPr');
1553 1
1554
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:xfrm
1555
        $objWriter->startElement('a:xfrm');
1556 1
1557
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:xfrm/a:off
1558
        $objWriter->startElement('a:off');
1559 1
        $objWriter->writeAttribute('x', 0);
1560
        $objWriter->writeAttribute('y', 0);
1561
        $objWriter->endElement();
1562 1
1563 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:xfrm/a:ext
1564 1
        $objWriter->startElement('a:ext');
1565 1
        $objWriter->writeAttribute('cx', CommonDrawing::pixelsToEmu(round($pNote->getExtentX() / 2)));
1566
        $objWriter->writeAttribute('cy', CommonDrawing::pixelsToEmu(round($pNote->getExtentY() / 2)));
1567
        $objWriter->endElement();
1568 1
1569 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:xfrm
1570 1
        $objWriter->endElement();
1571 1
1572
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:prstGeom
1573
        $objWriter->startElement('a:prstGeom');
1574 1
        $objWriter->writeAttribute('prst', 'rect');
1575
1576
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:prstGeom/a:avLst
1577 1
        $objWriter->writeElement('a:avLst', null);
1578 1
1579
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:prstGeom
1580
        $objWriter->endElement();
1581 1
1582
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:noFill
1583
        $objWriter->writeElement('a:noFill', null);
1584 1
1585
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:ln
1586
        $objWriter->startElement('a:ln');
1587 1
        $objWriter->writeAttribute('w', '12700');
1588
1589
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:ln/a:solidFill
1590 1
        $objWriter->startElement('a:solidFill');
1591 1
1592
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:ln/a:solidFill/a:prstClr
1593
        $objWriter->startElement('a:prstClr');
1594 1
        $objWriter->writeAttribute('val', 'black');
1595
        $objWriter->endElement();
1596
1597 1
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:ln/a:solidFill
1598 1
        $objWriter->endElement();
1599 1
1600
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr/a:ln
1601
        $objWriter->endElement();
1602 1
1603
        // p:notes/p:cSld/p:spTree/p:sp[1]/p:spPr
1604
        $objWriter->endElement();
1605 1
1606
        // p:notes/p:cSld/p:spTree/p:sp[1]
1607
        $objWriter->endElement();
1608 1
1609
        // p:notes/p:cSld/p:spTree/p:sp[2]
1610
        $objWriter->startElement('p:sp');
1611 1
1612
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr
1613
        $objWriter->startElement('p:nvSpPr');
1614 1
1615
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:cNvPr
1616
        $objWriter->startElement('p:cNvPr');
1617 1
        $objWriter->writeAttribute('id', '3');
1618
        $objWriter->writeAttribute('name', 'Notes Placeholder');
1619
        $objWriter->endElement();
1620 1
1621 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:cNvSpPr
1622 1
        $objWriter->startElement('p:cNvSpPr');
1623 1
1624
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:cNvSpPr/a:spLocks
1625
        $objWriter->startElement('a:spLocks');
1626 1
        $objWriter->writeAttribute('noGrp', '1');
1627
        $objWriter->endElement();
1628
1629 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:cNvSpPr
1630 1
        $objWriter->endElement();
1631 1
1632
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:nvPr
1633
        $objWriter->startElement('p:nvPr');
1634 1
1635
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:nvPr/p:ph
1636
        $objWriter->startElement('p:ph');
1637 1
        $objWriter->writeAttribute('type', 'body');
1638
        $objWriter->writeAttribute('idx', '1');
1639
        $objWriter->endElement();
1640 1
1641 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr/p:nvPr
1642 1
        $objWriter->endElement();
1643 1
1644
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:nvSpPr
1645
        $objWriter->endElement();
1646 1
1647
        // START notes print below rectangle section
1648
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr
1649 1
        $objWriter->startElement('p:spPr');
1650
1651
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:xfrm
1652
        $objWriter->startElement('a:xfrm');
1653 1
1654
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:xfrm/a:off
1655
        $objWriter->startElement('a:off');
1656 1
        $objWriter->writeAttribute('x', CommonDrawing::pixelsToEmu($pNote->getOffsetX()));
1657
        $objWriter->writeAttribute('y', CommonDrawing::pixelsToEmu(round($pNote->getExtentY() / 2) + $pNote->getOffsetY()));
1658
        $objWriter->endElement();
1659 1
1660 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:xfrm/a:ext
1661 1
        $objWriter->startElement('a:ext');
1662 1
        $objWriter->writeAttribute('cx', '5486400');
1663
        $objWriter->writeAttribute('cy', '3600450');
1664
        $objWriter->endElement();
1665 1
1666 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:xfrm
1667 1
        $objWriter->endElement();
1668 1
1669
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:prstGeom
1670
        $objWriter->startElement('a:prstGeom');
1671 1
        $objWriter->writeAttribute('prst', 'rect');
1672
1673
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:prstGeom/a:avLst
1674 1
        $objWriter->writeElement('a:avLst', null);
1675 1
1676
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr/a:prstGeom
1677
        $objWriter->endElement();
1678 1
1679
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:spPr
1680
        $objWriter->endElement();
1681 1
1682
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:txBody
1683
        $objWriter->startElement('p:txBody');
1684 1
1685
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:txBody/a:bodyPr
1686
        $objWriter->writeElement('a:bodyPr', null);
1687 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:txBody/a:lstStyle
1688
        $objWriter->writeElement('a:lstStyle', null);
1689
1690 1
        // Loop shapes
1691
        $shapes  = $pNote->getShapeCollection();
1692 1
        foreach ($shapes as $shape) {
1693
            // Check type
1694
            if ($shape instanceof RichText) {
1695 1
                $paragraphs = $shape->getParagraphs();
1696 1
                $this->writeParagraphs($objWriter, $paragraphs);
1697
            }
1698 1
        }
1699 1
1700 1
        // p:notes/p:cSld/p:spTree/p:sp[2]/p:txBody
1701 1
        $objWriter->endElement();
1702 1
1703
        // p:notes/p:cSld/p:spTree/p:sp[2]
1704
        $objWriter->endElement();
1705 1
1706
        // p:notes/p:cSld/p:spTree
1707
        $objWriter->endElement();
1708 1
1709
        // p:notes/p:cSld
1710
        $objWriter->endElement();
1711 1
1712
        // p:notes
1713
        $objWriter->endElement();
1714 1
1715
        // Return
1716
        return $objWriter->getData();
1717 1
    }
1718
1719
    /**
1720 1
     * Write Transition Slide
1721
     * @link http://officeopenxml.com/prSlide-transitions.php
1722
     * @param XMLWriter $objWriter
1723
     * @param Transition $transition
1724
     */
1725
    protected function writeTransition(XMLWriter $objWriter, Transition $transition)
1726
    {
1727
        $objWriter->startElement('p:transition');
1728
        if (!is_null($transition->getSpeed())) {
1729 1
            $objWriter->writeAttribute('spd', $transition->getSpeed());
1730
        }
1731 1
        $objWriter->writeAttribute('advClick', $transition->hasManualTrigger() ? '1' : '0');
1732 1
        if ($transition->hasTimeTrigger()) {
1733 1
            $objWriter->writeAttribute('advTm', $transition->getAdvanceTimeTrigger());
1734 1
        }
1735 1
1736 1
        switch ($transition->getTransitionType()) {
1737 1
            case Transition::TRANSITION_BLINDS_HORIZONTAL:
1738 1
                $objWriter->startElement('p:blinds');
1739
                $objWriter->writeAttribute('dir', 'horz');
1740 1
                $objWriter->endElement();
1741 1
                break;
1742 1
            case Transition::TRANSITION_BLINDS_VERTICAL:
1743 1
                $objWriter->startElement('p:blinds');
1744 1
                $objWriter->writeAttribute('dir', 'vert');
1745 1
                $objWriter->endElement();
1746 1
                break;
1747 1
            case Transition::TRANSITION_CHECKER_HORIZONTAL:
1748 1
                $objWriter->startElement('p:checker');
1749 1
                $objWriter->writeAttribute('dir', 'horz');
1750 1
                $objWriter->endElement();
1751 1
                break;
1752 1
            case Transition::TRANSITION_CHECKER_VERTICAL:
1753 1
                $objWriter->startElement('p:checker');
1754 1
                $objWriter->writeAttribute('dir', 'vert');
1755 1
                $objWriter->endElement();
1756 1
                break;
1757 1
            case Transition::TRANSITION_CIRCLE_HORIZONTAL:
1758 1
                $objWriter->startElement('p:circle');
1759 1
                $objWriter->writeAttribute('dir', 'horz');
1760 1
                $objWriter->endElement();
1761 1
                break;
1762 1
            case Transition::TRANSITION_CIRCLE_VERTICAL:
1763 1
                $objWriter->startElement('p:circle');
1764 1
                $objWriter->writeAttribute('dir', 'vert');
1765 1
                $objWriter->endElement();
1766 1
                break;
1767 1
            case Transition::TRANSITION_COMB_HORIZONTAL:
1768 1
                $objWriter->startElement('p:comb');
1769 1
                $objWriter->writeAttribute('dir', 'horz');
1770 1
                $objWriter->endElement();
1771 1
                break;
1772 1
            case Transition::TRANSITION_COMB_VERTICAL:
1773 1
                $objWriter->startElement('p:comb');
1774 1
                $objWriter->writeAttribute('dir', 'vert');
1775 1
                $objWriter->endElement();
1776 1
                break;
1777 1
            case Transition::TRANSITION_COVER_DOWN:
1778 1
                $objWriter->startElement('p:cover');
1779 1
                $objWriter->writeAttribute('dir', 'd');
1780 1
                $objWriter->endElement();
1781 1
                break;
1782 1
            case Transition::TRANSITION_COVER_LEFT:
1783 1
                $objWriter->startElement('p:cover');
1784 1
                $objWriter->writeAttribute('dir', 'l');
1785 1
                $objWriter->endElement();
1786 1
                break;
1787 1
            case Transition::TRANSITION_COVER_LEFT_DOWN:
1788 1
                $objWriter->startElement('p:cover');
1789 1
                $objWriter->writeAttribute('dir', 'ld');
1790 1
                $objWriter->endElement();
1791 1
                break;
1792 1
            case Transition::TRANSITION_COVER_LEFT_UP:
1793 1
                $objWriter->startElement('p:cover');
1794 1
                $objWriter->writeAttribute('dir', 'lu');
1795 1
                $objWriter->endElement();
1796 1
                break;
1797 1
            case Transition::TRANSITION_COVER_RIGHT:
1798 1
                $objWriter->startElement('p:cover');
1799 1
                $objWriter->writeAttribute('dir', 'r');
1800 1
                $objWriter->endElement();
1801 1
                break;
1802 1
            case Transition::TRANSITION_COVER_RIGHT_DOWN:
1803 1
                $objWriter->startElement('p:cover');
1804 1
                $objWriter->writeAttribute('dir', 'rd');
1805 1
                $objWriter->endElement();
1806 1
                break;
1807 1
            case Transition::TRANSITION_COVER_RIGHT_UP:
1808 1
                $objWriter->startElement('p:cover');
1809 1
                $objWriter->writeAttribute('dir', 'ru');
1810 1
                $objWriter->endElement();
1811 1
                break;
1812 1
            case Transition::TRANSITION_COVER_UP:
1813 1
                $objWriter->startElement('p:cover');
1814 1
                $objWriter->writeAttribute('dir', 'u');
1815 1
                $objWriter->endElement();
1816 1
                break;
1817 1
            case Transition::TRANSITION_CUT:
1818 1
                $objWriter->writeElement('p:cut');
1819 1
                break;
1820 1
            case Transition::TRANSITION_DIAMOND:
1821 1
                $objWriter->writeElement('p:diamond');
1822 1
                break;
1823 1
            case Transition::TRANSITION_DISSOLVE:
1824 1
                $objWriter->writeElement('p:dissolve');
1825 1
                break;
1826 1
            case Transition::TRANSITION_FADE:
1827 1
                $objWriter->writeElement('p:fade');
1828 1
                break;
1829 1
            case Transition::TRANSITION_NEWSFLASH:
1830 1
                $objWriter->writeElement('p:newsflash');
1831 1
                break;
1832 1
            case Transition::TRANSITION_PLUS:
1833 1
                $objWriter->writeElement('p:plus');
1834 1
                break;
1835 1
            case Transition::TRANSITION_PULL_DOWN:
1836 1
                $objWriter->startElement('p:pull');
1837 1
                $objWriter->writeAttribute('dir', 'd');
1838 1
                $objWriter->endElement();
1839 1
                break;
1840 1
            case Transition::TRANSITION_PULL_LEFT:
1841 1
                $objWriter->startElement('p:pull');
1842 1
                $objWriter->writeAttribute('dir', 'l');
1843 1
                $objWriter->endElement();
1844 1
                break;
1845 1
            case Transition::TRANSITION_PULL_RIGHT:
1846 1
                $objWriter->startElement('p:pull');
1847 1
                $objWriter->writeAttribute('dir', 'r');
1848 1
                $objWriter->endElement();
1849 1
                break;
1850 1
            case Transition::TRANSITION_PULL_UP:
1851 1
                $objWriter->startElement('p:pull');
1852 1
                $objWriter->writeAttribute('dir', 'u');
1853 1
                $objWriter->endElement();
1854 1
                break;
1855 1
            case Transition::TRANSITION_PUSH_DOWN:
1856 1
                $objWriter->startElement('p:push');
1857 1
                $objWriter->writeAttribute('dir', 'd');
1858 1
                $objWriter->endElement();
1859 1
                break;
1860 1
            case Transition::TRANSITION_PUSH_LEFT:
1861 1
                $objWriter->startElement('p:push');
1862 1
                $objWriter->writeAttribute('dir', 'l');
1863 1
                $objWriter->endElement();
1864 1
                break;
1865 1
            case Transition::TRANSITION_PUSH_RIGHT:
1866 1
                $objWriter->startElement('p:push');
1867 1
                $objWriter->writeAttribute('dir', 'r');
1868 1
                $objWriter->endElement();
1869 1
                break;
1870 1
            case Transition::TRANSITION_PUSH_UP:
1871 1
                $objWriter->startElement('p:push');
1872 1
                $objWriter->writeAttribute('dir', 'u');
1873 1
                $objWriter->endElement();
1874 1
                break;
1875 1
            case Transition::TRANSITION_RANDOM:
1876 1
                $objWriter->writeElement('p:random');
1877 1
                break;
1878 1
            case Transition::TRANSITION_RANDOMBAR_HORIZONTAL:
1879 1
                $objWriter->startElement('p:randomBar');
1880 1
                $objWriter->writeAttribute('dir', 'horz');
1881 1
                $objWriter->endElement();
1882 1
                break;
1883 1
            case Transition::TRANSITION_RANDOMBAR_VERTICAL:
1884 1
                $objWriter->startElement('p:randomBar');
1885 1
                $objWriter->writeAttribute('dir', 'vert');
1886 1
                $objWriter->endElement();
1887 1
                break;
1888 1
            case Transition::TRANSITION_SPLIT_IN_HORIZONTAL:
1889 1
                $objWriter->startElement('p:split');
1890 1
                $objWriter->writeAttribute('dir', 'in');
1891 1
                $objWriter->writeAttribute('orient', 'horz');
1892 1
                $objWriter->endElement();
1893 1
                break;
1894 1
            case Transition::TRANSITION_SPLIT_OUT_HORIZONTAL:
1895 1
                $objWriter->startElement('p:split');
1896 1
                $objWriter->writeAttribute('dir', 'out');
1897 1
                $objWriter->writeAttribute('orient', 'horz');
1898 1
                $objWriter->endElement();
1899 1
                break;
1900 1
            case Transition::TRANSITION_SPLIT_IN_VERTICAL:
1901 1
                $objWriter->startElement('p:split');
1902 1
                $objWriter->writeAttribute('dir', 'in');
1903 1
                $objWriter->writeAttribute('orient', 'vert');
1904 1
                $objWriter->endElement();
1905 1
                break;
1906 1
            case Transition::TRANSITION_SPLIT_OUT_VERTICAL:
1907 1
                $objWriter->startElement('p:split');
1908 1
                $objWriter->writeAttribute('dir', 'out');
1909 1
                $objWriter->writeAttribute('orient', 'vert');
1910 1
                $objWriter->endElement();
1911 1
                break;
1912 1
            case Transition::TRANSITION_STRIPS_LEFT_DOWN:
1913 1
                $objWriter->startElement('p:strips');
1914 1
                $objWriter->writeAttribute('dir', 'ld');
1915 1
                $objWriter->endElement();
1916 1
                break;
1917 1
            case Transition::TRANSITION_STRIPS_LEFT_UP:
1918 1
                $objWriter->startElement('p:strips');
1919 1
                $objWriter->writeAttribute('dir', 'lu');
1920 1
                $objWriter->endElement();
1921 1
                break;
1922 1
            case Transition::TRANSITION_STRIPS_RIGHT_DOWN:
1923 1
                $objWriter->startElement('p:strips');
1924 1
                $objWriter->writeAttribute('dir', 'rd');
1925 1
                $objWriter->endElement();
1926 1
                break;
1927 1
            case Transition::TRANSITION_STRIPS_RIGHT_UP:
1928 1
                $objWriter->startElement('p:strips');
1929 1
                $objWriter->writeAttribute('dir', 'ru');
1930 1
                $objWriter->endElement();
1931 1
                break;
1932 1
            case Transition::TRANSITION_WEDGE:
1933 1
                $objWriter->writeElement('p:wedge');
1934 1
                break;
1935 1
            case Transition::TRANSITION_WIPE_DOWN:
1936 1
                $objWriter->startElement('p:wipe');
1937 1
                $objWriter->writeAttribute('dir', 'd');
1938 1
                $objWriter->endElement();
1939 1
                break;
1940 1
            case Transition::TRANSITION_WIPE_LEFT:
1941 1
                $objWriter->startElement('p:wipe');
1942 1
                $objWriter->writeAttribute('dir', 'l');
1943 1
                $objWriter->endElement();
1944 1
                break;
1945 1
            case Transition::TRANSITION_WIPE_RIGHT:
1946 1
                $objWriter->startElement('p:wipe');
1947 1
                $objWriter->writeAttribute('dir', 'r');
1948 1
                $objWriter->endElement();
1949 1
                break;
1950 1
            case Transition::TRANSITION_WIPE_UP:
1951 1
                $objWriter->startElement('p:wipe');
1952 1
                $objWriter->writeAttribute('dir', 'u');
1953 1
                $objWriter->endElement();
1954 1
                break;
1955 1
            case Transition::TRANSITION_ZOOM_IN:
1956 1
                $objWriter->startElement('p:zoom');
1957 1
                $objWriter->writeAttribute('dir', 'in');
1958 1
                $objWriter->endElement();
1959 1
                break;
1960 1
            case Transition::TRANSITION_ZOOM_OUT:
1961 1
                $objWriter->startElement('p:zoom');
1962 1
                $objWriter->writeAttribute('dir', 'out');
1963 1
                $objWriter->endElement();
1964 1
                break;
1965 1
        }
1966 1
1967 1
        $objWriter->endElement();
1968 1
    }
1969
}
1970