Wordpress 4.6
[autoinstalls/wordpress.git] / wp-admin / custom-background.php
1 <?php
2 /**
3  * The custom background script.
4  *
5  * @package WordPress
6  * @subpackage Administration
7  */
8
9 /**
10  * The custom background class.
11  *
12  * @since 3.0.0
13  * @package WordPress
14  * @subpackage Administration
15  */
16 class Custom_Background {
17
18         /**
19          * Callback for administration header.
20          *
21          * @var callable
22          * @since 3.0.0
23          */
24         public $admin_header_callback;
25
26         /**
27          * Callback for header div.
28          *
29          * @var callable
30          * @since 3.0.0
31          */
32         public $admin_image_div_callback;
33
34         /**
35          * Used to trigger a success message when settings updated and set to true.
36          *
37          * @since 3.0.0
38          * @access private
39          * @var bool
40          */
41         private $updated;
42
43         /**
44          * Constructor - Register administration header callback.
45          *
46          * @since 3.0.0
47          * @param callable $admin_header_callback
48          * @param callable $admin_image_div_callback Optional custom image div output callback.
49          */
50         public function __construct($admin_header_callback = '', $admin_image_div_callback = '') {
51                 $this->admin_header_callback = $admin_header_callback;
52                 $this->admin_image_div_callback = $admin_image_div_callback;
53
54                 add_action( 'admin_menu', array( $this, 'init' ) );
55
56                 add_action( 'wp_ajax_custom-background-add', array( $this, 'ajax_background_add' ) );
57
58                 // Unused since 3.5.0.
59                 add_action( 'wp_ajax_set-background-image', array( $this, 'wp_set_background_image' ) );
60         }
61
62         /**
63          * Set up the hooks for the Custom Background admin page.
64          *
65          * @since 3.0.0
66          */
67         public function init() {
68                 $page = add_theme_page( __( 'Background' ), __( 'Background' ), 'edit_theme_options', 'custom-background', array( $this, 'admin_page' ) );
69                 if ( ! $page ) {
70                         return;
71                 }
72
73                 add_action( "load-$page", array( $this, 'admin_load' ) );
74                 add_action( "load-$page", array( $this, 'take_action' ), 49 );
75                 add_action( "load-$page", array( $this, 'handle_upload' ), 49 );
76
77                 if ( $this->admin_header_callback ) {
78                         add_action( "admin_head-$page", $this->admin_header_callback, 51 );
79                 }
80         }
81
82         /**
83          * Set up the enqueue for the CSS & JavaScript files.
84          *
85          * @since 3.0.0
86          */
87         public function admin_load() {
88                 get_current_screen()->add_help_tab( array(
89                         'id'      => 'overview',
90                         'title'   => __('Overview'),
91                         'content' =>
92                                 '<p>' . __( 'You can customize the look of your site without touching any of your theme&#8217;s code by using a custom background. Your background can be an image or a color.' ) . '</p>' .
93                                 '<p>' . __( 'To use a background image, simply upload it or choose an image that has already been uploaded to your Media Library by clicking the &#8220;Choose Image&#8221; button. You can display a single instance of your image, or tile it to fill the screen. You can have your background fixed in place, so your site content moves on top of it, or you can have it scroll with your site.' ) . '</p>' .
94                                 '<p>' . __( 'You can also choose a background color by clicking the Select Color button and either typing in a legitimate HTML hex value, e.g. &#8220;#ff0000&#8221; for red, or by choosing a color using the color picker.' ) . '</p>' .
95                                 '<p>' . __( 'Don&#8217;t forget to click on the Save Changes button when you are finished.' ) . '</p>'
96                 ) );
97
98                 get_current_screen()->set_help_sidebar(
99                         '<p><strong>' . __( 'For more information:' ) . '</strong></p>' .
100                         '<p>' . __( '<a href="https://codex.wordpress.org/Appearance_Background_Screen" target="_blank">Documentation on Custom Background</a>' ) . '</p>' .
101                         '<p>' . __( '<a href="https://wordpress.org/support/" target="_blank">Support Forums</a>' ) . '</p>'
102                 );
103
104                 wp_enqueue_media();
105                 wp_enqueue_script('custom-background');
106                 wp_enqueue_style('wp-color-picker');
107         }
108
109         /**
110          * Execute custom background modification.
111          *
112          * @since 3.0.0
113          */
114         public function take_action() {
115                 if ( empty($_POST) )
116                         return;
117
118                 if ( isset($_POST['reset-background']) ) {
119                         check_admin_referer('custom-background-reset', '_wpnonce-custom-background-reset');
120                         remove_theme_mod('background_image');
121                         remove_theme_mod('background_image_thumb');
122                         $this->updated = true;
123                         return;
124                 }
125
126                 if ( isset($_POST['remove-background']) ) {
127                         // @TODO: Uploaded files are not removed here.
128                         check_admin_referer('custom-background-remove', '_wpnonce-custom-background-remove');
129                         set_theme_mod('background_image', '');
130                         set_theme_mod('background_image_thumb', '');
131                         $this->updated = true;
132                         wp_safe_redirect( $_POST['_wp_http_referer'] );
133                         return;
134                 }
135
136                 if ( isset($_POST['background-repeat']) ) {
137                         check_admin_referer('custom-background');
138                         if ( in_array($_POST['background-repeat'], array('repeat', 'no-repeat', 'repeat-x', 'repeat-y')) )
139                                 $repeat = $_POST['background-repeat'];
140                         else
141                                 $repeat = 'repeat';
142                         set_theme_mod('background_repeat', $repeat);
143                 }
144
145                 if ( isset($_POST['background-position-x']) ) {
146                         check_admin_referer('custom-background');
147                         if ( in_array($_POST['background-position-x'], array('center', 'right', 'left')) )
148                                 $position = $_POST['background-position-x'];
149                         else
150                                 $position = 'left';
151                         set_theme_mod('background_position_x', $position);
152                 }
153
154                 if ( isset($_POST['background-attachment']) ) {
155                         check_admin_referer('custom-background');
156                         if ( in_array($_POST['background-attachment'], array('fixed', 'scroll')) )
157                                 $attachment = $_POST['background-attachment'];
158                         else
159                                 $attachment = 'fixed';
160                         set_theme_mod('background_attachment', $attachment);
161                 }
162
163                 if ( isset($_POST['background-color']) ) {
164                         check_admin_referer('custom-background');
165                         $color = preg_replace('/[^0-9a-fA-F]/', '', $_POST['background-color']);
166                         if ( strlen($color) == 6 || strlen($color) == 3 )
167                                 set_theme_mod('background_color', $color);
168                         else
169                                 set_theme_mod('background_color', '');
170                 }
171
172                 $this->updated = true;
173         }
174
175         /**
176          * Display the custom background page.
177          *
178          * @since 3.0.0
179          */
180         public function admin_page() {
181 ?>
182 <div class="wrap" id="custom-background">
183 <h1><?php _e( 'Custom Background' ); ?></h1>
184
185 <?php if ( current_user_can( 'customize' ) ) { ?>
186 <div class="notice notice-info hide-if-no-customize">
187         <p>
188                 <?php
189                 printf(
190                         __( 'You can now manage and live-preview Custom Backgrounds in the <a href="%1$s">Customizer</a>.' ),
191                         admin_url( 'customize.php?autofocus[control]=background_image' )
192                 );
193                 ?>
194         </p>
195 </div>
196 <?php } ?>
197
198 <?php if ( ! empty( $this->updated ) ) { ?>
199 <div id="message" class="updated">
200 <p><?php printf( __( 'Background updated. <a href="%s">Visit your site</a> to see how it looks.' ), home_url( '/' ) ); ?></p>
201 </div>
202 <?php } ?>
203
204 <h3><?php _e( 'Background Image' ); ?></h3>
205
206 <table class="form-table">
207 <tbody>
208 <tr>
209 <th scope="row"><?php _e( 'Preview' ); ?></th>
210 <td>
211         <?php
212         if ( $this->admin_image_div_callback ) {
213                 call_user_func( $this->admin_image_div_callback );
214         } else {
215                 $background_styles = '';
216                 if ( $bgcolor = get_background_color() )
217                         $background_styles .= 'background-color: #' . $bgcolor . ';';
218
219                 $background_image_thumb = get_background_image();
220                 if ( $background_image_thumb ) {
221                         $background_image_thumb = esc_url( set_url_scheme( get_theme_mod( 'background_image_thumb', str_replace( '%', '%%', $background_image_thumb ) ) ) );
222
223                         // Background-image URL must be single quote, see below.
224                         $background_styles .= ' background-image: url(\'' . $background_image_thumb . '\');'
225                                 . ' background-repeat: ' . get_theme_mod( 'background_repeat', get_theme_support( 'custom-background', 'default-repeat' ) ) . ';'
226                                 . ' background-position: top ' . get_theme_mod( 'background_position_x', get_theme_support( 'custom-background', 'default-position-x' ) );
227                 }
228         ?>
229         <div id="custom-background-image" style="<?php echo $background_styles; ?>"><?php // must be double quote, see above ?>
230                 <?php if ( $background_image_thumb ) { ?>
231                 <img class="custom-background-image" src="<?php echo $background_image_thumb; ?>" style="visibility:hidden;" alt="" /><br />
232                 <img class="custom-background-image" src="<?php echo $background_image_thumb; ?>" style="visibility:hidden;" alt="" />
233                 <?php } ?>
234         </div>
235         <?php } ?>
236 </td>
237 </tr>
238
239 <?php if ( get_background_image() ) : ?>
240 <tr>
241 <th scope="row"><?php _e('Remove Image'); ?></th>
242 <td>
243 <form method="post">
244 <?php wp_nonce_field('custom-background-remove', '_wpnonce-custom-background-remove'); ?>
245 <?php submit_button( __( 'Remove Background Image' ), 'button', 'remove-background', false ); ?><br/>
246 <?php _e('This will remove the background image. You will not be able to restore any customizations.') ?>
247 </form>
248 </td>
249 </tr>
250 <?php endif; ?>
251
252 <?php $default_image = get_theme_support( 'custom-background', 'default-image' ); ?>
253 <?php if ( $default_image && get_background_image() != $default_image ) : ?>
254 <tr>
255 <th scope="row"><?php _e('Restore Original Image'); ?></th>
256 <td>
257 <form method="post">
258 <?php wp_nonce_field('custom-background-reset', '_wpnonce-custom-background-reset'); ?>
259 <?php submit_button( __( 'Restore Original Image' ), 'button', 'reset-background', false ); ?><br/>
260 <?php _e('This will restore the original background image. You will not be able to restore any customizations.') ?>
261 </form>
262 </td>
263 </tr>
264 <?php endif; ?>
265
266 <?php if ( current_user_can( 'upload_files' ) ): ?>
267 <tr>
268 <th scope="row"><?php _e('Select Image'); ?></th>
269 <td><form enctype="multipart/form-data" id="upload-form" class="wp-upload-form" method="post">
270         <p>
271                 <label for="upload"><?php _e( 'Choose an image from your computer:' ); ?></label><br />
272                 <input type="file" id="upload" name="import" />
273                 <input type="hidden" name="action" value="save" />
274                 <?php wp_nonce_field( 'custom-background-upload', '_wpnonce-custom-background-upload' ); ?>
275                 <?php submit_button( __( 'Upload' ), 'button', 'submit', false ); ?>
276         </p>
277         <p>
278                 <label for="choose-from-library-link"><?php _e( 'Or choose an image from your media library:' ); ?></label><br />
279                 <button id="choose-from-library-link" class="button"
280                         data-choose="<?php esc_attr_e( 'Choose a Background Image' ); ?>"
281                         data-update="<?php esc_attr_e( 'Set as background' ); ?>"><?php _e( 'Choose Image' ); ?></button>
282         </p>
283         </form>
284 </td>
285 </tr>
286 <?php endif; ?>
287 </tbody>
288 </table>
289
290 <h3><?php _e('Display Options') ?></h3>
291 <form method="post">
292 <table class="form-table">
293 <tbody>
294 <?php if ( get_background_image() ) : ?>
295 <tr>
296 <th scope="row"><?php _e( 'Position' ); ?></th>
297 <td><fieldset><legend class="screen-reader-text"><span><?php _e( 'Background Position' ); ?></span></legend>
298 <label>
299 <input name="background-position-x" type="radio" value="left"<?php checked( 'left', get_theme_mod( 'background_position_x', get_theme_support( 'custom-background', 'default-position-x' ) ) ); ?> />
300 <?php _e('Left') ?>
301 </label>
302 <label>
303 <input name="background-position-x" type="radio" value="center"<?php checked( 'center', get_theme_mod( 'background_position_x', get_theme_support( 'custom-background', 'default-position-x' ) ) ); ?> />
304 <?php _e('Center') ?>
305 </label>
306 <label>
307 <input name="background-position-x" type="radio" value="right"<?php checked( 'right', get_theme_mod( 'background_position_x', get_theme_support( 'custom-background', 'default-position-x' ) ) ); ?> />
308 <?php _e('Right') ?>
309 </label>
310 </fieldset></td>
311 </tr>
312
313 <tr>
314 <th scope="row"><?php _e( 'Repeat' ); ?></th>
315 <td><fieldset><legend class="screen-reader-text"><span><?php _e( 'Background Repeat' ); ?></span></legend>
316 <label><input type="radio" name="background-repeat" value="no-repeat"<?php checked( 'no-repeat', get_theme_mod( 'background_repeat', get_theme_support( 'custom-background', 'default-repeat' ) ) ); ?> /> <?php _e('No Repeat'); ?></label>
317         <label><input type="radio" name="background-repeat" value="repeat"<?php checked( 'repeat', get_theme_mod( 'background_repeat', get_theme_support( 'custom-background', 'default-repeat' ) ) ); ?> /> <?php _e('Tile'); ?></label>
318         <label><input type="radio" name="background-repeat" value="repeat-x"<?php checked( 'repeat-x', get_theme_mod( 'background_repeat', get_theme_support( 'custom-background', 'default-repeat' ) ) ); ?> /> <?php _e('Tile Horizontally'); ?></label>
319         <label><input type="radio" name="background-repeat" value="repeat-y"<?php checked( 'repeat-y', get_theme_mod( 'background_repeat', get_theme_support( 'custom-background', 'default-repeat' ) ) ); ?> /> <?php _e('Tile Vertically'); ?></label>
320 </fieldset></td>
321 </tr>
322
323 <tr>
324 <th scope="row"><?php _ex( 'Attachment', 'Background Attachment' ); ?></th>
325 <td><fieldset><legend class="screen-reader-text"><span><?php _e( 'Background Attachment' ); ?></span></legend>
326 <label>
327 <input name="background-attachment" type="radio" value="scroll" <?php checked( 'scroll', get_theme_mod( 'background_attachment', get_theme_support( 'custom-background', 'default-attachment' ) ) ); ?> />
328 <?php _e( 'Scroll' ); ?>
329 </label>
330 <label>
331 <input name="background-attachment" type="radio" value="fixed" <?php checked( 'fixed', get_theme_mod( 'background_attachment', get_theme_support( 'custom-background', 'default-attachment' ) ) ); ?> />
332 <?php _e( 'Fixed' ); ?>
333 </label>
334 </fieldset></td>
335 </tr>
336 <?php endif; // get_background_image() ?>
337 <tr>
338 <th scope="row"><?php _e( 'Background Color' ); ?></th>
339 <td><fieldset><legend class="screen-reader-text"><span><?php _e( 'Background Color' ); ?></span></legend>
340 <?php
341 $default_color = '';
342 if ( current_theme_supports( 'custom-background', 'default-color' ) )
343         $default_color = ' data-default-color="#' . esc_attr( get_theme_support( 'custom-background', 'default-color' ) ) . '"';
344 ?>
345 <input type="text" name="background-color" id="background-color" value="#<?php echo esc_attr( get_background_color() ); ?>"<?php echo $default_color ?> />
346 </fieldset></td>
347 </tr>
348 </tbody>
349 </table>
350
351 <?php wp_nonce_field('custom-background'); ?>
352 <?php submit_button( null, 'primary', 'save-background-options' ); ?>
353 </form>
354
355 </div>
356 <?php
357         }
358
359         /**
360          * Handle an Image upload for the background image.
361          *
362          * @since 3.0.0
363          */
364         public function handle_upload() {
365                 if ( empty($_FILES) )
366                         return;
367
368                 check_admin_referer('custom-background-upload', '_wpnonce-custom-background-upload');
369                 $overrides = array('test_form' => false);
370
371                 $uploaded_file = $_FILES['import'];
372                 $wp_filetype = wp_check_filetype_and_ext( $uploaded_file['tmp_name'], $uploaded_file['name'] );
373                 if ( ! wp_match_mime_types( 'image', $wp_filetype['type'] ) )
374                         wp_die( __( 'The uploaded file is not a valid image. Please try again.' ) );
375
376                 $file = wp_handle_upload($uploaded_file, $overrides);
377
378                 if ( isset($file['error']) )
379                         wp_die( $file['error'] );
380
381                 $url = $file['url'];
382                 $type = $file['type'];
383                 $file = $file['file'];
384                 $filename = basename($file);
385
386                 // Construct the object array
387                 $object = array(
388                         'post_title' => $filename,
389                         'post_content' => $url,
390                         'post_mime_type' => $type,
391                         'guid' => $url,
392                         'context' => 'custom-background'
393                 );
394
395                 // Save the data
396                 $id = wp_insert_attachment($object, $file);
397
398                 // Add the meta-data
399                 wp_update_attachment_metadata( $id, wp_generate_attachment_metadata( $id, $file ) );
400                 update_post_meta( $id, '_wp_attachment_is_custom_background', get_option('stylesheet' ) );
401
402                 set_theme_mod('background_image', esc_url_raw($url));
403
404                 $thumbnail = wp_get_attachment_image_src( $id, 'thumbnail' );
405                 set_theme_mod('background_image_thumb', esc_url_raw( $thumbnail[0] ) );
406
407                 /** This action is documented in wp-admin/custom-header.php */
408                 do_action( 'wp_create_file_in_uploads', $file, $id ); // For replication
409                 $this->updated = true;
410         }
411
412         /**
413          * Ajax handler for adding custom background context to an attachment.
414          *
415          * Triggered when the user adds a new background image from the
416          * Media Manager.
417          *
418          * @since 4.1.0
419          */
420         public function ajax_background_add() {
421                 check_ajax_referer( 'background-add', 'nonce' );
422
423                 if ( ! current_user_can( 'edit_theme_options' ) ) {
424                         wp_send_json_error();
425                 }
426
427                 $attachment_id = absint( $_POST['attachment_id'] );
428                 if ( $attachment_id < 1 ) {
429                         wp_send_json_error();
430                 }
431
432                 update_post_meta( $attachment_id, '_wp_attachment_is_custom_background', get_stylesheet() );
433
434                 wp_send_json_success();
435         }
436
437         /**
438          *
439          * @since 3.4.0
440          * @deprecated 3.5.0
441          *
442          * @param array $form_fields
443          * @return array $form_fields
444          */
445         public function attachment_fields_to_edit( $form_fields ) {
446                 return $form_fields;
447         }
448
449         /**
450          *
451          * @since 3.4.0
452          * @deprecated 3.5.0
453          *
454          * @param array $tabs
455          * @return array $tabs
456          */
457         public function filter_upload_tabs( $tabs ) {
458                 return $tabs;
459         }
460
461         /**
462          *
463          * @since 3.4.0
464          * @deprecated 3.5.0
465          */
466         public function wp_set_background_image() {
467                 if ( ! current_user_can('edit_theme_options') || ! isset( $_POST['attachment_id'] ) ) exit;
468                 $attachment_id = absint($_POST['attachment_id']);
469                 /** This filter is documented in wp-admin/includes/media.php */
470                 $sizes = array_keys(apply_filters( 'image_size_names_choose', array('thumbnail' => __('Thumbnail'), 'medium' => __('Medium'), 'large' => __('Large'), 'full' => __('Full Size')) ));
471                 $size = 'thumbnail';
472                 if ( in_array( $_POST['size'], $sizes ) )
473                         $size = esc_attr( $_POST['size'] );
474
475                 update_post_meta( $attachment_id, '_wp_attachment_is_custom_background', get_option('stylesheet' ) );
476                 $url = wp_get_attachment_image_src( $attachment_id, $size );
477                 $thumbnail = wp_get_attachment_image_src( $attachment_id, 'thumbnail' );
478                 set_theme_mod( 'background_image', esc_url_raw( $url[0] ) );
479                 set_theme_mod( 'background_image_thumb', esc_url_raw( $thumbnail[0] ) );
480                 exit;
481         }
482 }