1<?php 2 3namespace dokuwiki\plugin\wordimport\docx; 4 5/** 6 * Numbering information 7 */ 8class Numbering extends AbstractXMLFile 9{ 10 /** @var array the numbering information numID -> level -> type */ 11 protected $numbering = []; 12 13 /** 14 * The files defines "abstract numbers" first. They define a set of rules for each indentation level of a list. 15 * Then the actual numbers are defined. They reference one of the abstract numbers. List items reference one of the 16 * actual numbers. 17 * 18 * @inheritdoc 19 */ 20 protected function parse() 21 { 22 $xml = $this->docx->loadXMLFile($this->docx->getRelationships()->getTarget('numbering')); 23 $this->registerNamespaces($xml); 24 25 $types = []; 26 foreach ($xml->xpath('//w:abstractNum') as $num) { 27 $id = (int)$num->attributes('w', true)->abstractNumId; 28 $types[$id] = []; 29 30 foreach ($num->xpath('.//w:lvl') as $lvl) { 31 $depth = (int)$lvl->attributes('w', true)->ilvl; 32 $lvlType = (string)$lvl->xpath('.//w:numFmt')[0]->attributes('w', true)->val; 33 $lvlType = ($lvlType === 'decimal') ? 'ordered' : 'unordered'; 34 35 $types[$id][$depth] = $lvlType; 36 } 37 } 38 39 foreach ($xml->xpath('//w:num') as $num) { 40 $id = (int)$num->attributes('w', true)->numId; 41 $typeId = (int)$num->xpath('.//w:abstractNumId')[0]->attributes('w', true)->val; 42 if (isset($types[$typeId])) { 43 $this->numbering[$id] = $types[$typeId]; 44 } 45 } 46 } 47 48 /** 49 * Get the type of the numbering for the given ID and depth 50 * 51 * @param string $id 52 * @param int $depth the depth of the list starting at 0 53 * @return string 'ordered' or 'unordered' 54 */ 55 public function getType($id, int $depth): string 56 { 57 return $this->numbering[$id][$depth] ?? 'unordered'; 58 } 59} 60