WP_Themes_List_Table

Core class used to implement displaying installed themes in a list table.

Defined (1)

The class is defined in the following location(s).

/wp-admin/includes/class-wp-themes-list-table.php  
  1. class WP_Themes_List_Table extends WP_List_Table { 
  2.  
  3. protected $search_terms = array(); 
  4. public $features = array(); 
  5.  
  6. /** 
  7. * Constructor. 
  8. * @since 3.1.0 
  9. * @access public 
  10. * @see WP_List_Table::__construct() for more information on default arguments. 
  11. * @param array $args An associative array of arguments. 
  12. */ 
  13. public function __construct( $args = array() ) { 
  14. parent::__construct( array( 
  15. 'ajax' => true,  
  16. 'screen' => isset( $args['screen'] ) ? $args['screen'] : null,  
  17. ) ); 
  18.  
  19. /** 
  20. * @return bool 
  21. */ 
  22. public function ajax_user_can() { 
  23. // Do not check edit_theme_options here. Ajax calls for available themes require switch_themes. 
  24. return current_user_can( 'switch_themes' ); 
  25.  
  26. /** 
  27. * @access public 
  28. */ 
  29. public function prepare_items() { 
  30. $themes = wp_get_themes( array( 'allowed' => true ) ); 
  31.  
  32. if ( ! empty( $_REQUEST['s'] ) ) 
  33. $this->search_terms = array_unique( array_filter( array_map( 'trim', explode( ', ', strtolower( wp_unslash( $_REQUEST['s'] ) ) ) ) ) ); 
  34.  
  35. if ( ! empty( $_REQUEST['features'] ) ) 
  36. $this->features = $_REQUEST['features']; 
  37.  
  38. if ( $this->search_terms || $this->features ) { 
  39. foreach ( $themes as $key => $theme ) { 
  40. if ( ! $this->search_theme( $theme ) ) 
  41. unset( $themes[ $key ] ); 
  42.  
  43. unset( $themes[ get_option( 'stylesheet' ) ] ); 
  44. WP_Theme::sort_by_name( $themes ); 
  45.  
  46. $per_page = 36; 
  47. $page = $this->get_pagenum(); 
  48.  
  49. $start = ( $page - 1 ) * $per_page; 
  50.  
  51. $this->items = array_slice( $themes, $start, $per_page, true ); 
  52.  
  53. $this->set_pagination_args( array( 
  54. 'total_items' => count( $themes ),  
  55. 'per_page' => $per_page,  
  56. 'infinite_scroll' => true,  
  57. ) ); 
  58.  
  59. /** 
  60. * @access public 
  61. */ 
  62. public function no_items() { 
  63. if ( $this->search_terms || $this->features ) { 
  64. _e( 'No items found.' ); 
  65. return; 
  66.  
  67. $blog_id = get_current_blog_id(); 
  68. if ( is_multisite() ) { 
  69. if ( current_user_can( 'install_themes' ) && current_user_can( 'manage_network_themes' ) ) { 
  70. printf( __( 'You only have one theme enabled for this site right now. Visit the Network Admin to <a href="%1$s">enable</a> or <a href="%2$s">install</a> more themes.' ), network_admin_url( 'site-themes.php?id=' . $blog_id ), network_admin_url( 'theme-install.php' ) ); 
  71.  
  72. return; 
  73. } elseif ( current_user_can( 'manage_network_themes' ) ) { 
  74. printf( __( 'You only have one theme enabled for this site right now. Visit the Network Admin to <a href="%1$s">enable</a> more themes.' ), network_admin_url( 'site-themes.php?id=' . $blog_id ) ); 
  75.  
  76. return; 
  77. // Else, fallthrough. install_themes doesn't help if you can't enable it. 
  78. } else { 
  79. if ( current_user_can( 'install_themes' ) ) { 
  80. printf( __( 'You only have one theme installed right now. Live a little! You can choose from over 1, 000 free themes in the WordPress Theme Directory at any time: just click on the <a href="%s">Install Themes</a> tab above.' ), admin_url( 'theme-install.php' ) ); 
  81.  
  82. return; 
  83. // Fallthrough. 
  84. printf( __( 'Only the current theme is available to you. Contact the %s administrator for information about accessing additional themes.' ), get_site_option( 'site_name' ) ); 
  85.  
  86. /** 
  87. * @param string $which 
  88. */ 
  89. public function tablenav( $which = 'top' ) { 
  90. if ( $this->get_pagination_arg( 'total_pages' ) <= 1 ) 
  91. return; 
  92. ?> 
  93. <div class="tablenav themes <?php echo $which; ?>"> 
  94. <?php $this->pagination( $which ); ?> 
  95. <span class="spinner"></span> 
  96. <br class="clear" /> 
  97. </div> 
  98. <?php 
  99.  
  100. /** 
  101. * @access public 
  102. */ 
  103. public function display() { 
  104. wp_nonce_field( "fetch-list-" . get_class( $this ), '_ajax_fetch_list_nonce' ); 
  105. ?> 
  106. <?php $this->tablenav( 'top' ); ?> 
  107.  
  108. <div id="availablethemes"> 
  109. <?php $this->display_rows_or_placeholder(); ?> 
  110. </div> 
  111.  
  112. <?php $this->tablenav( 'bottom' ); ?> 
  113. <?php 
  114.  
  115. /** 
  116. * @return array 
  117. */ 
  118. public function get_columns() { 
  119. return array(); 
  120.  
  121. /** 
  122. * @access public 
  123. */ 
  124. public function display_rows_or_placeholder() { 
  125. if ( $this->has_items() ) { 
  126. $this->display_rows(); 
  127. } else { 
  128. echo '<div class="no-items">'; 
  129. $this->no_items(); 
  130. echo '</div>'; 
  131.  
  132. /** 
  133. * @access public 
  134. */ 
  135. public function display_rows() { 
  136. $themes = $this->items; 
  137.  
  138. foreach ( $themes as $theme ): 
  139. ?><div class="available-theme"><?php 
  140.  
  141. $template = $theme->get_template(); 
  142. $stylesheet = $theme->get_stylesheet(); 
  143. $title = $theme->display('Name'); 
  144. $version = $theme->display('Version'); 
  145. $author = $theme->display('Author'); 
  146.  
  147. $activate_link = wp_nonce_url( "themes.php?action=activate&template=" . urlencode( $template ) . "&stylesheet=" . urlencode( $stylesheet ), 'switch-theme_' . $stylesheet ); 
  148.  
  149. $actions = array(); 
  150. $actions['activate'] = '<a href="' . $activate_link . '" class="activatelink" title="' 
  151. . esc_attr( sprintf( __( 'Activate “%s”' ), $title ) ) . '">' . __( 'Activate' ) . '</a>'; 
  152.  
  153. if ( current_user_can( 'edit_theme_options' ) && current_user_can( 'customize' ) ) { 
  154. $actions['preview'] .= '<a href="' . wp_customize_url( $stylesheet ) . '" class="load-customize hide-if-no-customize">' 
  155. . __( 'Live Preview' ) . '</a>'; 
  156.  
  157. if ( ! is_multisite() && current_user_can( 'delete_themes' ) ) 
  158. $actions['delete'] = '<a class="submitdelete deletion" href="' . wp_nonce_url( 'themes.php?action=delete&stylesheet=' . urlencode( $stylesheet ), 'delete-theme_' . $stylesheet ) 
  159. . '" onclick="' . "return confirm( '" . esc_js( sprintf( __( "You are about to delete this theme '%s'\n 'Cancel' to stop, 'OK' to delete." ), $title ) ) 
  160. . "' );" . '">' . __( 'Delete' ) . '</a>'; 
  161.  
  162. /** This filter is documented in wp-admin/includes/class-wp-ms-themes-list-table.php */ 
  163. $actions = apply_filters( 'theme_action_links', $actions, $theme ); 
  164.  
  165. /** This filter is documented in wp-admin/includes/class-wp-ms-themes-list-table.php */ 
  166. $actions = apply_filters( "theme_action_links_$stylesheet", $actions, $theme ); 
  167. $delete_action = isset( $actions['delete'] ) ? '<div class="delete-theme">' . $actions['delete'] . '</div>' : ''; 
  168. unset( $actions['delete'] ); 
  169.  
  170. ?> 
  171.  
  172. <span class="screenshot hide-if-customize"> 
  173. <?php if ( $screenshot = $theme->get_screenshot() ) : ?> 
  174. <img src="<?php echo esc_url( $screenshot ); ?>" alt="" /> 
  175. <?php endif; ?> 
  176. </span> 
  177. <a href="<?php echo wp_customize_url( $stylesheet ); ?>" class="screenshot load-customize hide-if-no-customize"> 
  178. <?php if ( $screenshot = $theme->get_screenshot() ) : ?> 
  179. <img src="<?php echo esc_url( $screenshot ); ?>" alt="" /> 
  180. <?php endif; ?> 
  181. </a> 
  182.  
  183. <h3><?php echo $title; ?></h3> 
  184. <div class="theme-author"><?php printf( __( 'By %s' ), $author ); ?></div> 
  185. <div class="action-links"> 
  186. <ul> 
  187. <?php foreach ( $actions as $action ): ?> 
  188. <li><?php echo $action; ?></li> 
  189. <?php endforeach; ?> 
  190. <li class="hide-if-no-js"><a href="#" class="theme-detail"><?php _e('Details') ?></a></li> 
  191. </ul> 
  192. <?php echo $delete_action; ?> 
  193.  
  194. <?php theme_update_available( $theme ); ?> 
  195. </div> 
  196.  
  197. <div class="themedetaildiv hide-if-js"> 
  198. <p><strong><?php _e('Version:'); ?></strong> <?php echo $version; ?></p> 
  199. <p><?php echo $theme->display('Description'); ?></p> 
  200. <?php if ( $theme->parent() ) { 
  201. printf( ' <p class="howto">' . __( 'This <a href="%1$s">child theme</a> requires its parent theme, %2$s.' ) . '</p>',  
  202. __( 'https://codex.wordpress.org/Child_Themes' ),  
  203. $theme->parent()->display( 'Name' ) ); 
  204. } ?> 
  205. </div> 
  206.  
  207. </div> 
  208. <?php 
  209. endforeach; 
  210.  
  211. /** 
  212. * @param WP_Theme $theme 
  213. * @return bool 
  214. */ 
  215. public function search_theme( $theme ) { 
  216. // Search the features 
  217. foreach ( $this->features as $word ) { 
  218. if ( ! in_array( $word, $theme->get('Tags') ) ) 
  219. return false; 
  220.  
  221. // Match all phrases 
  222. foreach ( $this->search_terms as $word ) { 
  223. if ( in_array( $word, $theme->get('Tags') ) ) 
  224. continue; 
  225.  
  226. foreach ( array( 'Name', 'Description', 'Author', 'AuthorURI' ) as $header ) { 
  227. // Don't mark up; Do translate. 
  228. if ( false !== stripos( strip_tags( $theme->display( $header, false, true ) ), $word ) ) { 
  229. continue 2; 
  230.  
  231. if ( false !== stripos( $theme->get_stylesheet(), $word ) ) 
  232. continue; 
  233.  
  234. if ( false !== stripos( $theme->get_template(), $word ) ) 
  235. continue; 
  236.  
  237. return false; 
  238.  
  239. return true; 
  240.  
  241. /** 
  242. * Send required variables to JavaScript land 
  243. * @since 3.4.0 
  244. * @access public 
  245. * @param array $extra_args 
  246. */ 
  247. public function _js_vars( $extra_args = array() ) { 
  248. $search_string = isset( $_REQUEST['s'] ) ? esc_attr( wp_unslash( $_REQUEST['s'] ) ) : ''; 
  249.  
  250. $args = array( 
  251. 'search' => $search_string,  
  252. 'features' => $this->features,  
  253. 'paged' => $this->get_pagenum(),  
  254. 'total_pages' => ! empty( $this->_pagination_args['total_pages'] ) ? $this->_pagination_args['total_pages'] : 1,  
  255. ); 
  256.  
  257. if ( is_array( $extra_args ) ) 
  258. $args = array_merge( $args, $extra_args ); 
  259.  
  260. printf( "<script type='text/javascript'>var theme_list_args = %s;</script>\n", wp_json_encode( $args ) ); 
  261. parent::_js_vars();