Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.
Common duplication problems, and corresponding solutions are:
Complex classes like ManageFeatures_Controller often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.
Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.
While breaking up the class, it is a good idea to analyze how other classes use ManageFeatures_Controller, and based on these observations, apply Extract Interface, too.
1 | <?php |
||
24 | class ManageFeatures_Controller extends Action_Controller |
||
25 | { |
||
26 | /** |
||
27 | * Pre Dispatch, called before other methods. |
||
28 | */ |
||
29 | 1 | public function pre_dispatch() |
|
34 | |||
35 | /** |
||
36 | * This function passes control through to the relevant tab. |
||
37 | * |
||
38 | * @event integrate_sa_modify_features Use to add new Configuration tabs |
||
39 | * @see Action_Controller::action_index() |
||
40 | * @uses Help, ManageSettings languages |
||
41 | * @uses sub_template show_settings |
||
42 | */ |
||
43 | public function action_index() |
||
44 | { |
||
45 | global $context, $txt, $settings, $scripturl; |
||
46 | |||
47 | // Often Helpful |
||
48 | theme()->getTemplates()->loadLanguageFile('Help'); |
||
49 | theme()->getTemplates()->loadLanguageFile('ManageSettings'); |
||
50 | theme()->getTemplates()->loadLanguageFile('Mentions'); |
||
51 | |||
52 | // All the actions we know about |
||
53 | $subActions = array( |
||
54 | 'basic' => array( |
||
55 | 'controller' => $this, |
||
56 | 'function' => 'action_basicSettings_display', |
||
57 | 'permission' => 'admin_forum' |
||
58 | ), |
||
59 | 'layout' => array( |
||
60 | 'controller' => $this, |
||
61 | 'function' => 'action_layoutSettings_display', |
||
62 | 'permission' => 'admin_forum' |
||
63 | ), |
||
64 | 'karma' => array( |
||
65 | 'controller' => $this, |
||
66 | 'function' => 'action_karmaSettings_display', |
||
67 | 'enabled' => in_array('k', $context['admin_features']), |
||
68 | 'permission' => 'admin_forum' |
||
69 | ), |
||
70 | 'pmsettings' => array( |
||
71 | 'controller' => $this, |
||
72 | 'function' => 'action_pmsettings', |
||
73 | 'permission' => 'admin_forum' |
||
74 | ), |
||
75 | 'likes' => array( |
||
76 | 'controller' => $this, |
||
77 | 'function' => 'action_likesSettings_display', |
||
78 | 'enabled' => in_array('l', $context['admin_features']), |
||
79 | 'permission' => 'admin_forum' |
||
80 | ), |
||
81 | 'mention' => array( |
||
82 | 'controller' => $this, |
||
83 | 'function' => 'action_notificationsSettings_display', |
||
84 | 'permission' => 'admin_forum' |
||
85 | ), |
||
86 | 'sig' => array( |
||
87 | 'controller' => $this, |
||
88 | 'function' => 'action_signatureSettings_display', |
||
89 | 'permission' => 'admin_forum' |
||
90 | ), |
||
91 | 'profile' => array( |
||
92 | 'controller' => $this, |
||
93 | 'function' => 'action_profile', |
||
94 | 'enabled' => in_array('cp', $context['admin_features']), |
||
95 | 'permission' => 'admin_forum' |
||
96 | ), |
||
97 | 'profileedit' => array( |
||
98 | 'controller' => $this, |
||
99 | 'function' => 'action_profileedit', |
||
100 | 'permission' => 'admin_forum' |
||
101 | ), |
||
102 | ); |
||
103 | |||
104 | // Set up the action control |
||
105 | $action = new Action('modify_features'); |
||
106 | |||
107 | // Load up all the tabs... |
||
108 | $context[$context['admin_menu_name']]['tab_data'] = array( |
||
109 | 'title' => $txt['modSettings_title'], |
||
110 | 'help' => 'featuresettings', |
||
111 | 'description' => sprintf($txt['modSettings_desc'], $scripturl . '?action=admin;area=theme;sa=list;th=' . $settings['theme_id'] . ';' . $context['session_id'] . '=' . $context['session_var']), |
||
112 | 'tabs' => array( |
||
113 | 'basic' => array( |
||
114 | ), |
||
115 | 'layout' => array( |
||
116 | ), |
||
117 | 'pmsettings' => array( |
||
118 | ), |
||
119 | 'karma' => array( |
||
120 | ), |
||
121 | 'likes' => array( |
||
122 | ), |
||
123 | 'mention' => array( |
||
124 | 'description' => $txt['mentions_settings_desc'], |
||
125 | ), |
||
126 | 'sig' => array( |
||
127 | 'description' => $txt['signature_settings_desc'], |
||
128 | ), |
||
129 | 'profile' => array( |
||
130 | 'description' => $txt['custom_profile_desc'], |
||
131 | ), |
||
132 | ), |
||
133 | ); |
||
134 | |||
135 | // By default do the basic settings, call integrate_sa_modify_features |
||
136 | $subAction = $action->initialize($subActions, 'basic'); |
||
137 | |||
138 | // Some final pieces for the template |
||
139 | $context['sub_template'] = 'show_settings'; |
||
140 | $context['sub_action'] = $subAction; |
||
141 | $context['page_title'] = $txt['modSettings_title']; |
||
142 | |||
143 | // Call the right function for this sub-action. |
||
144 | $action->dispatch($subAction); |
||
145 | } |
||
146 | |||
147 | /** |
||
148 | * Config array for changing the basic forum settings |
||
149 | * |
||
150 | * - Accessed from ?action=admin;area=featuresettings;sa=basic; |
||
151 | * |
||
152 | * @event integrate_save_basic_settings |
||
153 | */ |
||
154 | public function action_basicSettings_display() |
||
155 | { |
||
156 | global $txt, $scripturl, $context; |
||
157 | |||
158 | // Initialize the form |
||
159 | $settingsForm = new Settings_Form(Settings_Form::DB_ADAPTER); |
||
160 | |||
161 | // Initialize it with our settings |
||
162 | $settingsForm->setConfigVars($this->_basicSettings()); |
||
163 | |||
164 | // Saving? |
||
165 | if (isset($this->_req->query->save)) |
||
166 | { |
||
167 | checkSession(); |
||
168 | |||
169 | // Prevent absurd boundaries here - make it a day tops. |
||
170 | if (isset($this->_req->post->lastActive)) |
||
171 | $this->_req->post->lastActive = min((int) $this->_req->post->lastActive, 1440); |
||
172 | |||
173 | call_integration_hook('integrate_save_basic_settings'); |
||
174 | |||
175 | $settingsForm->setConfigValues((array) $this->_req->post); |
||
176 | $settingsForm->save(); |
||
177 | |||
178 | writeLog(); |
||
179 | redirectexit('action=admin;area=featuresettings;sa=basic'); |
||
180 | } |
||
181 | if (isset($this->_req->post->cleanhives)) |
||
182 | { |
||
183 | $clean_hives_result = theme()->cleanHives(); |
||
184 | |||
185 | theme()->getLayers()->removeAll(); |
||
186 | theme()->getTemplates()->load('Json'); |
||
187 | theme()->addJavascriptVar(array('txt_invalid_response' => $txt['ajax_bad_response']), true); |
||
188 | $context['sub_template'] = 'send_json'; |
||
189 | $context['json_data'] = array( |
||
190 | 'success' => $clean_hives_result, |
||
191 | 'response' => $clean_hives_result ? $txt['clean_hives_sucess'] : $txt['clean_hives_failed'] |
||
192 | ); |
||
193 | return; |
||
194 | } |
||
195 | |||
196 | $context['post_url'] = $scripturl . '?action=admin;area=featuresettings;save;sa=basic'; |
||
197 | $context['settings_title'] = $txt['mods_cat_features']; |
||
198 | |||
199 | // Show / hide custom jquery fields as required |
||
200 | theme()->addInlineJavascript('showhideJqueryOptions();', true); |
||
201 | |||
202 | $settingsForm->prepare(); |
||
203 | } |
||
204 | |||
205 | /** |
||
206 | * Allows modifying the global layout settings in the forum |
||
207 | * |
||
208 | * - Accessed through ?action=admin;area=featuresettings;sa=layout; |
||
209 | * |
||
210 | * @event integrate_save_layout_settings |
||
211 | */ |
||
212 | public function action_layoutSettings_display() |
||
213 | { |
||
214 | global $txt, $scripturl, $context, $modSettings; |
||
215 | |||
216 | // Initialize the form |
||
217 | $settingsForm = new Settings_Form(Settings_Form::DB_ADAPTER); |
||
218 | |||
219 | // Initialize it with our settings |
||
220 | $settingsForm->setConfigVars($this->_layoutSettings()); |
||
221 | |||
222 | // Saving? |
||
223 | if (isset($this->_req->query->save)) |
||
224 | { |
||
225 | // Setting a custom frontpage, set the hook to the FrontpageInterface of the controller |
||
226 | if (!empty($this->_req->post->front_page)) |
||
227 | { |
||
228 | $front_page = (string) $this->_req->post->front_page; |
||
229 | if ( |
||
230 | is_callable(array($modSettings['front_page'], 'validateFrontPageOptions')) |
||
231 | && !$front_page::validateFrontPageOptions($this->_req->post) |
||
232 | ) { |
||
233 | $this->_req->post->front_page = ''; |
||
234 | } |
||
235 | } |
||
236 | |||
237 | checkSession(); |
||
238 | |||
239 | call_integration_hook('integrate_save_layout_settings'); |
||
240 | |||
241 | $settingsForm->setConfigValues((array) $this->_req->post); |
||
242 | $settingsForm->save(); |
||
243 | writeLog(); |
||
244 | |||
245 | redirectexit('action=admin;area=featuresettings;sa=layout'); |
||
246 | } |
||
247 | |||
248 | $context['post_url'] = $scripturl . '?action=admin;area=featuresettings;save;sa=layout'; |
||
249 | $context['settings_title'] = $txt['mods_cat_layout']; |
||
250 | |||
251 | $settingsForm->prepare(); |
||
252 | } |
||
253 | |||
254 | /** |
||
255 | * Display configuration settings page for karma settings. |
||
256 | * |
||
257 | * - Accessed from ?action=admin;area=featuresettings;sa=karma; |
||
258 | * |
||
259 | * @event integrate_save_karma_settings |
||
260 | */ |
||
261 | View Code Duplication | public function action_karmaSettings_display() |
|
288 | |||
289 | /** |
||
290 | * Display configuration settings page for likes settings. |
||
291 | * |
||
292 | * - Accessed from ?action=admin;area=featuresettings;sa=likes; |
||
293 | * |
||
294 | * @event integrate_save_likes_settings |
||
295 | */ |
||
296 | View Code Duplication | public function action_likesSettings_display() |
|
323 | |||
324 | /** |
||
325 | * Initializes the mentions settings admin page. |
||
326 | * |
||
327 | * - Accessed from ?action=admin;area=featuresettings;sa=mention; |
||
328 | * |
||
329 | * @event integrate_save_modify_mention_settings |
||
330 | */ |
||
331 | public function action_notificationsSettings_display() |
||
332 | { |
||
333 | global $txt, $context, $scripturl, $modSettings; |
||
334 | |||
335 | theme()->getTemplates()->loadLanguageFile('Mentions'); |
||
336 | |||
337 | // Instantiate the form |
||
338 | $settingsForm = new Settings_Form(Settings_Form::DB_ADAPTER); |
||
339 | |||
340 | // Initialize it with our settings |
||
341 | $settingsForm->setConfigVars($this->_notificationsSettings()); |
||
342 | |||
343 | // Some context stuff |
||
344 | $context['page_title'] = $txt['mentions_settings']; |
||
345 | $context['sub_template'] = 'show_settings'; |
||
346 | |||
347 | // Saving the settings? |
||
348 | if (isset($this->_req->query->save)) |
||
349 | { |
||
350 | checkSession(); |
||
351 | |||
352 | call_integration_hook('integrate_save_modify_mention_settings'); |
||
353 | |||
354 | if (!empty($this->_req->post->mentions_enabled)) |
||
355 | { |
||
356 | enableModules('mentions', array('post', 'display')); |
||
357 | } |
||
358 | else |
||
359 | { |
||
360 | disableModules('mentions', array('post', 'display')); |
||
361 | } |
||
362 | |||
363 | if (empty($this->_req->post->notifications)) |
||
364 | { |
||
365 | $notification_methods = serialize(array()); |
||
366 | } |
||
367 | else |
||
368 | { |
||
369 | $notification_methods = serialize($this->_req->post->notifications); |
||
370 | } |
||
371 | |||
372 | require_once(SUBSDIR . '/Mentions.subs.php'); |
||
373 | $enabled_mentions = array(); |
||
374 | $current_settings = unserialize($modSettings['notification_methods']); |
||
375 | |||
376 | // Fist hide what was visible |
||
377 | $modules_toggle = array('enable' => array(), 'disable' => array()); |
||
378 | View Code Duplication | foreach ($current_settings as $type => $val) |
|
379 | { |
||
380 | if (!isset($this->_req->post->notifications[$type])) |
||
381 | { |
||
382 | toggleMentionsVisibility($type, false); |
||
383 | $modules_toggle['disable'][] = $type; |
||
384 | } |
||
385 | } |
||
386 | |||
387 | // Then make visible what was hidden, but only if there is anything |
||
388 | if (!empty($this->_req->post->notifications)) |
||
389 | { |
||
390 | View Code Duplication | foreach ($this->_req->post->notifications as $type => $val) |
|
391 | { |
||
392 | if (!isset($current_settings[$type])) |
||
393 | { |
||
394 | toggleMentionsVisibility($type, true); |
||
395 | $modules_toggle['enable'][] = $type; |
||
396 | } |
||
397 | } |
||
398 | |||
399 | $enabled_mentions = array_keys($this->_req->post->notifications); |
||
400 | } |
||
401 | |||
402 | // Let's just keep it active, there are too many reasons it should be. |
||
403 | require_once(SUBSDIR . '/ScheduledTasks.subs.php'); |
||
404 | toggleTaskStatusByName('user_access_mentions', true); |
||
405 | |||
406 | // Disable or enable modules as needed |
||
407 | foreach ($modules_toggle as $action => $toggles) |
||
408 | { |
||
409 | if (!empty($toggles)) |
||
410 | { |
||
411 | // The modules associated with the notification (mentionmem, likes, etc) area |
||
412 | $modules = getMentionsModules($toggles); |
||
413 | |||
414 | // The action will either be enable to disable |
||
415 | $function = $action . 'Modules'; |
||
416 | |||
417 | // Something like enableModule('mentions', array('post', 'display'); |
||
418 | foreach ($modules as $key => $val) |
||
419 | $function($key, $val); |
||
420 | } |
||
421 | } |
||
422 | |||
423 | updateSettings(array('enabled_mentions' => implode(',', array_unique($enabled_mentions)), 'notification_methods' => $notification_methods)); |
||
424 | $settingsForm->setConfigValues((array) $this->_req->post); |
||
425 | $settingsForm->save(); |
||
426 | redirectexit('action=admin;area=featuresettings;sa=mention'); |
||
427 | } |
||
428 | |||
429 | // Prepare the settings for display |
||
430 | $context['post_url'] = $scripturl . '?action=admin;area=featuresettings;save;sa=mention'; |
||
431 | $settingsForm->prepare(); |
||
432 | } |
||
433 | |||
434 | /** |
||
435 | * Display configuration settings for signatures on forum. |
||
436 | * |
||
437 | * - Accessed from ?action=admin;area=featuresettings;sa=sig; |
||
438 | * |
||
439 | * @event integrate_save_signature_settings |
||
440 | */ |
||
441 | public function action_signatureSettings_display() |
||
442 | { |
||
443 | global $context, $txt, $modSettings, $sig_start, $scripturl; |
||
444 | |||
445 | // Initialize the form |
||
446 | $settingsForm = new Settings_Form(Settings_Form::DB_ADAPTER); |
||
447 | |||
448 | // Initialize it with our settings |
||
449 | $settingsForm->setConfigVars($this->_signatureSettings()); |
||
450 | |||
451 | // Setup the template. |
||
452 | $context['page_title'] = $txt['signature_settings']; |
||
453 | $context['sub_template'] = 'show_settings'; |
||
454 | |||
455 | // Disable the max smileys option if we don't allow smileys at all! |
||
456 | theme()->addInlineJavascript(' |
||
457 | document.getElementById(\'signature_max_smileys\').disabled = !document.getElementById(\'signature_allow_smileys\').checked;', true); |
||
458 | |||
459 | // Load all the signature settings. |
||
460 | list ($sig_limits, $sig_bbc) = explode(':', $modSettings['signature_settings']); |
||
461 | $sig_limits = explode(',', $sig_limits); |
||
462 | $disabledTags = !empty($sig_bbc) ? explode(',', $sig_bbc) : array(); |
||
463 | |||
464 | // @todo temporary since it does not work, and seriously why would you do this? |
||
465 | $disabledTags[] = 'footnote'; |
||
466 | |||
467 | // Applying to ALL signatures?!! |
||
468 | if (isset($this->_req->query->apply)) |
||
469 | { |
||
470 | // Security! |
||
471 | checkSession('get'); |
||
472 | |||
473 | $sig_start = time(); |
||
474 | |||
475 | // This is horrid - but I suppose some people will want the option to do it. |
||
476 | $applied_sigs = $this->_req->getQuery('step', 'intval', 0); |
||
477 | updateAllSignatures($applied_sigs); |
||
478 | |||
479 | $settings_applied = true; |
||
480 | } |
||
481 | |||
482 | $context['signature_settings'] = array( |
||
483 | 'enable' => isset($sig_limits[0]) ? $sig_limits[0] : 0, |
||
484 | 'max_length' => isset($sig_limits[1]) ? $sig_limits[1] : 0, |
||
485 | 'max_lines' => isset($sig_limits[2]) ? $sig_limits[2] : 0, |
||
486 | 'max_images' => isset($sig_limits[3]) ? $sig_limits[3] : 0, |
||
487 | 'allow_smileys' => isset($sig_limits[4]) && $sig_limits[4] == -1 ? 0 : 1, |
||
488 | 'max_smileys' => isset($sig_limits[4]) && $sig_limits[4] != -1 ? $sig_limits[4] : 0, |
||
489 | 'max_image_width' => isset($sig_limits[5]) ? $sig_limits[5] : 0, |
||
490 | 'max_image_height' => isset($sig_limits[6]) ? $sig_limits[6] : 0, |
||
491 | 'max_font_size' => isset($sig_limits[7]) ? $sig_limits[7] : 0, |
||
492 | 'repetition_guests' => isset($sig_limits[8]) ? $sig_limits[8] : 0, |
||
493 | 'repetition_members' => isset($sig_limits[9]) ? $sig_limits[9] : 0, |
||
494 | ); |
||
495 | |||
496 | // Temporarily make each setting a modSetting! |
||
497 | foreach ($context['signature_settings'] as $key => $value) |
||
498 | $modSettings['signature_' . $key] = $value; |
||
499 | |||
500 | // Make sure we check the right tags! |
||
501 | $modSettings['bbc_disabled_signature_bbc'] = $disabledTags; |
||
502 | |||
503 | // Saving? |
||
504 | if (isset($this->_req->query->save)) |
||
505 | { |
||
506 | checkSession(); |
||
507 | |||
508 | // Clean up the tag stuff! |
||
509 | $codes = \BBC\ParserWrapper::instance()->getCodes(); |
||
510 | $bbcTags = $codes->getTags(); |
||
511 | |||
512 | View Code Duplication | if (!isset($this->_req->post->signature_bbc_enabledTags)) |
|
513 | $this->_req->post->signature_bbc_enabledTags = array(); |
||
514 | elseif (!is_array($this->_req->post->signature_bbc_enabledTags)) |
||
515 | $this->_req->post->signature_bbc_enabledTags = array($this->_req->post->signature_bbc_enabledTags); |
||
516 | |||
517 | $sig_limits = array(); |
||
518 | foreach ($context['signature_settings'] as $key => $value) |
||
519 | { |
||
520 | if ($key == 'allow_smileys') |
||
521 | continue; |
||
522 | elseif ($key == 'max_smileys' && empty($this->_req->post->signature_allow_smileys)) |
||
523 | $sig_limits[] = -1; |
||
524 | else |
||
525 | { |
||
526 | $current_key = $this->_req->getPost('signature_' . $key, 'intval'); |
||
527 | $sig_limits[] = !empty($current_key) ? max(1, $current_key) : 0; |
||
528 | } |
||
529 | } |
||
530 | |||
531 | call_integration_hook('integrate_save_signature_settings', array(&$sig_limits, &$bbcTags)); |
||
532 | |||
533 | $this->_req->post->signature_settings = implode(',', $sig_limits) . ':' . implode(',', array_diff($bbcTags, $this->_req->post->signature_bbc_enabledTags)); |
||
534 | |||
535 | // Even though we have practically no settings let's keep the convention going! |
||
536 | $save_vars = array(); |
||
537 | $save_vars[] = array('text', 'signature_settings'); |
||
538 | |||
539 | $settingsForm->setConfigVars($save_vars); |
||
540 | $settingsForm->setConfigValues((array) $this->_req->post); |
||
541 | $settingsForm->save(); |
||
542 | redirectexit('action=admin;area=featuresettings;sa=sig'); |
||
543 | } |
||
544 | |||
545 | $context['post_url'] = $scripturl . '?action=admin;area=featuresettings;save;sa=sig'; |
||
546 | $context['settings_title'] = $txt['signature_settings']; |
||
547 | $context['settings_message'] = !empty($settings_applied) ? $txt['signature_settings_applied'] : sprintf($txt['signature_settings_warning'], $scripturl . '?action=admin;area=featuresettings;sa=sig;apply;' . $context['session_var'] . '=' . $context['session_id']); |
||
548 | |||
549 | $settingsForm->prepare(); |
||
550 | } |
||
551 | |||
552 | /** |
||
553 | * Show all the custom profile fields available to the user. |
||
554 | * |
||
555 | * - Allows for drag/drop sorting of custom profile fields |
||
556 | * - Accessed with ?action=admin;area=featuresettings;sa=profile |
||
557 | * |
||
558 | * @uses sub template show_custom_profile |
||
559 | */ |
||
560 | public function action_profile() |
||
561 | { |
||
562 | global $txt, $scripturl, $context; |
||
563 | |||
564 | theme()->getTemplates()->load('ManageFeatures'); |
||
565 | $context['page_title'] = $txt['custom_profile_title']; |
||
566 | $context['sub_template'] = 'show_custom_profile'; |
||
567 | |||
568 | // What about standard fields they can tweak? |
||
569 | $standard_fields = array('website', 'posts', 'warning_status', 'date_registered'); |
||
570 | |||
571 | // What fields can't you put on the registration page? |
||
572 | $context['fields_no_registration'] = array('posts', 'warning_status', 'date_registered'); |
||
573 | |||
574 | // Are we saving any standard field changes? |
||
575 | if (isset($this->_req->post->save)) |
||
576 | { |
||
577 | checkSession(); |
||
578 | validateToken('admin-scp'); |
||
579 | |||
580 | $changes = array(); |
||
581 | |||
582 | // Do the active ones first. |
||
583 | $disable_fields = array_flip($standard_fields); |
||
584 | if (!empty($this->_req->post->active)) |
||
585 | { |
||
586 | foreach ($this->_req->post->active as $value) |
||
587 | { |
||
588 | if (isset($disable_fields[$value])) |
||
589 | { |
||
590 | unset($disable_fields[$value]); |
||
591 | } |
||
592 | } |
||
593 | } |
||
594 | |||
595 | // What we have left! |
||
596 | $changes['disabled_profile_fields'] = empty($disable_fields) ? '' : implode(',', array_keys($disable_fields)); |
||
597 | |||
598 | // Things we want to show on registration? |
||
599 | $reg_fields = array(); |
||
600 | if (!empty($this->_req->post->reg)) |
||
601 | { |
||
602 | foreach ($this->_req->post->reg as $value) |
||
603 | { |
||
604 | if (in_array($value, $standard_fields) && !isset($disable_fields[$value])) |
||
605 | $reg_fields[] = $value; |
||
606 | } |
||
607 | } |
||
608 | |||
609 | // What we have left! |
||
610 | $changes['registration_fields'] = empty($reg_fields) ? '' : implode(',', $reg_fields); |
||
611 | |||
612 | if (!empty($changes)) |
||
613 | updateSettings($changes); |
||
614 | } |
||
615 | |||
616 | createToken('admin-scp'); |
||
617 | |||
618 | // Create a listing for all our standard fields |
||
619 | $listOptions = array( |
||
620 | 'id' => 'standard_profile_fields', |
||
621 | 'title' => $txt['standard_profile_title'], |
||
622 | 'base_href' => $scripturl . '?action=admin;area=featuresettings;sa=profile', |
||
623 | 'get_items' => array( |
||
624 | 'function' => 'list_getProfileFields', |
||
625 | 'params' => array( |
||
626 | true, |
||
627 | ), |
||
628 | ), |
||
629 | 'columns' => array( |
||
630 | 'field' => array( |
||
631 | 'header' => array( |
||
632 | 'value' => $txt['standard_profile_field'], |
||
633 | ), |
||
634 | 'data' => array( |
||
635 | 'db' => 'label', |
||
636 | 'style' => 'width: 60%;', |
||
637 | ), |
||
638 | ), |
||
639 | 'active' => array( |
||
640 | 'header' => array( |
||
641 | 'value' => $txt['custom_edit_active'], |
||
642 | 'class' => 'centertext', |
||
643 | ), |
||
644 | 'data' => array( |
||
645 | View Code Duplication | 'function' => function ($rowData) { |
|
646 | $isChecked = $rowData['disabled'] ? '' : ' checked="checked"'; |
||
647 | $onClickHandler = $rowData['can_show_register'] ? sprintf('onclick="document.getElementById(\'reg_%1$s\').disabled = !this.checked;"', $rowData['id']) : ''; |
||
648 | return sprintf('<input type="checkbox" name="active[]" id="active_%1$s" value="%1$s" class="input_check" %2$s %3$s />', $rowData['id'], $isChecked, $onClickHandler); |
||
649 | }, |
||
650 | 'style' => 'width: 20%;', |
||
651 | 'class' => 'centertext', |
||
652 | ), |
||
653 | ), |
||
654 | 'show_on_registration' => array( |
||
655 | 'header' => array( |
||
656 | 'value' => $txt['custom_edit_registration'], |
||
657 | 'class' => 'centertext', |
||
658 | ), |
||
659 | 'data' => array( |
||
660 | View Code Duplication | 'function' => function ($rowData) { |
|
661 | $isChecked = $rowData['on_register'] && !$rowData['disabled'] ? ' checked="checked"' : ''; |
||
662 | $isDisabled = $rowData['can_show_register'] ? '' : ' disabled="disabled"'; |
||
663 | return sprintf('<input type="checkbox" name="reg[]" id="reg_%1$s" value="%1$s" class="input_check" %2$s %3$s />', $rowData['id'], $isChecked, $isDisabled); |
||
664 | }, |
||
665 | 'style' => 'width: 20%;', |
||
666 | 'class' => 'centertext', |
||
667 | ), |
||
668 | ), |
||
669 | ), |
||
670 | 'form' => array( |
||
671 | 'href' => $scripturl . '?action=admin;area=featuresettings;sa=profile', |
||
672 | 'name' => 'standardProfileFields', |
||
673 | 'token' => 'admin-scp', |
||
674 | ), |
||
675 | 'additional_rows' => array( |
||
676 | array( |
||
677 | 'position' => 'below_table_data', |
||
678 | 'value' => '<input type="submit" name="save" value="' . $txt['save'] . '" class="right_submit" />', |
||
679 | ), |
||
680 | ), |
||
681 | ); |
||
682 | createList($listOptions); |
||
683 | |||
684 | // And now we do the same for all of our custom ones |
||
685 | $token = createToken('admin-sort'); |
||
686 | $listOptions = array( |
||
687 | 'id' => 'custom_profile_fields', |
||
688 | 'title' => $txt['custom_profile_title'], |
||
689 | 'base_href' => $scripturl . '?action=admin;area=featuresettings;sa=profile', |
||
690 | 'default_sort_col' => 'vieworder', |
||
691 | 'no_items_label' => $txt['custom_profile_none'], |
||
692 | 'items_per_page' => 25, |
||
693 | 'sortable' => true, |
||
694 | 'get_items' => array( |
||
695 | 'function' => 'list_getProfileFields', |
||
696 | 'params' => array( |
||
697 | false, |
||
698 | ), |
||
699 | ), |
||
700 | 'get_count' => array( |
||
701 | 'function' => 'list_getProfileFieldSize', |
||
702 | ), |
||
703 | 'columns' => array( |
||
704 | 'vieworder' => array( |
||
705 | 'header' => array( |
||
706 | 'value' => '', |
||
707 | 'class' => 'hide', |
||
708 | ), |
||
709 | 'data' => array( |
||
710 | 'db' => 'vieworder', |
||
711 | 'class' => 'hide', |
||
712 | ), |
||
713 | 'sort' => array( |
||
714 | 'default' => 'vieworder', |
||
715 | ), |
||
716 | ), |
||
717 | 'field_name' => array( |
||
718 | 'header' => array( |
||
719 | 'value' => $txt['custom_profile_fieldname'], |
||
720 | ), |
||
721 | 'data' => array( |
||
722 | 'function' => function ($rowData) { |
||
723 | global $scripturl; |
||
724 | |||
725 | return sprintf('<a href="%1$s?action=admin;area=featuresettings;sa=profileedit;fid=%2$d">%3$s</a><div class="smalltext">%4$s</div>', $scripturl, $rowData['id_field'], $rowData['field_name'], $rowData['field_desc']); |
||
726 | }, |
||
727 | 'style' => 'width: 65%;', |
||
728 | ), |
||
729 | 'sort' => array( |
||
730 | 'default' => 'field_name', |
||
731 | 'reverse' => 'field_name DESC', |
||
732 | ), |
||
733 | ), |
||
734 | 'field_type' => array( |
||
735 | 'header' => array( |
||
736 | 'value' => $txt['custom_profile_fieldtype'], |
||
737 | ), |
||
738 | 'data' => array( |
||
739 | 'function' => function ($rowData) { |
||
740 | global $txt; |
||
741 | |||
742 | $textKey = sprintf('custom_profile_type_%1$s', $rowData['field_type']); |
||
743 | return isset($txt[$textKey]) ? $txt[$textKey] : $textKey; |
||
744 | }, |
||
745 | 'style' => 'width: 10%;', |
||
746 | ), |
||
747 | 'sort' => array( |
||
748 | 'default' => 'field_type', |
||
749 | 'reverse' => 'field_type DESC', |
||
750 | ), |
||
751 | ), |
||
752 | 'cust' => array( |
||
753 | 'header' => array( |
||
754 | 'value' => $txt['custom_profile_active'], |
||
755 | 'class' => 'centertext', |
||
756 | ), |
||
757 | 'data' => array( |
||
758 | 'function' => function ($rowData) { |
||
759 | $isChecked = $rowData['active'] ? ' checked="checked"' : ''; |
||
760 | return sprintf('<input type="checkbox" name="cust[]" id="cust_%1$s" value="%1$s" class="input_check"%2$s />', $rowData['id_field'], $isChecked); |
||
761 | }, |
||
762 | 'style' => 'width: 8%;', |
||
763 | 'class' => 'centertext', |
||
764 | ), |
||
765 | 'sort' => array( |
||
766 | 'default' => 'active DESC', |
||
767 | 'reverse' => 'active', |
||
768 | ), |
||
769 | ), |
||
770 | 'placement' => array( |
||
771 | 'header' => array( |
||
772 | 'value' => $txt['custom_profile_placement'], |
||
773 | ), |
||
774 | 'data' => array( |
||
775 | 'function' => function ($rowData) { |
||
776 | global $txt; |
||
777 | $placement = 'custom_profile_placement_'; |
||
778 | |||
779 | switch ((int) $rowData['placement']) |
||
780 | { |
||
781 | case 0: |
||
782 | $placement .= 'standard'; |
||
783 | break; |
||
784 | case 1: |
||
785 | $placement .= 'withicons'; |
||
786 | break; |
||
787 | case 2: |
||
788 | $placement .= 'abovesignature'; |
||
789 | break; |
||
790 | case 3: |
||
791 | $placement .= 'aboveicons'; |
||
792 | break; |
||
793 | } |
||
794 | |||
795 | return $txt[$placement]; |
||
796 | }, |
||
797 | 'style' => 'width: 5%;', |
||
798 | ), |
||
799 | 'sort' => array( |
||
800 | 'default' => 'placement DESC', |
||
801 | 'reverse' => 'placement', |
||
802 | ), |
||
803 | ), |
||
804 | 'show_on_registration' => array( |
||
805 | 'data' => array( |
||
806 | 'sprintf' => array( |
||
807 | 'format' => '<a href="' . $scripturl . '?action=admin;area=featuresettings;sa=profileedit;fid=%1$s">' . $txt['modify'] . '</a>', |
||
808 | 'params' => array( |
||
809 | 'id_field' => false, |
||
810 | ), |
||
811 | ), |
||
812 | 'style' => 'width: 5%;', |
||
813 | ), |
||
814 | ), |
||
815 | ), |
||
816 | 'form' => array( |
||
817 | 'href' => $scripturl . '?action=admin;area=featuresettings;sa=profileedit', |
||
818 | 'name' => 'customProfileFields', |
||
819 | 'token' => 'admin-scp', |
||
820 | ), |
||
821 | 'additional_rows' => array( |
||
822 | array( |
||
823 | 'class' => 'submitbutton', |
||
824 | 'position' => 'below_table_data', |
||
825 | 'value' => '<input type="submit" name="onoff" value="' . $txt['save'] . '" class="right_submit" /> |
||
826 | <input type="submit" name="new" value="' . $txt['custom_profile_make_new'] . '" class="right_submit" />', |
||
827 | ), |
||
828 | array( |
||
829 | 'position' => 'top_of_list', |
||
830 | 'value' => '<p class="infobox">' . $txt['custom_profile_sort'] . '</p>', |
||
831 | ), |
||
832 | ), |
||
833 | 'javascript' => ' |
||
834 | $().elkSortable({ |
||
835 | sa: "profileorder", |
||
836 | error: "' . $txt['admin_order_error'] . '", |
||
837 | title: "' . $txt['admin_order_title'] . '", |
||
838 | placeholder: "ui-state-highlight", |
||
839 | href: "?action=admin;area=featuresettings;sa=profile", |
||
840 | token: {token_var: "' . $token['admin-sort_token_var'] . '", token_id: "' . $token['admin-sort_token'] . '"} |
||
841 | }); |
||
842 | ', |
||
843 | ); |
||
844 | |||
845 | createList($listOptions); |
||
846 | } |
||
847 | |||
848 | /** |
||
849 | * Edit some profile fields? |
||
850 | * |
||
851 | * - Accessed with ?action=admin;area=featuresettings;sa=profileedit |
||
852 | * |
||
853 | * @uses sub template edit_profile_field |
||
854 | */ |
||
855 | public function action_profileedit() |
||
856 | { |
||
857 | global $txt, $scripturl, $context; |
||
858 | |||
859 | theme()->getTemplates()->load('ManageFeatures'); |
||
860 | |||
861 | // Sort out the context! |
||
862 | $context['fid'] = $this->_req->getQuery('fid', 'intval', 0); |
||
863 | $context[$context['admin_menu_name']]['current_subsection'] = 'profile'; |
||
864 | $context['page_title'] = $context['fid'] ? $txt['custom_edit_title'] : $txt['custom_add_title']; |
||
865 | $context['sub_template'] = 'edit_profile_field'; |
||
866 | |||
867 | // Any errors messages to show? |
||
868 | if (isset($this->_req->query->msg)) |
||
869 | { |
||
870 | theme()->getTemplates()->loadLanguageFile('Errors'); |
||
871 | |||
872 | if (isset($txt['custom_option_' . $this->_req->query->msg])) |
||
873 | $context['custom_option__error'] = $txt['custom_option_' . $this->_req->query->msg]; |
||
874 | } |
||
875 | |||
876 | // Load the profile language for section names. |
||
877 | theme()->getTemplates()->loadLanguageFile('Profile'); |
||
878 | |||
879 | // Load up the profile field, if one was supplied |
||
880 | if ($context['fid']) |
||
881 | $context['field'] = getProfileField($context['fid']); |
||
882 | |||
883 | // Setup the default values as needed. |
||
884 | if (empty($context['field'])) |
||
885 | $context['field'] = array( |
||
886 | 'name' => '', |
||
887 | 'colname' => '???', |
||
888 | 'desc' => '', |
||
889 | 'profile_area' => 'forumprofile', |
||
890 | 'reg' => false, |
||
891 | 'display' => false, |
||
892 | 'memberlist' => false, |
||
893 | 'type' => 'text', |
||
894 | 'max_length' => 255, |
||
895 | 'rows' => 4, |
||
896 | 'cols' => 30, |
||
897 | 'bbc' => false, |
||
898 | 'default_check' => false, |
||
899 | 'default_select' => '', |
||
900 | 'default_value' => '', |
||
901 | 'options' => array('', '', ''), |
||
902 | 'active' => true, |
||
903 | 'private' => false, |
||
904 | 'can_search' => false, |
||
905 | 'mask' => 'nohtml', |
||
906 | 'regex' => '', |
||
907 | 'enclose' => '', |
||
908 | 'placement' => 0, |
||
909 | ); |
||
910 | |||
911 | // All the javascript for this page... everything else is in admin.js |
||
912 | theme()->addJavascriptVar(array('startOptID' => count($context['field']['options']))); |
||
913 | theme()->addInlineJavascript('updateInputBoxes();', true); |
||
914 | |||
915 | // Are we toggling which ones are active? |
||
916 | if (isset($this->_req->post->onoff)) |
||
917 | { |
||
918 | checkSession(); |
||
919 | validateToken('admin-scp'); |
||
920 | |||
921 | // Enable and disable custom fields as required. |
||
922 | $enabled = array(0); |
||
923 | if(isset($this->_req->post->cust) && is_array($this->_req->post->cust)) { |
||
924 | foreach ($this->_req->post->cust as $id) |
||
925 | $enabled[] = (int) $id; |
||
926 | } |
||
927 | |||
928 | updateRenamedProfileStatus($enabled); |
||
929 | } |
||
930 | // Are we saving? |
||
931 | elseif (isset($this->_req->post->save)) |
||
932 | { |
||
933 | checkSession(); |
||
934 | validateToken('admin-ecp'); |
||
935 | |||
936 | // Everyone needs a name - even the (bracket) unknown... |
||
937 | if (trim($this->_req->post->field_name) == '') |
||
938 | redirectexit($scripturl . '?action=admin;area=featuresettings;sa=profileedit;fid=' . $this->_req->query->fid . ';msg=need_name'); |
||
939 | |||
940 | // Regex you say? Do a very basic test to see if the pattern is valid |
||
941 | if (!empty($this->_req->post->regex) && @preg_match($this->_req->post->regex, 'dummy') === false) |
||
942 | redirectexit($scripturl . '?action=admin;area=featuresettings;sa=profileedit;fid=' . $this->_req->query->fid . ';msg=regex_error'); |
||
943 | |||
944 | $this->_req->post->field_name = $this->_req->getPost('field_name', 'Util::htmlspecialchars'); |
||
945 | $this->_req->post->field_desc = $this->_req->getPost('field_desc', 'Util::htmlspecialchars'); |
||
946 | |||
947 | $rows = isset($this->_req->post->rows) ? (int) $this->_req->post->rows : 4; |
||
948 | $cols = isset($this->_req->post->cols) ? (int) $this->_req->post->cols : 30; |
||
949 | |||
950 | // Checkboxes... |
||
951 | $show_reg = $this->_req->getPost('reg', 'intval', 0); |
||
952 | $show_display = isset($this->_req->post->display) ? 1 : 0; |
||
953 | $show_memberlist = isset($this->_req->post->memberlist) ? 1 : 0; |
||
954 | $bbc = isset($this->_req->post->bbc) ? 1 : 0; |
||
955 | $show_profile = $this->_req->post->profile_area; |
||
956 | $active = isset($this->_req->post->active) ? 1 : 0; |
||
957 | $private = $this->_req->getPost('private', 'intval', 0); |
||
958 | $can_search = isset($this->_req->post->can_search) ? 1 : 0; |
||
959 | |||
960 | // Some masking stuff... |
||
961 | $mask = $this->_req->getPost('mask', 'strval', ''); |
||
962 | if ($mask == 'regex' && isset($this->_req->post->regex)) |
||
963 | $mask .= $this->_req->post->regex; |
||
964 | |||
965 | $field_length = $this->_req->getPost('max_length', 'intval', 255); |
||
966 | $enclose = $this->_req->getPost('enclose', 'strval', ''); |
||
967 | $placement = $this->_req->getPost('placement', 'intval', 0); |
||
968 | |||
969 | // Select options? |
||
970 | $field_options = ''; |
||
971 | $newOptions = array(); |
||
972 | |||
973 | // Set default |
||
974 | $default = ''; |
||
975 | |||
976 | switch ($this->_req->post->field_type) |
||
977 | { |
||
978 | case 'check': |
||
979 | $default = isset($this->_req->post->default_check) ? 1 : ''; |
||
980 | break; |
||
981 | case 'select': |
||
982 | case 'radio': |
||
983 | if (!empty($this->_req->post->select_option)) |
||
984 | { |
||
985 | foreach ($this->_req->post->select_option as $k => $v) |
||
986 | { |
||
987 | // Clean, clean, clean... |
||
988 | $v = Util::htmlspecialchars($v); |
||
989 | $v = strtr($v, array(',' => '')); |
||
990 | |||
991 | // Nada, zip, etc... |
||
992 | if (trim($v) == '') |
||
993 | continue; |
||
994 | |||
995 | // Otherwise, save it boy. |
||
996 | $field_options .= $v . ','; |
||
997 | |||
998 | // This is just for working out what happened with old options... |
||
999 | $newOptions[$k] = $v; |
||
1000 | |||
1001 | // Is it default? |
||
1002 | if (isset($this->_req->post->default_select) && $this->_req->post->default_select == $k) |
||
1003 | $default = $v; |
||
1004 | } |
||
1005 | |||
1006 | if (isset($_POST['default_select']) && $_POST['default_select'] == 'no_default') |
||
1007 | $default = 'no_default'; |
||
1008 | |||
1009 | $field_options = substr($field_options, 0, -1); |
||
1010 | } |
||
1011 | break; |
||
1012 | default: |
||
1013 | $default = isset($this->_req->post->default_value) ? $this->_req->post->default_value : ''; |
||
1014 | } |
||
1015 | |||
1016 | // Text area by default has dimensions |
||
1017 | // if ($this->_req->post->field_type == 'textarea') |
||
1018 | // $default = (int) $this->_req->post->rows . ',' . (int) $this->_req->post->cols; |
||
1019 | |||
1020 | // Come up with the unique name? |
||
1021 | if (empty($context['fid'])) |
||
1022 | { |
||
1023 | $colname = Util::substr(strtr($this->_req->post->field_name, array(' ' => '')), 0, 6); |
||
1024 | preg_match('~([\w\d_-]+)~', $colname, $matches); |
||
1025 | |||
1026 | // If there is nothing to the name, then let's start our own - for foreign languages etc. |
||
1027 | if (isset($matches[1])) |
||
1028 | $colname = $initial_colname = 'cust_' . strtolower($matches[1]); |
||
1029 | else |
||
1030 | $colname = $initial_colname = 'cust_' . mt_rand(1, 999999); |
||
1031 | |||
1032 | $unique = ensureUniqueProfileField($colname, $initial_colname); |
||
1033 | |||
1034 | // Still not a unique column name? Leave it up to the user, then. |
||
1035 | if (!$unique) |
||
1036 | throw new Elk_Exception('custom_option_not_unique'); |
||
1037 | |||
1038 | // And create a new field |
||
1039 | $new_field = array( |
||
1040 | 'col_name' => $colname, |
||
1041 | 'field_name' => $this->_req->post->field_name, |
||
1042 | 'field_desc' => $this->_req->post->field_desc, |
||
1043 | 'field_type' => $this->_req->post->field_type, |
||
1044 | 'field_length' => $field_length, |
||
1045 | 'field_options' => $field_options, |
||
1046 | 'show_reg' => $show_reg, |
||
1047 | 'show_display' => $show_display, |
||
1048 | 'show_memberlist' => $show_memberlist, |
||
1049 | 'show_profile' => $show_profile, |
||
1050 | 'private' => $private, |
||
1051 | 'active' => $active, |
||
1052 | 'default_value' => $default, |
||
1053 | 'rows' => $rows, |
||
1054 | 'cols' => $cols, |
||
1055 | 'can_search' => $can_search, |
||
1056 | 'bbc' => $bbc, |
||
1057 | 'mask' => $mask, |
||
1058 | 'enclose' => $enclose, |
||
1059 | 'placement' => $placement, |
||
1060 | 'vieworder' => list_getProfileFieldSize() + 1, |
||
1061 | ); |
||
1062 | addProfileField($new_field); |
||
1063 | } |
||
1064 | // Work out what to do with the user data otherwise... |
||
1065 | else |
||
1066 | { |
||
1067 | // Anything going to check or select is pointless keeping - as is anything coming from check! |
||
1068 | if (($this->_req->post->field_type == 'check' && $context['field']['type'] != 'check') |
||
1069 | || (($this->_req->post->field_type == 'select' || $this->_req->post->field_type == 'radio') && $context['field']['type'] != 'select' && $context['field']['type'] != 'radio') |
||
1070 | || ($context['field']['type'] == 'check' && $this->_req->post->field_type != 'check')) |
||
1071 | { |
||
1072 | deleteProfileFieldUserData($context['field']['colname']); |
||
1073 | } |
||
1074 | // Otherwise - if the select is edited may need to adjust! |
||
1075 | elseif ($this->_req->post->field_type == 'select' || $this->_req->post->field_type == 'radio') |
||
1076 | { |
||
1077 | $optionChanges = array(); |
||
1078 | $takenKeys = array(); |
||
1079 | |||
1080 | // Work out what's changed! |
||
1081 | foreach ($context['field']['options'] as $k => $option) |
||
1082 | { |
||
1083 | if (trim($option) == '') |
||
1084 | continue; |
||
1085 | |||
1086 | // Still exists? |
||
1087 | if (in_array($option, $newOptions)) |
||
1088 | { |
||
1089 | $takenKeys[] = $k; |
||
1090 | continue; |
||
1091 | } |
||
1092 | } |
||
1093 | |||
1094 | // Finally - have we renamed it - or is it really gone? |
||
1095 | foreach ($optionChanges as $k => $option) |
||
1096 | { |
||
1097 | // Just been renamed? |
||
1098 | if (!in_array($k, $takenKeys) && !empty($newOptions[$k])) |
||
1099 | updateRenamedProfileField($k, $newOptions, $context['field']['colname'], $option); |
||
1100 | } |
||
1101 | } |
||
1102 | // @todo Maybe we should adjust based on new text length limits? |
||
1103 | |||
1104 | // And finally update an existing field |
||
1105 | $field_data = array( |
||
1106 | 'field_length' => $field_length, |
||
1107 | 'show_reg' => $show_reg, |
||
1108 | 'show_display' => $show_display, |
||
1109 | 'show_memberlist' => $show_memberlist, |
||
1110 | 'private' => $private, |
||
1111 | 'active' => $active, |
||
1112 | 'can_search' => $can_search, |
||
1113 | 'bbc' => $bbc, |
||
1114 | 'current_field' => $context['fid'], |
||
1115 | 'field_name' => $this->_req->post->field_name, |
||
1116 | 'field_desc' => $this->_req->post->field_desc, |
||
1117 | 'field_type' => $this->_req->post->field_type, |
||
1118 | 'field_options' => $field_options, |
||
1119 | 'show_profile' => $show_profile, |
||
1120 | 'default_value' => $default, |
||
1121 | 'mask' => $mask, |
||
1122 | 'enclose' => $enclose, |
||
1123 | 'placement' => $placement, |
||
1124 | 'rows' => $rows, |
||
1125 | 'cols' => $cols, |
||
1126 | ); |
||
1127 | |||
1128 | updateProfileField($field_data); |
||
1129 | |||
1130 | // Just clean up any old selects - these are a pain! |
||
1131 | if (($this->_req->post->field_type == 'select' || $this->_req->post->field_type == 'radio') && !empty($newOptions)) |
||
1132 | deleteOldProfileFieldSelects($newOptions, $context['field']['colname']); |
||
1133 | } |
||
1134 | } |
||
1135 | // Deleting? |
||
1136 | elseif (isset($this->_req->post->delete) && $context['field']['colname']) |
||
1137 | { |
||
1138 | checkSession(); |
||
1139 | validateToken('admin-ecp'); |
||
1140 | |||
1141 | // Delete the old data first, then the field. |
||
1142 | deleteProfileFieldUserData($context['field']['colname']); |
||
1143 | deleteProfileField($context['fid']); |
||
1144 | } |
||
1145 | |||
1146 | // Rebuild display cache etc. |
||
1147 | if (isset($this->_req->post->delete) || isset($this->_req->post->save) || isset($this->_req->post->onoff)) |
||
1148 | { |
||
1149 | checkSession(); |
||
1150 | |||
1151 | // Update the display cache |
||
1152 | updateDisplayCache(); |
||
1153 | redirectexit('action=admin;area=featuresettings;sa=profile'); |
||
1154 | } |
||
1155 | |||
1156 | createToken('admin-ecp'); |
||
1157 | } |
||
1158 | |||
1159 | /** |
||
1160 | * Editing personal messages settings |
||
1161 | * |
||
1162 | * - Accessed with ?action=admin;area=featuresettings;sa=pmsettings |
||
1163 | * |
||
1164 | * @event integrate_save_pmsettings_settings |
||
1165 | */ |
||
1166 | public function action_pmsettings() |
||
1167 | { |
||
1168 | global $txt, $scripturl, $context; |
||
1169 | |||
1170 | // Initialize the form |
||
1171 | $settingsForm = new Settings_Form(Settings_Form::DB_ADAPTER); |
||
1172 | |||
1173 | // Initialize it with our settings |
||
1174 | $settingsForm->setConfigVars($this->_pmSettings()); |
||
1175 | |||
1176 | require_once(SUBSDIR . '/PersonalMessage.subs.php'); |
||
1177 | theme()->getTemplates()->loadLanguageFile('ManageMembers'); |
||
1178 | |||
1179 | $context['pm_limits'] = loadPMLimits(); |
||
1180 | |||
1181 | // Saving? |
||
1182 | if (isset($this->_req->query->save)) |
||
1183 | { |
||
1184 | checkSession(); |
||
1185 | |||
1186 | require_once(SUBSDIR . '/Membergroups.subs.php'); |
||
1187 | foreach ($context['pm_limits'] as $group_id => $group) |
||
1188 | { |
||
1189 | if (isset($this->_req->post->group[$group_id]) && $this->_req->post->group[$group_id] != $group['max_messages']) |
||
1190 | updateMembergroupProperties(array('current_group' => $group_id, 'max_messages' => $this->_req->post->group[$group_id])); |
||
1191 | } |
||
1192 | |||
1193 | call_integration_hook('integrate_save_pmsettings_settings'); |
||
1194 | |||
1195 | $settingsForm->setConfigValues((array) $this->_req->post); |
||
1196 | $settingsForm->save(); |
||
1197 | redirectexit('action=admin;area=featuresettings;sa=pmsettings'); |
||
1198 | } |
||
1199 | |||
1200 | $context['post_url'] = $scripturl . '?action=admin;area=featuresettings;save;sa=pmsettings'; |
||
1201 | $context['settings_title'] = $txt['personal_messages']; |
||
1202 | |||
1203 | $settingsForm->prepare(); |
||
1204 | } |
||
1205 | |||
1206 | /** |
||
1207 | * Return basic feature settings. |
||
1208 | * |
||
1209 | * @event integrate_modify_basic_settings Adds to General features and Options |
||
1210 | */ |
||
1211 | 1 | private function _basicSettings() |
|
1212 | { |
||
1213 | 1 | global $txt; |
|
1214 | |||
1215 | $config_vars = array( |
||
1216 | // Basic stuff, titles, permissions... |
||
1217 | 1 | array('check', 'allow_guestAccess'), |
|
1218 | array('check', 'enable_buddylist'), |
||
1219 | array('check', 'allow_editDisplayName'), |
||
1220 | array('check', 'allow_hideOnline'), |
||
1221 | array('check', 'titlesEnable'), |
||
1222 | 1 | '', |
|
1223 | // Javascript and CSS options |
||
1224 | 1 | array('select', 'jquery_source', array('auto' => $txt['jquery_auto'], 'local' => $txt['jquery_local'], 'cdn' => $txt['jquery_cdn'])), |
|
1225 | array('check', 'jquery_default', 'onchange' => 'showhideJqueryOptions();'), |
||
1226 | 1 | array('text', 'jquery_version', 'postinput' => $txt['jquery_custom_after']), |
|
1227 | array('check', 'jqueryui_default', 'onchange' => 'showhideJqueryOptions();'), |
||
1228 | 1 | array('text', 'jqueryui_version', 'postinput' => $txt['jqueryui_custom_after']), |
|
1229 | 1 | array('check', 'minify_css_js', 'postinput' => '<a href="#" id="clean_hives" class="linkbutton">' . $txt['clean_hives'] . '</a>'), |
|
1230 | 1 | '', |
|
1231 | // Number formatting, timezones. |
||
1232 | array('text', 'time_format'), |
||
1233 | 1 | array('float', 'time_offset', 'subtext' => $txt['setting_time_offset_note'], 6, 'postinput' => $txt['hours']), |
|
1234 | 'default_timezone' => array('select', 'default_timezone', array()), |
||
1235 | 1 | '', |
|
1236 | // Who's online? |
||
1237 | array('check', 'who_enabled'), |
||
1238 | 1 | array('int', 'lastActive', 6, 'postinput' => $txt['minutes']), |
|
1239 | 1 | '', |
|
1240 | // Statistics. |
||
1241 | array('check', 'trackStats'), |
||
1242 | array('check', 'hitStats'), |
||
1243 | 1 | '', |
|
1244 | // Option-ish things... miscellaneous sorta. |
||
1245 | array('check', 'allow_disableAnnounce'), |
||
1246 | array('check', 'disallow_sendBody'), |
||
1247 | 1 | array('select', 'enable_contactform', array('disabled' => $txt['contact_form_disabled'], 'registration' => $txt['contact_form_registration'], 'menu' => $txt['contact_form_menu'])), |
|
1248 | ); |
||
1249 | |||
1250 | // Get all the time zones. |
||
1251 | 1 | $all_zones = timezone_identifiers_list(); |
|
1252 | 1 | if ($all_zones === false) |
|
1253 | unset($config_vars['default_timezone']); |
||
1254 | else |
||
1255 | { |
||
1256 | // Make sure we set the value to the same as the printed value. |
||
1257 | 1 | foreach ($all_zones as $zone) |
|
1258 | 1 | $config_vars['default_timezone'][2][$zone] = $zone; |
|
1259 | } |
||
1260 | |||
1261 | 1 | call_integration_hook('integrate_modify_basic_settings', array(&$config_vars)); |
|
1262 | |||
1263 | 1 | return $config_vars; |
|
1264 | } |
||
1265 | |||
1266 | /** |
||
1267 | * Public method to return the basic settings, used for admin search |
||
1268 | */ |
||
1269 | 1 | public function basicSettings_search() |
|
1273 | |||
1274 | /** |
||
1275 | * Return layout settings. |
||
1276 | * |
||
1277 | * @event integrate_modify_layout_settings Adds options to Configuration->Layout |
||
1278 | */ |
||
1279 | 1 | private function _layoutSettings() |
|
1280 | { |
||
1281 | 1 | global $txt; |
|
1282 | |||
1283 | 1 | $config_vars = array_merge(getFrontPageControllers(), array( |
|
1284 | 1 | '', |
|
1285 | // Pagination stuff. |
||
1286 | array('check', 'compactTopicPagesEnable'), |
||
1287 | 1 | array('int', 'compactTopicPagesContiguous', 'subtext' => str_replace(' ', ' ', '"3" ' . $txt['to_display'] . ': <strong>1 ... 4 [5] 6 ... 9</strong>') . '<br />' . str_replace(' ', ' ', '"5" ' . $txt['to_display'] . ': <strong>1 ... 3 4 [5] 6 7 ... 9</strong>')), |
|
1288 | array('int', 'defaultMaxMembers'), |
||
1289 | array('check', 'displayMemberNames'), |
||
1290 | 1 | '', |
|
1291 | // Stuff that just is everywhere - today, search, online, etc. |
||
1292 | 1 | array('select', 'todayMod', array($txt['today_disabled'], $txt['today_only'], $txt['yesterday_today'], $txt['relative_time'])), |
|
1293 | array('check', 'onlineEnable'), |
||
1294 | array('check', 'enableVBStyleLogin'), |
||
1295 | 1 | '', |
|
1296 | // Automagic image resizing. |
||
1297 | 1 | array('int', 'max_image_width', 'subtext' => $txt['zero_for_no_limit']), |
|
1298 | 1 | array('int', 'max_image_height', 'subtext' => $txt['zero_for_no_limit']), |
|
1299 | 1 | '', |
|
1300 | // This is like debugging sorta. |
||
1301 | array('check', 'timeLoadPageEnable'), |
||
1302 | )); |
||
1303 | |||
1304 | 1 | call_integration_hook('integrate_modify_layout_settings', array(&$config_vars)); |
|
1305 | |||
1306 | 1 | return $config_vars; |
|
1307 | } |
||
1308 | |||
1309 | /** |
||
1310 | * Public method to return the layout settings, used for admin search |
||
1311 | */ |
||
1312 | 1 | public function layoutSettings_search() |
|
1316 | |||
1317 | /** |
||
1318 | * Return karma settings. |
||
1319 | * |
||
1320 | * @event integrate_modify_karma_settings Adds to Configuration->Karma |
||
1321 | */ |
||
1322 | 1 | private function _karmaSettings() |
|
1323 | { |
||
1324 | 1 | global $txt; |
|
1325 | |||
1326 | $config_vars = array( |
||
1327 | // Karma - On or off? |
||
1328 | 1 | array('select', 'karmaMode', explode('|', $txt['karma_options'])), |
|
1329 | 1 | '', |
|
1330 | // Who can do it.... and who is restricted by time limits? |
||
1331 | 1 | array('int', 'karmaMinPosts', 6, 'postinput' => $txt['manageposts_posts']), |
|
1332 | 1 | array('float', 'karmaWaitTime', 6, 'postinput' => $txt['hours']), |
|
1333 | array('check', 'karmaTimeRestrictAdmins'), |
||
1334 | array('check', 'karmaDisableSmite'), |
||
1335 | 1 | '', |
|
1336 | // What does it look like? [smite]? |
||
1337 | array('text', 'karmaLabel'), |
||
1338 | array('text', 'karmaApplaudLabel', 'mask' => 'nohtml'), |
||
1339 | array('text', 'karmaSmiteLabel', 'mask' => 'nohtml'), |
||
1340 | ); |
||
1341 | |||
1342 | 1 | call_integration_hook('integrate_modify_karma_settings', array(&$config_vars)); |
|
1343 | |||
1344 | 1 | return $config_vars; |
|
1345 | } |
||
1346 | |||
1347 | /** |
||
1348 | * Public method to return the karma settings, used for admin search |
||
1349 | */ |
||
1350 | 1 | public function karmaSettings_search() |
|
1354 | |||
1355 | /** |
||
1356 | * Return likes settings. |
||
1357 | * |
||
1358 | * @event integrate_modify_likes_settings Adds to Configuration->Likes |
||
1359 | */ |
||
1360 | 1 | private function _likesSettings() |
|
1361 | { |
||
1362 | 1 | global $txt; |
|
1363 | |||
1364 | $config_vars = array( |
||
1365 | // Likes - On or off? |
||
1366 | 1 | array('check', 'likes_enabled'), |
|
1367 | 1 | '', |
|
1368 | // Who can do it.... and who is restricted by count limits? |
||
1369 | 1 | array('int', 'likeMinPosts', 6, 'postinput' => $txt['manageposts_posts']), |
|
1370 | 1 | array('int', 'likeWaitTime', 6, 'postinput' => $txt['minutes']), |
|
1371 | array('int', 'likeWaitCount', 6), |
||
1372 | array('check', 'likeRestrictAdmins'), |
||
1373 | array('check', 'likeAllowSelf'), |
||
1374 | 1 | '', |
|
1375 | array('int', 'likeDisplayLimit', 6) |
||
1376 | ); |
||
1377 | |||
1378 | 1 | call_integration_hook('integrate_modify_likes_settings', array(&$config_vars)); |
|
1379 | |||
1380 | 1 | return $config_vars; |
|
1381 | } |
||
1382 | |||
1383 | /** |
||
1384 | * Public method to return the likes settings, used for admin search |
||
1385 | */ |
||
1386 | 1 | public function likesSettings_search() |
|
1390 | |||
1391 | /** |
||
1392 | * Return mentions settings. |
||
1393 | * |
||
1394 | * @event integrate_modify_mention_settings Adds to Configuration->Mentions |
||
1395 | */ |
||
1396 | 1 | private function _notificationsSettings() |
|
1397 | { |
||
1398 | 1 | global $txt, $modSettings; |
|
1399 | |||
1400 | 1 | theme()->getTemplates()->loadLanguageFile('Profile'); |
|
1401 | 1 | theme()->getTemplates()->loadLanguageFile('UserNotifications'); |
|
1402 | |||
1403 | // The mentions settings |
||
1404 | $config_vars = array( |
||
1405 | 1 | array('title', 'mentions_settings'), |
|
1406 | array('check', 'mentions_enabled'), |
||
1407 | ); |
||
1408 | |||
1409 | 1 | $notification_methods = Notifications::instance()->getNotifiers(); |
|
1410 | 1 | $notification_types = getNotificationTypes(); |
|
1411 | 1 | $current_settings = unserialize($modSettings['notification_methods']); |
|
1412 | |||
1413 | 1 | foreach ($notification_types as $title) |
|
1414 | { |
||
1415 | 1 | $config_vars[] = array('title', 'setting_' . $title); |
|
1416 | |||
1417 | 1 | foreach ($notification_methods as $method) |
|
1418 | { |
||
1419 | 1 | if ($method === 'notification') |
|
1420 | 1 | $text_label = $txt['setting_notify_enable_this']; |
|
1421 | else |
||
1422 | 1 | $text_label = $txt['notify_' . $method]; |
|
1423 | |||
1424 | 1 | $config_vars[] = array('check', 'notifications[' . $title . '][' . $method . ']', 'text_label' => $text_label); |
|
1425 | 1 | $modSettings['notifications[' . $title . '][' . $method . ']'] = !empty($current_settings[$title][$method]); |
|
1426 | } |
||
1427 | } |
||
1428 | |||
1429 | 1 | call_integration_hook('integrate_modify_mention_settings', array(&$config_vars)); |
|
1430 | |||
1431 | 1 | return $config_vars; |
|
1432 | } |
||
1433 | |||
1434 | /** |
||
1435 | * Public method to return the mention settings, used for admin search |
||
1436 | */ |
||
1437 | 1 | public function mentionSettings_search() |
|
1441 | |||
1442 | /** |
||
1443 | * Return signature settings. |
||
1444 | * |
||
1445 | * - Used in admin center search and settings form |
||
1446 | * |
||
1447 | * @event integrate_modify_signature_settings Adds options to Signature Settings |
||
1448 | */ |
||
1449 | 1 | private function _signatureSettings() |
|
1450 | { |
||
1451 | 1 | global $txt; |
|
1452 | |||
1453 | $config_vars = array( |
||
1454 | // Are signatures even enabled? |
||
1455 | 1 | array('check', 'signature_enable'), |
|
1456 | 1 | '', |
|
1457 | // Tweaking settings! |
||
1458 | 1 | array('int', 'signature_max_length', 'subtext' => $txt['zero_for_no_limit']), |
|
1459 | 1 | array('int', 'signature_max_lines', 'subtext' => $txt['zero_for_no_limit']), |
|
1460 | 1 | array('int', 'signature_max_font_size', 'subtext' => $txt['zero_for_no_limit']), |
|
1461 | array('check', 'signature_allow_smileys', 'onclick' => 'document.getElementById(\'signature_max_smileys\').disabled = !this.checked;'), |
||
1462 | 1 | array('int', 'signature_max_smileys', 'subtext' => $txt['zero_for_no_limit']), |
|
1463 | 1 | array('select', 'signature_repetition_guests', |
|
1464 | array( |
||
1465 | 1 | $txt['signature_always'], |
|
1466 | 1 | $txt['signature_onlyfirst'], |
|
1467 | 1 | $txt['signature_never'], |
|
1468 | ), |
||
1469 | ), |
||
1470 | 1 | array('select', 'signature_repetition_members', |
|
1471 | array( |
||
1472 | 1 | $txt['signature_always'], |
|
1473 | 1 | $txt['signature_onlyfirst'], |
|
1474 | 1 | $txt['signature_never'], |
|
1475 | ), |
||
1476 | ), |
||
1477 | 1 | '', |
|
1478 | // Image settings. |
||
1479 | 1 | array('int', 'signature_max_images', 'subtext' => $txt['signature_max_images_note']), |
|
1480 | 1 | array('int', 'signature_max_image_width', 'subtext' => $txt['zero_for_no_limit']), |
|
1481 | 1 | array('int', 'signature_max_image_height', 'subtext' => $txt['zero_for_no_limit']), |
|
1482 | 1 | '', |
|
1483 | array('bbc', 'signature_bbc'), |
||
1484 | ); |
||
1485 | |||
1486 | 1 | call_integration_hook('integrate_modify_signature_settings', array(&$config_vars)); |
|
1487 | |||
1488 | 1 | return $config_vars; |
|
1489 | } |
||
1490 | |||
1491 | /** |
||
1492 | * Public method to return the signature settings, used for admin search |
||
1493 | */ |
||
1494 | 1 | public function signatureSettings_search() |
|
1498 | |||
1499 | /** |
||
1500 | * Return pm settings. |
||
1501 | * |
||
1502 | * - Used in admin center search and settings form |
||
1503 | * |
||
1504 | * @event integrate_modify_pmsettings_settings Adds / Modifies PM Settings |
||
1505 | */ |
||
1506 | private function _pmSettings() |
||
1507 | { |
||
1508 | global $txt; |
||
1509 | |||
1510 | $config_vars = array( |
||
1511 | // Reporting of personal messages? |
||
1512 | array('check', 'enableReportPM'), |
||
1529 | } |
||
1530 | |||
1569 |