Passed
Push — master ( 1778f3...9e4eed )
by John
01:26
created

ManageUltimateMenu::rebuildMenu()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 16
Code Lines 10

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 2
eloc 10
nc 2
nop 0
dl 0
loc 16
rs 9.9332
c 0
b 0
f 0
1
<?php
2
/**
3
 * @package   Ultimate Menu mod
4
 * @version   1.1
5
 * @author    John Rayes <[email protected]>
6
 * @copyright Copyright (c) 2014, John Rayes
7
 * @license   http://opensource.org/licenses/MIT MIT
8
 */
9
10
class ManageUltimateMenu
11
{
12
	private $um;
13
14
	function __construct()
15
	{
16
		global $context, $txt;
17
18
		isAllowedTo('admin_forum');
0 ignored issues
show
Bug introduced by
The function isAllowedTo was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

18
		/** @scrutinizer ignore-call */ 
19
  isAllowedTo('admin_forum');
Loading history...
19
20
		$context['page_title'] = $txt['admin_menu_title'];
21
		$context[$context['admin_menu_name']]['tab_data'] = array(
22
			'title' => $txt['admin_menu'],
23
			'description' => $txt['admin_menu_desc'],
24
			'tabs' => array(
25
				'manmenu' => array(
26
					'description' => $txt['admin_manage_menu_desc'],
27
				),
28
				'addbutton' => array(
29
					'description' => $txt['admin_menu_add_button_desc'],
30
				),
31
			),
32
		);
33
		loadTemplate('ManageUltimateMenu');
0 ignored issues
show
Bug introduced by
The function loadTemplate was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

33
		/** @scrutinizer ignore-call */ 
34
  loadTemplate('ManageUltimateMenu');
Loading history...
34
35
		$subActions = array(
36
			'manmenu' => 'ManageUltimateMenu',
37
			'addbutton' => 'PrepareContext',
38
			'savebutton' => 'SaveButton',
39
		);
40
		if (!isset($_GET['sa']) || !isset($subActions[$_GET['sa']]))
41
			$_GET['sa'] = 'manmenu';
42
		$this->$subActions[$_GET['sa']]();
43
	}
44
45
	function ManageUltimateMenu()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
46
	{
47
		global $context, $txt, $modSettings, $scripturl, $sourcedir, $smcFunc;
48
49
		// Get rid of all of em!
50
		if (!empty($_POST['removeAll']))
51
		{
52
			checkSession();
0 ignored issues
show
Bug introduced by
The function checkSession was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

52
			/** @scrutinizer ignore-call */ 
53
   checkSession();
Loading history...
53
54
			$smcFunc['db_query']('', '
55
				TRUNCATE {db_prefix}um_menu');
56
57
			$this->rebuildMenu();
58
			redirectexit('action=admin;area=umen');
0 ignored issues
show
Bug introduced by
The function redirectexit was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

58
			/** @scrutinizer ignore-call */ 
59
   redirectexit('action=admin;area=umen');
Loading history...
59
		}
60
61
		// User pressed the 'remove selection button'.
62
		if (!empty($_POST['removeButtons']) && !empty($_POST['remove']) && is_array($_POST['remove']))
63
		{
64
			checkSession();
65
66
			// Make sure every entry is a proper integer.
67
			foreach ($_POST['remove'] as $index => $page_id)
68
				$_POST['remove'][(int) $index] = (int) $page_id;
69
70
			// Delete the page!
71
			$smcFunc['db_query']('', '
72
				DELETE FROM {db_prefix}um_menu
73
				WHERE id_button IN ({array_int:button_list})',
74
				array(
75
					'button_list' => $_POST['remove'],
76
				)
77
			);
78
			$this->rebuildMenu();
79
			redirectexit('action=admin;area=umen');
80
		}
81
82
		// Changing the status?
83
		if (isset($_POST['save']))
84
		{
85
			checkSession();
86
			foreach ($this->total_getMenu() as $item)
87
			{
88
				$status = !empty($_POST['status'][$item['id_button']]) ? 'active' : 'inactive';
89
				if ($status != $item['status'])
90
					$smcFunc['db_query']('', '
91
						UPDATE {db_prefix}um_menu
92
						SET status = {string:status}
93
						WHERE id_button = {int:item}',
94
						array(
95
							'status' => $status,
96
							'item' => $item['id_button'],
97
						)
98
					);
99
			}
100
			$this->rebuildMenu();
101
			redirectexit('action=admin;area=umen');
102
		}
103
104
		// New item?
105
		if (isset($_POST['new']))
106
			redirectexit('action=admin;area=umen;sa=addbutton');
107
108
		loadLanguage('ManageBoards');
0 ignored issues
show
Bug introduced by
The function loadLanguage was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

108
		/** @scrutinizer ignore-call */ 
109
  loadLanguage('ManageBoards');
Loading history...
109
		$button_names = $this->getButtonNames();
110
111
		// Our options for our list.
112
		$listOptions = array(
113
			'id' => 'menu_list',
114
			'items_per_page' => 20,
115
			'base_href' => $scripturl . '?action=admin;area=umen;sa=manmenu',
116
			'default_sort_col' => 'name',
117
			'default_sort_dir' => 'desc',
118
			'get_items' => array(
119
				'function' => 'list_getMenu',
120
			),
121
			'get_count' => array(
122
				'function' => 'list_getNumButtons',
123
			),
124
			'no_items_label' => $txt['um_menu_no_buttons'],
125
			'columns' => array(
126
				'name' => array(
127
					'header' => array(
128
						'value' => $txt['um_menu_button_name'],
129
					),
130
					'data' => array(
131
						'db_htmlsafe' => 'name',
132
						'class' => 'centertext',
133
					),
134
					'sort' => array(
135
						'default' => 'name',
136
						'reverse' => 'name DESC',
137
					),
138
				),
139
				'type' => array(
140
					'header' => array(
141
						'value' => $txt['um_menu_button_type'],
142
					),
143
					'data' => array(
144
						'function' => function($rowData) use ($txt)
145
						{
146
							return $txt[$rowData['type'] . '_link'];
147
						},
148
						'class' => 'centertext',
149
					),
150
					'sort' => array(
151
						'default' => 'type',
152
						'reverse' => 'type DESC',
153
					),
154
				),
155
				'poition' => array(
156
					'header' => array(
157
						'value' => $txt['um_menu_button_position'],
158
					),
159
					'data' => array(
160
						'function' => function($rowData) use ($txt, $button_names)
161
						{
162
							return $txt['mboards_order_' . $rowData['position']] . ' ' . (isset($button_names[$rowData['parent']]) ? $button_names[$rowData['parent']] : ucwords($rowData['parent']));
163
						},
164
						'class' => 'centertext',
165
					),
166
					'sort' => array(
167
						'default' => 'position',
168
						'reverse' => 'position DESC',
169
					),
170
				),
171
				'link' => array(
172
					'header' => array(
173
						'value' => $txt['um_menu_button_link'],
174
					),
175
					'data' => array(
176
						'db_htmlsafe' => 'link',
177
						'class' => 'centertext',
178
					),
179
					'sort' => array(
180
						'default' => 'link',
181
						'reverse' => 'link DESC',
182
					),
183
				),
184
				'status' => array(
185
					'header' => array(
186
						'value' => $txt['um_menu_button_active'],
187
					),
188
					'data' => array(
189
						'function' => function($rowData) use ($txt)
0 ignored issues
show
Unused Code introduced by
The import $txt is not used and could be removed.

This check looks for imports that have been defined, but are not used in the scope.

Loading history...
190
						{
191
							return sprintf('<input type="checkbox" name="status[%1$s]" id="status_%1$s" value="%1$s"%2$s />', $rowData['id_button'], $rowData['status'] == 'inactive' ? '' : ' checked="checked"');
192
						},
193
						'class' => 'centertext',
194
					),
195
					'sort' => array(
196
						'default' => 'status',
197
						'reverse' => 'status DESC',
198
					),
199
				),
200
				'actions' => array(
201
					'header' => array(
202
						'value' => $txt['um_menu_actions'],
203
					),
204
					'data' => array(
205
						'sprintf' => array(
206
							'format' => '<a href="' . strtr($scripturl, array('%' => '%%')) . '?action=admin;area=umen;sa=addbutton;edit;in=%1$d">' . $txt['modify'] . '</a>',
207
							'params' => array(
208
								'id_button' => false,
209
							),
210
						),
211
						'class' => 'centertext',
212
					),
213
				),
214
				'check' => array(
215
					'header' => array(
216
						'value' => '<input type="checkbox" onclick="invertAll(this, this.form);" class="input_check" />',
217
					),
218
					'data' => array(
219
						'sprintf' => array(
220
							'format' => '<input type="checkbox" name="remove[]" value="%1$d" class="input_check" />',
221
							'params' => array(
222
								'id_button' => false,
223
							),
224
						),
225
						'class' => 'centertext',
226
					),
227
				),
228
			),
229
			'form' => array(
230
				'href' => $scripturl . '?action=admin;area=umen;sa=manmenu',
231
			),
232
			'additional_rows' => array(
233
				array(
234
					'position' => 'below_table_data',
235
					'value' => '
236
						<input type="submit" name="removeButtons" value="' . $txt['um_menu_remove_selected'] . '" onclick="return confirm(\'' . $txt['um_menu_remove_confirm'] . '\');" class="button_submit" />
237
						<input type="submit" name="removeAll" value="' . $txt['um_menu_remove_all'] . '" onclick="return confirm(\'' . $txt['um_menu_remove_all_confirm'] . '\');" class="button_submit" />
238
						<input type="submit" name="new" value="' . $txt['um_admin_add_button'] . '" class="button_submit" />
239
						<input type="submit" name="save" value="' . $txt['save'] . '" class="button_submit" />',
240
					'class' => 'righttext',
241
				),
242
			),
243
		);
244
245
		require_once($sourcedir . '/Subs-List.php');
246
		createList($listOptions);
0 ignored issues
show
Bug introduced by
The function createList was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

246
		/** @scrutinizer ignore-call */ 
247
  createList($listOptions);
Loading history...
247
248
		$context['sub_template'] = 'show_list';
249
		$context['default_list'] = 'menu_list';
250
	}
251
252
	function SaveButton()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
253
	{
254
		global $context, $smcFunc, $txt, $sourcedir;
255
256
		// It's expected to be present.
257
		$context['user']['unread_messages'] = 0;
258
259
		// Load SMF's default menu context
260
		setupMenuContext();
0 ignored issues
show
Bug introduced by
The function setupMenuContext was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

260
		/** @scrutinizer ignore-call */ 
261
  setupMenuContext();
Loading history...
261
262
		if (isset($_REQUEST['submit']))
263
		{
264
			$post_errors = array();
265
			$required_fields = array(
266
				'name',
267
				'link',
268
				'parent',
269
			);
270
271
			// Make sure we grab all of the content
272
			$id = isset($_REQUEST['in']) ? (int) $_REQUEST['in'] : 0;
273
			$name = isset($_REQUEST['name']) ? $_REQUEST['name'] : '';
274
			$position = isset($_REQUEST['position']) ? $_REQUEST['position'] : 'before';
275
			$type = isset($_REQUEST['type']) ? $_REQUEST['type'] : 'forum';
276
			$link = isset($_REQUEST['link']) ? $_REQUEST['link'] : '';
277
			$permissions = isset($_REQUEST['permissions']) ? implode(',', array_intersect($_REQUEST['permissions'], array_keys(list_groups(-3, 1)))) : '1';
278
			$status = isset($_REQUEST['status']) ? $_REQUEST['status'] : 'active';
279
			$parent = isset($_REQUEST['parent']) ? $_REQUEST['parent'] : 'home';
280
			$target = isset($_REQUEST['target']) ? $_REQUEST['target'] : '_self';
281
282
			// These fields are required!
283
			foreach ($required_fields as $required_field)
284
				if ($_POST[$required_field] == '')
285
					$post_errors[$required_field] = 'um_menu_empty_' . $required_field;
286
287
			// Stop making numeric names!
288
			if (is_numeric($name))
289
				$post_errors['name'] = 'um_menu_numeric';
290
291
			// Let's make sure you're not trying to make a name that's already taken.
292
			$request = $smcFunc['db_query']('', '
293
				SELECT id_button
294
				FROM {db_prefix}um_menu
295
				WHERE name = {string:name}
296
					AND id_button != {int:id}',
297
				array(
298
					'name' => $name,
299
					'id' => $id,
300
				)
301
			);
302
			$check = $smcFunc['db_num_rows']($request);
303
			$smcFunc['db_free_result']($request);
304
305
			if ($check > 0)
306
				$post_errors['name'] = 'um_menu_mysql';
307
308
			if (empty($post_errors))
309
			{
310
				// I see you made it to the final stage, my young padawan.
311
				if (!empty($id))
312
					$smcFunc['db_query']('','
313
						UPDATE {db_prefix}um_menu
314
						SET name = {string:name}, type = {string:type}, target = {string:target}, position = {string:position}, link = {string:link}, status = {string:status}, permissions = {string:permissions}, parent = {string:parent}
315
						WHERE id_button = {int:id}',
316
						array(
317
							'id' => $id,
318
							'name' => $name,
319
							'type' => $type,
320
							'target' => $target,
321
							'position' => $position,
322
							'link' => $link,
323
							'status' => $status,
324
							'permissions' => $permissions,
325
							'parent' => $parent,
326
						)
327
					);
328
				else
329
					$smcFunc['db_insert']('insert',
330
						'{db_prefix}um_menu',
331
							array(
332
								'name' => 'string', 'type' => 'string', 'target' => 'string', 'position' => 'string', 'link' => 'string', 'status' => 'string', 'permissions' => 'string', 'parent' => 'string',
333
							),
334
							array(
335
								$name, $type, $target, $position, $link, $status, $permissions, $parent,
336
							),
337
							array('id_button')
338
						);
339
340
				$this->rebuildMenu();
341
342
				// Before we leave, we must clear the cache. See, SMF
343
				// caches its menu at level 2 or higher.
344
				clean_cache('menu_buttons');
0 ignored issues
show
Bug introduced by
The function clean_cache was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

344
				/** @scrutinizer ignore-call */ 
345
    clean_cache('menu_buttons');
Loading history...
345
346
				redirectexit('action=admin;area=umen');
0 ignored issues
show
Bug introduced by
The function redirectexit was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

346
				/** @scrutinizer ignore-call */ 
347
    redirectexit('action=admin;area=umen');
Loading history...
347
			}
348
			else
349
			{
350
				$context['post_error'] = $post_errors;
351
				$context['error_title'] = empty($id) ? 'um_menu_errors_create' : 'um_menu_errors_modify';
352
353
				$context['button_data'] = array(
354
					'name' => $name,
355
					'type' => $type,
356
					'target' => $target,
357
					'position' => $position,
358
					'link' => $link,
359
					'parent' => $parent,
360
					'permissions' => list_groups($permissions, 1),
361
					'status' => $status,
362
					'id' => $id,
363
				);
364
365
				$context['page_title'] = $txt['um_menu_edit_title'];
366
			}
367
		}
368
	}
369
370
	function PrepareContext()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
371
	{
372
		global $context, $smcFunc, $txt, $sourcedir;
373
374
		// It's expected to be present.
375
		$context['user']['unread_messages'] = 0;
376
377
		// Load SMF's default menu context
378
		setupMenuContext();
0 ignored issues
show
Bug introduced by
The function setupMenuContext was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

378
		/** @scrutinizer ignore-call */ 
379
  setupMenuContext();
Loading history...
379
380
		if (isset($_GET['in']))
381
		{
382
			$request = $smcFunc['db_query']('', '
383
				SELECT name, target, type, position, link, status, permissions, parent
384
				FROM {db_prefix}um_menu
385
				WHERE id_button = {int:button}
386
				LIMIT 1',
387
				array(
388
					'button' => (int) $_GET['in'],
389
				)
390
			);
391
392
			$row = $smcFunc['db_fetch_assoc']($request);
393
394
			$context['button_data'] = array(
395
				'id' => $_GET['in'],
396
				'name' => $row['name'],
397
				'target' => $row['target'],
398
				'type' => $row['type'],
399
				'position' => $row['position'],
400
				'permissions' => list_groups($row['permissions'], 1),
401
				'link' => $row['link'],
402
				'status' => $row['status'],
403
				'parent' => $row['parent'],
404
			);
405
		}
406
		else
407
		{
408
			$context['button_data'] = array(
409
				'name' => '',
410
				'link' => '',
411
				'target' => '_self',
412
				'type' => 'forum',
413
				'position' => 'before',
414
				'status' => 'active',
415
				'permissions' => list_groups('-3', 1),
416
				'parent' => 'home',
417
				'id' => 0,
418
			);
419
420
			$context['page_title'] = $txt['um_menu_add_title'];
421
		}
422
	}
423
424
	function total_getMenu()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
425
	{
426
		global $smcFunc;
427
428
		$request = $smcFunc['db_query']('', '
429
			SELECT id_button, name, target, type, position, link, status, permissions, parent
430
			FROM {db_prefix}um_menu');
431
		$buttons = array();
432
		while ($row = $smcFunc['db_fetch_assoc']($request))
433
			$buttons[] = $row;
434
		$smcFunc['db_free_result']($request);
435
436
		return $buttons;
437
	}
438
439
	function list_getMenu($start, $items_per_page, $sort)
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
440
	{
441
		global $smcFunc;
442
443
		$request = $smcFunc['db_query']('', '
444
			SELECT id_button, name, target, type, position, link, status, permissions, parent
445
			FROM {db_prefix}um_menu
446
			ORDER BY {raw:sort}
447
			LIMIT {int:offset}, {int:limit}',
448
			array(
449
				'sort' => $sort,
450
				'offset' => $start,
451
				'limit' => $items_per_page,
452
			)
453
		);
454
		$buttons = array();
455
		while ($row = $smcFunc['db_fetch_assoc']($request))
456
			$buttons[] = $row;
457
		$smcFunc['db_free_result']($request);
458
459
		return $buttons;
460
	}
461
462
	function list_getNumButtons()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
463
	{
464
		global $smcFunc;
465
466
		$request = $smcFunc['db_query']('', '
467
			SELECT COUNT(*)
468
			FROM {db_prefix}um_menu');
469
		list ($numButtons) = $smcFunc['db_fetch_row']($request);
470
		$smcFunc['db_free_result']($request);
471
472
		return $numButtons;
473
	}
474
475
	function rebuildMenu()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
476
	{
477
		global $smcFunc;
478
479
		$request = $smcFunc['db_query']('', '
480
			SELECT id_button, name, target, type, position, link, status, permissions, parent
481
			FROM {db_prefix}um_menu');
482
483
		$buttons = array();
484
		while ($row = $smcFunc['db_fetch_assoc']($request))
485
			$buttons['um_button_' . $row['id_button']] = json_encode($row);
486
		$smcFunc['db_free_result']($request);
487
		updateSettings(
0 ignored issues
show
Bug introduced by
The function updateSettings was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

487
		/** @scrutinizer ignore-call */ 
488
  updateSettings(
Loading history...
488
			array(
489
				'um_count' => count($buttons),
490
			) + $buttons
491
		);
492
	}
493
494
	function getButtonNames()
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
495
	{
496
		global $context, $smcFunc;
497
498
		// It's expected to be present.
499
		$context['user']['unread_messages'] = 0;
500
501
		// Load SMF's default menu context
502
		setupMenuContext();
0 ignored issues
show
Bug introduced by
The function setupMenuContext was not found. Maybe you did not declare it correctly or list all dependencies? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

502
		/** @scrutinizer ignore-call */ 
503
  setupMenuContext();
Loading history...
503
504
		$button_names = [];
505
		foreach ($context['menu_buttons'] as $buttonIndex => $buttonData)
506
		{
507
			$button_names[$buttonIndex] = $buttonData['title'];
508
509
			if (!empty($buttonData['sub_buttons']))
510
			{
511
				foreach ($buttonData['sub_buttons'] as $childButton => $childButtonData)
512
					$button_names[$childButton] = $childButtonData['title'];
513
514
				if (!empty($childButtonData['sub_buttons']))
515
					foreach ($childButtonData['sub_buttons'] as $grandChildButton => $grandChildButtonData)
516
						$button_names[$grandChildButton] = $grandChildButtonData['title'];
517
			}
518
		}
519
520
		return $button_names;
521
	}
522
}