Version Description
(Released: December 12, 2018) = * Added: Catch Themes and Catch Plugins tabs in Add themes and Add plugins page respectively * Added: Themes by Catch Themes section under Themes panel in customizer * Bug Fixed: Undefined index when no section is selected for food items * Compatibility check up to version 5.0 * Updated: How to use link
Download this release
Release Info
Developer | catchthemes |
Plugin | Essential Content Types |
Version | 1.4 |
Comparing to | |
See all releases |
Code changes from version 1.3 to 1.4
- README.txt +8 -1
- admin/class-food-menu.php +3 -3
- admin/js/our-themes.js +4 -0
- admin/partials/dashboard-display.php +5 -5
- ect-templates/content-featured-content.php +1 -1
- ect-templates/content-portfolio.php +1 -1
- ect-templates/content-service.php +1 -1
- essential-content-types.php +28 -1
- includes/class-essential-content-types.php +1 -1
- includes/our-plugins.php +61 -0
- includes/our-themes.php +386 -0
README.txt
CHANGED
@@ -3,7 +3,7 @@ Contributors: catchplugins, catchthemes, sakinshrestha, pratikshrestha, maheshma
|
|
3 |
Donate link: https://catchplugins.com/plugins/essential-content-types-pro/
|
4 |
Tags: custom post types, CPT, CMS, post, types, post type, taxonomy, tax, custom, content types, post types, custom content types, testimonial, portfolio, featured content, service
|
5 |
Requires at least: 4.5
|
6 |
-
Tested up to:
|
7 |
Stable tag: trunk
|
8 |
License: GPLv3 or later
|
9 |
License URI: http://www.gnu.org/licenses/gpl-3.0.html
|
@@ -195,6 +195,13 @@ Not so easy way (via FTP) :
|
|
195 |
|
196 |
== Changelog ==
|
197 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
198 |
= 1.3 (Released: July 05, 2018) =
|
199 |
* Added: Default featured-image-size
|
200 |
* Bug fixed: settings_page function found
|
3 |
Donate link: https://catchplugins.com/plugins/essential-content-types-pro/
|
4 |
Tags: custom post types, CPT, CMS, post, types, post type, taxonomy, tax, custom, content types, post types, custom content types, testimonial, portfolio, featured content, service
|
5 |
Requires at least: 4.5
|
6 |
+
Tested up to: 5.0
|
7 |
Stable tag: trunk
|
8 |
License: GPLv3 or later
|
9 |
License URI: http://www.gnu.org/licenses/gpl-3.0.html
|
195 |
|
196 |
== Changelog ==
|
197 |
|
198 |
+
= 1.4 (Released: December 12, 2018) =
|
199 |
+
* Added: Catch Themes and Catch Plugins tabs in Add themes and Add plugins page respectively
|
200 |
+
* Added: Themes by Catch Themes section under Themes panel in customizer
|
201 |
+
* Bug Fixed: Undefined index when no section is selected for food items
|
202 |
+
* Compatibility check up to version 5.0
|
203 |
+
* Updated: How to use link
|
204 |
+
|
205 |
= 1.3 (Released: July 05, 2018) =
|
206 |
* Added: Default featured-image-size
|
207 |
* Bug fixed: settings_page function found
|
admin/class-food-menu.php
CHANGED
@@ -1165,7 +1165,7 @@ class Essential_Content_Food_Menu {
|
|
1165 |
$this->menu_item_loop_header(); // Output the menu's header
|
1166 |
}
|
1167 |
|
1168 |
-
$this->menu_item_loop_last_term_id = $this->menu_item_loop_current_term->term_id;
|
1169 |
}
|
1170 |
|
1171 |
/**
|
@@ -1192,9 +1192,9 @@ class Essential_Content_Food_Menu {
|
|
1192 |
function menu_item_loop_header() {
|
1193 |
$this->menu_item_loop_open_element( 'menu_header' );
|
1194 |
$this->menu_item_loop_open_element( 'menu_title' );
|
1195 |
-
echo esc_html( $this->menu_item_loop_current_term->name ); // @todo tax filter
|
1196 |
$this->menu_item_loop_close_element( 'menu_title' );
|
1197 |
-
if ( $this->menu_item_loop_current_term->description ) :
|
1198 |
$this->menu_item_loop_open_element( 'menu_description' );
|
1199 |
echo esc_html( $this->menu_item_loop_current_term->description ); // @todo kses, tax filter
|
1200 |
$this->menu_item_loop_close_element( 'menu_description' );
|
1165 |
$this->menu_item_loop_header(); // Output the menu's header
|
1166 |
}
|
1167 |
|
1168 |
+
$this->menu_item_loop_last_term_id = isset( $this->menu_item_loop_current_term->term_id ) ? $this->menu_item_loop_current_term->term_id : '' ;
|
1169 |
}
|
1170 |
|
1171 |
/**
|
1192 |
function menu_item_loop_header() {
|
1193 |
$this->menu_item_loop_open_element( 'menu_header' );
|
1194 |
$this->menu_item_loop_open_element( 'menu_title' );
|
1195 |
+
echo isset( $this->menu_item_loop_current_term->name ) ? esc_html( $this->menu_item_loop_current_term->name ) : ''; // @todo tax filter
|
1196 |
$this->menu_item_loop_close_element( 'menu_title' );
|
1197 |
+
if ( isset( $this->menu_item_loop_current_term->description ) && $this->menu_item_loop_current_term->description ) :
|
1198 |
$this->menu_item_loop_open_element( 'menu_description' );
|
1199 |
echo esc_html( $this->menu_item_loop_current_term->description ); // @todo kses, tax filter
|
1200 |
$this->menu_item_loop_close_element( 'menu_description' );
|
admin/js/our-themes.js
ADDED
@@ -0,0 +1,4 @@
|
|
|
|
|
|
|
|
|
1 |
+
jQuery(document).ready(function($){
|
2 |
+
var our_themes = '<li><a href="#" data-sort="catchthemes">Catch Themes</a></li>';
|
3 |
+
$('.filter-links').append( our_themes );
|
4 |
+
});
|
admin/partials/dashboard-display.php
CHANGED
@@ -43,7 +43,7 @@
|
|
43 |
|
44 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Portfolio Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=jetpack_portfolio_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
45 |
|
46 |
-
<p>For more information on <strong>How to use Portfolio Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-
|
47 |
</div>
|
48 |
</div><!-- #module-portfolio -->
|
49 |
</div><!-- .module-wrap -->
|
@@ -70,7 +70,7 @@
|
|
70 |
|
71 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Testimonial Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=jetpack_testimonials[page-title]' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
72 |
|
73 |
-
<p>For more information on <strong>How to use Testimonials Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-
|
74 |
</div>
|
75 |
</div><!-- #module-testimonial -->
|
76 |
</div><!-- .module-wrap -->
|
@@ -98,7 +98,7 @@
|
|
98 |
|
99 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Featured Content Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=featured_content_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
100 |
|
101 |
-
<p>For more information on <strong>How to use Featured Content Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-
|
102 |
</div>
|
103 |
</div><!-- #module-featured-content -->
|
104 |
</div><!-- .module-wrap -->
|
@@ -126,7 +126,7 @@
|
|
126 |
|
127 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Service Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=ect_service_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
128 |
|
129 |
-
<p>For more information on <strong>How to use Service Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-
|
130 |
</div>
|
131 |
</div><!-- #module-service -->
|
132 |
</div><!-- .module-wrap -->
|
@@ -154,7 +154,7 @@
|
|
154 |
|
155 |
<p><?php esc_html_e( 'Once enabled, Food Menu Items Post Type options will appear on Dashboard Menu', 'essential-content-types' ); ?></p>
|
156 |
|
157 |
-
<p>For more information on <strong>How to use Food Menu Shortcodes</strong>, <a href="https://catchplugins.com/blog/
|
158 |
</div>
|
159 |
</div><!-- #module-food-menu -->
|
160 |
</div><!-- .module-wrap -->
|
43 |
|
44 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Portfolio Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=jetpack_portfolio_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
45 |
|
46 |
+
<p>For more information on <strong>How to use Portfolio Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-pro/#Portfolio" title="Essential Content Type: Portfolio Shortcode" target="_blank">Click here</a></p>
|
47 |
</div>
|
48 |
</div><!-- #module-portfolio -->
|
49 |
</div><!-- .module-wrap -->
|
70 |
|
71 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Testimonial Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=jetpack_testimonials[page-title]' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
72 |
|
73 |
+
<p>For more information on <strong>How to use Testimonials Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-pro/#Testimonial" title="Essential Content Type: Testimonial Shortcode" target="_blank">Click here</a></p>
|
74 |
</div>
|
75 |
</div><!-- #module-testimonial -->
|
76 |
</div><!-- .module-wrap -->
|
98 |
|
99 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Featured Content Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=featured_content_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
100 |
|
101 |
+
<p>For more information on <strong>How to use Featured Content Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-pro/#FeaturedContent" title="Essential Content Type: Featured Content Shortcode" target="_blank">Click here</a></p>
|
102 |
</div>
|
103 |
</div><!-- #module-featured-content -->
|
104 |
</div><!-- .module-wrap -->
|
126 |
|
127 |
<p><?php printf( esc_html__( '%1$sClick here%2$s to view Service Archive Options.', 'essential-content-types' ) , '<a href ="' . esc_url( admin_url( 'customize.php?autofocus[control]=ect_service_title' ) ) . '" target="_blank">', '</a>' ); ?></p>
|
128 |
|
129 |
+
<p>For more information on <strong>How to use Service Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-pro/#Service" title="Essential Content Type: Service Shortcode" target="_blank">Click here</a></p>
|
130 |
</div>
|
131 |
</div><!-- #module-service -->
|
132 |
</div><!-- .module-wrap -->
|
154 |
|
155 |
<p><?php esc_html_e( 'Once enabled, Food Menu Items Post Type options will appear on Dashboard Menu', 'essential-content-types' ); ?></p>
|
156 |
|
157 |
+
<p>For more information on <strong>How to use Food Menu Shortcodes</strong>, <a href="https://catchplugins.com/blog/essential-content-types-pro/#FoodMenu" title="Essential Content Type: Food Menu Shortcode" target="_blank">Click here</a></p>
|
158 |
</div>
|
159 |
</div><!-- #module-food-menu -->
|
160 |
</div><!-- .module-wrap -->
|
ect-templates/content-featured-content.php
CHANGED
@@ -15,7 +15,7 @@ if ( ! defined( 'ABSPATH' ) ) {
|
|
15 |
}
|
16 |
?>
|
17 |
|
18 |
-
<h2 class="featured-content-entry-title entry-title"><a href="<?php
|
19 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
20 |
<div class="featured-content-entry-meta entry-meta">
|
21 |
<?php
|
15 |
}
|
16 |
?>
|
17 |
|
18 |
+
<h2 class="featured-content-entry-title entry-title"><a href="<?php the_permalink(); ?>" title="<?php the_title_attribute(); ?>"><?php the_title(); ?></a></h2>
|
19 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
20 |
<div class="featured-content-entry-meta entry-meta">
|
21 |
<?php
|
ect-templates/content-portfolio.php
CHANGED
@@ -12,7 +12,7 @@ if ( ! defined( 'ABSPATH' ) ) {
|
|
12 |
echo essential_content_get_portfolio_thumbnail_link( get_the_ID(), 'ect-jetpack-portfolio-featured' );
|
13 |
?>
|
14 |
|
15 |
-
<h2 class="portfolio-entry-title entry-title"><a href="<?php
|
16 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
17 |
<div class="portfolio-entry-meta entry-meta">
|
18 |
<?php
|
12 |
echo essential_content_get_portfolio_thumbnail_link( get_the_ID(), 'ect-jetpack-portfolio-featured' );
|
13 |
?>
|
14 |
|
15 |
+
<h2 class="portfolio-entry-title entry-title"><a href="<?php the_permalink(); ?>" title="<?php the_title_attribute(); ?>"><?php the_title(); ?></a></h2>
|
16 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
17 |
<div class="portfolio-entry-meta entry-meta">
|
18 |
<?php
|
ect-templates/content-service.php
CHANGED
@@ -16,7 +16,7 @@ echo '</pre>'; die();*/
|
|
16 |
}
|
17 |
?>
|
18 |
|
19 |
-
<h2 class="service-entry-title entry-title"><a href="<?php
|
20 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
21 |
<div class="service-entry-meta entry-meta">
|
22 |
<?php
|
16 |
}
|
17 |
?>
|
18 |
|
19 |
+
<h2 class="service-entry-title entry-title"><a href="<?php the_permalink(); ?>" title="<?php the_title_attribute(); ?>"><?php the_title(); ?></a></h2>
|
20 |
<?php if ( false != $atts['display_types'] || false != $atts['display_tags'] || false != $atts['display_author'] ) : ?>
|
21 |
<div class="service-entry-meta entry-meta">
|
22 |
<?php
|
essential-content-types.php
CHANGED
@@ -16,7 +16,7 @@
|
|
16 |
* Plugin Name: Essential Content Types
|
17 |
* Plugin URI: https://catchplugins.com/plugins/essential-content-types/
|
18 |
* Description: Essential Content Types allows you to feature the impressive content through different content/post types on your website just the way you want it. These content/post types are missed by the themes in WordPress Theme Directory as the feature falls more towards the plugins’ territory.
|
19 |
-
* Version: 1.
|
20 |
* Author: Catch Plugins
|
21 |
* Author URI: https://catchplugins.com
|
22 |
* License: GPL-3.0+
|
@@ -34,6 +34,24 @@ if ( ! defined( 'WPINC' ) ) {
|
|
34 |
* The code that runs during plugin activation.
|
35 |
* This action is documented in includes/class-essential-content-types-activator.php
|
36 |
*/
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
37 |
function activate_essential_content_types() {
|
38 |
$required = 'essential-content-types-pro/essential-content-types-pro.php';
|
39 |
if ( is_plugin_active( $required ) ) {
|
@@ -175,3 +193,12 @@ function ect_body_classes( $classes ){
|
|
175 |
return $classes;
|
176 |
}
|
177 |
add_filter( 'body_class', 'ect_body_classes' );
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
16 |
* Plugin Name: Essential Content Types
|
17 |
* Plugin URI: https://catchplugins.com/plugins/essential-content-types/
|
18 |
* Description: Essential Content Types allows you to feature the impressive content through different content/post types on your website just the way you want it. These content/post types are missed by the themes in WordPress Theme Directory as the feature falls more towards the plugins’ territory.
|
19 |
+
* Version: 1.4
|
20 |
* Author: Catch Plugins
|
21 |
* Author URI: https://catchplugins.com
|
22 |
* License: GPL-3.0+
|
34 |
* The code that runs during plugin activation.
|
35 |
* This action is documented in includes/class-essential-content-types-activator.php
|
36 |
*/
|
37 |
+
// The URL of the directory that contains the plugin
|
38 |
+
if ( !defined( 'ESSENTIAL_CONTENT_TYPES_URL' ) )
|
39 |
+
define( 'ESSENTIAL_CONTENT_TYPES_URL', plugin_dir_url( __FILE__ ) );
|
40 |
+
|
41 |
+
|
42 |
+
// The absolute path of the directory that contains the file
|
43 |
+
if ( !defined( 'ESSENTIAL_CONTENT_TYPES_PATH' ) )
|
44 |
+
define( 'ESSENTIAL_CONTENT_TYPES_PATH', plugin_dir_path( __FILE__ ) );
|
45 |
+
|
46 |
+
|
47 |
+
// Gets the path to a plugin file or directory, relative to the plugins directory, without the leading and trailing slashes.
|
48 |
+
if ( !defined( 'ESSENTIAL_CONTENT_TYPES_BASENAME' ) )
|
49 |
+
define( 'ESSENTIAL_CONTENT_TYPES_BASENAME', plugin_basename( __FILE__ ) );
|
50 |
+
|
51 |
+
/**
|
52 |
+
* Make plugin available for translation
|
53 |
+
* Translations can be filed in the /languages/ directory
|
54 |
+
*/
|
55 |
function activate_essential_content_types() {
|
56 |
$required = 'essential-content-types-pro/essential-content-types-pro.php';
|
57 |
if ( is_plugin_active( $required ) ) {
|
193 |
return $classes;
|
194 |
}
|
195 |
add_filter( 'body_class', 'ect_body_classes' );
|
196 |
+
/* Adds Catch Themes tab in Add theme page and Themes by Catch Themes in Customizer's change theme option. */
|
197 |
+
require plugin_dir_path( __FILE__ ) . 'includes/our-themes.php';
|
198 |
+
|
199 |
+
|
200 |
+
/* Adds Catch Plugins tab in Add theme page. */
|
201 |
+
require plugin_dir_path( __FILE__ ) . 'includes/our-plugins.php';
|
202 |
+
|
203 |
+
|
204 |
+
|
includes/class-essential-content-types.php
CHANGED
@@ -69,7 +69,7 @@ class Essential_Content_Types {
|
|
69 |
public function __construct() {
|
70 |
|
71 |
$this->plugin_name = 'essential-content-types';
|
72 |
-
$this->version = '1.
|
73 |
|
74 |
$this->load_dependencies();
|
75 |
$this->set_locale();
|
69 |
public function __construct() {
|
70 |
|
71 |
$this->plugin_name = 'essential-content-types';
|
72 |
+
$this->version = '1.4';
|
73 |
|
74 |
$this->load_dependencies();
|
75 |
$this->set_locale();
|
includes/our-plugins.php
ADDED
@@ -0,0 +1,61 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/* Adds Catch Plugins tab in Add Plugin page to show all plugins by Catch Plugins in wordpress.org */
|
3 |
+
if( ! function_exists( 'add_our_plugins_tab' ) ) {
|
4 |
+
function add_our_plugins_tab($tabs) {
|
5 |
+
// Add our filter here
|
6 |
+
$tabs['catchplugins'] = _x( 'Catch Plugins', 'Plugin Installer' );
|
7 |
+
|
8 |
+
return $tabs;
|
9 |
+
}
|
10 |
+
add_filter( 'install_plugins_tabs', 'add_our_plugins_tab', 1 );
|
11 |
+
}
|
12 |
+
|
13 |
+
if( ! function_exists( 'catchplugins' ) ) {
|
14 |
+
function catchplugins() {
|
15 |
+
/* From CORE Start */
|
16 |
+
global $paged, $tab;
|
17 |
+
wp_reset_vars( array( 'tab' ) );
|
18 |
+
|
19 |
+
$defined_class = new WP_Plugin_Install_List_Table();
|
20 |
+
$paged = $defined_class->get_pagenum();
|
21 |
+
|
22 |
+
$per_page = 30;
|
23 |
+
//$installed_plugins = catch_get_installed_plugins();
|
24 |
+
|
25 |
+
$args = array(
|
26 |
+
'page' => $paged,
|
27 |
+
'per_page' => $per_page,
|
28 |
+
'fields' => array(
|
29 |
+
'last_updated' => true,
|
30 |
+
'icons' => true,
|
31 |
+
'active_installs' => true
|
32 |
+
),
|
33 |
+
// Send the locale and installed plugin slugs to the API so it can provide context-sensitive results.
|
34 |
+
'locale' => get_user_locale(),
|
35 |
+
//'installed_plugins' => array_keys( $installed_plugins ),
|
36 |
+
);
|
37 |
+
/* From CORE End */
|
38 |
+
|
39 |
+
// Add author filter for our plugins
|
40 |
+
$args['author'] = 'catchplugins';
|
41 |
+
|
42 |
+
return $args;
|
43 |
+
}
|
44 |
+
add_filter( "install_plugins_table_api_args_catchplugins", 'catchplugins', 1 );
|
45 |
+
}
|
46 |
+
|
47 |
+
if( ! function_exists( 'cathcplugins_plugins_table' ) ) {
|
48 |
+
add_action( 'install_plugins_catchplugins', 'cathcplugins_plugins_table' );
|
49 |
+
function cathcplugins_plugins_table() {
|
50 |
+
global $wp_list_table;
|
51 |
+
printf(
|
52 |
+
'<p class="catch-plugins-list">' . __( 'You can use any of our free plugins or premium plugins from <a href="%s" target="_blank">Catch Plugins</a>' ) . '.</p>',
|
53 |
+
'https://catchplugins.com/'
|
54 |
+
);
|
55 |
+
?>
|
56 |
+
<form id="plugin-filter" method="post">
|
57 |
+
<?php $wp_list_table->display(); ?>
|
58 |
+
</form>
|
59 |
+
<?php
|
60 |
+
}
|
61 |
+
}
|
includes/our-themes.php
ADDED
@@ -0,0 +1,386 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
<?php
|
2 |
+
/* Adds Catch Themes tab in Add Theme page to show all themes by Catch Themes in wordpress.org */
|
3 |
+
if( ! function_exists( 'wp_ajax_custom_query_themes' ) ) {
|
4 |
+
function wp_ajax_custom_query_themes() {
|
5 |
+
global $themes_allowedtags, $theme_field_defaults;
|
6 |
+
|
7 |
+
if ( ! current_user_can( 'install_themes' ) ) {
|
8 |
+
wp_send_json_error();
|
9 |
+
}
|
10 |
+
|
11 |
+
$args = wp_parse_args( wp_unslash( $_REQUEST['request'] ), array(
|
12 |
+
'per_page' => 20,
|
13 |
+
'fields' => $theme_field_defaults
|
14 |
+
) );
|
15 |
+
|
16 |
+
if ( isset( $args['browse'] ) && 'catchthemes' === $args['browse'] && ! isset( $args['user'] ) ) {
|
17 |
+
$args['author'] = 'catchthemes';
|
18 |
+
}
|
19 |
+
|
20 |
+
if ( isset( $args['browse'] ) && 'favorites' === $args['browse'] && ! isset( $args['user'] ) ) {
|
21 |
+
$user = get_user_option( 'wporg_favorites' );
|
22 |
+
if ( $user ) {
|
23 |
+
$args['user'] = $user;
|
24 |
+
}
|
25 |
+
}
|
26 |
+
|
27 |
+
$old_filter = isset( $args['browse'] ) ? $args['browse'] : 'search';
|
28 |
+
|
29 |
+
/** This filter is documented in wp-admin/includes/class-wp-theme-install-list-table.php */
|
30 |
+
$args = apply_filters( 'install_themes_table_api_args_' . $old_filter, $args );
|
31 |
+
|
32 |
+
$api = themes_api( 'query_themes', $args );
|
33 |
+
|
34 |
+
if ( is_wp_error( $api ) ) {
|
35 |
+
wp_send_json_error();
|
36 |
+
}
|
37 |
+
|
38 |
+
$update_php = network_admin_url( 'update.php?action=install-theme' );
|
39 |
+
foreach ( $api->themes as &$theme ) {
|
40 |
+
$theme->install_url = add_query_arg( array(
|
41 |
+
'theme' => $theme->slug,
|
42 |
+
'_wpnonce' => wp_create_nonce( 'install-theme_' . $theme->slug )
|
43 |
+
), $update_php );
|
44 |
+
|
45 |
+
if ( current_user_can( 'switch_themes' ) ) {
|
46 |
+
if ( is_multisite() ) {
|
47 |
+
$theme->activate_url = add_query_arg( array(
|
48 |
+
'action' => 'enable',
|
49 |
+
'_wpnonce' => wp_create_nonce( 'enable-theme_' . $theme->slug ),
|
50 |
+
'theme' => $theme->slug,
|
51 |
+
), network_admin_url( 'themes.php' ) );
|
52 |
+
} else {
|
53 |
+
$theme->activate_url = add_query_arg( array(
|
54 |
+
'action' => 'activate',
|
55 |
+
'_wpnonce' => wp_create_nonce( 'switch-theme_' . $theme->slug ),
|
56 |
+
'stylesheet' => $theme->slug,
|
57 |
+
), admin_url( 'themes.php' ) );
|
58 |
+
}
|
59 |
+
}
|
60 |
+
|
61 |
+
if ( ! is_multisite() && current_user_can( 'edit_theme_options' ) && current_user_can( 'customize' ) ) {
|
62 |
+
$theme->customize_url = add_query_arg( array(
|
63 |
+
'return' => urlencode( network_admin_url( 'theme-install.php', 'relative' ) ),
|
64 |
+
), wp_customize_url( $theme->slug ) );
|
65 |
+
}
|
66 |
+
|
67 |
+
$theme->name = wp_kses( $theme->name, $themes_allowedtags );
|
68 |
+
$theme->author = wp_kses( $theme->author, $themes_allowedtags );
|
69 |
+
$theme->version = wp_kses( $theme->version, $themes_allowedtags );
|
70 |
+
$theme->description = wp_kses( $theme->description, $themes_allowedtags );
|
71 |
+
$theme->stars = wp_star_rating( array( 'rating' => $theme->rating, 'type' => 'percent', 'number' => $theme->num_ratings, 'echo' => false ) );
|
72 |
+
$theme->num_ratings = number_format_i18n( $theme->num_ratings );
|
73 |
+
$theme->preview_url = set_url_scheme( $theme->preview_url );
|
74 |
+
}
|
75 |
+
|
76 |
+
wp_send_json_success( $api );
|
77 |
+
}
|
78 |
+
remove_action( 'wp_ajax_query-themes', 'wp_ajax_query_themes', 1 );
|
79 |
+
add_action( 'wp_ajax_query-themes', 'wp_ajax_custom_query_themes', 1 );
|
80 |
+
}
|
81 |
+
|
82 |
+
if( ! function_exists( 'catchthemes_our_themes_script' ) ) {
|
83 |
+
function catchthemes_our_themes_script( $hook_suffix ) {
|
84 |
+
|
85 |
+
if( 'theme-install.php' == $hook_suffix ) {
|
86 |
+
wp_enqueue_script( 'our-themes-script', ESSENTIAL_CONTENT_TYPES_URL . 'admin/js/our-themes.js', array( 'jquery' ), '2018-05-16' );
|
87 |
+
}
|
88 |
+
}
|
89 |
+
add_action( 'admin_enqueue_scripts', 'catchthemes_our_themes_script' );
|
90 |
+
}
|
91 |
+
|
92 |
+
|
93 |
+
/* Add Catch Themes Section in Theme in Customizer */
|
94 |
+
if( ! function_exists( 'catchthemes_customize_register' ) ) {
|
95 |
+
function catchthemes_customize_register($wp_customize) {
|
96 |
+
$wp_customize->add_section( new WP_Customize_Themes_Section( $wp_customize, 'catchthemes', array(
|
97 |
+
'title' => __( 'Themes by CatchThemes', 'catch-web-tools' ),
|
98 |
+
'action' => 'catchthemes',
|
99 |
+
'capability' => 'install_themes',
|
100 |
+
'panel' => 'themes',
|
101 |
+
'priority' => 6,
|
102 |
+
) ) );
|
103 |
+
}
|
104 |
+
if ( ! is_multisite() ) {
|
105 |
+
add_action( 'customize_register', 'catchthemes_customize_register' );
|
106 |
+
}
|
107 |
+
}
|
108 |
+
|
109 |
+
if( ! function_exists( 'catchthemes_handle_load_themes_request' ) ) {
|
110 |
+
global $wp_customize;
|
111 |
+
remove_action( 'wp_ajax_customize_load_themes', array( $wp_customize, 'handle_load_themes_request' ) );
|
112 |
+
add_action( 'wp_ajax_customize_load_themes', 'catchthemes_handle_load_themes_request' );
|
113 |
+
/**
|
114 |
+
* Load themes into the theme browsing/installation UI.
|
115 |
+
* taken from wp-includes/cllass-wp-customize-manager.php
|
116 |
+
* @since 4.9.0
|
117 |
+
*/
|
118 |
+
function catchthemes_handle_load_themes_request() {
|
119 |
+
check_ajax_referer( 'switch_themes', 'nonce' );
|
120 |
+
if ( ! current_user_can( 'switch_themes' ) ) {
|
121 |
+
wp_die( -1 );
|
122 |
+
}
|
123 |
+
|
124 |
+
if ( empty( $_POST['theme_action'] ) ) {
|
125 |
+
wp_send_json_error( 'missing_theme_action' );
|
126 |
+
}
|
127 |
+
$theme_action = sanitize_key( $_POST['theme_action'] );
|
128 |
+
$themes = array();
|
129 |
+
$args = array();
|
130 |
+
|
131 |
+
// Define query filters based on user input.
|
132 |
+
if ( ! array_key_exists( 'search', $_POST ) ) {
|
133 |
+
$args['search'] = '';
|
134 |
+
} else {
|
135 |
+
$args['search'] = sanitize_text_field( wp_unslash( $_POST['search'] ) );
|
136 |
+
}
|
137 |
+
|
138 |
+
if ( ! array_key_exists( 'tags', $_POST ) ) {
|
139 |
+
$args['tag'] = '';
|
140 |
+
} else {
|
141 |
+
$args['tag'] = array_map( 'sanitize_text_field', wp_unslash( (array) $_POST['tags'] ) );
|
142 |
+
}
|
143 |
+
|
144 |
+
if ( ! array_key_exists( 'page', $_POST ) ) {
|
145 |
+
$args['page'] = 1;
|
146 |
+
} else {
|
147 |
+
$args['page'] = absint( $_POST['page'] );
|
148 |
+
}
|
149 |
+
|
150 |
+
require_once ABSPATH . 'wp-admin/includes/theme.php';
|
151 |
+
|
152 |
+
if ( 'installed' === $theme_action ) {
|
153 |
+
|
154 |
+
// Load all installed themes from wp_prepare_themes_for_js().
|
155 |
+
$themes = array( 'themes' => wp_prepare_themes_for_js() );
|
156 |
+
foreach ( $themes['themes'] as &$theme ) {
|
157 |
+
$theme['type'] = 'installed';
|
158 |
+
$theme['active'] = ( isset( $_POST['customized_theme'] ) && $_POST['customized_theme'] === $theme['id'] );
|
159 |
+
}
|
160 |
+
|
161 |
+
} elseif ( 'catchthemes' === $theme_action ) {
|
162 |
+
|
163 |
+
// Load WordPress.org themes from the .org API and normalize data to match installed theme objects.
|
164 |
+
if ( ! current_user_can( 'install_themes' ) ) {
|
165 |
+
wp_die( -1 );
|
166 |
+
}
|
167 |
+
|
168 |
+
// Arguments for all queries.
|
169 |
+
$wporg_args = array(
|
170 |
+
'per_page' => -1,
|
171 |
+
'fields' => array(
|
172 |
+
'screenshot_url' => true,
|
173 |
+
'description' => true,
|
174 |
+
'rating' => true,
|
175 |
+
'downloaded' => true,
|
176 |
+
'downloadlink' => true,
|
177 |
+
'last_updated' => true,
|
178 |
+
'homepage' => true,
|
179 |
+
'num_ratings' => true,
|
180 |
+
'tags' => true,
|
181 |
+
'parent' => true,
|
182 |
+
// 'extended_author' => true, @todo: WordPress.org throws a 500 server error when this is here.
|
183 |
+
),
|
184 |
+
);
|
185 |
+
|
186 |
+
$args = array_merge( $wporg_args, $args );
|
187 |
+
|
188 |
+
if ( '' === $args['search'] && '' === $args['tag'] ) {
|
189 |
+
$args['browse'] = 'new'; // Sort by latest themes by default.
|
190 |
+
}
|
191 |
+
|
192 |
+
$args['author'] = 'catchthemes';
|
193 |
+
|
194 |
+
// Load themes from the .org API.
|
195 |
+
$themes = themes_api( 'query_themes', $args );
|
196 |
+
if ( is_wp_error( $themes ) ) {
|
197 |
+
wp_send_json_error();
|
198 |
+
}
|
199 |
+
|
200 |
+
// This list matches the allowed tags in wp-admin/includes/theme-install.php.
|
201 |
+
$themes_allowedtags = array_fill_keys(
|
202 |
+
array( 'a', 'abbr', 'acronym', 'code', 'pre', 'em', 'strong', 'div', 'p', 'ul', 'ol', 'li', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'img' ),
|
203 |
+
array()
|
204 |
+
);
|
205 |
+
$themes_allowedtags['a'] = array_fill_keys( array( 'href', 'title', 'target' ), true );
|
206 |
+
$themes_allowedtags['acronym']['title'] = true;
|
207 |
+
$themes_allowedtags['abbr']['title'] = true;
|
208 |
+
$themes_allowedtags['img'] = array_fill_keys( array( 'src', 'class', 'alt' ), true );
|
209 |
+
|
210 |
+
// Prepare a list of installed themes to check against before the loop.
|
211 |
+
$installed_themes = array();
|
212 |
+
$wp_themes = wp_get_themes();
|
213 |
+
foreach ( $wp_themes as $theme ) {
|
214 |
+
$installed_themes[] = $theme->get_stylesheet();
|
215 |
+
}
|
216 |
+
$update_php = network_admin_url( 'update.php?action=install-theme' );
|
217 |
+
|
218 |
+
// Set up properties for themes available on WordPress.org.
|
219 |
+
foreach ( $themes->themes as &$theme ) {
|
220 |
+
$theme->install_url = add_query_arg( array(
|
221 |
+
'theme' => $theme->slug,
|
222 |
+
'_wpnonce' => wp_create_nonce( 'install-theme_' . $theme->slug ),
|
223 |
+
), $update_php );
|
224 |
+
|
225 |
+
$theme->name = wp_kses( $theme->name, $themes_allowedtags );
|
226 |
+
$theme->author = wp_kses( $theme->author, $themes_allowedtags );
|
227 |
+
$theme->version = wp_kses( $theme->version, $themes_allowedtags );
|
228 |
+
$theme->description = wp_kses( $theme->description, $themes_allowedtags );
|
229 |
+
$theme->tags = implode( ', ', $theme->tags );
|
230 |
+
$theme->stars = wp_star_rating( array(
|
231 |
+
'rating' => $theme->rating,
|
232 |
+
'type' => 'percent',
|
233 |
+
'number' => $theme->num_ratings,
|
234 |
+
'echo' => false,
|
235 |
+
) );
|
236 |
+
$theme->num_ratings = number_format_i18n( $theme->num_ratings );
|
237 |
+
$theme->preview_url = set_url_scheme( $theme->preview_url );
|
238 |
+
|
239 |
+
// Handle themes that are already installed as installed themes.
|
240 |
+
if ( in_array( $theme->slug, $installed_themes, true ) ) {
|
241 |
+
$theme->type = 'installed';
|
242 |
+
} else {
|
243 |
+
$theme->type = $theme_action;
|
244 |
+
}
|
245 |
+
|
246 |
+
// Set active based on customized theme.
|
247 |
+
$theme->active = ( isset( $_POST['customized_theme'] ) && $_POST['customized_theme'] === $theme->slug );
|
248 |
+
|
249 |
+
// Map available theme properties to installed theme properties.
|
250 |
+
$theme->id = $theme->slug;
|
251 |
+
$theme->screenshot = array( $theme->screenshot_url );
|
252 |
+
$theme->authorAndUri = $theme->author;
|
253 |
+
// The .org API can return the full parent theme details if passed the 'parent' arg, or if passed the 'template' option it'll return that in the event it's a child theme.
|
254 |
+
if ( isset( $theme->parent ) ) {
|
255 |
+
$theme->parent = $theme->parent['slug'];
|
256 |
+
} else {
|
257 |
+
$theme->parent = false;
|
258 |
+
}
|
259 |
+
unset( $theme->slug );
|
260 |
+
unset( $theme->screenshot_url );
|
261 |
+
unset( $theme->author );
|
262 |
+
} // End foreach().
|
263 |
+
} elseif ( 'wporg' === $theme_action ) {
|
264 |
+
|
265 |
+
// Load WordPress.org themes from the .org API and normalize data to match installed theme objects.
|
266 |
+
if ( ! current_user_can( 'install_themes' ) ) {
|
267 |
+
wp_die( -1 );
|
268 |
+
}
|
269 |
+
|
270 |
+
// Arguments for all queries.
|
271 |
+
$wporg_args = array(
|
272 |
+
'per_page' => 100,
|
273 |
+
'fields' => array(
|
274 |
+
'screenshot_url' => true,
|
275 |
+
'description' => true,
|
276 |
+
'rating' => true,
|
277 |
+
'downloaded' => true,
|
278 |
+
'downloadlink' => true,
|
279 |
+
'last_updated' => true,
|
280 |
+
'homepage' => true,
|
281 |
+
'num_ratings' => true,
|
282 |
+
'tags' => true,
|
283 |
+
'parent' => true,
|
284 |
+
// 'extended_author' => true, @todo: WordPress.org throws a 500 server error when this is here.
|
285 |
+
),
|
286 |
+
);
|
287 |
+
|
288 |
+
$args = array_merge( $wporg_args, $args );
|
289 |
+
|
290 |
+
if ( '' === $args['search'] && '' === $args['tag'] ) {
|
291 |
+
$args['browse'] = 'new'; // Sort by latest themes by default.
|
292 |
+
}
|
293 |
+
|
294 |
+
// Load themes from the .org API.
|
295 |
+
$themes = themes_api( 'query_themes', $args );
|
296 |
+
if ( is_wp_error( $themes ) ) {
|
297 |
+
wp_send_json_error();
|
298 |
+
}
|
299 |
+
|
300 |
+
// This list matches the allowed tags in wp-admin/includes/theme-install.php.
|
301 |
+
$themes_allowedtags = array_fill_keys(
|
302 |
+
array( 'a', 'abbr', 'acronym', 'code', 'pre', 'em', 'strong', 'div', 'p', 'ul', 'ol', 'li', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'img' ),
|
303 |
+
array()
|
304 |
+
);
|
305 |
+
$themes_allowedtags['a'] = array_fill_keys( array( 'href', 'title', 'target' ), true );
|
306 |
+
$themes_allowedtags['acronym']['title'] = true;
|
307 |
+
$themes_allowedtags['abbr']['title'] = true;
|
308 |
+
$themes_allowedtags['img'] = array_fill_keys( array( 'src', 'class', 'alt' ), true );
|
309 |
+
|
310 |
+
// Prepare a list of installed themes to check against before the loop.
|
311 |
+
$installed_themes = array();
|
312 |
+
$wp_themes = wp_get_themes();
|
313 |
+
foreach ( $wp_themes as $theme ) {
|
314 |
+
$installed_themes[] = $theme->get_stylesheet();
|
315 |
+
}
|
316 |
+
$update_php = network_admin_url( 'update.php?action=install-theme' );
|
317 |
+
|
318 |
+
// Set up properties for themes available on WordPress.org.
|
319 |
+
foreach ( $themes->themes as &$theme ) {
|
320 |
+
$theme->install_url = add_query_arg( array(
|
321 |
+
'theme' => $theme->slug,
|
322 |
+
'_wpnonce' => wp_create_nonce( 'install-theme_' . $theme->slug ),
|
323 |
+
), $update_php );
|
324 |
+
|
325 |
+
$theme->name = wp_kses( $theme->name, $themes_allowedtags );
|
326 |
+
$theme->author = wp_kses( $theme->author, $themes_allowedtags );
|
327 |
+
$theme->version = wp_kses( $theme->version, $themes_allowedtags );
|
328 |
+
$theme->description = wp_kses( $theme->description, $themes_allowedtags );
|
329 |
+
$theme->tags = implode( ', ', $theme->tags );
|
330 |
+
$theme->stars = wp_star_rating( array(
|
331 |
+
'rating' => $theme->rating,
|
332 |
+
'type' => 'percent',
|
333 |
+
'number' => $theme->num_ratings,
|
334 |
+
'echo' => false,
|
335 |
+
) );
|
336 |
+
$theme->num_ratings = number_format_i18n( $theme->num_ratings );
|
337 |
+
$theme->preview_url = set_url_scheme( $theme->preview_url );
|
338 |
+
|
339 |
+
// Handle themes that are already installed as installed themes.
|
340 |
+
if ( in_array( $theme->slug, $installed_themes, true ) ) {
|
341 |
+
$theme->type = 'installed';
|
342 |
+
} else {
|
343 |
+
$theme->type = $theme_action;
|
344 |
+
}
|
345 |
+
|
346 |
+
// Set active based on customized theme.
|
347 |
+
$theme->active = ( isset( $_POST['customized_theme'] ) && $_POST['customized_theme'] === $theme->slug );
|
348 |
+
|
349 |
+
// Map available theme properties to installed theme properties.
|
350 |
+
$theme->id = $theme->slug;
|
351 |
+
$theme->screenshot = array( $theme->screenshot_url );
|
352 |
+
$theme->authorAndUri = $theme->author;
|
353 |
+
// The .org API can return the full parent theme details if passed the 'parent' arg, or if passed the 'template' option it'll return that in the event it's a child theme.
|
354 |
+
if ( isset( $theme->parent ) ) {
|
355 |
+
$theme->parent = $theme->parent['slug'];
|
356 |
+
} else {
|
357 |
+
$theme->parent = false;
|
358 |
+
}
|
359 |
+
unset( $theme->slug );
|
360 |
+
unset( $theme->screenshot_url );
|
361 |
+
unset( $theme->author );
|
362 |
+
} // End foreach().
|
363 |
+
} // End if().
|
364 |
+
|
365 |
+
/**
|
366 |
+
* Filters the theme data loaded in the customizer.
|
367 |
+
*
|
368 |
+
* This allows theme data to be loading from an external source,
|
369 |
+
* or modification of data loaded from `wp_prepare_themes_for_js()`
|
370 |
+
* or WordPress.org via `themes_api()`.
|
371 |
+
*
|
372 |
+
* @since 4.9.0
|
373 |
+
*
|
374 |
+
* @see wp_prepare_themes_for_js()
|
375 |
+
* @see themes_api()
|
376 |
+
* @see WP_Customize_Manager::__construct()
|
377 |
+
*
|
378 |
+
* @param array $themes Nested array of theme data.
|
379 |
+
* @param array $args List of arguments, such as page, search term, and tags to query for.
|
380 |
+
* @param WP_Customize_Manager $manager Instance of Customize manager.
|
381 |
+
*/
|
382 |
+
$themes = apply_filters( 'customize_load_themes', $themes, $args, $wp_customize );
|
383 |
+
|
384 |
+
wp_send_json_success( $themes );
|
385 |
+
}
|
386 |
+
}
|