PageRenderTime 63ms CodeModel.GetById 24ms RepoModel.GetById 0ms app.codeStats 0ms

/wp-includes/class-wp-customize-control.php

https://gitlab.com/math4youbyusgroupillinois/WordPress
PHP | 1188 lines | 641 code | 122 blank | 425 comment | 42 complexity | 67bdf112f353a48fada90883281e6dca MD5 | raw file
  1. <?php
  2. /**
  3. * Customize Control Class
  4. *
  5. * @package WordPress
  6. * @subpackage Customize
  7. * @since 3.4.0
  8. */
  9. class WP_Customize_Control {
  10. /**
  11. * Incremented with each new class instantiation, then stored in $instance_number.
  12. *
  13. * Used when sorting two instances whose priorities are equal.
  14. *
  15. * @since 4.1.0
  16. * @access protected
  17. * @var int
  18. */
  19. protected static $instance_count = 0;
  20. /**
  21. * Order in which this instance was created in relation to other instances.
  22. *
  23. * @since 4.1.0
  24. * @access public
  25. * @var int
  26. */
  27. public $instance_number;
  28. /**
  29. * @access public
  30. * @var WP_Customize_Manager
  31. */
  32. public $manager;
  33. /**
  34. * @access public
  35. * @var string
  36. */
  37. public $id;
  38. /**
  39. * All settings tied to the control.
  40. *
  41. * @access public
  42. * @var array
  43. */
  44. public $settings;
  45. /**
  46. * The primary setting for the control (if there is one).
  47. *
  48. * @access public
  49. * @var string
  50. */
  51. public $setting = 'default';
  52. /**
  53. * @access public
  54. * @var int
  55. */
  56. public $priority = 10;
  57. /**
  58. * @access public
  59. * @var string
  60. */
  61. public $section = '';
  62. /**
  63. * @access public
  64. * @var string
  65. */
  66. public $label = '';
  67. /**
  68. * @access public
  69. * @var string
  70. */
  71. public $description = '';
  72. /**
  73. * @todo: Remove choices
  74. *
  75. * @access public
  76. * @var array
  77. */
  78. public $choices = array();
  79. /**
  80. * @access public
  81. * @var array
  82. */
  83. public $input_attrs = array();
  84. /**
  85. * @deprecated It is better to just call the json() method
  86. * @access public
  87. * @var array
  88. */
  89. public $json = array();
  90. /**
  91. * @access public
  92. * @var string
  93. */
  94. public $type = 'text';
  95. /**
  96. * Callback.
  97. *
  98. * @since 4.0.0
  99. * @access public
  100. *
  101. * @see WP_Customize_Control::active()
  102. *
  103. * @var callable Callback is called with one argument, the instance of
  104. * WP_Customize_Control, and returns bool to indicate whether
  105. * the control is active (such as it relates to the URL
  106. * currently being previewed).
  107. */
  108. public $active_callback = '';
  109. /**
  110. * Constructor.
  111. *
  112. * Supplied $args override class property defaults.
  113. *
  114. * If $args['settings'] is not defined, use the $id as the setting ID.
  115. *
  116. * @since 3.4.0
  117. *
  118. * @param WP_Customize_Manager $manager
  119. * @param string $id
  120. * @param array $args
  121. */
  122. public function __construct( $manager, $id, $args = array() ) {
  123. $keys = array_keys( get_object_vars( $this ) );
  124. foreach ( $keys as $key ) {
  125. if ( isset( $args[ $key ] ) ) {
  126. $this->$key = $args[ $key ];
  127. }
  128. }
  129. $this->manager = $manager;
  130. $this->id = $id;
  131. if ( empty( $this->active_callback ) ) {
  132. $this->active_callback = array( $this, 'active_callback' );
  133. }
  134. self::$instance_count += 1;
  135. $this->instance_number = self::$instance_count;
  136. // Process settings.
  137. if ( empty( $this->settings ) ) {
  138. $this->settings = $id;
  139. }
  140. $settings = array();
  141. if ( is_array( $this->settings ) ) {
  142. foreach ( $this->settings as $key => $setting ) {
  143. $settings[ $key ] = $this->manager->get_setting( $setting );
  144. }
  145. } else {
  146. $this->setting = $this->manager->get_setting( $this->settings );
  147. $settings['default'] = $this->setting;
  148. }
  149. $this->settings = $settings;
  150. }
  151. /**
  152. * Enqueue control related scripts/styles.
  153. *
  154. * @since 3.4.0
  155. */
  156. public function enqueue() {}
  157. /**
  158. * Check whether control is active to current Customizer preview.
  159. *
  160. * @since 4.0.0
  161. * @access public
  162. *
  163. * @return bool Whether the control is active to the current preview.
  164. */
  165. final public function active() {
  166. $control = $this;
  167. $active = call_user_func( $this->active_callback, $this );
  168. /**
  169. * Filter response of WP_Customize_Control::active().
  170. *
  171. * @since 4.0.0
  172. *
  173. * @param bool $active Whether the Customizer control is active.
  174. * @param WP_Customize_Control $control WP_Customize_Control instance.
  175. */
  176. $active = apply_filters( 'customize_control_active', $active, $control );
  177. return $active;
  178. }
  179. /**
  180. * Default callback used when invoking WP_Customize_Control::active().
  181. *
  182. * Subclasses can override this with their specific logic, or they may
  183. * provide an 'active_callback' argument to the constructor.
  184. *
  185. * @since 4.0.0
  186. * @access public
  187. *
  188. * @return bool Always true.
  189. */
  190. public function active_callback() {
  191. return true;
  192. }
  193. /**
  194. * Fetch a setting's value.
  195. * Grabs the main setting by default.
  196. *
  197. * @since 3.4.0
  198. *
  199. * @param string $setting_key
  200. * @return mixed The requested setting's value, if the setting exists.
  201. */
  202. final public function value( $setting_key = 'default' ) {
  203. if ( isset( $this->settings[ $setting_key ] ) ) {
  204. return $this->settings[ $setting_key ]->value();
  205. }
  206. }
  207. /**
  208. * Refresh the parameters passed to the JavaScript via JSON.
  209. *
  210. * @since 3.4.0
  211. */
  212. public function to_json() {
  213. $this->json['settings'] = array();
  214. foreach ( $this->settings as $key => $setting ) {
  215. $this->json['settings'][ $key ] = $setting->id;
  216. }
  217. $this->json['type'] = $this->type;
  218. $this->json['priority'] = $this->priority;
  219. $this->json['active'] = $this->active();
  220. $this->json['section'] = $this->section;
  221. $this->json['content'] = $this->get_content();
  222. $this->json['label'] = $this->label;
  223. $this->json['description'] = $this->description;
  224. $this->json['instanceNumber'] = $this->instance_number;
  225. }
  226. /**
  227. * Get the data to export to the client via JSON.
  228. *
  229. * @since 4.1.0
  230. *
  231. * @return array Array of parameters passed to the JavaScript.
  232. */
  233. public function json() {
  234. $this->to_json();
  235. return $this->json;
  236. }
  237. /**
  238. * Check if the theme supports the control and check user capabilities.
  239. *
  240. * @since 3.4.0
  241. *
  242. * @return bool False if theme doesn't support the control or user doesn't have the required permissions, otherwise true.
  243. */
  244. final public function check_capabilities() {
  245. foreach ( $this->settings as $setting ) {
  246. if ( ! $setting->check_capabilities() )
  247. return false;
  248. }
  249. $section = $this->manager->get_section( $this->section );
  250. if ( isset( $section ) && ! $section->check_capabilities() )
  251. return false;
  252. return true;
  253. }
  254. /**
  255. * Get the control's content for insertion into the Customizer pane.
  256. *
  257. * @since 4.1.0
  258. *
  259. * @return string Contents of the control.
  260. */
  261. final public function get_content() {
  262. ob_start();
  263. $this->maybe_render();
  264. $template = trim( ob_get_contents() );
  265. ob_end_clean();
  266. return $template;
  267. }
  268. /**
  269. * Check capabilities and render the control.
  270. *
  271. * @since 3.4.0
  272. * @uses WP_Customize_Control::render()
  273. */
  274. final public function maybe_render() {
  275. if ( ! $this->check_capabilities() )
  276. return;
  277. /**
  278. * Fires just before the current Customizer control is rendered.
  279. *
  280. * @since 3.4.0
  281. *
  282. * @param WP_Customize_Control $this WP_Customize_Control instance.
  283. */
  284. do_action( 'customize_render_control', $this );
  285. /**
  286. * Fires just before a specific Customizer control is rendered.
  287. *
  288. * The dynamic portion of the hook name, `$this->id`, refers to
  289. * the control ID.
  290. *
  291. * @since 3.4.0
  292. *
  293. * @param WP_Customize_Control $this {@see WP_Customize_Control} instance.
  294. */
  295. do_action( 'customize_render_control_' . $this->id, $this );
  296. $this->render();
  297. }
  298. /**
  299. * Renders the control wrapper and calls $this->render_content() for the internals.
  300. *
  301. * @since 3.4.0
  302. */
  303. protected function render() {
  304. $id = 'customize-control-' . str_replace( '[', '-', str_replace( ']', '', $this->id ) );
  305. $class = 'customize-control customize-control-' . $this->type;
  306. ?><li id="<?php echo esc_attr( $id ); ?>" class="<?php echo esc_attr( $class ); ?>">
  307. <?php $this->render_content(); ?>
  308. </li><?php
  309. }
  310. /**
  311. * Get the data link attribute for a setting.
  312. *
  313. * @since 3.4.0
  314. *
  315. * @param string $setting_key
  316. * @return string Data link parameter, if $setting_key is a valid setting, empty string otherwise.
  317. */
  318. public function get_link( $setting_key = 'default' ) {
  319. if ( ! isset( $this->settings[ $setting_key ] ) )
  320. return '';
  321. return 'data-customize-setting-link="' . esc_attr( $this->settings[ $setting_key ]->id ) . '"';
  322. }
  323. /**
  324. * Render the data link attribute for the control's input element.
  325. *
  326. * @since 3.4.0
  327. * @uses WP_Customize_Control::get_link()
  328. *
  329. * @param string $setting_key
  330. */
  331. public function link( $setting_key = 'default' ) {
  332. echo $this->get_link( $setting_key );
  333. }
  334. /**
  335. * Render the custom attributes for the control's input element.
  336. *
  337. * @since 4.0.0
  338. * @access public
  339. */
  340. public function input_attrs() {
  341. foreach( $this->input_attrs as $attr => $value ) {
  342. echo $attr . '="' . esc_attr( $value ) . '" ';
  343. }
  344. }
  345. /**
  346. * Render the control's content.
  347. *
  348. * Allows the content to be overriden without having to rewrite the wrapper in $this->render().
  349. *
  350. * Supports basic input types `text`, `checkbox`, `textarea`, `radio`, `select` and `dropdown-pages`.
  351. * Additional input types such as `email`, `url`, `number`, `hidden` and `date` are supported implicitly.
  352. *
  353. * Control content can alternately be rendered in JS. See {@see WP_Customize_Control::print_template()}.
  354. *
  355. * @since 3.4.0
  356. */
  357. protected function render_content() {
  358. switch( $this->type ) {
  359. case 'checkbox':
  360. ?>
  361. <label>
  362. <input type="checkbox" value="<?php echo esc_attr( $this->value() ); ?>" <?php $this->link(); checked( $this->value() ); ?> />
  363. <?php echo esc_html( $this->label ); ?>
  364. <?php if ( ! empty( $this->description ) ) : ?>
  365. <span class="description customize-control-description"><?php echo $this->description; ?></span>
  366. <?php endif; ?>
  367. </label>
  368. <?php
  369. break;
  370. case 'radio':
  371. if ( empty( $this->choices ) )
  372. return;
  373. $name = '_customize-radio-' . $this->id;
  374. if ( ! empty( $this->label ) ) : ?>
  375. <span class="customize-control-title"><?php echo esc_html( $this->label ); ?></span>
  376. <?php endif;
  377. if ( ! empty( $this->description ) ) : ?>
  378. <span class="description customize-control-description"><?php echo $this->description ; ?></span>
  379. <?php endif;
  380. foreach ( $this->choices as $value => $label ) :
  381. ?>
  382. <label>
  383. <input type="radio" value="<?php echo esc_attr( $value ); ?>" name="<?php echo esc_attr( $name ); ?>" <?php $this->link(); checked( $this->value(), $value ); ?> />
  384. <?php echo esc_html( $label ); ?><br/>
  385. </label>
  386. <?php
  387. endforeach;
  388. break;
  389. case 'select':
  390. if ( empty( $this->choices ) )
  391. return;
  392. ?>
  393. <label>
  394. <?php if ( ! empty( $this->label ) ) : ?>
  395. <span class="customize-control-title"><?php echo esc_html( $this->label ); ?></span>
  396. <?php endif;
  397. if ( ! empty( $this->description ) ) : ?>
  398. <span class="description customize-control-description"><?php echo $this->description; ?></span>
  399. <?php endif; ?>
  400. <select <?php $this->link(); ?>>
  401. <?php
  402. foreach ( $this->choices as $value => $label )
  403. echo '<option value="' . esc_attr( $value ) . '"' . selected( $this->value(), $value, false ) . '>' . $label . '</option>';
  404. ?>
  405. </select>
  406. </label>
  407. <?php
  408. break;
  409. case 'textarea':
  410. ?>
  411. <label>
  412. <?php if ( ! empty( $this->label ) ) : ?>
  413. <span class="customize-control-title"><?php echo esc_html( $this->label ); ?></span>
  414. <?php endif;
  415. if ( ! empty( $this->description ) ) : ?>
  416. <span class="description customize-control-description"><?php echo $this->description; ?></span>
  417. <?php endif; ?>
  418. <textarea rows="5" <?php $this->link(); ?>><?php echo esc_textarea( $this->value() ); ?></textarea>
  419. </label>
  420. <?php
  421. break;
  422. case 'dropdown-pages':
  423. $dropdown = wp_dropdown_pages(
  424. array(
  425. 'name' => '_customize-dropdown-pages-' . $this->id,
  426. 'echo' => 0,
  427. 'show_option_none' => __( '&mdash; Select &mdash;' ),
  428. 'option_none_value' => '0',
  429. 'selected' => $this->value(),
  430. )
  431. );
  432. // Hackily add in the data link parameter.
  433. $dropdown = str_replace( '<select', '<select ' . $this->get_link(), $dropdown );
  434. printf(
  435. '<label class="customize-control-select"><span class="customize-control-title">%s</span> %s</label>',
  436. $this->label,
  437. $dropdown
  438. );
  439. break;
  440. default:
  441. ?>
  442. <label>
  443. <?php if ( ! empty( $this->label ) ) : ?>
  444. <span class="customize-control-title"><?php echo esc_html( $this->label ); ?></span>
  445. <?php endif;
  446. if ( ! empty( $this->description ) ) : ?>
  447. <span class="description customize-control-description"><?php echo $this->description; ?></span>
  448. <?php endif; ?>
  449. <input type="<?php echo esc_attr( $this->type ); ?>" <?php $this->input_attrs(); ?> value="<?php echo esc_attr( $this->value() ); ?>" <?php $this->link(); ?> />
  450. </label>
  451. <?php
  452. break;
  453. }
  454. }
  455. /**
  456. * Render the control's JS template.
  457. *
  458. * This function is only run for control types that have been registered with
  459. * {@see WP_Customize_Manager::register_control_type()}.
  460. *
  461. * In the future, this will also print the template for the control's container
  462. * element and be override-able.
  463. *
  464. * @since 4.1.0
  465. */
  466. final public function print_template() {
  467. ?>
  468. <script type="text/html" id="tmpl-customize-control-<?php echo $this->type; ?>-content">
  469. <?php $this->content_template(); ?>
  470. </script>
  471. <?php
  472. }
  473. /**
  474. * An Underscore (JS) template for this control's content (but not its container).
  475. *
  476. * Class variables for this control class are available in the `data` JS object;
  477. * export custom variables by overriding {@see WP_Customize_Control::to_json()}.
  478. *
  479. * @see WP_Customize_Control::print_template()
  480. *
  481. * @since 4.1.0
  482. */
  483. protected function content_template() {}
  484. }
  485. /**
  486. * Customize Color Control Class
  487. *
  488. * @package WordPress
  489. * @subpackage Customize
  490. * @since 3.4.0
  491. */
  492. class WP_Customize_Color_Control extends WP_Customize_Control {
  493. /**
  494. * @access public
  495. * @var string
  496. */
  497. public $type = 'color';
  498. /**
  499. * @access public
  500. * @var array
  501. */
  502. public $statuses;
  503. /**
  504. * Constructor.
  505. *
  506. * @since 3.4.0
  507. * @uses WP_Customize_Control::__construct()
  508. *
  509. * @param WP_Customize_Manager $manager
  510. * @param string $id
  511. * @param array $args
  512. */
  513. public function __construct( $manager, $id, $args = array() ) {
  514. $this->statuses = array( '' => __('Default') );
  515. parent::__construct( $manager, $id, $args );
  516. }
  517. /**
  518. * Enqueue scripts/styles for the color picker.
  519. *
  520. * @since 3.4.0
  521. */
  522. public function enqueue() {
  523. wp_enqueue_script( 'wp-color-picker' );
  524. wp_enqueue_style( 'wp-color-picker' );
  525. }
  526. /**
  527. * Refresh the parameters passed to the JavaScript via JSON.
  528. *
  529. * @since 3.4.0
  530. * @uses WP_Customize_Control::to_json()
  531. */
  532. public function to_json() {
  533. parent::to_json();
  534. $this->json['statuses'] = $this->statuses;
  535. $this->json['defaultValue'] = $this->setting->default;
  536. }
  537. /**
  538. * Don't render the control content from PHP, as it's rendered via JS on load.
  539. *
  540. * @since 3.4.0
  541. */
  542. public function render_content() {}
  543. /**
  544. * Render a JS template for the content of the color picker control.
  545. *
  546. * @since 4.1.0
  547. */
  548. public function content_template() {
  549. ?>
  550. <# var defaultValue = '';
  551. if ( data.defaultValue ) {
  552. if ( '#' !== data.defaultValue.substring( 0, 1 ) ) {
  553. defaultValue = '#' + data.defaultValue;
  554. } else {
  555. defaultValue = data.defaultValue;
  556. }
  557. defaultValue = ' data-default-color=' + defaultValue; // Quotes added automatically.
  558. } #>
  559. <label>
  560. <# if ( data.label ) { #>
  561. <span class="customize-control-title">{{{ data.label }}}</span>
  562. <# } #>
  563. <# if ( data.description ) { #>
  564. <span class="description customize-control-description">{{{ data.description }}}</span>
  565. <# } #>
  566. <div class="customize-control-content">
  567. <input class="color-picker-hex" type="text" maxlength="7" placeholder="<?php esc_attr_e( 'Hex Value' ); ?>" {{ defaultValue }} />
  568. </div>
  569. </label>
  570. <?php
  571. }
  572. }
  573. /**
  574. * Customize Upload Control Class
  575. *
  576. * @package WordPress
  577. * @subpackage Customize
  578. * @since 3.4.0
  579. */
  580. class WP_Customize_Upload_Control extends WP_Customize_Control {
  581. public $type = 'upload';
  582. public $mime_type = '';
  583. public $button_labels = array();
  584. public $removed = ''; // unused
  585. public $context; // unused
  586. public $extensions = array(); // unused
  587. /**
  588. * Constructor.
  589. *
  590. * @since 4.1.0
  591. *
  592. * @param WP_Customize_Manager $manager {@see WP_Customize_Manager} instance.
  593. */
  594. public function __construct( $manager, $id, $args = array() ) {
  595. parent::__construct( $manager, $id, $args );
  596. $this->button_labels = array(
  597. 'select' => __( 'Select File' ),
  598. 'change' => __( 'Change File' ),
  599. 'default' => __( 'Default' ),
  600. 'remove' => __( 'Remove' ),
  601. 'placeholder' => __( 'No file selected' ),
  602. 'frame_title' => __( 'Select File' ),
  603. 'frame_button' => __( 'Choose File' ),
  604. );
  605. }
  606. /**
  607. * Enqueue control related scripts/styles.
  608. *
  609. * @since 3.4.0
  610. */
  611. public function enqueue() {
  612. wp_enqueue_media();
  613. }
  614. /**
  615. * Refresh the parameters passed to the JavaScript via JSON.
  616. *
  617. * @since 3.4.0
  618. * @uses WP_Customize_Control::to_json()
  619. */
  620. public function to_json() {
  621. parent::to_json();
  622. $this->json['mime_type'] = $this->mime_type;
  623. $this->json['button_labels'] = $this->button_labels;
  624. $value = $this->value();
  625. if ( is_object( $this->setting ) ) {
  626. if ( $this->setting->default ) {
  627. // Fake an attachment model - needs all fields used by template.
  628. $type = in_array( substr( $this->setting->default, -3 ), array( 'jpg', 'png', 'gif', 'bmp' ) ) ? 'image' : 'document';
  629. $default_attachment = array(
  630. 'id' => 1,
  631. 'url' => $this->setting->default,
  632. 'type' => $type,
  633. 'icon' => wp_mime_type_icon( $type ),
  634. 'title' => basename( $this->setting->default ),
  635. );
  636. if ( 'image' === $type ) {
  637. $default_attachment['sizes'] = array(
  638. 'full' => array( 'url' => $this->setting->default ),
  639. );
  640. }
  641. $this->json['defaultAttachment'] = $default_attachment;
  642. }
  643. if ( $value && $this->setting->default && $value === $this->setting->default ) {
  644. // Set the default as the attachment.
  645. $this->json['attachment'] = $this->json['defaultAttachment'];
  646. } elseif ( $value ) {
  647. // Get the attachment model for the existing file.
  648. $attachment_id = attachment_url_to_postid( $value );
  649. if ( $attachment_id ) {
  650. $this->json['attachment'] = wp_prepare_attachment_for_js( $attachment_id );
  651. }
  652. }
  653. }
  654. }
  655. /**
  656. * Don't render any content for this control from PHP.
  657. *
  658. * @see WP_Customize_Upload_Control::content_template()
  659. * @since 3.4.0
  660. */
  661. public function render_content() {}
  662. /**
  663. * Render a JS template for the content of the upload control.
  664. *
  665. * @since 4.1.0
  666. */
  667. public function content_template() {
  668. ?>
  669. <label for="{{ data.settings['default'] }}-button">
  670. <# if ( data.label ) { #>
  671. <span class="customize-control-title">{{ data.label }}</span>
  672. <# } #>
  673. <# if ( data.description ) { #>
  674. <span class="description customize-control-description">{{{ data.description }}}</span>
  675. <# } #>
  676. </label>
  677. <# if ( data.attachment && data.attachment.id ) { #>
  678. <div class="current">
  679. <div class="container">
  680. <div class="attachment-media-view attachment-media-view-{{ data.attachment.type }} {{ data.attachment.orientation }}">
  681. <div class="thumbnail thumbnail-{{ data.attachment.type }}">
  682. <# if ( 'image' === data.attachment.type && data.attachment.sizes && data.attachment.sizes.medium ) { #>
  683. <img class="attachment-thumb" src="{{ data.attachment.sizes.medium.url }}" draggable="false" />
  684. <# } else if ( 'image' === data.attachment.type && data.attachment.sizes && data.attachment.sizes.full ) { #>
  685. <img class="attachment-thumb" src="{{ data.attachment.sizes.full.url }}" draggable="false" />
  686. <# } else if ( 'audio' === data.attachment.type ) { #>
  687. <img class="attachment-thumb type-icon" src="{{ data.attachment.icon }}" class="icon" draggable="false" />
  688. <p class="attachment-meta attachment-meta-title">&#8220;{{ data.attachment.title }}&#8221;</p>
  689. <# if ( data.attachment.album || data.attachment.meta.album ) { #>
  690. <p class="attachment-meta"><em>{{ data.attachment.album || data.attachment.meta.album }}</em></p>
  691. <# } #>
  692. <# if ( data.attachment.artist || data.attachment.meta.artist ) { #>
  693. <p class="attachment-meta">{{ data.attachment.artist || data.attachment.meta.artist }}</p>
  694. <# } #>
  695. <# } else { #>
  696. <img class="attachment-thumb type-icon" src="{{ data.attachment.icon }}" class="icon" draggable="false" />
  697. <p class="attachment-title">{{ data.attachment.title }}</p>
  698. <# } #>
  699. </div>
  700. </div>
  701. </div>
  702. </div>
  703. <div class="actions">
  704. <button type="button" class="button remove-button"><?php echo $this->button_labels['remove']; ?></button>
  705. <button type="button" class="button upload-button" id="{{ data.settings['default'] }}-button"><?php echo $this->button_labels['change']; ?></button>
  706. <div style="clear:both"></div>
  707. </div>
  708. <# } else { #>
  709. <div class="current">
  710. <div class="container">
  711. <div class="placeholder">
  712. <div class="inner">
  713. <span>
  714. <?php echo $this->button_labels['placeholder']; ?>
  715. </span>
  716. </div>
  717. </div>
  718. </div>
  719. </div>
  720. <div class="actions">
  721. <# if ( data.defaultAttachment ) { #>
  722. <button type="button" class="button default-button"><?php echo $this->button_labels['default']; ?></button>
  723. <# } #>
  724. <button type="button" class="button upload-button" id="{{ data.settings['default'] }}-button"><?php echo $this->button_labels['select']; ?></button>
  725. <div style="clear:both"></div>
  726. </div>
  727. <# } #>
  728. <?php
  729. }
  730. }
  731. /**
  732. * Customize Image Control Class
  733. *
  734. * @package WordPress
  735. * @subpackage Customize
  736. * @since 3.4.0
  737. */
  738. class WP_Customize_Image_Control extends WP_Customize_Upload_Control {
  739. public $type = 'image';
  740. public $mime_type = 'image';
  741. /**
  742. * Constructor.
  743. *
  744. * @since 3.4.0
  745. * @uses WP_Customize_Upload_Control::__construct()
  746. *
  747. * @param WP_Customize_Manager $manager
  748. * @param string $id
  749. * @param array $args
  750. */
  751. public function __construct( $manager, $id, $args = array() ) {
  752. parent::__construct( $manager, $id, $args );
  753. $this->button_labels = array(
  754. 'select' => __( 'Select Image' ),
  755. 'change' => __( 'Change Image' ),
  756. 'remove' => __( 'Remove' ),
  757. 'default' => __( 'Default' ),
  758. 'placeholder' => __( 'No image selected' ),
  759. 'frame_title' => __( 'Select Image' ),
  760. 'frame_button' => __( 'Choose Image' ),
  761. );
  762. }
  763. /**
  764. * @since 3.4.2
  765. * @deprecated 4.1.0
  766. */
  767. public function prepare_control() {}
  768. /**
  769. * @since 3.4.0
  770. * @deprecated 4.1.0
  771. *
  772. * @param string $id
  773. * @param string $label
  774. * @param mixed $callback
  775. */
  776. public function add_tab( $id, $label, $callback ) {}
  777. /**
  778. * @since 3.4.0
  779. * @deprecated 4.1.0
  780. *
  781. * @param string $id
  782. */
  783. public function remove_tab( $id ) {}
  784. /**
  785. * @since 3.4.0
  786. * @deprecated 4.1.0
  787. *
  788. * @param string $url
  789. * @param string $thumbnail_url
  790. */
  791. public function print_tab_image( $url, $thumbnail_url = null ) {}
  792. }
  793. /**
  794. * Customize Background Image Control Class
  795. *
  796. * @package WordPress
  797. * @subpackage Customize
  798. * @since 3.4.0
  799. */
  800. class WP_Customize_Background_Image_Control extends WP_Customize_Image_Control {
  801. public $type = 'background';
  802. /**
  803. * Constructor.
  804. *
  805. * @since 3.4.0
  806. * @uses WP_Customize_Image_Control::__construct()
  807. *
  808. * @param WP_Customize_Manager $manager
  809. */
  810. public function __construct( $manager ) {
  811. parent::__construct( $manager, 'background_image', array(
  812. 'label' => __( 'Background Image' ),
  813. 'section' => 'background_image',
  814. ) );
  815. }
  816. /**
  817. * Enqueue control related scripts/styles.
  818. *
  819. * @since 4.1.0
  820. */
  821. public function enqueue() {
  822. parent::enqueue();
  823. wp_localize_script( 'customize-controls', '_wpCustomizeBackground', array(
  824. 'nonces' => array(
  825. 'add' => wp_create_nonce( 'background-add' ),
  826. ),
  827. ) );
  828. }
  829. }
  830. class WP_Customize_Header_Image_Control extends WP_Customize_Image_Control {
  831. public $type = 'header';
  832. public $uploaded_headers;
  833. public $default_headers;
  834. /**
  835. * @param WP_Customize_Manager $manager
  836. */
  837. public function __construct( $manager ) {
  838. parent::__construct( $manager, 'header_image', array(
  839. 'label' => __( 'Header Image' ),
  840. 'settings' => array(
  841. 'default' => 'header_image',
  842. 'data' => 'header_image_data',
  843. ),
  844. 'section' => 'header_image',
  845. 'removed' => 'remove-header',
  846. 'get_url' => 'get_header_image',
  847. ) );
  848. }
  849. public function enqueue() {
  850. wp_enqueue_media();
  851. wp_enqueue_script( 'customize-views' );
  852. $this->prepare_control();
  853. wp_localize_script( 'customize-views', '_wpCustomizeHeader', array(
  854. 'data' => array(
  855. 'width' => absint( get_theme_support( 'custom-header', 'width' ) ),
  856. 'height' => absint( get_theme_support( 'custom-header', 'height' ) ),
  857. 'flex-width' => absint( get_theme_support( 'custom-header', 'flex-width' ) ),
  858. 'flex-height' => absint( get_theme_support( 'custom-header', 'flex-height' ) ),
  859. 'currentImgSrc' => $this->get_current_image_src(),
  860. ),
  861. 'nonces' => array(
  862. 'add' => wp_create_nonce( 'header-add' ),
  863. 'remove' => wp_create_nonce( 'header-remove' ),
  864. ),
  865. 'uploads' => $this->uploaded_headers,
  866. 'defaults' => $this->default_headers
  867. ) );
  868. parent::enqueue();
  869. }
  870. public function prepare_control() {
  871. global $custom_image_header;
  872. if ( empty( $custom_image_header ) ) {
  873. return;
  874. }
  875. // Process default headers and uploaded headers.
  876. $custom_image_header->process_default_headers();
  877. $this->default_headers = $custom_image_header->get_default_header_images();
  878. $this->uploaded_headers = $custom_image_header->get_uploaded_header_images();
  879. }
  880. public function print_header_image_template() {
  881. ?>
  882. <script type="text/template" id="tmpl-header-choice">
  883. <# if (data.random) { #>
  884. <button type="button" class="button display-options random">
  885. <span class="dashicons dashicons-randomize dice"></span>
  886. <# if ( data.type === 'uploaded' ) { #>
  887. <?php _e( 'Randomize uploaded headers' ); ?>
  888. <# } else if ( data.type === 'default' ) { #>
  889. <?php _e( 'Randomize suggested headers' ); ?>
  890. <# } #>
  891. </button>
  892. <# } else { #>
  893. <# if (data.type === 'uploaded') { #>
  894. <div class="dashicons dashicons-no close"></div>
  895. <# } #>
  896. <button type="button" class="choice thumbnail"
  897. data-customize-image-value="{{{data.header.url}}}"
  898. data-customize-header-image-data="{{JSON.stringify(data.header)}}">
  899. <span class="screen-reader-text"><?php _e( 'Set image' ); ?></span>
  900. <img src="{{{data.header.thumbnail_url}}}" alt="{{{data.header.alt_text || data.header.description}}}">
  901. </button>
  902. <# } #>
  903. </script>
  904. <script type="text/template" id="tmpl-header-current">
  905. <# if (data.choice) { #>
  906. <# if (data.random) { #>
  907. <div class="placeholder">
  908. <div class="inner">
  909. <span><span class="dashicons dashicons-randomize dice"></span>
  910. <# if ( data.type === 'uploaded' ) { #>
  911. <?php _e( 'Randomizing uploaded headers' ); ?>
  912. <# } else if ( data.type === 'default' ) { #>
  913. <?php _e( 'Randomizing suggested headers' ); ?>
  914. <# } #>
  915. </span>
  916. </div>
  917. </div>
  918. <# } else { #>
  919. <img src="{{{data.header.thumbnail_url}}}" alt="{{{data.header.alt_text || data.header.description}}}" tabindex="0"/>
  920. <# } #>
  921. <# } else { #>
  922. <div class="placeholder">
  923. <div class="inner">
  924. <span>
  925. <?php _e( 'No image set' ); ?>
  926. </span>
  927. </div>
  928. </div>
  929. <# } #>
  930. </script>
  931. <?php
  932. }
  933. public function get_current_image_src() {
  934. $src = $this->value();
  935. if ( isset( $this->get_url ) ) {
  936. $src = call_user_func( $this->get_url, $src );
  937. return $src;
  938. }
  939. return null;
  940. }
  941. public function render_content() {
  942. $this->print_header_image_template();
  943. $visibility = $this->get_current_image_src() ? '' : ' style="display:none" ';
  944. $width = absint( get_theme_support( 'custom-header', 'width' ) );
  945. $height = absint( get_theme_support( 'custom-header', 'height' ) );
  946. ?>
  947. <div class="customize-control-content">
  948. <p class="customizer-section-intro">
  949. <?php
  950. if ( $width && $height ) {
  951. printf( __( 'While you can crop images to your liking after clicking <strong>Add new image</strong>, your theme recommends a header size of <strong>%s &times; %s</strong> pixels.' ), $width, $height );
  952. } elseif ( $width ) {
  953. printf( __( 'While you can crop images to your liking after clicking <strong>Add new image</strong>, your theme recommends a header width of <strong>%s</strong> pixels.' ), $width );
  954. } else {
  955. printf( __( 'While you can crop images to your liking after clicking <strong>Add new image</strong>, your theme recommends a header height of <strong>%s</strong> pixels.' ), $height );
  956. }
  957. ?>
  958. </p>
  959. <div class="current">
  960. <span class="customize-control-title">
  961. <?php _e( 'Current header' ); ?>
  962. </span>
  963. <div class="container">
  964. </div>
  965. </div>
  966. <div class="actions">
  967. <?php /* translators: Hide as in hide header image via the Customizer */ ?>
  968. <button type="button"<?php echo $visibility ?> class="button remove"><?php _ex( 'Hide image', 'custom header' ); ?></button>
  969. <?php /* translators: New as in add new header image via the Customizer */ ?>
  970. <button type="button" class="button new"><?php _ex( 'Add new image', 'header image' ); ?></button>
  971. <div style="clear:both"></div>
  972. </div>
  973. <div class="choices">
  974. <span class="customize-control-title header-previously-uploaded">
  975. <?php _ex( 'Previously uploaded', 'custom headers' ); ?>
  976. </span>
  977. <div class="uploaded">
  978. <div class="list">
  979. </div>
  980. </div>
  981. <span class="customize-control-title header-default">
  982. <?php _ex( 'Suggested', 'custom headers' ); ?>
  983. </span>
  984. <div class="default">
  985. <div class="list">
  986. </div>
  987. </div>
  988. </div>
  989. </div>
  990. <?php
  991. }
  992. }
  993. /**
  994. * Widget Area Customize Control Class
  995. *
  996. * @since 3.9.0
  997. */
  998. class WP_Widget_Area_Customize_Control extends WP_Customize_Control {
  999. public $type = 'sidebar_widgets';
  1000. public $sidebar_id;
  1001. public function to_json() {
  1002. parent::to_json();
  1003. $exported_properties = array( 'sidebar_id' );
  1004. foreach ( $exported_properties as $key ) {
  1005. $this->json[ $key ] = $this->$key;
  1006. }
  1007. }
  1008. public function render_content() {
  1009. ?>
  1010. <span class="button-secondary add-new-widget" tabindex="0">
  1011. <?php _e( 'Add a Widget' ); ?>
  1012. </span>
  1013. <span class="reorder-toggle" tabindex="0">
  1014. <span class="reorder"><?php _ex( 'Reorder', 'Reorder widgets in Customizer' ); ?></span>
  1015. <span class="reorder-done"><?php _ex( 'Done', 'Cancel reordering widgets in Customizer' ); ?></span>
  1016. </span>
  1017. <?php
  1018. }
  1019. }
  1020. /**
  1021. * Widget Form Customize Control Class
  1022. *
  1023. * @since 3.9.0
  1024. */
  1025. class WP_Widget_Form_Customize_Control extends WP_Customize_Control {
  1026. public $type = 'widget_form';
  1027. public $widget_id;
  1028. public $widget_id_base;
  1029. public $sidebar_id;
  1030. public $is_new = false;
  1031. public $width;
  1032. public $height;
  1033. public $is_wide = false;
  1034. public function to_json() {
  1035. parent::to_json();
  1036. $exported_properties = array( 'widget_id', 'widget_id_base', 'sidebar_id', 'width', 'height', 'is_wide' );
  1037. foreach ( $exported_properties as $key ) {
  1038. $this->json[ $key ] = $this->$key;
  1039. }
  1040. }
  1041. public function render_content() {
  1042. global $wp_registered_widgets;
  1043. require_once ABSPATH . '/wp-admin/includes/widgets.php';
  1044. $widget = $wp_registered_widgets[ $this->widget_id ];
  1045. if ( ! isset( $widget['params'][0] ) ) {
  1046. $widget['params'][0] = array();
  1047. }
  1048. $args = array(
  1049. 'widget_id' => $widget['id'],
  1050. 'widget_name' => $widget['name'],
  1051. );
  1052. $args = wp_list_widget_controls_dynamic_sidebar( array( 0 => $args, 1 => $widget['params'][0] ) );
  1053. echo $this->manager->widgets->get_widget_control( $args );
  1054. }
  1055. /**
  1056. * Whether the current widget is rendered on the page.
  1057. *
  1058. * @since 4.0.0
  1059. * @access public
  1060. *
  1061. * @return bool Whether the widget is rendered.
  1062. */
  1063. public function active_callback() {
  1064. return $this->manager->widgets->is_widget_rendered( $this->widget_id );
  1065. }
  1066. }