/includes/class-wc-breadcrumb.php

  1. <?php 
  2.  
  3. if ( ! defined( 'ABSPATH' ) ) { 
  4. exit; 
  5.  
  6. /** 
  7. * WC_Breadcrumb class. 
  8. * 
  9. * @class WC_Breadcrumb 
  10. * @version 2.3.0 
  11. * @package WooCommerce/Classes 
  12. * @category Class 
  13. * @author WooThemes 
  14. */ 
  15. class WC_Breadcrumb { 
  16.  
  17. /** 
  18. * Breadcrumb trail. 
  19. * 
  20. * @var array 
  21. */ 
  22. private $crumbs = array(); 
  23.  
  24. /** 
  25. * Add a crumb so we don't get lost. 
  26. * 
  27. * @param string $name 
  28. * @param string $link 
  29. */ 
  30. public function add_crumb( $name, $link = '' ) { 
  31. $this->crumbs[] = array( 
  32. strip_tags( $name ),  
  33. $link,  
  34. ); 
  35.  
  36. /** 
  37. * Reset crumbs. 
  38. */ 
  39. public function reset() { 
  40. $this->crumbs = array(); 
  41.  
  42. /** 
  43. * Get the breadcrumb. 
  44. * 
  45. * @return array 
  46. */ 
  47. public function get_breadcrumb() { 
  48. return apply_filters( 'woocommerce_get_breadcrumb', $this->crumbs, $this ); 
  49.  
  50. /** 
  51. * Generate breadcrumb trail. 
  52. * 
  53. * @return array of breadcrumbs 
  54. */ 
  55. public function generate() { 
  56. $conditionals = array( 
  57. 'is_home',  
  58. 'is_404',  
  59. 'is_attachment',  
  60. 'is_single',  
  61. 'is_product_category',  
  62. 'is_product_tag',  
  63. 'is_shop',  
  64. 'is_page',  
  65. 'is_post_type_archive',  
  66. 'is_category',  
  67. 'is_tag',  
  68. 'is_author',  
  69. 'is_date',  
  70. 'is_tax',  
  71. ); 
  72.  
  73. if ( ( ! is_front_page() && ! ( is_post_type_archive() && intval( get_option( 'page_on_front' ) ) === wc_get_page_id( 'shop' ) ) ) || is_paged() ) { 
  74. foreach ( $conditionals as $conditional ) { 
  75. if ( call_user_func( $conditional ) ) { 
  76. call_user_func( array( $this, 'add_crumbs_' . substr( $conditional, 3 ) ) ); 
  77. break; 
  78.  
  79. $this->search_trail(); 
  80. $this->paged_trail(); 
  81.  
  82. return $this->get_breadcrumb(); 
  83.  
  84. return array(); 
  85.  
  86. /** 
  87. * Prepend the shop page to shop breadcrumbs. 
  88. */ 
  89. private function prepend_shop_page() { 
  90. $permalinks = wc_get_permalink_structure(); 
  91. $shop_page_id = wc_get_page_id( 'shop' ); 
  92. $shop_page = get_post( $shop_page_id ); 
  93.  
  94. // If permalinks contain the shop page in the URI prepend the breadcrumb with shop 
  95. if ( $shop_page_id && $shop_page && isset( $permalinks['product_base'] ) && strstr( $permalinks['product_base'], '/' . $shop_page->post_name ) && get_option( 'page_on_front' ) != $shop_page_id ) { 
  96. $this->add_crumb( get_the_title( $shop_page ), get_permalink( $shop_page ) ); 
  97.  
  98. /** 
  99. * is home trail. 
  100. */ 
  101. private function add_crumbs_home() { 
  102. $this->add_crumb( single_post_title( '', false ) ); 
  103.  
  104. /** 
  105. * 404 trail. 
  106. */ 
  107. private function add_crumbs_404() { 
  108. $this->add_crumb( __( 'Error 404', 'woocommerce' ) ); 
  109.  
  110. /** 
  111. * attachment trail. 
  112. */ 
  113. private function add_crumbs_attachment() { 
  114. global $post; 
  115.  
  116. $this->add_crumbs_single( $post->post_parent, get_permalink( $post->post_parent ) ); 
  117. $this->add_crumb( get_the_title(), get_permalink() ); 
  118.  
  119. /** 
  120. * Single post trail. 
  121. * 
  122. * @param int $post_id 
  123. * @param string $permalink 
  124. */ 
  125. private function add_crumbs_single( $post_id = 0, $permalink = '' ) { 
  126. if ( ! $post_id ) { 
  127. global $post; 
  128. } else { 
  129. $post = get_post( $post_id ); 
  130.  
  131. if ( 'product' === get_post_type( $post ) ) { 
  132. $this->prepend_shop_page(); 
  133. if ( $terms = wc_get_product_terms( $post->ID, 'product_cat', array( 'orderby' => 'parent', 'order' => 'DESC' ) ) ) { 
  134. $main_term = apply_filters( 'woocommerce_breadcrumb_main_term', $terms[0], $terms ); 
  135. $this->term_ancestors( $main_term->term_id, 'product_cat' ); 
  136. $this->add_crumb( $main_term->name, get_term_link( $main_term ) ); 
  137. } elseif ( 'post' != get_post_type( $post ) ) { 
  138. $post_type = get_post_type_object( get_post_type( $post ) ); 
  139. $this->add_crumb( $post_type->labels->singular_name, get_post_type_archive_link( get_post_type( $post ) ) ); 
  140. } else { 
  141. $cat = current( get_the_category( $post ) ); 
  142. if ( $cat ) { 
  143. $this->term_ancestors( $cat->term_id, 'post_category' ); 
  144. $this->add_crumb( $cat->name, get_term_link( $cat ) ); 
  145.  
  146. $this->add_crumb( get_the_title( $post ), $permalink ); 
  147.  
  148. /** 
  149. * Page trail. 
  150. */ 
  151. private function add_crumbs_page() { 
  152. global $post; 
  153.  
  154. if ( $post->post_parent ) { 
  155. $parent_crumbs = array(); 
  156. $parent_id = $post->post_parent; 
  157.  
  158. while ( $parent_id ) { 
  159. $page = get_post( $parent_id ); 
  160. $parent_id = $page->post_parent; 
  161. $parent_crumbs[] = array( get_the_title( $page->ID ), get_permalink( $page->ID ) ); 
  162.  
  163. $parent_crumbs = array_reverse( $parent_crumbs ); 
  164.  
  165. foreach ( $parent_crumbs as $crumb ) { 
  166. $this->add_crumb( $crumb[0], $crumb[1] ); 
  167.  
  168. $this->add_crumb( get_the_title(), get_permalink() ); 
  169. $this->endpoint_trail(); 
  170.  
  171. /** 
  172. * Product category trail. 
  173. */ 
  174. private function add_crumbs_product_category() { 
  175. $current_term = $GLOBALS['wp_query']->get_queried_object(); 
  176.  
  177. $this->prepend_shop_page(); 
  178. $this->term_ancestors( $current_term->term_id, 'product_cat' ); 
  179. $this->add_crumb( $current_term->name ); 
  180.  
  181. /** 
  182. * Product tag trail. 
  183. */ 
  184. private function add_crumbs_product_tag() { 
  185. $current_term = $GLOBALS['wp_query']->get_queried_object(); 
  186.  
  187. $this->prepend_shop_page(); 
  188. $this->add_crumb( sprintf( __( 'Products tagged “%s”', 'woocommerce' ), $current_term->name ) ); 
  189.  
  190. /** 
  191. * Shop breadcrumb. 
  192. */ 
  193. private function add_crumbs_shop() { 
  194. if ( get_option( 'page_on_front' ) == wc_get_page_id( 'shop' ) ) { 
  195. return; 
  196.  
  197. $_name = wc_get_page_id( 'shop' ) ? get_the_title( wc_get_page_id( 'shop' ) ) : ''; 
  198.  
  199. if ( ! $_name ) { 
  200. $product_post_type = get_post_type_object( 'product' ); 
  201. $_name = $product_post_type->labels->singular_name; 
  202.  
  203. $this->add_crumb( $_name, get_post_type_archive_link( 'product' ) ); 
  204.  
  205. /** 
  206. * Post type archive trail. 
  207. */ 
  208. private function add_crumbs_post_type_archive() { 
  209. $post_type = get_post_type_object( get_post_type() ); 
  210.  
  211. if ( $post_type ) { 
  212. $this->add_crumb( $post_type->labels->singular_name, get_post_type_archive_link( get_post_type() ) ); 
  213.  
  214. /** 
  215. * Category trail. 
  216. */ 
  217. private function add_crumbs_category() { 
  218. $this_category = get_category( $GLOBALS['wp_query']->get_queried_object() ); 
  219.  
  220. if ( 0 != $this_category->parent ) { 
  221. $this->term_ancestors( $this_category->parent, 'post_category' ); 
  222. $this->add_crumb( $this_category->name, get_category_link( $this_category->term_id ) ); 
  223.  
  224. $this->add_crumb( single_cat_title( '', false ), get_category_link( $this_category->term_id ) ); 
  225.  
  226. /** 
  227. * Tag trail. 
  228. */ 
  229. private function add_crumbs_tag() { 
  230. $queried_object = $GLOBALS['wp_query']->get_queried_object(); 
  231. $this->add_crumb( sprintf( __( 'Posts tagged “%s”', 'woocommerce' ), single_tag_title( '', false ) ), get_tag_link( $queried_object->term_id ) ); 
  232.  
  233. /** 
  234. * Add crumbs for date based archives. 
  235. */ 
  236. private function add_crumbs_date() { 
  237. if ( is_year() || is_month() || is_day() ) { 
  238. $this->add_crumb( get_the_time( 'Y' ), get_year_link( get_the_time( 'Y' ) ) ); 
  239. if ( is_month() || is_day() ) { 
  240. $this->add_crumb( get_the_time( 'F' ), get_month_link( get_the_time( 'Y' ), get_the_time( 'm' ) ) ); 
  241. if ( is_day() ) { 
  242. $this->add_crumb( get_the_time( 'd' ) ); 
  243.  
  244. /** 
  245. * Add crumbs for taxonomies 
  246. */ 
  247. private function add_crumbs_tax() { 
  248. $this_term = $GLOBALS['wp_query']->get_queried_object(); 
  249. $taxonomy = get_taxonomy( $this_term->taxonomy ); 
  250.  
  251. $this->add_crumb( $taxonomy->labels->name ); 
  252.  
  253. if ( 0 != $this_term->parent ) { 
  254. $this->term_ancestors( $this_term->term_id, $this_term->taxonomy ); 
  255.  
  256. $this->add_crumb( single_term_title( '', false ), get_term_link( $this_term->term_id, $this_term->taxonomy ) ); 
  257.  
  258. /** 
  259. * Add a breadcrumb for author archives. 
  260. */ 
  261. private function add_crumbs_author() { 
  262. global $author; 
  263.  
  264. $userdata = get_userdata( $author ); 
  265. $this->add_crumb( sprintf( __( 'Author: %s', 'woocommerce' ), $userdata->display_name ) ); 
  266.  
  267. /** 
  268. * Add crumbs for a term. 
  269. * @param string $taxonomy 
  270. */ 
  271. private function term_ancestors( $term_id, $taxonomy ) { 
  272. $ancestors = get_ancestors( $term_id, $taxonomy ); 
  273. $ancestors = array_reverse( $ancestors ); 
  274.  
  275. foreach ( $ancestors as $ancestor ) { 
  276. $ancestor = get_term( $ancestor, $taxonomy ); 
  277.  
  278. if ( ! is_wp_error( $ancestor ) && $ancestor ) { 
  279. $this->add_crumb( $ancestor->name, get_term_link( $ancestor ) ); 
  280.  
  281. /** 
  282. * Endpoints. 
  283. */ 
  284. private function endpoint_trail() { 
  285. // Is an endpoint showing? 
  286. if ( is_wc_endpoint_url() && ( $endpoint = WC()->query->get_current_endpoint() ) && ( $endpoint_title = WC()->query->get_endpoint_title( $endpoint ) ) ) { 
  287. $this->add_crumb( $endpoint_title ); 
  288.  
  289. /** 
  290. * Add a breadcrumb for search results. 
  291. */ 
  292. private function search_trail() { 
  293. if ( is_search() ) { 
  294. $this->add_crumb( sprintf( __( 'Search results for “%s”', 'woocommerce' ), get_search_query() ), remove_query_arg( 'paged' ) ); 
  295.  
  296. /** 
  297. * Add a breadcrumb for pagination. 
  298. */ 
  299. private function paged_trail() { 
  300. if ( get_query_var( 'paged' ) ) { 
  301. $this->add_crumb( sprintf( __( 'Page %d', 'woocommerce' ), get_query_var( 'paged' ) ) ); 
.