1<?php 2 3namespace dokuwiki\Ui; 4 5use dokuwiki\ChangeLog\PageChangeLog; 6use dokuwiki\Form\Form; 7 8/** 9 * DokuWiki PageRevisions Interface 10 * 11 * @package dokuwiki\Ui 12 */ 13class PageRevisions extends Revisions 14{ 15 /* @var PageChangeLog */ 16 protected $changelog; 17 18 /** 19 * PageRevisions Ui constructor 20 * 21 * @param string $id id of page 22 */ 23 public function __construct($id) 24 { 25 global $INFO; 26 if (!$id) $id = $INFO['id']; 27 $this->item = 'page'; 28 parent::__construct($id); 29 } 30 31 /** @inheritdoc */ 32 protected function setChangeLog() 33 { 34 $this->changelog = new PageChangeLog($this->id); 35 } 36 37 /** @inheritdoc */ 38 protected function itemFN($id, $rev = '') 39 { 40 return wikiFN($id, $rev); 41 } 42 43 /** 44 * Display list of old revisions of the page 45 * 46 * @author Andreas Gohr <andi@splitbrain.org> 47 * @author Ben Coburn <btcoburn@silicodon.net> 48 * @author Kate Arzamastseva <pshns@ukr.net> 49 * @author Satoshi Sahara <sahara.satoshi@gmail.com> 50 * 51 * @param int $first skip the first n changelog lines 52 * @return void 53 */ 54 public function show($first = 0) 55 { 56 global $lang, $REV; 57 58 // get revisions, and set correct pagenation parameters (first, hasNext) 59 if ($first === null) $first = 0; 60 $hasNext = false; 61 $revisions = $this->getRevisions($first, $hasNext); 62 63 // print intro 64 print p_locale_xhtml('revisions'); 65 66 // create the form 67 $form = new Form([ 68 'id' => 'page__revisions', 69 'class' => 'changes', 70 ]); 71 $form->addTagOpen('div')->addClass('no'); 72 73 // start listing 74 $form->addTagOpen('ul'); 75 foreach ($revisions as $info) { 76 $rev = $info['date']; 77 $class = ($info['type'] === DOKU_CHANGE_TYPE_MINOR_EDIT) ? 'minor' : ''; 78 $form->addTagOpen('li')->addClass($class); 79 $form->addTagOpen('div')->addClass('li'); 80 81 if (isset($info['current'])) { 82 $form->addCheckbox('rev2[]')->val('current'); 83 } elseif ($rev == $REV) { 84 $form->addCheckbox('rev2[]')->val($rev)->attr('checked','checked'); 85 } elseif (page_exists($this->id, $rev)) { 86 $form->addCheckbox('rev2[]')->val($rev); 87 } else { 88 $form->addCheckbox('')->val($rev)->attr('disabled','disabled'); 89 } 90 $form->addHTML(' '); 91 92 $objRevInfo = $this->getObjRevInfo($info); 93 $html = implode(' ', [ 94 $objRevInfo->editDate(), // edit date and time 95 $objRevInfo->difflink(), // link to diffview icon 96 $objRevInfo->itemName(), // name of page or media 97 $objRevInfo->editSummary(), // edit summary 98 $objRevInfo->editor(), // editor info 99 $objRevInfo->sizechange(), // size change indicator 100 $objRevInfo->currentIndicator(), // current indicator (only when k=1) 101 ]); 102 $form->addHTML($html); 103 $form->addTagClose('div'); 104 $form->addTagClose('li'); 105 } 106 $form->addTagClose('ul'); // end of revision list 107 108 // show button for diff view 109 $form->addButton('do[diff]', $lang['diff2'])->attr('type', 'submit'); 110 111 $form->addTagClose('div'); // close div class=no 112 113 print $form->toHTML('Revisions'); 114 115 // provide navigation for pagenated revision list (of pages and/or media files) 116 print $this->navigation($first, $hasNext, function ($n) { 117 return array('do' => 'revisions', 'first' => $n); 118 }); 119 } 120 121 /** 122 * Get revisions, and set correct pagenation parameters (first, hasNext) 123 * 124 * @param int $first 125 * @param bool $hasNext 126 * @return array revisions to be shown in a pagenated list 127 * @see also https://www.dokuwiki.org/devel:changelog 128 */ 129 protected function getRevisions(&$first, &$hasNext) 130 { 131 global $INFO, $conf; 132 133 if ($this->id != $INFO['id']) { 134 return parent::getRevisions($first, $hasNext); 135 } 136 137 $changelog =& $this->changelog; 138 139 $revisions = []; 140 141 /* we need to get one additional log entry to be able to 142 * decide if this is the last page or is there another one. 143 * see also Ui\Recent::getRecents() 144 */ 145 $revlist = $changelog->getRevisions($first, $conf['recent'] +1); 146 if (count($revlist) == 0 && $first != 0) { 147 $first = 0; 148 $revlist = $changelog->getRevisions($first, $conf['recent'] +1); 149 } 150 $exists = $INFO['exists']; 151 if ($first == 0 && $exists) { 152 // add current page as revision[0] 153 $revisions[] = array( 154 'date' => $INFO['lastmod'], 155 'ip' => null, 156 'type' => $INFO['meta']['last_change']['type'], 157 'id' => $INFO['id'], 158 'user' => $INFO['editor'], 159 'sum' => $INFO['sum'], 160 'extra' => null, 161 'sizechange' => $INFO['meta']['last_change']['sizechange'], 162 'item' => $this->item, 163 'current' => true, 164 ); 165 } 166 167 // decide if this is the last page or is there another one 168 $hasNext = false; 169 if (count($revlist) > $conf['recent']) { 170 $hasNext = true; 171 array_pop($revlist); // remove one additional log entry 172 } 173 174 // append each revison info array to the revisions 175 foreach ($revlist as $rev) { 176 $revisions[] = $changelog->getRevisionInfo($rev) + array('item' => $this->item); 177 } 178 return $revisions; 179 } 180 181} 182