';
}
}
}
// --------------------
// Discreet Text Widget
// --------------------
// most super useful widget, especially when used with shortcodes
// (so that if the shortcode returns empty the widget is not displayed)
// ref: https://wordpress.org/plugins/hackadelic-discreet-text-widget/
// 1.8.5: removed option, always on by default
if (!function_exists('bioship_muscle_discreet_text_widget')) {
add_action('widgets_init', 'bioship_muscle_discreet_text_widget');
function bioship_muscle_discreet_text_widget() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
// 1.9.8: added class check (for no conflict with content sidebars plugin)
// 2.0.9: no discreet text widget for WordPress.org version
// (widgets classes need to be in plugins not themes in repository)
if (!class_exists('DiscreetTextWidget') && !THEMEWPORG) {
// 2.0.8: extend classic text widget class
class DiscreetTextWidget extends WP_Widget_Classic_Text {
function __construct() {
$widgetops = array(
'classname' => 'discreet_text_widget',
'description' => esc_attr(__('Arbitrary text or HTML, only shown if not empty.','bioship'))
);
$controlops = array('width' => 400, 'height' => 350);
// 1.9.8: fix to deprecated class construction method
// 2.0.7: fix to incorrect text domain (csidebars)
call_user_func(array(get_parent_class(get_parent_class($this)), '__construct'), 'discrete_text', esc_attr(__('Discreet Text','bioship')), $widgetops, $controlops);
}
function widget($args, $instance) {
// 1.9.8: removed usage of extract here
$text = bioship_apply_filters('widget_text', $instance['text']);
if (empty($text)) {return;}
echo $args['before_widget']; // phpcs:ignore WordPress.Security.OutputNotEscaped
$title = bioship_apply_filters('widget_title', $instance['title']);
if (!empty($title)) {
echo $args['before_title'].esc_attr($title).$args['after_title']; // phpcs:ignore WordPress.Security.OutputNotEscaped
}
echo '
';
}
return $readmore;
}
}
// ---------------------
// Remove More Jump Link
// ---------------------
// TODO: maybe add a theme option for removing jump link?
if (!function_exists( 'bioship_muscle_remove_more_jump_link')) {
add_filter('the_content_more_link', 'bioship_muscle_remove_more_jump_link');
function bioship_muscle_remove_more_jump_link($link) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// --- remove the hashed suffix ---
$offset = strpos($link, '#more-');
// 2.0.9: fix to link variable typo
if ($offset) {$end = strpos($link, '"', $offset);}
if ($end) {$link = substr_replace($link, '', $offset, ($end - $offset));}
return $link;
}
}
// ---------------
// === Writing ===
// ---------------
// --------------------
// Limit Post Revisions
// --------------------
// 1.8.0: [deprecated] moved to separate AutoSave Net plugin
// ------------------------------------
// WP Subtitle Custom Post Type Support
// ------------------------------------
if (!function_exists('bioship_muscle_wp_subtitle_custom_support')) {
// 2.1.1: moved add_action internally for consistency
add_action('init', 'bioship_muscle_wp_subtitle_custom_support');
function bioship_muscle_wp_subtitle_custom_support() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
// --- WP Subtitle plugin check ---
if (!function_exists('get_the_subtitle')) {return;}
// -- add/remove CPT subtitle support ---
$cptsubtitles = $vthemesettings['subtitlecpts'];
// 2.0.8: fix for possible empty subtitle setting
if (is_array($cptsubtitles)) {
foreach ($cptsubtitles as $cpt => $value) {
if ($value) {
if ( ($cpt != 'post') && ($cpt != 'page') ) {add_post_type_support($cpt, 'wps_subtitle');}
} else {
if ($cpt == 'post') {remove_post_type_support('post', 'wps_subtitle');}
if ($cpt == 'page') {remove_post_type_support('page', 'wps_subtitle');}
}
}
}
}
}
// -----------------
// === RSS Feeds ===
// -----------------
// --------------------
// Automatic Feed Links
// --------------------
// 2.0.5: added missing setting filter
if ( (isset($vthemesettings['autofeedlinks'])) && ($vthemesettings['autofeedlinks'] == '1') ) {
$autofeedlinks = true;
} else {$autofeedlinks = false;}
$autofeedlinks = bioship_apply_filters('muscle_automatic_feed_links', $autofeedlinks);
if ($autofeedlinks) {add_theme_support('automatic-feed-links');}
else {remove_theme_support('automatic-feed-links');}
// -----------------
// RSS Publish Delay
// -----------------
// 2.0.5: check setting internally to allow filtering
if (!function_exists('bioship_muscle_delay_feed_publish')) {
add_filter('posts_where', 'bioship_muscle_delay_feed_publish');
function bioship_muscle_delay_feed_publish($where) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $wpdb, $vthemesettings;
// --- check conditions ---
// 2.0.5: added missing setting filter
// 2.1.0: still allow filtering if not set (wp.org version)
// 2.1.1: fix to delay bypass conditions
if (!is_feed()) {return $where;}
if (!isset($vthemesettings['rsspublishdelay'])) {$delay = false;}
else {$delay = $vthemesettings['rsspublishdelay'];}
$delay = bioship_apply_filters('muscle_rss_feed_publish_delay', $delay);
if ( !$delay || !is_numeric($delay) || ($delay == 0)) {return $where;}
$now = gmdate('Y-m-d H:i:s');
// ref: http://dev.mysql.com/doc/refman/5.0/en/date-and-time-functions.html#function_timestampdiff
$units = 'MINUTE'; // MINUTE, HOUR, DAY, WEEK, MONTH, YEAR
$units = bioship_apply_filters('muscle_rss_feed_delay_units', $units);
// add SQL-sytax to default $where
$where .= " AND TIMESTAMPDIFF(".$units.", $wpdb->posts.post_date_gmt, '".$now."') > ".$delay." ";
return $where;
}
}
// --------------------------
// Set Post Types in RSS Feed
// --------------------------
// 2.0.5: check settings internally to allow filtering
// 2.0.5: simplified logic for this filter function
if (!function_exists('bioship_muscle_custom_feed_request')) {
add_filter('request', 'bioship_muscle_custom_feed_request');
function bioship_muscle_custom_feed_request($vars) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
if (!is_feed()) {return $vars;}
// 2.1.0: set to false if setting is not present (WordPress.Org version)
if (!isset($vthemesettings['cptsinfeed'])) {$cptsinfeed = false;}
else {$cptsinfeed = $vthemesettings['cptsinfeed'];}
$cptsinfeed = bioship_apply_filters('muscle_rss_feed_post_types', $cptsinfeed);
bioship_debug("Feed CPTs", $cptsinfeed);
if ($cptsinfeed && is_array($cptsinfeed)) {
if (isset($vars['feed']) && !isset($vars['post_type'])) {
// TODO: recheck whether this is still working as desired
$vars['post_type'] = $cptsinfeed;
}
}
return $vars;
}
}
// -----------------------
// Full Content Page Feeds
// -----------------------
// ref: http://wordpress.stackexchange.com/a/227455/76440
// 1.8.5: added this option
// 2.0.0: fix to query object typo
// 2.0.1: fix to match function_exists check
// 2.0.5: check setting internally to allow filtering
if (!function_exists('bioship_muscle_rss_page_feed_full_content')) {
// 2.0.5: move add_action inside for consistency
add_action('pre_get_posts', 'bioship_muscle_rss_page_feed_full_content');
function bioship_muscle_rss_page_feed_full_content($query) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
// --- check conditions ---
// 2.1.0: default to false if setting is not present (WordPress.Org version)
if (!isset($vthemesettings['pagecontentfeeds'])) {$pagefeeds = false;}
else {$pagefeeds = $vthemesettings['pagecontentfeeds'];}
$pagefeeds = bioship_apply_filters('muscle_rss_full_page_feeds', $pagefeeds);
if (!$pagefeeds) {return $query;}
// --- check for single page feed request ---
if ($query->is_main_query() && $query->is_feed() && $query->is_page()) {
// set the post type to page
$query->set('post_type', array('page'));
// allow for page comments feed via ?withcomments=1
if (isset($_GET['withcomments']) && ($_GET['withcomments'] == '1')) {return;}
// set the comment feed to false
$query->is_comment_feed = false;
}
// --- debug feed query ---
if ($query->is_feed()) {bioship_debug("Feed Query", $query);}
}
}
// -----------------------------
// Full Content Page Feed Filter
// -----------------------------
// 2.0.0: fix to typo in funcname
if (!function_exists('bioship_muscle_page_rss_excerpt_option')) {
// 2.0.5: move add_filter inside for consistency
add_filter('pre_option_rss_use_excerpt', 'bioship_muscle_page_rss_excerpt_option');
function bioship_muscle_page_rss_excerpt_option($option) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
// --- check setting ---
$pagefeeds = bioship_apply_filters('muscle_rss_full_page_feeds', $vthemesettings['pagecontentfeeds']);
if (!$pagefeeds) {return $option;}
// --- force full content output for pages ---
if (is_page()) {return '0';}
return $option;
}
}
// TODO: test strip_shortcode result for excerpt_rss (on multiple installs?)
// (this code causing some troubles)
// add_filter('the_excerpt_rss','bioship_muscle_rss_page_excerpt');
// if (!function_exists('bioship_muscle_rss_page_excerpt')) {
// function bioship_muscle_rss_page_excerpt($excerpt) {
// if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// if (is_page()) {
// global $post; $text = $post->post_content;
// // removed this line otherwise got blank
// // $text = strip_shortcodes( $text );
// $text = bioship_apply_filters( 'the_content', $text );
// $text = str_replace(']]>', ']]>', $text);
// $excerpt_length = bioship_apply_filters( 'excerpt_length', 55 );
// $excerpt_more = bioship_apply_filters( 'excerpt_more', ' ' . '[…]' );
// $excerpt = wp_trim_words( $text, $excerpt_length, $excerpt_more );
// }
// return $excerpt;
// }
// }
// -------------
// === Admin ===
// -------------
// ------------------------------
// Add Theme Options to Admin Bar
// ------------------------------
// 1.8.5: moved here from muscle.php, option changed to filter
// 2.1.3: moved back to muscle.php (so it works on frontend)
if (!function_exists('bioship_muscle_adminbar_theme_options')) {
// 2.0.5: check filter inside function for consistency
add_action('wp_before_admin_bar_render', 'bioship_muscle_adminbar_theme_options');
function bioship_muscle_adminbar_theme_options() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $wp_admin_bar, $vthemename, $vthemedirs;
// 2.1.2: check admin permissions
if (!current_user_can('manage_options') && !current_user_can('edit_theme_options')) {return;}
// --- filter adding of theme options link ---
$adminbar = bioship_apply_filters('admin_adminbar_theme_options', true);
if (!$adminbar) {return;}
// --- set theme options link ---
if (THEMEOPT || THEMETITAN || class_exists('TitanFramework')) {
// 1.8.5: use add_query_arg here
$themelink = admin_url('themes.php');
if (THEMEOPT) {$themepage = 'options-framework';} else {$themepage = 'bioship-options';}
$themelink = add_query_arg('page', $themepage, $themelink);
} else {
// 1.8.0: link to customize.php if no theme options page exists
$themelink = admin_url('customize.php');
$themelink = add_query_arg('return', urlencode(wp_unslash($_SERVER['REQUEST_URI'])), $themelink);
}
// --- theme test drive compatibility ---
// 1.8.5: maybe append the Theme Test Drive querystring
if (isset($_REQUEST['theme']) && ($_REQUEST['theme'] != '')) {
$themelink = add_query_arg('theme', $_REQUEST['theme'], $themelink);
}
// --- add theme options link icon ---
// 1.5.0: Add an Icon next to the Theme Options menu item
// ref: http://wordpress.stackexchange.com/questions/172939/how-do-i-add-an-icon-to-a-new-admin-bar-item
// default is set to \f115 Dashicon (an eye in a screen) in skin.php
// and can be overridden using admin_adminbar_menu_icon filter
$icon = bioship_file_hierarchy('url', 'theme-icon.png', $vthemedirs['image']);
$icon = bioship_apply_filters('admin_adminbar_theme_options_icon', $icon);
if ($icon) {
// 2.0.9: fix for variable name (vthemesettingsicon)
$iconspan = '';
} else {$iconspan = '';}
// --- add admin bar link and title ---
$title = esc_attr(__('Theme Options','bioship'));
$title = bioship_apply_filters('admin_adminbar_theme_options_title', $title);
$menu = array('id' => 'theme-options', 'title' => $iconspan.$title, 'href' => $themelink);
$wp_admin_bar->add_menu($menu);
}
}
// ----------------------------
// Replace Welcome in Admin Bar
// ----------------------------
// 1.8.5: moved here from muscle.php
// 2.1.3: moved back to muscle.php (to work on frontend)
if (!function_exists('bioship_muscle_adminbar_replace_howdy')) {
add_filter('admin_bar_menu', 'bioship_muscle_adminbar_replace_howdy', 25);
function bioship_muscle_adminbar_replace_howdy($wp_admin_bar) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 2.1.1: filter whether to replace welcome message
$replacehowdy = bioship_apply_filters('admin_adminbar_replace_howdy', true);
if (!$replacehowdy) {return;}
// 1.9.8: replaced deprecated function get_currentuserinfo();
// 2.0.7: use new prefixed current user function
$current_user = bioship_get_current_user();
$username = $current_user->user_login;
$myaccount = $wp_admin_bar->get_node('my-account');
// --- filter the new node title ---
// 1.5.5: fixed translation for Theme Check
$newtitle = esc_attr(__('Logged in as', 'bioship')).' '.$username;
$newtitle = bioship_apply_filters('admin_adminbar_howdy_title', $newtitle);
$wp_admin_bar->add_node(array('id' => 'my-account', 'title' => $newtitle));
}
}
// ---------------------------------------
// Add "All Options" Page to Settings Menu
// ---------------------------------------
if (!function_exists('bioship_muscle_all_options_link')) {
// 2.0.1: moved filter option internally
add_action('admin_menu', 'bioship_muscle_all_options_link', 11);
function bioship_muscle_all_options_link() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings, $submenu;
// 2.1.1: do not add All Options link for WordPress.Org version
if (THEMEWPORG) {return;}
// --- check setting ---
if (isset($vthemesettings['alloptionspage'])) {$addlink = $vthemesettings['alloptionspage'];} else {$addlink = false;}
$addlink = bioship_apply_filters('muscle_all_options_page', $addlink);
if ($addlink == '1') {
// 2.0.7: changed to use add_theme_page instead of add_options_page
add_theme_page(esc_attr(__('All Options','bioship')), esc_attr(__('All Options','bioship')), 'manage_options', 'options.php');
// 2.0.7: then shift from themes to settings menu
// 2.1.0: check submenu key exists before looping
if (isset($submenu['options-general.php'])) {
foreach ($submenu['options-general.php'] as $key => $values) {$lastkey = $key + 1;}
}
if (isset($submenu['themes.php'])) {
foreach ($submenu['themes.php'] as $key => $values) {
if ($values[2] == 'options.php') {
$submenu['options-general.php'][$lastkey] = $values;
unset($submenu['themes.php'][$key]);
}
}
}
}
}
}
// --------------------
// Remove Update Notice
// --------------------
if (!function_exists('bioship_muscle_remove_update_notice')) {
add_action('init', 'bioship_muscle_remove_update_notice', 1);
function bioship_muscle_remove_update_notice() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
// --- check setting ---
if (isset($vthemesettings['removeupdatenotice'])) {$remove = $vthemesettings['removeupdatenotice'];} else {$remove = false;}
$remove = bioship_apply_filters('muscle_remove_update_notice', $remove);
if ($remove != '1') {return;}
// --- permission checks ---
// 2.1.1: changed from update_plugins to update_core
if (!current_user_can('update_core')) {
// 2.0.1: simplify to remove version check action here
remove_action('init', 'wp_version_check');
add_filter('pre_option_update_core', '__return_null');
}
}
}
// ---------------------------
// Stop New User Notifications
// ---------------------------
// 2.0.1: check themesettings internally to allow filtering
if (!function_exists('bioship_muscle_stop_new_user_notifications')) {
add_action('phpmailer_init', 'bioship_muscle_stop_new_user_notifications');
function bioship_muscle_stop_new_user_notifications() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
if (isset($vthemesettings['disablenotifications'])) {$disable = $vthemesettings['disablenotifications'];} else {$disable = false;}
$disable = bioship_apply_filters('muscle_stop_new_user_notifications', $disable);
if ($disable != '1') {return;}
// note: handling translation wrappers in subject line is not working,
// so this feature may not work with multi-language translations
global $phpmailer;
if (is_multisite()) {
// 2.0.7: added missing translation wrapper
// 2.0.9: duh, removed translation wrapper
$subject = 'New User Registration';
if ($phpmailer->Subject == $subject) {$phpmailer = new PHPMailer(true);}
} else {
$blogname = wp_specialchars_decode(get_option('blogname'), ENT_QUOTES);
// 2.0.7: added missing text domain
// 2.0.9: duh, removed text domain again
// 2.1.0: need to remove translation wrappers
$subject = array(
sprintf('[%s] New User Registration', $blogname),
sprintf('[%s] Password Lost/Changed', $blogname)
);
if (in_array($phpmailer->Subject, $subject)) {$phpmailer = new PHPMailer(true);}
}
}
}
// ------------------
// Disable Self Pings
// ------------------
// 2.0.1: check themesettings internally to allow filtering
if (!function_exists('bioship_muscle_disable_self_pings')) {
add_action('pre_ping','bioship_muscle_disable_self_pings');
// 2.0.0: remove unneeded pass by reference in argument
function bioship_muscle_disable_self_pings($links) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
// --- check settings ---
if (isset($vthemesettings['disableselfpings'])) {$disable = $vthemesettings['disableselfpings'];} else {$disable = false;}
$disable = bioship_apply_filters('muscle_disable_self_pings', $disable);
if ($disable != '1') {return;}
// --- remove ping if contains home URL ---
// 1.5.5: fix to use home_url for theme check
$home = home_url();
foreach ($links as $i => $link) {if (0 === strpos($link, $home)) {unset($links[$i]);} }
}
}
// -----------------
// Cleaner Admin Bar
// -----------------
// (removes WP links)
// 2.0.1: check themesettings internally to allow filtering
if (!function_exists('bioship_muscle_cleaner_adminbar')) {
add_action('wp_before_admin_bar_render', 'bioship_muscle_cleaner_adminbar');
function bioship_muscle_cleaner_adminbar() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
// --- check settings ---
if (isset($vthemesettings['cleaneradminbar'])) {$clean = $vthemesettings['cleaneradminbar'];} else {$clean = false;}
$clean = bioship_apply_filters('muscle_cleaner_admin_bar', $clean);
if ($clean != '1') {return;}
// --- set items to remove ---
global $wp_admin_bar;
// 1.8.0: added array filter for altering adminbar link removal
$removeitems = array('wp-logo', 'about', 'wporg', 'documentation', 'support-forums', 'feedback');
$removeitems = bioship_apply_filters('admin_adminbar_remove_items', $removeitems);
// --- remove admin bar items ---
if (count($removeitems) > 0) {
foreach ($removeitems as $removeitem) {$wp_admin_bar->remove_menu($removeitem);}
}
}
}
// -------------
// === Login ===
// -------------
// ----------------
// Login Header URL
// ----------------
if (!function_exists('bioship_muscle_login_headerurl')) {
add_filter('login_headerurl', 'bioship_muscle_login_headerurl' );
function bioship_muscle_login_headerurl($url) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 2.0.9: added missing theme-specific filtering
// 2.1.1: added missing bioship_ function prefix
$url = bioship_apply_filters('muscle_login_header_title', site_url('/'));
return $url;
}
}
// ------------------
// Login Header Title
// ------------------
if (!function_exists('bioship_muscle_login_headertitle')) {
add_filter('login_headertitle', 'bioship_muscle_login_headertitle');
function bioship_muscle_login_headertitle($title) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 2.0.9: added missing theme-specific filtering
// 2.1.1: added missing bioship_ function prefix
$title = bioship_apply_filters('muscle_login_header_title', get_bloginfo('name'));
return $title;
}
}
// ---------------
// Login Page Logo
// ---------------
// (adds a #loginwrapper element to help styling)
// 1.8.5: moved actual login styling to skin.php
// 1.8.5: much fun with login wrapper hacks!
if (!function_exists('bioship_muscle_login_styles')) {
add_action('login_head', 'bioship_muscle_login_styles');
function bioship_muscle_login_styles() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
// --- add loginwrapper class placeholder ---
if (!function_exists('bioship_muscle_login_body_hack')) {
add_filter('login_body_class', 'bioship_muscle_login_body_hack', 999);
function bioship_muscle_login_body_hack($classes) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
$classes[] = 'LOGINWRAPPER';
add_filter('attribute_escape', 'bioship_muscle_login_body_filter_hack', 999, 2);
return $classes;
}
}
// --- replace loginwrapper class with div ---
if (!function_exists('bioship_muscle_login_body_filter_hack')) {
function bioship_muscle_login_body_filter_hack($safetext, $text) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
$replace = '">
".PHP_EOL;
bioship_html_comment('/#loginwrapper');
}
}
}
}
// --------------------
// === Integrations ===
// --------------------
// ========
// CSS Hero
// ========
// ---------------------------------
// Adjust CSS Hero Declarations Path
// ---------------------------------
// also allows for the file to be in the parent theme directory
// (this is a bit hacky, hopefully a real filter is available for this in future!)
// 1.8.5: allow moving of csshero.js from theme root to javascript dirs
// 2.1.1: moved integration function here from skull.php
if (isset($_GET['csshero_action']) && ($_GET['csshero_action'] == 'edit_page')) {
// 1.9.5: added filter to optionally disable this path adjustment
$csshero = bioship_apply_filters('skeleton_adjust_css_hero_script_dir', true);
if ($csshero) {
// TODO: maybe prefix function name with bioship_muscle_
if (!function_exists('bioship_csshero_script_dir')) {
// 2.1.1: moved add_action internally for consistency
add_action('wp_loaded', 'bioship_csshero_script_dir', 0);
function bioship_csshero_script_dir() {
add_filter('stylesheet_directory_uri', 'bioship_csshero_script_url', 10, 3);
// 2.1.1: added missing function_exists wrapper
// 2.1.3: renamed csshero.js to bioship-csshero.js
if (!function_exists('bioship_csshero_script_url')) {
function bioship_csshero_script_url($stylesheet_dir_url, $stylesheet, $theme_root_url) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemedirs;
$csshero = bioship_file_hierarchy('url', 'bioship-csshero.js', $vthemedirs['script']);
if ($csshero) {$stylesheet_dir_url = dirname($csshero);}
remove_filter('stylesheet_directory_url', 'skeleton_css_hero_script_url', 10, 3);
return $stylesheet_dir_url;
}
}
}
}
}
}
// ===========
// WooCommerce
// ===========
// ------------------------------
// WooCommerce Template Directory
// ------------------------------
// Changes directory for Woocommerce templates (for both child and parent theme directories)
// intended so you could use: /theme/theme-name/templates/woocommerce/
// instead of the default: /theme/theme-name/woocommerce/
// (as a better way of organizing 3rd party templates)
// WARNING: use one directory OR the other, it is NOT a hierarchy so you cannot use both!
// --------------------------------
// WooCommerce Template Path Filter
// --------------------------------
if (class_exists('WC_Template_Loader')) {
add_filter('woocommerce_template_path', 'bioship_muscle_woocommerce_template_path');
if (!function_exists('bioship_muscle_woocommerce_template_path')) {
function bioship_muscle_woocommerce_template_path($path) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 1.9.5: added this filter to allow further change
// override woocommerce/ to (filtered) templates/woocommerce/
$newpath = bioship_apply_filters('skeleton_woocommerce_template_directory', 'templates/woocommerce/');
global $vthemetemplatedir, $vthemestyledir;
if (is_dir($vthemetemplatedir.$newpath) || is_dir($vthemestyledir.$newpath)) {
// 1.9.5: only if new template directory exists do we apply other template filters
add_filter('wc_get_template', 'bioship_muscle_woocommerce_template', 10, 5);
add_filter('wc_get_template_part', 'bioship_muscle_woocommerce_template_part', 10, 3);
return $newpath;
}
else {return $path;}
}
}
}
// ---------------------------------------------
// Woocommerce Template subdirectories Templates
// ---------------------------------------------
// 2.1.1: removed unneeded function_exists check
if (!function_exists('bioship_muscle_woocommerce_template')) {
function bioship_muscle_woocommerce_template($located, $template_name, $args, $template_path, $default_path) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// --- find the new template via file hierarchy ---
// looking in templates/woocommerce/ then woocommerce/
// 1.9.5: apply the template directory filter and search that only
// 2.1.1: removed unnecessary trailing slash from default path
$newpath = bioship_apply_filters('skeleton_woocommerce_template_directory', 'templates/woocommerce');
$newtemplate = bioship_file_hierarchy('file', $template_name, array($newpath));
// -- write debug info ---
// (not used but kept here as useful for finding templates)
// ob_start();
// echo "new template: "; print_r($newtemplate); echo PHP_EOL;
// echo "located: "; print_r($located); echo PHP_EOL;
// echo "template_name: "; print_r($template_name); echo PHP_EOL;
// $data = ob_get_contents(); ob_end_clean();
// bioship_write_debug_file('woo-templates.txt', $data);
// return the new template location if found
if ($newtemplate) {return $newtemplate;}
return $located;
}
}
// --------------------------
// Woocommerce Template Parts
// --------------------------
// 2.1.1: removed unneeded function_exists check
// eg. single-product-content.php and anything retrieved by wc_get_template_part
if (!function_exists('bioship_muscle_woocommerce_template_part')) {
function bioship_muscle_woocommerce_template_part($template, $slug, $name) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 1.9.5: apply the template directory filter and search that only
// 2.1.1: removed unnecessary trailing slash from default path
$newpath = bioship_apply_filters('skeleton_woocommerce_template_directory', 'templates/woocommerce');
// get slug-name template via file hierarchy
$newtemplate = bioship_file_hierarchy('file', $slug.'-'.$name.'.php', array($newpath));
// include a fallback to slug based template
$slugtemplate = bioship_file_hierarchy('file', $slug.'.php', array($newpath));
// write debug info (kept here as useful for finding templates)
// ob_start();
// echo "name template (".$name."): "; print_r($newtemplate); echo PHP_EOL;
// echo "slug template (".$slug."): "; print_r($slugtemplate); echo PHP_EOL;
// $data = ob_get_contents(); ob_end_clean();
// bioship_write_debug_file('woo-template-parts.txt', $data);
// maybe return the altered template location
if ($newtemplate) {return $newtemplate;}
if ($slugtemplate) {return $slugtemplate;}
return $template;
}
}
// =============================
// Open Graph Protocol Framework
// =============================
// ...yah down wid OGP? yeah u know me...
// Ref: http://www.itthinx.com/plugins/open-graph-protocol/
// -------------------------------------
// Set Open Graph Protocol Default Image
// -------------------------------------
// requires Open Graph Protocol plugin to be installed and active
// note: if using Jetpack see filter: jetpack_open_graph_image_default
// 1.5.0: added default image meta
if (!function_exists('bioship_muscle_open_graph_default_image')) {
// 2.0.5: move filter inside for consistency
add_filter('open_graph_protocol_metas', 'bioship_muscle_open_graph_default_image');
function bioship_muscle_open_graph_default_image($metas) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemename, $vthemesettings, $vthemedirs;
// --- allow for open graph image override filter ---
// (see next func for in-built custom field override)
$image = array();
if (isset($metas['og:image:width'])) {$image[0] = $metas['og:image:width'];}
if (isset($metas['og:image:height'])) {$image[1] = $metas['og:image:height'];}
if (isset($metas['og:image'])) {$image[2] = $metas['og:image'];}
$image = bioship_apply_filters('muscle_open_graph_override_image', $image);
// --- if we now have an image and it is a different URL ---
if (isset($image[2])) {
if ($image[2] != $metas['og:image']) {
// --- allow override to turn this meta off completely ---
if ($image[2] == 'off') {return array();}
// --- if image changed/updated, check for new width and height ---
if (isset($image[0]) && isset($image[1])) {
$metas['og:image:width'] = $image[0];
$metas['og:image:height'] = $image[1];
$metas['og:image'] = $image[2];
} else {
// --- otherwise, use getimagesize (slower) ---
// 2.0.9: set missing default value
// 2.1.1: try filepath conversion in any case as file system is faster
$filepath = ABSPATH.parse_url($url, PHP_URL_PATH);
if (file_exists($filepath)) {$urltofilepath = true;} else {$urltofilepath = false;}
if ($urltofilepath || ini_get('allow_url_fopen')) {
if ($urltofilepath) {$imagesize = getimagesize($filepath);}
else {$imagesize = getimagesize($image[2]);}
if ($imagesize) {
$metas['og:image:width'] = $imagesize[0];
$metas['og:image:height'] = $imagesize[1];
$metas['og:image'] = $image[2];
}
}
}
} else {
// same URL, maybe a change in size though
// as it is an override, just do that
$metas['og:image:width'] = $image[0];
$metas['og:image:height'] = $image[1];
}
}
// --- default (fallback) open graph image option ---
if (!isset($metas['og:image'])) {
// 1.9.6: removed this code as even 192 does not meet OG minimum of 200
// maybe pick the largest size if set to precomposed apple touch icons
// if ($vthemesettings['ogdefaultimage'] == 'appletouchicon') {
// $sizes = array('192','180','152','144','120','114','75','72');
// $found = false;
// foreach ($sizes as $size) {
// if (!$found) {
// $checkurl = bioship_file_hierarchy('url', 'touch-icon-'.$size.'x'.$size.'-precomposed.png', $vthemedirs['image']);
// if ($checkurl) {vurl = $checkurl; $found = true;}
// }
// }
// }
// else {
// --- set the URL via theme settings suboption ---
$key = $vthemesettings['ogdefaultimage'];
if ($key == '') {$key = 'header_logo';}
// 1.9.5: fix for uploaded default image
// 2.0.8: added new open graph image off option
if ($key == 'none') {$url = '';}
elseif ($key == 'site_icon') {$url = get_site_icon_url();}
else {$url = $vthemesettings[$key];}
// }
// --- allow for default open graph image filter ---
bioship_debug("Open Graph Default Image URL", $url);
$url = bioship_apply_filters('muscle_open_graph_default_image_url', $url);
bioship_debug("Filtered OpenGraph URL", $url);
if ($url != '') {
// best to cache image size like in skin.php header logo for getimagesize
// ...but again need to check for allow_url_fopen to do that
// --- try to convert URL to filepath ---
// 2.1.1: try filepath conversion in any case as file system is faster
$filepath = ABSPATH.parse_url($url, PHP_URL_PATH);
if (file_exists($filepath)) {$urltofilepath = true;} else {$urltofilepath = false;}
if ($urltofilepath || ini_get('allow_url_fopen')) {
$imagesize = get_option($vthemename.'_ogdefaultimage');
if (strstr($imagesize,':')) {
$imagesize = explode(':', $imagesize);
if ($imagesize[2] != $url) {
if ($urltofilepath) {$imagesize = getimagesize($filepath);}
else {$imagesize = getimagesize($url);}
if ($imagesize) {
$imagedata = $imagesize[0].':'.$imagesize[1].':'.$url;
// 2.0.5: remove unnecessary add_option fallback
update_option($vthemename.'_ogdefaultimage', $imagedata);
}
}
} else {
if ($urltofilepath) {$imagesize = getimagesize($filepath);}
else {$imagesize = getimagesize($url);}
if ($imagesize) {
$imagedata = $imagesize[0].':'.$imagesize[1].':'.$url;
// 2.0.5: remove unnecessary add_option fallback
update_option($vthemename.'_ogdefaultimage', $imagedata);
}
}
// --- set image meta ---
if ($imagesize) {
$metas['og:image'] = $url;
$metas['og:image:width'] = $imagesize[0];
$metas['og:image:height'] = $imagesize[1];
}
} else {
// no allow_fopen_url and filepath failed :-(
// rely on a matching explicit width/height set via filter
$imagesize = bioship_apply_filters('muscle_open_graph_default_image_size', array());
if (isset($imagesize[0]) && isset($imagesize[1])) {
$metas['og:image'] = $url;
$metas['og:image:width'] = $imagesize[0];
$metas['og:image:height'] = $imagesize[1];
}
}
}
}
// 1.9.6: fix some mismatching WP to FB locales
// ...there may be a number more of these?
// http://www.roseindia.net/tutorials/i18n/locales-list.shtml
// https://www.facebook.com/translations/FacebookLocales.xml
if ($metas['og:locale'] == 'en_AU') {$metas['og:locale'] = 'en_GB';}
if ($metas['og:locale'] == 'ja') {$metas['og:locale'] = 'ja_JP';}
if ($metas['og:locale'] == 'iw_IL') {$metas['og:locale'] = 'he_IL';}
bioship_debug("Open Graph Meta", $metas);
return $metas;
}
}
// --------------------------------------------------
// Add Custom Field Override for the Open Graph image
// --------------------------------------------------
// 1.5.0: added this opengraph override
// requires the Open Graph Protocol plugin to be installed and active
// by default the plugin only sets the featured image if there is one
// this lets you add custom image fields on a post/page screen and have them used:
// opengraphimageurl (required), opengraphimagewidth, opengraphimageheight
if (!function_exists('bioship_muscle_open_graph_override_image_fields')) {
// 2.0.5: moved inside for consistency
add_filter('muscle_open_graph_override_image', 'bioship_muscle_open_graph_override_image_fields', 0);
function bioship_muscle_open_graph_override_image_fields($image) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 2.1.2: added check for singular but not-404 page
if (is_singular() && !is_404()) {
// --- override existing open graph image meta with post custom field meta ---
// (better to set width and height field values but not totally necessary)
global $post; $postid = $post->ID;
$ogimage[0] = get_post_meta($postid, 'opengraphimagewidth', true);
$ogimage[1] = get_post_meta($postid, 'opengraphimageheight', true);
$ogimage[2] = get_post_meta($postid, 'opengraphimageurl', true);
// --- allow image removal for this page ---
// (by setting opengraphimageurl value to 'off'
if ($ogimage[2] == 'off') {return array();}
// --- require the URL to be there ---
if ($ogimage[2] != '') {return $ogimage;}
}
// else {
// TODO: handle archive page overrides via archive CPT ?
// }
return $image;
}
}
// ===========
// Hybrid Hook
// ===========
// (does not require Hybrid Core to be loaded)
// (note: Hybrid Hook Widgets is available also)
// 2.0.1: filter Hybrid Hook loading here
if (isset($vthemesettings['hybridhook'])) {$loadhybridhook = $vthemesettings['hybridhook'];} else {$loadhybridhook = false;}
$loadhybridhook = bioship_apply_filters('muscle_load_hybrid_hook', $loadhybridhook);
if ($loadhybridhook == '1') {
// --- check Hybrid Hook directory ---
// 1.8.0: changed hybrid hook location to /includes/ subfolder
// 2.1.1: check alternative includes directories
$hybridhookdirs = array();
if (count($vthemedirs['includes']) > 0) {
foreach ($vthemedirs['includes'] as $dir) {
if (is_dir($dir.DIRSEP.'hybrid-hook')) {$hybridhookdirs[] = $dir.DIRSEP.'hybrid-hook';}
}
}
// --- load Hybrid Hook ---
$hybridhook = bioship_file_hierarchy('file', 'hybrid-hook.php', $hybridhookdirs);
if ($hybridhook) {
include($hybridhook);
if (THEMEDEBUG) {bioship_debug("Hybrid Hook Loaded");}
// --- load setup now ---
// (as we have missed the plugins_loaded hook)
hybrid_hook_setup();
// --- disallow PHP execution ---
// 1.8.5: added this filter (as e-v-a-l commented out for Theme Check)
// (HTML / Shortcode / Widget methods are better anyway)
add_filter('hybrid_hook_allow_php', 'bioship_muscle_disallow_hook_php', 5);
if (!function_exists('bioship_muscle_disallow_hook_php')) {
function bioship_muscle_disallow_hook_php($v) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
return false;
}
}
// --- load theme layout hooks ---
add_filter('hybrid_hooks', 'bioship_muscle_hybrid_get_hooks');
if (!function_exists('bioship_muscle_hybrid_get_hooks')) {
function bioship_muscle_hybrid_get_hooks() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
// 1.9.0: hooks now loaded by default in functions.php
global $vthemehooks;
if (THEMEDEBUG) {bioship_debug("Hybrid Hooks", $vthemehooks['hybrid']);}
// 1.9.0: handle admin metabox defaults
if (is_admin()) {
// 1.8.5: default the hybrid hook metaboxes to closed
// ref: https://surniaulula.com/2013/05/29/collapse-close-wordpress-metaboxes/
$userid = get_current_user_id();
$optionkey = 'closedpostboxes_'.'appearance_page_'.'hybrid-hook-settings';
if (isset($_REQUEST['metaboxes']) && ($_REQUEST['metaboxes'] == 'reset')) {
delete_user_option($optionkey, $userid);
} else {$closedboxes = get_user_option($optionkey, $userid);}
// create an empty array if get_user_option() had nothing to return
if (!is_array($closedboxes)) {
$closedboxes = array();
// 2.1.1: fix to use vthemehooks subkey
foreach ($vthemehooks['hybrid'] as $hook) {$closedboxes[] = 'hybrid-hook-'.$hook;}
update_user_option($userid, $optionkey, $closedboxes, true);
}
if (THEMEDEBUG) {bioship_debug("Closed Boxes", $closedboxes);}
}
return $vthemehooks['hybrid'];
}
}
// --- filter Hybrid Hook theme prefix ---
// hook into the theme filter (for modified Hybrid Hook plugin)
add_filter('hybrid_hook_theme_prefix', 'bioship_muscle_hybrid_hook_prefix');
if (!function_exists('bioship_muscle_hybrid_hook_prefix')) {
function bioship_muscle_hybrid_hook_prefix() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
// 2.0.5: change to bioship prefix to match new action names
return 'bioship';
}
}
}
}
// ==========
// Foundation
// ==========
// ref: http://foundation.zurb.com/docs
if (!function_exists('bioship_muscle_load_foundation')) {
add_action('wp_enqueue_scripts', 'bioship_muscle_load_foundation');
function bioship_muscle_load_foundation() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings, $vthemevars, $vcsscachebust, $vjscachebust;
// --- check load ---
// 2.0.9: filter Foundation loading internally
if (isset($vthemesettings['loadfoundation'])) {$load = $vthemesettings['loadfoundation'];} else {$load = false;}
$load = bioship_apply_filters('muscle_load_foundation', $load);
if (!$load || ($load == 'off')) {return;}
// --- check Foundation version ---
// 1.8.0: check Foundation 5 or 6 directory to use for loading
// TODO: check for alternative includes directory
if (isset($vthemesettings['foundationversion'])) {$foundation = 'includes/'.$vthemesettings['foundationversion'];}
else {$foundation = 'includes/foundation5';} // backwards compatibility default
// --- force auto-load of modernizr and fastclick for Foundation 5 ---
if (strstr($foundation, '5')) {
if (!has_action('wp_enqueue_scripts', 'bioship_muscle_load_modernizr')) {add_action('wp_enqueue_scripts', 'bioship_muscle_load_modernizr');}
if (!has_action('wp_enqueue_scripts', 'bioship_muscle_load_fastclick')) {add_action('wp_enqueue_scripts', 'bioship_muscle_load_fastclick');}
$deps = array('jquery', 'fastclick', 'modernizr');
} else {$deps = array('jquery');}
// Foundation Stylesheet
// ---------------------
// http://foundation.zurb.com/docs/css.html
if ($vthemesettings['foundationcss']) {
if ($vthemesettings['loadfoundation'] == 'essentials') {
$stylesheet = bioship_file_hierarchy('both', 'foundation.essentials.min.css', array($foundation.'/css','css'));
} else {
$stylesheet = bioship_file_hierarchy('both', 'foundation.min.css', array($foundation.'/css','css'));
}
if (is_array($stylesheet)) {
if ($vthemesettings['stylesheetcachebusting'] == 'filemtime') {
$cachebust = date('ymdHi', filemtime($stylesheet['file']));
} else {$cachebust = $vcsscachebust;}
wp_register_style('foundation', $stylesheet['url'], array(), $cachebust);
wp_enqueue_style('foundation');
}
}
// Full or Partial Foundation Javascript
// -------------------------------------
// http://foundation.zurb.com/docs/javascript.html
// --- get Foundation script ---
// TODO: add check for alternative script directories
if ($vthemesettings['loadfoundation'] == 'full') {
$script = bioship_file_hierarchy('both', 'foundation.min.js', array($foundation.'/js', 'javascripts'));
}
if ($vthemesettings['loadfoundation'] == 'essentials') {
$script = bioship_file_hierarchy('both', 'foundation.essentials.js', array($foundation.'/js', 'javascripts'));
} elseif ($vthemesettings['loadfoundation'] == 'selective') {
$script = bioship_file_hierarchy('both', 'foundation.selected.js', array('javascripts', $foundation.'/js'));
// 1.8.0: note, selective javascript is currently only working for Foundation 5, so just in case, fallback to min.js
if (!is_array($script)) {$script = bioship_file_hierarchy('both', 'foundation.min.js', array('javascripts', $foundation.'/js'));}
}
// --- enqueue Foundation script ---
if (is_array($script)) {
// 2.1.1: fix to cachebusting conditions
if ($vthemesettings['javascriptcachebusting'] == 'filemtime') {
$vjscachebust = date('ymdHi', filemtime($script['file']));
} else {$cachebust = $vjscachebust;}
wp_enqueue_script('foundation', $script['url'], $deps, $cachebust, true);
// --- initialize via script variable ---
// 2.0.9: use script load variable instead of input
// 2.1.3: add to prefixed global settings variable
$vthemevars[] = "var bioship.loadfoundation = 'yes'; ";}
}
}
}
// ==============
// Theme My Login
// ==============
// 2.0.1: filter Theme My Login template loading
// 2.0.9: check loading filter internally
if (!function_exists('muscle_load_theme_my_login_filters')) {
add_action('plugins_loaded', 'muscle_load_theme_my_login_filters');
function muscle_load_theme_my_login_filters() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
// --- check load ---
if (isset($vthemesettings['tmltemplates'])) {$load = $vthemesettings['tmltemplates'];} else {$load = false;}
$load = bioship_apply_filters('muscle_load_tml_templates', $load);
if (!$load || ($load != '1')) {return;}
// --- add Theme My Login filters ---
// 2.0.9: add Theme My Login filters here
add_filter('tml_template_paths', 'bioship_muscle_tml_template_paths');
add_filter('login_button_url', 'bioship_muscle_login_button_url');
add_filter('register_button_url', 'bioship_muscle_register_button_url');
add_filter('profile_button_url', 'bioship_muscle_profile_button_url');
add_filter('register_form_image', 'bioship_muscle_register_form_image');
add_filter('login_form_image', 'bioship_muscle_login_form_image');
}
}
// -------------------------------
// TML Improved Template Hierarchy
// -------------------------------
if (!function_exists('muscle_tml_template_paths')) {
function bioship_muscle_tml_template_paths($paths) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
// 1.8.5: use existing globals
global $vthemestyledir, $vthemetemplatedir;
$templatepaths = array(
$vthemestyledir.'templates/theme-my-login',
$vthemestyledir.'theme-my-login',
$vthemestyledir,
$vthemetemplatedir.'templates/theme-my-login',
$vthemetemplatedir.'theme-my-login',
$vthemetemplatedir,
WP_PLUGIN_DIR.'/theme-my-login/templates'
);
bioship_debug("New ThemeMyLogin Paths", $newpaths);
return $templatepaths;
}
}
// ---------------------------
// TML Login Button URL Filter
// ---------------------------
if (!function_exists('bioship_muscle_login_button_url')) {
function bioship_muscle_login_button_url($buttonurl) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
if ($vthemesettings['loginbuttonurl'] != '') {$buttonurl = $vthemesettings['loginbuttonurl'];}
return $buttonurl;
}
}
// ------------------------------
// TML Register Button URL Filter
// ------------------------------
if (!function_exists('bioship_muscle_register_button_url')) {
function bioship_muscle_register_button_url($buttonurl) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
if ($vthemesettings['registerbuttonurl'] != '') {$buttonurl = $vthemesettings['registerbuttonurl'];}
return $buttonurl;
}
}
// -----------------------------
// TML Profile Button URL Filter
// -----------------------------
if (!function_exists('bioship_muscle_profile_button_url')) {
function bioship_muscle_profile_button_url($buttonurl) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__,func_get_args());}
global $vthemesettings;
if ($vthemesettings['profilebuttonurl'] != '') {$buttonurl = $vthemesettings['profilebuttonurl'];}
return $buttonurl;
}
}
// ----------------------------
// TML Register Form Logo Image
// ----------------------------
if (!function_exists('bioship_muscle_register_form_image')) {
function bioship_muscle_register_form_image($image) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
if ($vthemesettings['registerformimage'] == '1') {
if ($vthemesettings['loginlogo'] == 'custom') {$image = $vthemesettings['header_logo'];}
if ($vthemesettings['loginlogo'] == 'upload') {$image = $vthemesettings['loginlogourl'];}
}
return $image;
}
}
// -------------------------
// TML Login Form Logo Image
// -------------------------
// 2.1.1: added missing image argument definition
if (!function_exists('bioship_muscle_login_form_image')) {
function bioship_muscle_login_form_image($image) {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
global $vthemesettings;
if ($vthemesettings['loginformimage'] == '1') {
if ($vthemesettings['loginlogo'] == 'custom') {$image = $vthemesettings['header_logo'];}
if ($vthemesettings['loginlogo'] == 'upload') {$image = $vthemesettings['loginlogourl'];}
}
return $image;
}
}
// ===============
// Theme Switching
// ===============
// TODO: retest this Theme Switching functionality
// for Theme Test Drive and JonRadio Multiple Themes...
// ref: http://wordpress.stackexchange.com/q/227532/76440
// *** IMPORTANT USAGE NOTE *** only works *HERE* for BioShip Parent and Child Theme switching
// if you want the same theme switching functionality to work with other themes as well,
// you will need to simply put a copy of this function in /wp-content/mu-plugins/ folder.
// and that is because THIS file is loaded BY this theme, so therefore the fix will not be
// loaded for other themes - unless it is loaded at an earlier time, ie. mu-plugins or plugins
// note: currently for JonRadio Multiple Themes, select-theme.php is NOT loaded for admin
// (this means the advanced setting 'AJAX All' currently has no effect anyway...)
// loading select-theme.php will automatically set the active theme via cookie storage,
// BUT this will not work for using admin-ajax.php or admin-post.php when visiting multiple
// pages on the same site at once where a different theme may be active for different pages!
// note: if loading via mu-plugins or a plugin, this action hook must change to 'plugins_loaded'
// 2.0.5: disable all this by default until retesting
if (!function_exists('bioship_muscle_theme_switch_admin_fix')) {
// 2.1.1: move add_action internally for consistency
add_action('init', 'bioship_muscle_theme_switch_admin_fix');
function bioship_muscle_theme_switch_admin_fix() {
if (THEMETRACE) {bioship_trace('F',__FUNCTION__,__FILE__);}
// --- check for a valid active plugin ---
$activeplugins = maybe_unserialize(get_option('active_plugins'));
if (!is_array($activeplugins)) {return;}
$multiplethemes = $themetestdrive = false;
if (in_array('jonradio-multiple-themes/jonradio-multiple-themes.php', $activeplugins)) {
// 2.1.1: add extra check to ensure plugin is actually loaded
if (function_exists('jr_mt_template')) {$multiplethemes = true;}
}
if (in_array('theme-test-drive/themedrive.php', $activeplugins)) {
// 2.1.1: add extra check to ensure plugin is actually loaded
if (function_exists('themedrive_get_template')) {$themetestdrive = true;}
}
if (!$multiplethemes && !$themetestdrive) {return;} // bug out
// --- multiple themes option: 'site', 'sticky' or 'both' ---
if (defined('MT_METHOD')) {$method = MT_METHOD;} else {$method = 'site';}
$parameter = 'theme'; // multiple theme switch querystring parameter name
// --- user data save settings ---
$datamethod = 'both'; // how to save user data: 'cookie', 'usermeta' or 'both'
$datakey = 'theme_switch_data'; // cookie and user meta key name
$expires = 24*60*60; // length of time for cookies and transients
// --- maybe include pluggable.php for accessing user ---
// 2.1.1: fix to incorrect variable name (userdata)
if ( ($datamethod != 'cookie') && !function_exists('is_user_logged_in')) {
require(ABSPATH.WPINC.'/pluggable.php');
}
// --- maybe reset cookie and URL data by user request ---
if (isset($_GET['resetthemes']) && ($_GET['resetthemes'] == '1')) {
if ($debug) {echo "";}
if ($themetestdrive) {setCookie($themecookie, '', -300);}
delete_option('theme_switch_request_urls'); return;
}
// --- maybe set debug switch ---
$debug = false;
if (isset($_GET['debug']) && ($_GET['debug'] == '1')) {$debug = true;}
elseif (defined('THEMEDEBUG')) {$debug = THEMEDEBUG;}
// --- improve theme test drive to use options filters like multiple themes ---
// (theme test drive by default only filters via get_stylesheet and get_template)
if ($themetestdrive) {
$parameter = 'theme';
remove_filter('template', 'themedrive_get_template'); remove_filter('stylesheet', 'themedrive_get_stylesheet');
add_filter('pre_option_stylesheet', 'themedrive_get_stylesheet'); add_filter('pre_option_template', 'themedrive_get_template');
}
// --- maybe load stored alternative theme for AJAX/admin calls ---
if (is_admin()) {
// --- let WordPress handle customize previews ---
if (is_customize_preview()) {return;}
// --- get pagenow to check for admin-post.php as well ---
global $pagenow;
if ( (defined('DOING_AJAX') && DOING_AJAX) || ($pagenow == 'admin-post.php') ) {
// set the referer path for URL matching
$referer = parse_url($_SERVER['HTTP_REFERER'], PHP_URL_PATH);
// 2.1.4: fix for undefined variable warning
$matchedurlpath = false;
// set some globals for the AJAX theme options
global $ajax_stylesheet, $ajax_template;
// --- check for temporary Theme Test Drive cookie data ---
if ($themetestdrive || ($multiplethemes && ($method != 'site'))) {
if ($datamethod != 'usermeta') {
if (isset($_COOKIE[$datakey]) && ($_COOKIE[$datakey] != '')) {
$cookiedata = explode(',', $_COOKIE[$datakey]);
// attempt to match referer data with stored transient request
foreach ($cookiedata as $transientkey) {
$transientdata = get_transient($transientkey);
if ($transientdata) {
$data = explode(':', $transientdata);
if ($data[0] == $referer) {
$ajax_stylesheet = $data[1]; $ajax_template = $data[2];
$transientdebug = $transientdata; $matchedurlpath = true;
}
}
}
}
if (($datamethod != 'cookie') && is_user_logged_in()) {
// 2.0.1: allow for fallback for older installs
$current_user = bioship_get_current_user();
$usermetadata = get_user_meta($current_user->ID, $datakey, true);
if (is_array($usermetadata)) {
// --- attempt to match referer data with stored transient request ---
foreach ($usermetadata as $transientkey) {
$transientdata = get_transient($transientkey);
if ($transientdata) {
$data = explode(':', $transientdata);
if ($data[0] == $referer) {
$ajax_stylesheet = $data[1]; $ajax_template = $data[2];
$transientdebug = $transientdata; $matchedurlpath = true;
}
}
}
}
}
}
}
elseif ($multiplethemes && ($method != 'sticky')) {
// --- check the request URL list to handle sitewide cases ---
if (!$matchedurlpath) { // but not if we already have a match
$requesturls = get_option('theme_switch_request_urls');
if (is_array($requesturls)) {
if (is_array($requesturls) && array_key_exists($referer, $requesturls)) {
$matchedurlpath = true;
$ajax_stylesheet = $requesturls[$referer]['stylesheet'];
$ajax_template = $requesturls[$referer]['template'];
}
}
}
}
if ($matchedurlpath) {
// add theme option filters for admin-ajax (and admin-post)
// so any admin actions defined by the theme are finally loaded!
add_filter('pre_option_stylesheet', 'bioship_muscle_admin_ajax_stylesheet');
add_filter('pre_option_template', 'bioship_muscle_admin_ajax_template');
// 2.1.1: added function_exists wrappers for consistency
if (!function_exists('bioship_muscle_admin_ajax_stylesheet')) {
function bioship_muscle_admin_ajax_stylesheet() {global $ajax_stylesheet; return $ajax_stylesheet;}
}
if (!function_exists('bioship_muscle_admin_ajax_template')) {
function bioship_muscle_admin_ajax_template() {global $ajax_template; return $ajax_template;}
}
}
// --- maybe output debug info for AJAX/admin test frame ---
if ($debug) {
echo "";
echo "";
echo "";
echo "";
if ($matchedurlpath) {echo "";} else {echo "";}
echo "";
echo "";
}
return; // done for admin requests so bug out here
}
}
// --- store public request URLs where an alternate theme is active ---
// (note: multiple themes does not load in admin, but theme test drive does)
if ($themetestdrive || (!is_admin() && $multiplethemes)) {
// --- get current theme (possibly overriden) setting ---
$themestylesheet = get_option('stylesheet'); $themetemplate = get_option('template');
// --- remove filters, get default theme setting, re-add filters ---
if ($multiplethemes) {
remove_filter('pre_option_stylesheet', 'jr_mt_stylesheet'); remove_filter('pre_option_template', 'jr_mt_template');
$stylesheet = get_option('stylesheet'); $template = get_option('template');
add_filter('pre_option_stylesheet', 'jr_mt_stylesheet'); add_filter('pre_option_template', 'jr_mt_template');
}
if ($themetestdrive) {
// note: default theme test drive filters are changed earlier on
remove_filter('pre_option_stylesheet', 'themedrive_get_stylesheet'); remove_filter('pre_option_template', 'themedrive_get_template');
$stylesheet = get_stylesheet(); $template = get_template();
add_filter('pre_option_stylesheet', 'themedrive_get_stylesheet'); add_filter('pre_option_template', 'themedrive_get_template');
}
// --- set/get request URL values (URL path only) ---
$requesturl = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
$requesturls = get_option('theme_switch_request_urls');
// --- store the request data ---
if ($themetestdrive || ($multiplethemes && ($method != 'site'))) {
if (isset($_REQUEST[$parameter]) && ($_REQUEST[$parameter] != '') ) {
if ($datamethod != 'usermeta') {
// --- check existing cookie data ---
$cookiedata = array();
if ( (isset($_COOKIE[$datakey])) && ($_COOKIE[$datakey] != '') ) {
$existingmatch = false;
$i = 0; $cookiedata = explode(',',$_COOKIE[$datakey]);
foreach ($cookiedata as $transientkey) {
$transientdata = get_transient($transientkey);
if ($transientdata) {
$data = explode(':',$transientdata);
if ($data[0] == $requesturl) {
// update existing transient data
$transientdata = $transientdebug = $requesturl.':'.$themestylesheet.':'.$themetemplate;
set_transient($transientkey, $transientdata, $expires);
$existingmatch = true;
}
} else {unset($cookiedata[$i]);} // remove expired
$i++;
}
}
}
if (($datamethod != 'cookie') && is_user_logged_in()) {
// --- check existing usermeta data ---
// 2.0.1: allow for fallback for older installs
// 2.0.7: use new prefixed current user function
$current_user = bioship_get_current_user();
$usermetadata = get_user_meta($current_user->ID, $datakey, true);
if (is_array($usermetadata)) {
$existingmatch = false;
$i = 0;
// --- remove expired transient IDs from usermeta ---
foreach ($usermetadata as $transientkey) {
$transientdata = get_transient($transientkey);
if ($transientdata) {
$data = explode(':',$transientdata);
if ($data[0] == $requesturl) {
// update existing transient data
$transientdata = $transientdebug = $requesturl.':'.$themestylesheet.':'.$themetemplate;
set_transient($transientkey, $transientdata, $expires);
$existingmatch = true;
}
} else {unset($usermetadata[$i]);} // remove expired
$i++;
}
} else {$usermetadata = array();}
}
// --- set the transient with matching cookie/usermeta data ---
if (!$existingmatch) { // avoid duplicates
// --- set the new transient ---
$transientkey = $datakey.'_'.uniqid();
$transientdata = $transientdebug = $requesturl.':'.$themestylesheet.':'.$themetemplate;
set_transient($transientkey, $transientdata, $expires);
// --- add transient to cookie for matching later ---
if ($datamethod != 'usermeta') {
$cookiedata[] = $transientkey; $cookiedatastring = implode(',', $cookiedata);
setCookie($themecookie, $cookiedatastring, time()+$expires);
}
// --- add transient to usermeta for matching later ---
if ($datamethod != 'cookie') {
$usermetadata[] = $transientkey; update_user_meta($current_user->ID, $datakey, $usermetadata);
}
}
// --- maybe output debug info ---
if ($debug) {
echo "";
if ($datamethod != 'cookie') {echo "";}
echo "";
}
}
} elseif ($multiplethemes && ($method != 'sticky')) {
// --- save/remove the requested URL path in the list ---
if ( ($stylesheet == $themestylesheet) && ($template == $themetemplate) ) {
// maybe remove this request from the stored URL list
if (is_array($requesturls) && array_key_exists($requesturl, $requesturls)) {
unset($requesturls[$requesturl]);
if (count($requesturls) === 0) {delete_option('theme_switch_request_urls');}
else {update_option('theme_switch_request_urls', $requesturls);}
}
} else {
// --- add this request URL to the stored list ---
$requesturls[$requesturl]['stylesheet'] = $themestylesheet;
$requesturls[$requesturl]['template'] = $themetemplate;
update_option('theme_switch_request_urls', $requesturls);
}
// --- maybe output debug info ---
if (!is_admin() && $debug) {
echo "";
echo "";
}
}
// --- maybe output hidden ajax debugging frames ---
if (!is_admin() && $debug) {
echo "";
echo "";
}
}
}
}