1<?php 2 3use dokuwiki\Form\Form; 4use dokuwiki\Extension\ActionPlugin; 5use dokuwiki\Extension\EventHandler; 6use dokuwiki\Extension\Event; 7use dokuwiki\Form\InputElement; 8 9/** 10 * DokuWiki Plugin searchns (Action Component) 11 * 12 * @license GPL 2 http://www.gnu.org/licenses/gpl-2.0.html 13 * @author Anna Dabrowska <dokuwiki@cosmocode.de> 14 */ 15class action_plugin_searchns extends ActionPlugin 16{ 17 /** @inheritDoc */ 18 public function register(EventHandler $controller) 19 { 20 $controller->register_hook('FORM_QUICKSEARCH_OUTPUT', 'BEFORE', $this, 'handleForm'); 21 $controller->register_hook('DOKUWIKI_STARTED', 'AFTER', $this, 'handleStart'); 22 $controller->register_hook('AJAX_CALL_UNKNOWN', 'BEFORE', $this, 'handleAjax'); 23 $controller->register_hook('SEARCH_QUERY_PAGELOOKUP', 'AFTER', $this, 'sortResults'); 24 $controller->register_hook('SEARCH_RESULT_PAGELOOKUP', 'AFTER', $this, 'resultHeading'); 25 } 26 27 /** 28 * Performs the quick search 29 * 30 * @param Event $event 31 * @return void 32 */ 33 public function handleAjax(Event $event) 34 { 35 if ($event->data !== 'plugin_searchns_qsearch') return; 36 37 $event->preventDefault(); 38 $event->stopPropagation(); 39 40 /** @var helper_plugin_searchns $helper */ 41 $helper = plugin_load('helper', 'searchns'); 42 echo $helper->qSearch(); 43 } 44 45 /** 46 * Adds selected namespace to global query 47 * @param Event $event 48 * @return void 49 */ 50 public function handleStart(Event $event) 51 { 52 global $INPUT; 53 global $QUERY; 54 55 if ($INPUT->str('ns')) { 56 $QUERY .= ' @' . $INPUT->str('ns'); 57 } 58 } 59 60 /** 61 * Modifies the quicksearch form 62 * 63 * @param Event $event Event object 64 * @return void 65 */ 66 public function handleForm(Event $event) 67 { 68 global $ACT; 69 global $QUERY; 70 global $INPUT; 71 global $lang; 72 73 /** @var Form $form */ 74 $form = $event->data; 75 76 /** @var \helper_plugin_searchns $helper */ 77 $helper = plugin_load('helper', 'searchns'); 78 79 $ns = $INPUT->str('ns'); 80 81 // strip namespace from text input, we have a dropdown for this 82 if ($ns) { 83 $q = str_replace('@' . $ns, '', $QUERY); 84 } else { 85 $q = ''; 86 } 87 88 $newQ = new InputElement('text', 'q'); 89 $newQ->addClass('edit') 90 ->attrs([ 91 'title' => '[F]', 92 'accesskey' => 'f', 93 'placeholder' => $lang['btn_search'], 94 'autocomplete' => 'off', 95 ]) 96 ->id('qsearchns__in') 97 ->val($ACT === 'search' ? $q : '') 98 ->useInput(false); 99 100 $form->replaceElement( 101 $newQ, 102 $form->findPositionByAttribute('name', 'q') 103 ); 104 105 $namespaces = $helper->getNsFromConfig(); 106 if ($this->getConf('filter by acl')) { 107 $namespaces = array_filter($namespaces, [$helper, 'filterByACL']); 108 } 109 110 // prepend namespace dropdown 111 $form->addDropdown( 112 'ns', 113 array_flip($namespaces), 114 $this->getLang('namespace label'), 115 0 116 ) 117 ->id('qsearchns__ns') 118 ->val($ns); 119 } 120 121 /** 122 * Sort and group results based on configured namespaces. 123 * 124 * @param Event $event 125 * @return void 126 */ 127 public function sortResults(Event $event) 128 { 129 global $INPUT; 130 global $QUERY; 131 132 if ($INPUT->str('ns') || strpos($QUERY, '@') !== false) return; 133 134 $event->stopPropagation(); 135 136 /** @var \helper_plugin_searchns $helper */ 137 $helper = plugin_load('helper', 'searchns'); 138 139 $event->result = $helper->sortAndGroup($event->result); 140 } 141 142 /** 143 * Format namespace headings (pseudo results) 144 * 145 * @param Event $event 146 * @return void 147 */ 148 public function resultHeading(Event $event) 149 { 150 global $INPUT; 151 global $QUERY; 152 153 if ($INPUT->str('ns') || strpos($QUERY, '@') !== false) return; 154 155 /** @var \helper_plugin_searchns $helper */ 156 $helper = plugin_load('helper', 'searchns'); 157 158 $labels = array_keys($helper->getNsFromConfig() + [$this->getLang('other label') => '']); 159 160 if (in_array($event->data['page'], $labels)) { 161 $event->data['listItemContent'][0] = '<div class="searchns_heading">' . $event->data['page'] . '</div>'; 162 } 163 } 164} 165