diff --git a/index.php b/index.php index c1f71d0..ca49a00 100644 --- a/index.php +++ b/index.php @@ -49,6 +49,7 @@ try { $tmp = SiteMeta::getBookshelf()->getBook($uri[0]); if ($tmp == null) throw new RequestNotExistException("Book required \"$uri[0]\" not found!"); + PageMeta::$bookId = $uri[0]; PageMeta::$book = $tmp->getContentedNode(); } @@ -58,12 +59,13 @@ try { if ($tmp == null) throw new RequestNotExistException("Page required \"$uri[1]\" not found on book \"$uri[0]\"!"); PageMeta::$page = $tmp; } else { - PageMeta::$page = PageMeta::$book->getChilds()->getChildren()[0]; + PageMeta::$page = PageMeta::$book->getChildren()->getChildren()[0]; } } else { // 主页面 + PageMeta::$bookId = "%root"; PageMeta::$book = SiteMeta::getBookshelf()->getRootBook(); - PageMeta::$page = PageMeta::$book->getChilds()->getChildren()[0]; + PageMeta::$page = PageMeta::$book->getChildren()->getChildren()[0]; PageMeta::$isMainPage = true; } diff --git a/src/Data/PageMeta.php b/src/Data/PageMeta.php index 50bb544..efbccdd 100644 --- a/src/Data/PageMeta.php +++ b/src/Data/PageMeta.php @@ -8,6 +8,7 @@ use SukWs\Bookshelf\Element\BookContent\Page; class PageMeta { + public static string $bookId; public static BookContented $book; public static Page $page; public static bool $isMainPage = false; diff --git a/src/Element/Book.php b/src/Element/Book.php index d9b2e7d..26bd001 100644 --- a/src/Element/Book.php +++ b/src/Element/Book.php @@ -66,8 +66,8 @@ class Book { %s href='%s'" . ">%s EOF, str_repeat("\t", $indent), $this->id, $this->id, - str_repeat("\t", $indent), PageMeta::$book->getId()==$this->id ? " current" : "", - str_repeat("\t", $indent), PageMeta::$book->getId()==$this->id ? "javascript:void(0)" : $this->encodeUrl(), $this->name + str_repeat("\t", $indent), PageMeta::$bookId==$this->id ? " current" : "", + str_repeat("\t", $indent), PageMeta::$bookId==$this->id ? "javascript:void(0)" : $this->encodeUrl(), $this->name ); } diff --git a/src/Element/BookContent/BookContented.php b/src/Element/BookContent/BookContented.php index 2722bb6..ad73d3c 100644 --- a/src/Element/BookContent/BookContented.php +++ b/src/Element/BookContent/BookContented.php @@ -4,44 +4,49 @@ namespace SukWs\Bookshelf\Element\BookContent; use DOMDocument; use DOMNode; -use SukWs\Bookshelf\Element\Bookshelf; use Exception; class BookContented { - private string $id; + private string $configVersion; + private string $name; private array $configurations = array(); - public function __construct (string $id, string $name) { - $this->id = $id; - $this->name = $name; + public function __construct (string $configVersion) { + $this->configVersion = $configVersion; } - private Chapter $childs; + private Chapter $children; /** - * @param DOMNode $xmlData + * @param DOMNode $nodeBook * @return BookContented * @throws Exception */ - public static function parse (DOMNode $xmlData): BookContented { - if ($xmlData->hasAttributes() && $xmlData->hasChildNodes()) { - $attrName = $xmlData->attributes->getNamedItem("name"); - $attrId = $xmlData->attributes->getNamedItem("id"); - if ($attrName == null) - if ($attrId == null) throw new Exception("BookWithContent xml data missing attribute \"name\""); - else throw new Exception("BookWithContent xml data with id \"$attrId->nodeValue\" missing attribute \"name\""); - else $name = $attrName->nodeValue; - if ($attrId == null) throw new Exception("BookWithContent xml data named \"$name\" missing attribute \"id\""); - else $id = $attrId->nodeValue; - $node = new BookContented($id, $name); - $node->childs = Chapter::parse($xmlData, null); - Bookshelf::parseConfigurationAttr($xmlData->attributes, $node->configurations, array("name", "id")); - } else - throw new Exception("No child or attribute found on BookWithContent"); - return $node; + public static function parse (DOMNode $nodeBook): BookContented { + $attrVersion = $nodeBook->attributes->getNamedItem("version"); + $bookConfigVersion = $attrVersion?->nodeValue; + $return = new BookContented($bookConfigVersion); + for ($child = $nodeBook->firstChild; $child != null; $child = $child->nextSibling) { + switch ($child->nodeName) { + case "book_name": + if (!empty($return->name)) throw new Exception("Duplicated contents in Book.xml"); + $return->name = $child->nodeValue; + break; + case "contents": + if (!empty($return->children)) throw new Exception("Duplicated contents in Book.xml"); + $return->children = Chapter::parse($child, null); + break; + case "#comment": + case "#text": + if (empty(trim($child->nodeValue))) break; + default: + throw new Exception("Book.xml has sub-node \"$child->nodeName\" with is not supported."); + } + } + return $return; } /** @@ -49,9 +54,10 @@ class BookContented { * @return BookContented * @throws Exception */ - public static function parseRootBook (DOMNode $rootBookNode): BookContented { - $return = new BookContented("%root", ""); - $return->childs = Chapter::parse($rootBookNode, null); + public static function parseRootBook (DOMNode $rootBookNode, string $bookName): BookContented { + $return = new BookContented("2.0"); + $return->name = $bookName; + $return->children = Chapter::parse($rootBookNode, null); return $return; } @@ -69,24 +75,24 @@ class BookContented { } - public function getId (): string { - return $this->id; + public function getConfigVersion (): string { + return $this->configVersion; } public function getName (): string { return $this->name; } - public function getChilds (): Chapter { - return $this->childs; + public function getChildren (): Chapter { + return $this->children; } public function getSummaryHtml (): string { - return $this->childs->getSummaryHtml(); + return $this->children->getSummaryHtml(); } public function getPage (string $id): ?Page { - return $this->childs->getPage($id); + return $this->children->getPage($id); } public function getConfiguration (string $key): ?string { diff --git a/src/Element/BookContent/Chapter.php b/src/Element/BookContent/Chapter.php index f0bb3a7..ce0e81e 100644 --- a/src/Element/BookContent/Chapter.php +++ b/src/Element/BookContent/Chapter.php @@ -27,7 +27,7 @@ class Chapter { * @return Chapter * @throws Exception */ - public static function parse (DOMNode $xmlData, ?Chapter $parent): Chapter { + public static function parse (DOMNode $xmlData, ?Chapter $parent, ?string $idRoot = null): Chapter { $child = $xmlData->firstChild; if ($parent != null) { while ($child->nodeName != "caption") { @@ -44,13 +44,15 @@ class Chapter { $node = new Chapter($child->nodeValue, array(), $parent); $child = $child->nextSibling; } else $node = new Chapter("", array(), $parent); + $attrRoot = $xmlData->attributes->getNamedItem("root"); + $chapterIdRoot = $idRoot . $attrRoot?->nodeValue; for (;$child != null ; $child = $child->nextSibling) { switch ($child->nodeName) { case "Page": - $node->children[] = Page::parse($child, $node); + $node->children[] = Page::parse($child, $node, $chapterIdRoot); break; case "Chapter": - $node->children[] = self::parse($child, $node); + $node->children[] = self::parse($child, $node, $chapterIdRoot); break; case "Separator": $node->children[] = Separator::parse($child, $node); diff --git a/src/Element/BookContent/Page.php b/src/Element/BookContent/Page.php index c29ee0d..2d37a5e 100644 --- a/src/Element/BookContent/Page.php +++ b/src/Element/BookContent/Page.php @@ -28,11 +28,11 @@ class Page { * @return Page * @throws Exception */ - public static function parse (DOMNode $pageNode, Chapter $parent): Page { + public static function parse (DOMNode $pageNode, Chapter $parent, ?string $idRoot): Page { if ($pageNode->hasAttributes()) { $attrId = $pageNode->attributes->getNamedItem("id"); if ($attrId == null) throw new Exception("an Page xml data missing attribute \"id\""); - else $id = $attrId->nodeValue; + else $id = $idRoot . $attrId->nodeValue; } else throw new Exception("Book xml data missing attributes"); return new Page($id, $pageNode->nodeValue, $parent); @@ -89,12 +89,12 @@ class Page { public function encodeUrl (): string { return str_replace( "%2F", "/", - sprintf("/%s/%s", urlencode(PageMeta::$book->getId()), urlencode($this->id)) + sprintf("/%s/%s", urlencode(PageMeta::$bookId), urlencode($this->id)) ); } public function getContentFilename (string $type): string { - return sprintf("./data/%s/%s.%s", PageMeta::$book->getId(), $this->id, $type); + return sprintf("./data/%s/%s.%s", PageMeta::$bookId, $this->id, $type); } public function hasContent (string $type): string { diff --git a/src/Element/Bookshelf.php b/src/Element/Bookshelf.php index afe5c6f..7725690 100644 --- a/src/Element/Bookshelf.php +++ b/src/Element/Bookshelf.php @@ -48,7 +48,7 @@ class Bookshelf { $return->books = BookCollection::parse($rc, null, true); break; case "root_book": - $return->rootBook = BookContented::parseRootBook($rc); + $return->rootBook = BookContented::parseRootBook($rc, $return->siteName); break; case "configurations": self::parseConfiguration($rc, $return->configurations); diff --git a/template/footer.php b/template/footer.php index 325ab22..f935c43 100644 --- a/template/footer.php +++ b/template/footer.php @@ -12,7 +12,7 @@ ?>