summaryrefslogtreecommitdiffstats
path: root/src/Plugin/ConditionalFormatFixer.php
blob: 409f9c71e48753748793f3b5bce63c0d26eefab6 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
<?php

namespace PHPExcelFixer\StyleFixer\Plugin;

use PHPExcelFixer\StyleFixer\Util\Book as BookUtil;
use PHPExcelFixer\StyleFixer\Util\XmlNamespace;

/**
 * Class ConditionalFormatFixer
 * PHPExcelが壊した条件付き書式を修復する
 */
class ConditionalFormatFixer implements Plugin
{
    /**
     * @var \PHPExcelFixer\StyleFixer\Util\Book
     */
    private $bookUtil;

    public function __construct(BookUtil $bookUtil)
    {
        $this->bookUtil = $bookUtil;
    }

    /**
     * 各ワークシート内の条件付き書式設定を修復する
     *
     * @param \ZipArchive $output
     * @param \ZipArchive $template
     */
    public function execute(\ZipArchive $output, \ZipArchive $template)
    {
        // テンプレート側のシート名のマッピング
        $srcSheetMap = $this->bookUtil->makeSheetMap($template);
        // 出力ファイル側のシート名のマッピング
        $distSheetMap = $this->bookUtil->makeSheetMap($output);

        foreach ($distSheetMap as $sheetName => $distSheetPath) {
            $distXml = $output->getFromName($distSheetPath);
            if (false !== strpos($distXml, 'conditionalFormatting')) {
                $distDom = new \DOMDocument;
                $distDom->loadXML($distXml);
                $distXPath = new \DOMXPath($distDom);
                $distXPath->registerNamespace('s', XmlNamespace::SPREADSHEETML_NS_URL);
                $distRoot = $distXPath->query('//s:worksheet')->item(0);
                $distConditionalFormattings = $distXPath->query('//s:worksheet/s:conditionalFormatting');
                $elementAfterConditionalFormatting = null;
                foreach ($distConditionalFormattings as $distConditionalFormatting) {
                    $elementAfterConditionalFormatting = $distConditionalFormatting->nextSibling;
                    $distRoot->removeChild($distConditionalFormatting);
                }

                while ($elementAfterConditionalFormatting instanceOf \DOMNode && !$elementAfterConditionalFormatting instanceOf \DOMElement) {
                    $elementAfterConditionalFormatting = $elementAfterConditionalFormatting->nextSibling;
                }
                if (!$elementAfterConditionalFormatting instanceOf \DOMElement) {
                    break;
                }

                $srcSheetPath = $srcSheetMap[$sheetName];
                $srcXml = $template->getFromName($srcSheetPath);
                $srcDom = new \DOMDocument;
                $srcDom->loadXML($srcXml);
                $srcXPath = new \DOMXPath($srcDom);
                $srcXPath->registerNamespace('s', XmlNamespace::SPREADSHEETML_NS_URL);
                
                $conditionalFormattings = $srcXPath->query('//s:worksheet/s:conditionalFormatting');
                foreach ($conditionalFormattings as $conditionalFormatting) {
                    /** @var \DOMElement $conditionalFormatting */
                    $newDistConditionalFormatting = $distDom->importNode($conditionalFormatting, true);
                    $distRoot->insertBefore($newDistConditionalFormatting, $elementAfterConditionalFormatting);
                }

                $output->addFromString($distSheetPath, $distDom->saveXML());
            }
        }
    }
}