]> git.mxchange.org Git - quix0rs-gnu-social.git/blob - actions/designadminpanel.php
d1aadc8c276ee112a151af5541ab175ca939d405
[quix0rs-gnu-social.git] / actions / designadminpanel.php
1 <?php
2 /**
3  * StatusNet, the distributed open-source microblogging tool
4  *
5  * Design administration panel
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  Settings
23  * @package   StatusNet
24  * @author    Evan Prodromou <evan@status.net>
25  * @author    Zach Copley <zach@status.net>
26  * @author    Sarven Capadisli <csarven@status.net>
27  * @copyright 2008-2009 StatusNet, Inc.
28  * @license   http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
29  * @link      http://status.net/
30  */
31
32 if (!defined('STATUSNET')) {
33     exit(1);
34 }
35
36 /**
37  * Administer design settings
38  *
39  * @category Admin
40  * @package  StatusNet
41  * @author   Evan Prodromou <evan@status.net>
42  * @author   Zach Copley <zach@status.net>
43  * @author   Sarven Capadisli <csarven@status.net>
44  * @license  http://www.fsf.org/licensing/licenses/agpl-3.0.html GNU Affero General Public License version 3.0
45  * @link     http://status.net/
46  */
47
48 class DesignadminpanelAction extends AdminPanelAction
49 {
50
51     /* The default site design */
52     var $design = null;
53
54     /**
55      * Returns the page title
56      *
57      * @return string page title
58      */
59
60     function title()
61     {
62         return _('Design');
63     }
64
65     /**
66      * Instructions for using this form.
67      *
68      * @return string instructions
69      */
70
71     function getInstructions()
72     {
73         return _('Design settings for this StatusNet site.');
74     }
75
76     /**
77      * Show the site admin panel form
78      *
79      * @return void
80      */
81
82     function showForm()
83     {
84         $this->design = Design::siteDesign();
85
86         $form = new DesignAdminPanelForm($this);
87         $form->show();
88         return;
89     }
90
91     /**
92      * Save settings from the form
93      *
94      * @return void
95      */
96
97     function saveSettings()
98     {
99         if ($this->arg('save')) {
100             $this->saveDesignSettings();
101         } else if ($this->arg('defaults')) {
102             $this->restoreDefaults();
103         } else {
104             $this->success = false;
105             $this->message = 'Unexpected form submission.';
106         }
107     }
108
109     /**
110      * Save the new design settings
111      *
112      * @return void
113      */
114
115     function saveDesignSettings()
116     {
117
118         // Workaround for PHP returning empty $_POST and $_FILES when POST
119         // length > post_max_size in php.ini
120
121         if (empty($_FILES)
122             && empty($_POST)
123             && ($_SERVER['CONTENT_LENGTH'] > 0)
124         ) {
125             $msg = _('The server was unable to handle that much POST ' .
126                 'data (%s bytes) due to its current configuration.');
127             $this->success = false;
128             $this->msg     = $e->getMessage(sprintf($msg, $_SERVER['CONTENT_LENGTH']));
129             return;
130         }
131
132         // check for an image upload
133
134         $bgimage = $this->saveBackgroundImage();
135
136         static $settings = array('theme');
137         $values = array();
138
139         foreach ($settings as $setting) {
140             $values[$setting] = $this->trimmed($setting);
141         }
142
143         // This throws an exception on validation errors
144         try {
145             $bgcolor = new WebColor($this->trimmed('design_background'));
146             $ccolor  = new WebColor($this->trimmed('design_content'));
147             $sbcolor = new WebColor($this->trimmed('design_sidebar'));
148             $tcolor  = new WebColor($this->trimmed('design_text'));
149             $lcolor  = new WebColor($this->trimmed('design_links'));
150         } catch (WebColorException $e) {
151             $this->success = false;
152             $this->msg = $e->getMessage();
153             return;
154         }
155
156         $onoff = $this->arg('design_background-image_onoff');
157
158         $on   = false;
159         $off  = false;
160
161         if ($onoff == 'on') {
162             $on = true;
163         } else {
164             $off = true;
165         }
166
167         $tile = $this->boolean('design_background-image_repeat');
168
169         $this->validate($values);
170
171         // assert(all values are valid);
172
173         $config = new Config();
174
175         $config->query('BEGIN');
176
177         foreach ($settings as $setting) {
178             Config::save('site', $setting, $values[$setting]);
179         }
180
181         if (isset($bgimage)) {
182             Config::save('design', 'backgroundimage', $bgimage);
183         }
184
185         Config::save('design', 'backgroundcolor', $bgcolor->intValue());
186         Config::save('design', 'contentcolor', $ccolor->intValue());
187         Config::save('design', 'sidebarcolor', $sbcolor->intValue());
188         Config::save('design', 'textcolor', $tcolor->intValue());
189         Config::save('design', 'linkcolor', $lcolor->intValue());
190
191         // Hack to use Design's bit setter
192         $scratch = new Design();
193         $scratch->setDisposition($on, $off, $tile);
194
195         Config::save('design', 'disposition', $scratch->disposition);
196
197         $config->query('COMMIT');
198
199         return;
200
201     }
202
203     /**
204      * Delete a design setting
205      *
206      * @return mixed $result false if something didn't work
207      */
208
209     function deleteSetting($section, $setting)
210     {
211         $config = new Config();
212
213         $config->section = $section;
214         $config->setting = $setting;
215
216         if ($config->find(true)) {
217             $result = $config->delete();
218             if (!$result) {
219                 common_log_db_error($config, 'DELETE', __FILE__);
220                 $this->clientError(_("Unable to delete design setting."));
221                 return null;
222             }
223         }
224
225         return $result;
226     }
227
228     /**
229       * Restore the default design
230       *
231       * @return void
232       */
233
234     function restoreDefaults()
235     {
236         $this->deleteSetting('site', 'theme');
237
238         $settings = array(
239             'theme', 'backgroundimage', 'backgroundcolor', 'contentcolor',
240             'sidebarcolor', 'textcolor', 'linkcolor', 'disposition'
241         );
242
243         foreach ($settings as $setting) {
244             $this->deleteSetting('design', $setting);
245         }
246     }
247
248     /**
249      * Save the background image if the user uploaded one
250      *
251      * @return string $filename the filename of the image
252      */
253
254     function saveBackgroundImage()
255     {
256         $filename = null;
257
258         if ($_FILES['design_background-image_file']['error'] ==
259             UPLOAD_ERR_OK) {
260
261             $filepath = null;
262
263             try {
264                 $imagefile =
265                     ImageFile::fromUpload('design_background-image_file');
266             } catch (Exception $e) {
267                 $this->success = false;
268                 $this->msg     = $e->getMessage();
269                 return;
270             }
271
272             // Note: site design background image has a special filename
273
274             $filename = Design::filename('site-design-background',
275                 image_type_to_extension($imagefile->type),
276                     common_timestamp());
277
278             $filepath = Design::path($filename);
279
280             move_uploaded_file($imagefile->filepath, $filepath);
281
282             // delete any old backround img laying around
283
284             if (isset($this->design->backgroundimage)) {
285                 @unlink(Design::path($design->backgroundimage));
286             }
287
288             return $filename;
289         }
290     }
291
292     /**
293      * Attempt to validate setting values
294      *
295      * @return void
296      */
297
298     function validate(&$values)
299     {
300         if (!in_array($values['theme'], Theme::listAvailable())) {
301             $this->clientError(sprintf(_("Theme not available: %s"), $values['theme']));
302         }
303     }
304
305     /**
306      * Add the Farbtastic stylesheet
307      *
308      * @return void
309      */
310
311     function showStylesheets()
312     {
313         parent::showStylesheets();
314         $this->cssLink('css/farbtastic.css','base','screen, projection, tv');
315     }
316
317     /**
318      * Add the Farbtastic scripts
319      *
320      * @return void
321      */
322
323     function showScripts()
324     {
325         parent::showScripts();
326
327         $this->script('js/farbtastic/farbtastic.js');
328         $this->script('js/userdesign.go.js');
329
330         $this->autofocus('design_background-image_file');
331     }
332
333 }
334
335 class DesignAdminPanelForm extends Form
336 {
337
338     /**
339      * ID of the form
340      *
341      * @return int ID of the form
342      */
343
344     function id()
345     {
346         return 'form_design_admin_panel';
347     }
348
349     /**
350      * class of the form
351      *
352      * @return string class of the form
353      */
354
355     function formClass()
356     {
357         return 'form_settings';
358     }
359
360     /**
361      * HTTP method used to submit the form
362      *
363      * For image data we need to send multipart/form-data
364      * so we set that here too
365      *
366      * @return string the method to use for submitting
367      */
368
369     function method()
370     {
371         $this->enctype = 'multipart/form-data';
372
373         return 'post';
374     }
375
376     /**
377      * Action of the form
378      *
379      * @return string URL of the action
380      */
381
382     function action()
383     {
384         return common_local_url('designadminpanel');
385     }
386
387     /**
388      * Data elements of the form
389      *
390      * @return void
391      */
392
393     function formData()
394     {
395
396         $design = $this->out->design;
397
398         $themes = Theme::listAvailable();
399
400         asort($themes);
401
402         $themes = array_combine($themes, $themes);
403
404         $this->out->elementStart('fieldset', array('id' =>
405             'settings_design_theme'));
406         $this->out->element('legend', null, _('Change theme'));
407         $this->out->elementStart('ul', 'form_data');
408
409         $this->out->elementStart('li');
410         $this->out->dropdown('theme', _('Theme'),
411                              $themes, _('Theme for the site.'),
412                              false, $this->value('theme'));
413         $this->out->elementEnd('li');
414         $this->out->elementEnd('ul');
415         $this->out->elementEnd('fieldset');
416
417
418         $this->out->elementStart('fieldset', array('id' =>
419             'settings_design_background-image'));
420         $this->out->element('legend', null, _('Change background image'));
421         $this->out->elementStart('ul', 'form_data');
422         $this->out->elementStart('li');
423         $this->out->element('label', array('for' => 'design_background-image_file'),
424                                 _('Background'));
425         $this->out->element('input', array('name' => 'design_background-image_file',
426                                      'type' => 'file',
427                                      'id' => 'design_background-image_file'));
428         $this->out->element('p', 'form_guide',
429             sprintf(_('You can upload a background image for the site. ' .
430               'The maximum file size is %1$s.'), ImageFile::maxFileSize()));
431         $this->out->element('input', array('name' => 'MAX_FILE_SIZE',
432                                           'type' => 'hidden',
433                                           'id' => 'MAX_FILE_SIZE',
434                                           'value' => ImageFile::maxFileSizeInt()));
435         $this->out->elementEnd('li');
436
437         if (!empty($design->backgroundimage)) {
438
439             $this->out->elementStart('li', array('id' =>
440                 'design_background-image_onoff'));
441
442             $this->out->element('img', array('src' =>
443                 Design::url($design->backgroundimage)));
444
445             $attrs = array('name' => 'design_background-image_onoff',
446                            'type' => 'radio',
447                            'id' => 'design_background-image_on',
448                            'class' => 'radio',
449                            'value' => 'on');
450
451             if ($design->disposition & BACKGROUND_ON) {
452                 $attrs['checked'] = 'checked';
453             }
454
455             $this->out->element('input', $attrs);
456
457             $this->out->element('label', array('for' => 'design_background-image_on',
458                                           'class' => 'radio'),
459                                           _('On'));
460
461             $attrs = array('name' => 'design_background-image_onoff',
462                            'type' => 'radio',
463                            'id' => 'design_background-image_off',
464                            'class' => 'radio',
465                            'value' => 'off');
466
467             if ($design->disposition & BACKGROUND_OFF) {
468                 $attrs['checked'] = 'checked';
469             }
470
471             $this->out->element('input', $attrs);
472
473             $this->out->element('label', array('for' => 'design_background-image_off',
474                                           'class' => 'radio'),
475                                           _('Off'));
476             $this->out->element('p', 'form_guide', _('Turn background image on or off.'));
477             $this->out->elementEnd('li');
478
479             $this->out->elementStart('li');
480             $this->out->checkbox('design_background-image_repeat',
481                             _('Tile background image'),
482                             ($design->disposition & BACKGROUND_TILE) ? true : false);
483             $this->out->elementEnd('li');
484         }
485
486         $this->out->elementEnd('ul');
487         $this->out->elementEnd('fieldset');
488
489         $this->out->elementStart('fieldset', array('id' => 'settings_design_color'));
490         $this->out->element('legend', null, _('Change colours'));
491         $this->out->elementStart('ul', 'form_data');
492
493         try {
494
495             $bgcolor = new WebColor($design->backgroundcolor);
496
497             $this->out->elementStart('li');
498             $this->out->element('label', array('for' => 'swatch-1'), _('Background'));
499             $this->out->element('input', array('name' => 'design_background',
500                                           'type' => 'text',
501                                           'id' => 'swatch-1',
502                                           'class' => 'swatch',
503                                           'maxlength' => '7',
504                                           'size' => '7',
505                                           'value' => ''));
506             $this->out->elementEnd('li');
507
508             $ccolor = new WebColor($design->contentcolor);
509
510             $this->out->elementStart('li');
511             $this->out->element('label', array('for' => 'swatch-2'), _('Content'));
512             $this->out->element('input', array('name' => 'design_content',
513                                           'type' => 'text',
514                                           'id' => 'swatch-2',
515                                           'class' => 'swatch',
516                                           'maxlength' => '7',
517                                           'size' => '7',
518                                           'value' => ''));
519             $this->out->elementEnd('li');
520
521             $sbcolor = new WebColor($design->sidebarcolor);
522
523             $this->out->elementStart('li');
524             $this->out->element('label', array('for' => 'swatch-3'), _('Sidebar'));
525             $this->out->element('input', array('name' => 'design_sidebar',
526                                         'type' => 'text',
527                                         'id' => 'swatch-3',
528                                         'class' => 'swatch',
529                                         'maxlength' => '7',
530                                         'size' => '7',
531                                         'value' => ''));
532             $this->out->elementEnd('li');
533
534             $tcolor = new WebColor($design->textcolor);
535
536             $this->out->elementStart('li');
537             $this->out->element('label', array('for' => 'swatch-4'), _('Text'));
538             $this->out->element('input', array('name' => 'design_text',
539                                         'type' => 'text',
540                                         'id' => 'swatch-4',
541                                         'class' => 'swatch',
542                                         'maxlength' => '7',
543                                         'size' => '7',
544                                         'value' => ''));
545             $this->out->elementEnd('li');
546
547             $lcolor = new WebColor($design->linkcolor);
548
549             $this->out->elementStart('li');
550             $this->out->element('label', array('for' => 'swatch-5'), _('Links'));
551             $this->out->element('input', array('name' => 'design_links',
552                                          'type' => 'text',
553                                          'id' => 'swatch-5',
554                                          'class' => 'swatch',
555                                          'maxlength' => '7',
556                                          'size' => '7',
557                                          'value' => ''));
558             $this->out->elementEnd('li');
559
560         } catch (WebColorException $e) {
561             common_log(LOG_ERR, 'Bad color values in site design: ' .
562                 $e->getMessage());
563         }
564
565         $this->out->elementEnd('ul');
566         $this->out->elementEnd('fieldset');
567
568     }
569
570     /**
571      * Utility to simplify some of the duplicated code around
572      * params and settings.
573      *
574      * @param string $setting      Name of the setting
575      * @param string $title        Title to use for the input
576      * @param string $instructions Instructions for this field
577      *
578      * @return void
579      */
580
581     function input($setting, $title, $instructions)
582     {
583         $this->out->input($setting, $title, $this->value($setting), $instructions);
584     }
585
586     /**
587      * Utility to simplify getting the posted-or-stored setting value
588      *
589      * @param string $setting Name of the setting
590      *
591      * @return string param value if posted, or current config value
592      */
593
594     function value($setting)
595     {
596         $value = $this->out->trimmed($setting);
597         if (empty($value)) {
598             $value = common_config('site', $setting);
599         }
600         return $value;
601     }
602
603     /**
604      * Action elements
605      *
606      * @return void
607      */
608
609     function formActions()
610     {
611         $this->out->submit('defaults', _('Use defaults'), 'submit form_action-default',
612                 'defaults', _('Restore default designs'));
613
614         $this->out->element('input', array('id' => 'settings_design_reset',
615                                          'type' => 'reset',
616                                          'value' => 'Reset',
617                                          'class' => 'submit form_action-primary',
618                                          'title' => _('Reset back to default')));
619
620         $this->out->submit('save', _('Save'), 'submit form_action-secondary',
621                 'save', _('Save design'));    }
622 }