think\Template::parseExtend PHP Method

parseExtend() private method

解析模板中的extend标签
private parseExtend ( string &$content ) : void
$content string 要解析的模板内容
return void
    private function parseExtend(&$content)
    {
        $regex = $this->getRegex('extend');
        $array = $blocks = $baseBlocks = [];
        $extend = '';
        $func = function ($template) use(&$func, &$regex, &$array, &$extend, &$blocks, &$baseBlocks) {
            if (preg_match($regex, $template, $matches)) {
                if (!isset($array[$matches['name']])) {
                    $array[$matches['name']] = 1;
                    // 读取继承模板
                    $extend = $this->parseTemplateName($matches['name']);
                    // 递归检查继承
                    $func($extend);
                    // 取得block标签内容
                    $blocks = array_merge($blocks, $this->parseBlock($template));
                    return;
                }
            } else {
                // 取得顶层模板block标签内容
                $baseBlocks = $this->parseBlock($template, true);
                if (empty($extend)) {
                    // 无extend标签但有block标签的情况
                    $extend = $template;
                }
            }
        };
        $func($content);
        if (!empty($extend)) {
            if ($baseBlocks) {
                $children = [];
                foreach ($baseBlocks as $name => $val) {
                    $replace = $val['content'];
                    if (!empty($children[$name])) {
                        // 如果包含有子block标签
                        foreach ($children[$name] as $key) {
                            $replace = str_replace($baseBlocks[$key]['begin'] . $baseBlocks[$key]['content'] . $baseBlocks[$key]['end'], $blocks[$key]['content'], $replace);
                        }
                    }
                    if (isset($blocks[$name])) {
                        // 带有{__block__}表示与所继承模板的相应标签合并,而不是覆盖
                        $replace = str_replace(['{__BLOCK__}', '{__block__}'], $replace, $blocks[$name]['content']);
                        if (!empty($val['parent'])) {
                            // 如果不是最顶层的block标签
                            $parent = $val['parent'];
                            if (isset($blocks[$parent])) {
                                $blocks[$parent]['content'] = str_replace($blocks[$name]['begin'] . $blocks[$name]['content'] . $blocks[$name]['end'], $replace, $blocks[$parent]['content']);
                            }
                            $blocks[$name]['content'] = $replace;
                            $children[$parent][] = $name;
                            continue;
                        }
                    } elseif (!empty($val['parent'])) {
                        // 如果子标签没有被继承则用原值
                        $children[$val['parent']][] = $name;
                        $blocks[$name] = $val;
                    }
                    if (!$val['parent']) {
                        // 替换模板中的顶级block标签
                        $extend = str_replace($val['begin'] . $val['content'] . $val['end'], $replace, $extend);
                    }
                }
            }
            $content = $extend;
            unset($blocks, $baseBlocks);
        }
        return;
    }