]> git.mxchange.org Git - quix0rs-gnu-social.git/blob - plugins/Directory/actions/groupdirectory.php
Merge remote-tracking branch 'upstream/master' into social-master
[quix0rs-gnu-social.git] / plugins / Directory / actions / groupdirectory.php
1 <?php
2 /**
3  * StatusNet, the distributed open-source microblogging tool
4  *
5  * Output a group directory
6  *
7  * PHP version 5
8  *
9  * LICENCE: This program is free software: you can redistribute it and/or modify
10  * it under the terms of the GNU Affero General Public License as published by
11  * the Free Software Foundation, either version 3 of the License, or
12  * (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU Affero General Public License for more details.
18  *
19  * You should have received a copy of the GNU Affero General Public License
20  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
21  *
22  * @category  Public
23  * @package   StatusNet
24  * @author    Zach Copley <zach@status.net>
25  * @copyright 2011 StatusNet, Inc.
26  * @license   http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
27  * @link      http://status.net/
28  */
29
30 if (!defined('GNUSOCIAL')) { exit(1); }
31
32 /**
33  * Group directory
34  *
35  * @category Directory
36  * @package  StatusNet
37  * @author   Zach Copley <zach@status.net>
38  * @author   Mikael Nordfeldth <mmn@hethane.se>
39  * @license  http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
40  * @link     http://status.net/
41  */
42 class GroupdirectoryAction extends ManagedAction
43 {
44     /**
45      * The page we're on
46      *
47      * @var integer
48      */
49     public $page;
50
51     /**
52      * What to filter the search results by
53      *
54      * @var string
55      */
56     public $filter;
57
58     /**
59      * Column to sort by
60      *
61      * @var string
62      */
63     public $sort;
64
65     /**
66      * How to order search results, ascending or descending
67      *
68      * @var string
69      */
70     public $reverse;
71
72     /**
73      * Query
74      *
75      * @var string
76      */
77     public $q;
78
79     /**
80      * Title of the page
81      *
82      * @return string Title of the page
83      */
84     function title()
85     {
86         // @fixme: This looks kinda gross
87
88         if ($this->filter == 'all') {
89             if ($this->page != 1) {
90                 // TRANS: Title for group directory page. %d is a page number.
91                 return(sprintf(_m('Group Directory, page %d'), $this->page));
92             }
93             // TRANS: Title for group directory page.
94             return _m('Group directory');
95         } else if ($this->page == 1) {
96             return sprintf(
97                 // TRANS: Title for group directory page when it is filtered.
98                 // TRANS: %s is the filter string.
99                 _m('Group directory - %s'),
100                 strtoupper($this->filter)
101             );
102         } else {
103             return sprintf(
104                 // TRANS: Title for group directory page when it is filtered.
105                 // TRANS: %1$s is the filter string, %2$d is a page number.
106                 _m('Group directory - %1$s, page %2$d'),
107                 strtoupper($this->filter),
108                 $this->page
109             );
110         }
111     }
112
113     /**
114      * Instructions for use
115      *
116      * @return instructions for use
117      */
118     function getInstructions()
119     {
120         // TRANS: Page instructions.
121         return _m("After you join a group you can send messages to all other members\n".
122                  "using the syntax \"!groupname\".\n\n".
123                  "Browse groups, or search for groups by their name, location or topic.\n".
124                  "Separate the terms by spaces; they must be three characters or more.") . "\n";
125     }
126
127     /**
128      * Is this page read-only?
129      *
130      * @return boolean true
131      */
132     function isReadOnly(array $args=array())
133     {
134         return true;
135     }
136
137     protected function doPreparation()
138     {
139         $this->page    = ($this->arg('page')) ? ($this->arg('page') + 0) : 1;
140         $this->filter  = $this->arg('filter', 'all');
141         $this->reverse = $this->boolean('reverse');
142         $this->q       = $this->trimmed('q');
143         $this->sort    = $this->arg('sort', 'nickname');
144
145         common_set_returnto($this->selfUrl());
146     }
147
148     /**
149      * Show the page notice
150      *
151      * Shows instructions for the page
152      *
153      * @return void
154      */
155     function showPageNotice()
156     {
157         $instr  = $this->getInstructions();
158         $output = common_markup_to_html($instr);
159
160         $this->elementStart('div', 'instructions');
161         $this->raw($output);
162         $this->elementEnd('div');
163     }
164
165
166     /**
167      * Content area
168      *
169      * Shows the groups
170      *
171      * @return void
172      */
173     function showContent()
174     {
175         if (common_logged_in()) {
176             $this->elementStart(
177                 'p',
178                 array(
179                     'id' => 'new_group'
180                 )
181             );
182             $this->element(
183                 'a',
184                 array(
185                     'href'  => common_local_url('newgroup'),
186                     'class' => 'more'),
187                     // TRANS: Link to create a new group on the group list page.
188                     _m('Create a new group')
189             );
190             $this->elementEnd('p');
191         }
192
193         $this->showForm();
194
195         $this->elementStart('div', array('id' => 'profile_directory'));
196
197         // @todo FIXME: Does "All" need i18n here?
198         $alphaNav = new AlphaNav($this, false, false, array('0-9', 'All'));
199         $alphaNav->show();
200
201         $group   = null;
202         $group   = $this->getGroups();
203         $cnt     = 0;
204
205         if (!empty($group)) {
206             $groupList = new SortableGroupList(
207                 $group,
208                 common_current_user(),
209                 $this
210             );
211
212             $cnt = $groupList->show();
213             $group->free();
214
215             if (0 == $cnt) {
216                 $this->showEmptyListMessage();
217             }
218         }
219
220         $args = array();
221         if (isset($this->q)) {
222             $args['q'] = $this->q;
223         } else {
224             $args['filter'] = $this->filter;
225         }
226
227         $this->pagination(
228             $this->page > 1,
229             $cnt > PROFILES_PER_PAGE,
230             $this->page,
231             'groupdirectory',
232             $args
233         );
234
235         $this->elementEnd('div');
236     }
237
238     function showForm($error=null)
239     {
240         $this->elementStart(
241             'form',
242             array(
243                 'method' => 'get',
244                 'id'     => 'form_search',
245                 'class'  => 'form_settings',
246                 'action' => common_local_url('groupdirectory')
247             )
248         );
249
250         $this->elementStart('fieldset');
251
252         // TRANS: Fieldset legend.
253         $this->element('legend', null, _m('Search groups'));
254         $this->elementStart('ul', 'form_data');
255         $this->elementStart('li');
256
257         // TRANS: Field label for input of one or more keywords.
258         $this->input('q', _m('Keyword(s)'), $this->q);
259
260         // TRANS: Button text for searching group directory.
261         $this->submit('search', _m('BUTTON','Search'));
262         $this->elementEnd('li');
263         $this->elementEnd('ul');
264         $this->elementEnd('fieldset');
265         $this->elementEnd('form');
266     }
267
268     /*
269      * Get groups filtered by the current filter, sort key,
270      * sort order, and page
271      */
272     function getGroups()
273     {
274         $group = new User_group();
275
276         // Disable this to get global group searches
277         $group->joinAdd(array('id', 'local_group:group_id'));
278
279         $order = false;
280
281         if (!empty($this->q)) {
282             $wheres = array('nickname', 'fullname', 'homepage', 'description', 'location');
283             foreach ($wheres as $where) {
284                 // Double % because of sprintf
285                 $group->whereAdd(sprintf('LOWER(%1$s.%2$s) LIKE LOWER("%%%3$s%%")',
286                                         $group->escapedTableName(), $where,
287                                         $group->escape($this->q)),
288                                     'OR');
289             }
290
291             $order = sprintf('%1$s.%2$s %3$s',
292                             $group->escapedTableName(),
293                             $this->getSortKey('created'),
294                             $this->reverse ? 'DESC' : 'ASC');
295         } else {
296             // User is browsing via AlphaNav
297
298             switch($this->filter) {
299             case 'all':
300                 // NOOP
301                 break;
302             case '0-9':
303                 $group->whereAdd(sprintf('LEFT(%1$s.%2$s, 1) BETWEEN %3$s AND %4$s',
304                                         $group->escapedTableName(),
305                                         'nickname',
306                                         $group->_quote("0"),
307                                         $group->_quote("9")));
308                 break;
309             default:
310                 $group->whereAdd(sprintf('LEFT(LOWER(%1$s.%2$s), 1) = %3$s',
311                                             $group->escapedTableName(),
312                                             'nickname',
313                                             $group->_quote($this->filter)));
314             }
315
316             $order = sprintf('%1$s.%2$s %3$s, %1$s.%4$s ASC',
317                             $group->escapedTableName(),
318                             $this->getSortKey('nickname'),
319                             $this->reverse ? 'DESC' : 'ASC',
320                             'nickname');
321         }
322
323         $offset = ($this->page-1) * PROFILES_PER_PAGE;
324         $limit  = PROFILES_PER_PAGE + 1;
325
326         $group->orderBy($order);
327         $group->limit($offset, $limit);
328
329         $group->find();
330
331         return $group;
332     }
333
334     /**
335      * Filter the sort parameter
336      *
337      * @return string   a column name for sorting
338      */
339     function getSortKey($def='created')
340     {
341         switch ($this->sort) {
342         case 'nickname':
343         case 'created':
344             return $this->sort;
345         default:
346             return $def;
347         }
348     }
349
350     /**
351      * Show a nice message when there's no search results
352      */
353     function showEmptyListMessage()
354     {
355         if (!empty($this->filter) && ($this->filter != 'all')) {
356             $this->element(
357                 'p',
358                 'error',
359                 sprintf(
360                     // TRANS: Empty list message for searching group directory.
361                     // TRANS: %s is the search string.
362                     _m('No groups starting with %s.'),
363                     $this->filter
364                 )
365             );
366         } else {
367             // TRANS: Empty list message for searching group directory.
368             $this->element('p', 'error', _m('No results.'));
369             // TRANS: Help text for searching group directory.
370             $message = _m("* Make sure all words are spelled correctly.\n".
371                           "* Try different keywords.\n".
372                           "* Try more general keywords.\n".
373                           "* Try fewer keywords.");
374             $this->elementStart('div', 'help instructions');
375             $this->raw(common_markup_to_html($message));
376             $this->elementEnd('div');
377         }
378     }
379
380     function showSections()
381     {
382         $gbp = new GroupsByPostsSection($this);
383         $gbp->show();
384         $gbm = new GroupsByMembersSection($this);
385         $gbm->show();
386     }
387 }