1<?php 2/** 3 * @license GPL 2 (http://www.gnu.org/licenses/gpl.html) 4 * @author Andreas Gohr <gohr@cosmocode.de> 5 */ 6 7class syntax_plugin_pagenav extends DokuWiki_Syntax_Plugin 8{ 9 10 /** @inheritDoc */ 11 public function getType() 12 { 13 return 'substition'; 14 } 15 16 /** @inheritDoc */ 17 public function getPType() 18 { 19 return 'block'; 20 } 21 22 /** @inheritDoc */ 23 public function getSort() 24 { 25 return 155; 26 } 27 28 29 /** @inheritDoc */ 30 public function connectTo($mode) 31 { 32 $this->Lexer->addSpecialPattern('\[<\d*>(?: [^\]]+)?\]', $mode, 'plugin_pagenav'); 33 } 34 35 36 /** @inheritDoc */ 37 public function handle($match, $state, $pos, Doku_Handler $handler) 38 { 39 //split the match in it's parts 40 $match = substr($match, 1, -1); 41 list($mode, $glob) = explode(' ', $match, 2); 42 $mode = (int)substr($mode, 1, -1); 43 if (!$mode) $mode = 2 + 4 + 8; 44 45 return array(strtolower(trim($glob)), $mode); 46 } 47 48 /** @inheritDoc */ 49 public function render($format, Doku_Renderer $renderer, $data) 50 { 51 global $INFO; 52 global $conf; 53 if ($format != 'xhtml') return false; 54 55 list($glob, $mode) = $data; 56 $glob = preg_quote($glob, '/'); 57 58 // get all files in current namespace 59 static $list = null; // static to reuse the array for multiple calls. 60 if (is_null($list)) { 61 $list = array(); 62 $ns = str_replace(':', '/', getNS($INFO['id'])); 63 search($list, $conf['datadir'], 'search_list', array(), utf8_encodeFN($ns)); 64 } 65 $id = $INFO['id']; 66 67 // find the start page 68 $exist = false; 69 $start = getNS($INFO['id']) . ':'; 70 resolve_pageid('', $start, $exist); 71 72 $cnt = count($list); 73 if ($cnt < 2) return true; // there are no other doc in this namespace 74 75 $first = ''; 76 $prev = ''; 77 $last = ''; 78 $next = ''; 79 $self = false; 80 81 // we go through the list only once, handling all options and globs 82 // only for the 'last' command the whole list is iterated 83 for ($i = 0; $i < $cnt; $i++) { 84 if ($list[$i]['id'] == $id) { 85 $self = true; 86 } else { 87 if ($glob && !preg_match('/' . $glob . '/', noNS($list[$i]['id']))) continue; 88 if ($list[$i]['id'] == $start) continue; 89 if (isHiddenPage($list[$i]['id'])) continue; 90 91 if ($self) { 92 // we're after the current id 93 if (!$next) { 94 $next = $list[$i]['id']; 95 } 96 $last = $list[$i]['id']; 97 } else { 98 // we're before the current id 99 if (!$first) { 100 $first = $list[$i]['id']; 101 } 102 $prev = $list[$i]['id']; 103 } 104 } 105 } 106 107 $renderer->doc .= '<p class="plugin__pagenav">'; 108 if ($mode & 4) $renderer->doc .= $this->buildImgLink($first, 'first'); 109 if ($mode & 2) $renderer->doc .= $this->buildImgLink($prev, 'prev'); 110 if ($mode & 8) $renderer->doc .= $this->buildImgLink($start, 'up'); 111 if ($mode & 2) $renderer->doc .= $this->buildImgLink($next, 'next'); 112 if ($mode & 4) $renderer->doc .= $this->buildImgLink($last, 'last'); 113 $renderer->doc .= '</p>'; 114 115 return true; 116 } 117 118 /** 119 * Builds the link using an SVG image 120 * 121 * @param string $page page to link to 122 * @param string $cmd 123 * @return string 124 */ 125 protected function buildImgLink($page, $cmd) 126 { 127 $img = inlineSVG(__DIR__ . '/img/' . $cmd . '.svg'); 128 129 // no page, gray out item 130 if (blank($page)) { 131 return '<span class="' . $cmd . '">' . $img . '</span>'; 132 } 133 134 135 $title = p_get_first_heading($page); 136 $attr = [ 137 'href' => wl($page), 138 'title' => $this->getLang($cmd) . ': ' . hsc($title), 139 'class' => 'wikilink1 ' . $cmd, 140 ]; 141 return '<a ' . buildAttributes($attr) . '>' . $img . '</a>'; 142 } 143} 144