/home/arranoyd/www/wp-content/plugins/unyson/framework/extensions/seo/class-fw-extension-seo.php
<?php if ( ! defined( 'FW' ) ) {
die( 'Forbidden' );
}
class FW_Extension_SEO extends FW_Extension {
/**
* Holds the SEO tags that can be used by sub-extensions
* This member cannot be accessed directly, only by "get_seo_tags" method
* @var array
*/
private $seo_tags = array();
/**
* Holds the current location in front-end
* This member cannot be accessed directly, only by "get_location" method
* @var array
*/
private $current_location = array();
/**
* @internal
*/
public function _init() {
add_action('fw_option_types_init', array($this, '_action_option_types_init'));
if ( is_admin() ) {
$this->add_admin_actions();
$this->add_admin_filters();
} else {
$this->add_theme_actions();
}
}
public function _action_option_types_init() {
require_once dirname( __FILE__ ) . '/includes/option-types/seo-tags/class-fw-option-type-seo-tags.php';
}
public function _admin_action_add_static() {
$screen = array(
'only' => array(
array(
'base' => 'post'
)
)
);
if ( fw_current_screen_match($screen) ) {
wp_enqueue_style( $this->get_name() . '-style', $this->get_declared_URI('/static/css/style.css') );
}
}
private function add_admin_actions() {
add_action( 'admin_enqueue_scripts', array( $this, '_admin_action_add_static' ) );
}
/**
* Init the admin area filters
*/
private function add_admin_filters() {
add_filter( 'fw_post_options', array( $this, '_admin_filter_set_custom_posts_seo_options' ), 10, 2 );
add_filter( 'fw_taxonomy_options', array( $this, '_admin_filter_set_taxonomy_seo_options' ), 10, 2 );
}
/**
* Init the frontend area actions
*/
private function add_theme_actions() {
add_action( 'wp', array( $this, '_action_set_location' ) );
add_action( 'fw_ext_seo_init_location', array( $this, '_theme_action_update_seo_tags' ) );
}
/**
* @param $tag , SEO tag name
*
* @return string
*/
private function parse_seo_tag_helper( $tag ) {
$tag_str = trim( str_replace( '%%', '', $tag[0] ) );
$seo_tag = $this->get_seo_tags( $tag_str );
return isset( $seo_tag['value'] ) ? $seo_tag['value'] : '';
}
/**
* Init seo tags
* There will be defined only the name and description of the tags, and the value of few simple tags.
* The value of the tags is updated by "_action_init_update_tags" method on "wp" action
*/
public function init_seo_tags() {
if ( ! empty( $this->seo_tags ) ) {
return;
}
$this->seo_tags['sitename'] = array(
'name' => '%%sitename%%',
'desc' => __( 'Site name', 'fw' ),
'value' => get_bloginfo( 'name' ),
);
$this->seo_tags['sitedesc'] = array(
'name' => '%%sitedesc%%',
'desc' => __( 'Site description', 'fw' ),
'value' => get_bloginfo( 'description' ),
);
$this->seo_tags['currenttime'] = array(
'name' => '%%currenttime%%',
'desc' => __( 'Current time', 'fw' ),
'value' => date( 'H:i' ),
);
$this->seo_tags['currentdate'] = array(
'name' => '%%currentdate%%',
'desc' => __( 'Current date', 'fw' ),
'value' => date( 'M jS Y' ),
);
$this->seo_tags['currentmonth'] = array(
'name' => '%%currentmonth%%',
'desc' => __( 'Current month', 'fw' ),
'value' => date( 'F Y' ),
);
$this->seo_tags['currentyear'] = array(
'name' => '%%currentyear%%',
'desc' => __( 'Current year', 'fw' ),
'value' => date( 'Y' ),
);
$this->seo_tags['date'] = array(
'name' => '%%date%%',
'desc' => __( 'Date of the post/page', 'fw' ),
'value' => '',
);
$this->seo_tags['title'] = array(
'name' => '%%title%%',
'desc' => __( 'Title of the post/page/term', 'fw' ),
'value' => '',
);
$this->seo_tags['excerpt'] = array(
'name' => '%%excerpt%%',
'desc' => __( 'Excerpt of the current post, of auto-generate if it is not set', 'fw' ),
'value' => '',
);
$this->seo_tags['excerpt_only'] = array(
'name' => '%%excerpt_only%%',
'desc' => __( 'Excerpt of the current post, without auto-generation', 'fw' ),
'value' => '',
);
$this->seo_tags['post_tags'] = array(
'name' => '%%post_tags%%',
'desc' => __( 'Post tags, separated by coma', 'fw' ),
'value' => '',
);
$this->seo_tags['post_categories'] = array(
'name' => '%%post_categories%%',
'desc' => __( 'Post categories, separated by coma', 'fw' ),
'value' => '',
);
$this->seo_tags['description'] = array(
'name' => '%%description%%',
'desc' => __( 'Category/tag/term description', 'fw' ),
'value' => '',
);
$this->seo_tags['term_title'] = array(
'name' => '%%term_title%%',
'desc' => __( 'Term title', 'fw' ),
'value' => '',
);
$this->seo_tags['modified'] = array(
'name' => '%%modified%%',
'desc' => __( 'Post modified time', 'fw' ),
'value' => '',
);
$this->seo_tags['id'] = array(
'name' => '%%id%%',
'desc' => __( 'Post/page id', 'fw' ),
'value' => '',
);
$this->seo_tags['author_name'] = array(
'name' => '%%author_name%%',
'desc' => __( 'Post/page author "nicename"', 'fw' ),
'value' => '',
);
$this->seo_tags['author_id'] = array(
'name' => '%%author_id%%',
'desc' => __( 'Post/page author id', 'fw' ),
'value' => '',
);
$this->seo_tags['searchphrase'] = array(
'name' => '%%searchphrase%%',
'desc' => __( 'Search phrase in search page', 'fw' ),
'value' => '',
);
$this->seo_tags['pagenumber'] = array(
'name' => '%%pagenumber%%',
'desc' => __( 'Page number', 'fw' ),
'value' => '',
);
$this->seo_tags['max_page'] = array(
'name' => '%%max_page%%',
'desc' => __( 'Page number', 'fw' ),
'value' => '',
);
$this->seo_tags['caption'] = array(
'name' => '%%caption%%',
'desc' => __( 'Attachment caption', 'fw' ),
'value' => '',
);
foreach ( apply_filters( 'fw_ext_seo_init_tags', array() ) as $tag_id => $tag ) {
if ( isset( $this->seo_tags[ $tag_id ] ) ) {
continue;
}
$this->seo_tags[ $tag_id ] = $tag;
}
}
/**
* Return the current page type in front-end
* @return array
*/
public function get_location() {
return $this->current_location;
}
/**
* Parses string values and replaces the seo tags with their values
* This method should be called after wordpress "wp" action
*
* @param $value , option value that should be parsed
*
* @return string
*/
public function parse_seo_tags( $value ) {
$value = strip_tags( $value );
return preg_replace_callback( '/%%[a-z|0-9|_|-]*%%/', array( $this, 'parse_seo_tag_helper' ), $value );
}
/**
* Determine the current frontend page location
* @internal
*/
public function _action_set_location() {
global $wp_query;
$return = array();
if ( is_404() ) {
$return['type'] = '404';
} elseif ( is_search() ) {
$return['type'] = 'search';
} elseif ( is_front_page() ) {
$return['type'] = 'front_page';
if ( ! is_home() ) {
$return['id'] = get_option( 'page_on_front' );
}
} elseif ( is_home() ) {
$return['type'] = 'blog_page';
$return['id'] = get_option( 'page_for_posts' );
} elseif ( is_singular() ) {
global $post;
$return['type'] = 'singular';
$return['id'] = $post->ID;
$return['post_type'] = $post->post_type;
} elseif ( is_category() ) {
$return['type'] = 'category';
$return['taxonomy_type'] = get_query_var( 'category_name' );
$return['id'] = get_query_var( 'cat' );
} elseif ( is_tag() ) {
$return['type'] = 'tag';
$return['taxonomy_type'] = get_query_var( 'taxonomy' );
$return['id'] = get_query_var( 'tag_id' );
} elseif ( is_tax() ) {
$return['type'] = 'taxonomy';
$return['taxonomy_type'] = get_query_var( 'taxonomy' );
$return['id'] = get_queried_object()->term_id;
} elseif ( is_author() ) {
$return['type'] = 'author_archive';
} elseif ( is_date() ) {
$return['type'] = 'date_archive';
} elseif ( is_archive() ) {
$return['type'] = 'archive';
} elseif ( is_feed() ) {
$return['type'] = 'feed';
} else {
$return[''] = null;
}
/*
* Check if the location has pagination and add the page
*/
$paged = get_query_var( 'paged' );
$return['paged'] = ( $paged == 0 ) ? 1 : $paged;
$return['max_pages'] = $wp_query->max_num_pages;
$return = apply_filters( 'fw_ext_seo_get_location', $return );
$this->current_location = $return;
do_action( 'fw_ext_seo_init_location', $this->current_location );
}
/**
* Returns the SEO tags: %%title%%, %%excerpt%%, ...
* This function should be used after wordpress "wp" action
* If the method is called without parameters it returns the array of all tags and their values
* If the method is called with parameter, it returns the tag
* If the method is called with parameter and it is wrong, it returns an empty string
*
* @param $tag , name of the specific tag
*
* @return array
*/
public function get_seo_tags( $tag = null ) {
$this->init_seo_tags();
if ( is_null( $tag ) ) {
return $this->seo_tags;
}
if ( isset( $this->seo_tags[ $tag ] ) ) {
return $this->seo_tags[ $tag ];
}
return array();
}
/**
* @internal
*
* Update the SEO key tags values on wordpress "wp" action,
* such as %%title%%, %%excerpt%%, values can only be initialised after "wp" action
*
* @param array $location
*/
public function _theme_action_update_seo_tags( $location ) {
if ( empty( $this->seo_tags ) ) {
$this->get_seo_tags();
}
if (empty($location['type'])) {
return $location;
}
switch ( $location['type'] ) {
case 'search' :
$this->seo_tags['searchphrase']['value'] = get_search_query();
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'author_archive' :
$this->seo_tags['author_id']['value'] = get_query_var( 'author' );
$this->seo_tags['author_name']['value'] = get_the_author_meta( 'nickname', get_query_var( 'author' ) );
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'date_archive' :
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
// get date for current archive
if ( is_year() ) {
$date = get_the_date( 'Y', get_the_ID() );
} elseif ( is_month() ) {
$date = get_the_date( 'F Y', get_the_ID() );
} elseif ( is_day() ) {
$date = get_the_date( 'F j, Y', get_the_ID() );
} else {
$date = '';
}
$this->seo_tags['date']['value'] = $date;
break;
case 'front_page' :
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'blog_page' :
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'singular' :
global $post;
$this->seo_tags['date']['value'] = get_the_date();
$this->seo_tags['title']['value'] = get_the_title();
$this->seo_tags['excerpt']['value'] = ! empty( $post->post_excerpt ) ? get_the_excerpt() : wp_trim_excerpt( $post->post_content );
$this->seo_tags['excerpt_only']['value'] = ! empty( $post->post_excerpt ) ? get_the_excerpt() : '';
$this->seo_tags['modified']['value'] = $post->post_modified;
$this->seo_tags['id']['value'] = $post->ID;
$this->seo_tags['author_id']['value'] = $post->post_author;
$this->seo_tags['author_name']['value'] = get_the_author_meta( 'nickname', $post->post_author );
if ( $location['post_type'] == 'attachment' ) {
$this->seo_tags['caption']['value'] = ( has_excerpt() ) ? get_the_excerpt() : '';
}
$categories = wp_get_post_categories( $post->ID );
foreach ( $categories as $cat_id ) {
$category = get_category( $cat_id );
$this->seo_tags['post_categories']['value'] .= $category->name . ', ';
}
$this->seo_tags['post_categories']['value'] = rtrim( $this->seo_tags['post_categories']['value'], ', ' );
$tags = wp_get_post_tags( $post->ID );
foreach ( $tags as $tag_id ) {
$tag = get_tag( $tag_id );
$this->seo_tags['post_tags']['value'] .= $tag->name . ', ';
}
$this->seo_tags['post_tags']['value'] = rtrim( $this->seo_tags['post_tags']['value'], ', ' );
break;
case 'tag' :
$this->seo_tags['title']['value'] = single_term_title( '', false );
$this->seo_tags['description']['value'] = strip_tags( term_description( $location['id'], $location['taxonomy_type'] ) );
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'category' :
$this->seo_tags['title']['value'] = single_term_title( '', false );
$this->seo_tags['description']['value'] = strip_tags( term_description( $location['id'], $location['taxonomy_type'] ) );
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
case 'taxonomy' :
$this->seo_tags['title']['value'] = single_term_title( '', false );
$this->seo_tags['description']['value'] = strip_tags( term_description( $location['id'], $location['taxonomy_type'] ) );
$this->seo_tags['pagenumber'] = $location['paged'];
$this->seo_tags['max_page'] = $location['max_pages'];
break;
}
$this->seo_tags = apply_filters( 'fw_ext_seo_update_tags', $this->seo_tags, $location );
}
/**
* Inserts the SEO metabox tab in custom posts editor, where sub-extensions will attach their options
*
* @param $post_options , array of the current custom post options
* @param $post_type , custom post type
*
* @return array
* @internal
*/
public function _admin_filter_set_custom_posts_seo_options( $post_options, $post_type ) {
$seo_options = array(
'title' => __( 'SEO', 'fw' ),
'type' => 'tab',
'options' => array()
);
foreach ( apply_filters( 'fw_ext_seo_post_type_options', array(), $post_type ) as $tab_id => $options ) {
if ( isset( $seo_options['options'][ $tab_id ] ) ) {
continue;
}
$seo_options['options'][ $tab_id ] = $options;
}
if ( ( count( $seo_options['options'] ) == 1 ) ) {
$first_value = reset( $seo_options['options'] );
if ( isset( $first_value['type'] ) && ( $first_value['type'] == 'tab' ) ) {
$seo_options['options'] = $first_value['options'];
}
}
if ( is_array( $seo_options['options'] ) && ! empty( $seo_options['options'] ) ) {
if ( isset( $post_options['main'] ) && $post_options['main']['type'] == 'box' ) {
$seo_options['type'] = 'tab';
$post_options['main']['options'][ $this->get_name() ] = $seo_options;
} else {
$seo_options['type'] = 'box';
$post_options[ $this->get_name() ] = $seo_options;
}
}
return $post_options;
}
/**
* Inserts the SEO options section in taxonomy editor, where sub-extensions will attach their options
*
* @param $tax_options , array of the current taxonomy options
* @param $taxonomy , taxonomy type
*
* @return array
* @internal
*/
public function _admin_filter_set_taxonomy_seo_options( $tax_options, $taxonomy ) {
$seo_options = array();
foreach ( apply_filters( 'fw_ext_seo_taxonomy_options', array(), $taxonomy ) as $group_id => $options ) {
if ( isset( $seo_options[ $group_id ] ) ) {
continue;
}
$seo_options[ $group_id ] = $options;
}
if ( is_array( $seo_options ) && ! empty( $seo_options ) ) {
return array_merge( $tax_options, $seo_options );
}
return $tax_options;
}
}