使用 DOM 文档在 PHP 中的缩进

2022-08-30 16:07:17

我正在使用生成一个新的XML文件,我希望文件的输出可以很好地缩进,以便人类读者易于遵循。DOMDocument

例如,输出此数据时:DOMDocument

<?xml version="1.0"?>
<this attr="that"><foo>lkjalksjdlakjdlkasd</foo><foo>lkjlkasjlkajklajslk</foo></this>

我希望 XML 文件是:

<?xml version="1.0"?>
<this attr="that">
    <foo>lkjalksjdlakjdlkasd</foo>
    <foo>lkjlkasjlkajklajslk</foo>
</this>

我一直在寻找答案,我发现的一切似乎都在试图以这种方式控制空白:

$foo = new DOMDocument();
$foo->preserveWhiteSpace = false;
$foo->formatOutput = true;

但这似乎无济于事。也许这只在读取 XML 时才有效?请记住,我正在尝试编写新文档。

是否有任何内置功能可以执行此操作?还是一个可以轻松实现这一点的功能?DOMDocument


答案 1

DomDocument会做到这一点,我个人花了几个小时谷歌搜索并试图弄清楚这一点,我注意到如果你使用

$xmlDoc = new DOMDocument ();
$xmlDoc->loadXML ( $xml );
$xmlDoc->preserveWhiteSpace = false;
$xmlDoc->formatOutput = true;
$xmlDoc->save($xml_file);

按照这个顺序,它只是不起作用,但是,如果你使用相同的代码,但按以下顺序:

$xmlDoc = new DOMDocument ();
$xmlDoc->preserveWhiteSpace = false;
$xmlDoc->formatOutput = true;
$xmlDoc->loadXML ( $xml );
$xmlDoc->save($archivoxml);

像吊饰一样工作,希望这有帮助


答案 2

在John的一些帮助下,我自己尝试了这个问题,似乎即使是DOMDocument对格式化的固有支持也无法满足我的需求。因此,我决定编写自己的缩进函数。

这是一个非常粗糙的函数,我只是快速地放在一起,所以如果有人有任何优化技巧或关于它的任何东西要说,我会很高兴听到它!

function indent($text)
{
    // Create new lines where necessary
    $find = array('>', '</', "\n\n");
    $replace = array(">\n", "\n</", "\n");
    $text = str_replace($find, $replace, $text);
    $text = trim($text); // for the \n that was added after the final tag

    $text_array = explode("\n", $text);
    $open_tags = 0;
    foreach ($text_array AS $key => $line)
    {
        if (($key == 0) || ($key == 1)) // The first line shouldn't affect the indentation
            $tabs = '';
        else
        {
            for ($i = 1; $i <= $open_tags; $i++)
                $tabs .= "\t";
        }

        if ($key != 0)
        {
            if ((strpos($line, '</') === false) && (strpos($line, '>') !== false))
                $open_tags++;
            else if ($open_tags > 0)
                $open_tags--;
        }

        $new_array[] = $tabs . $line;

        unset($tabs);
    }
    $indented_text = implode("\n", $new_array);

    return $indented_text;
}

推荐