124 lines
3.4 KiB
PHP
124 lines
3.4 KiB
PHP
|
<?php
|
||
|
namespace Grav\Plugin\Breadcrumbs;
|
||
|
|
||
|
use Grav\Common\Grav;
|
||
|
|
||
|
class Breadcrumbs
|
||
|
{
|
||
|
/**
|
||
|
* @var array
|
||
|
*/
|
||
|
protected $breadcrumbs;
|
||
|
/**
|
||
|
* @var array
|
||
|
*/
|
||
|
protected $config;
|
||
|
|
||
|
/**
|
||
|
* @param $config
|
||
|
*/
|
||
|
public function __construct($config)
|
||
|
{
|
||
|
$this->config = $config;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Return an array of breadcrumbs for the current page.
|
||
|
*
|
||
|
* @return array An array of breadcrumbs.
|
||
|
*/
|
||
|
public function get()
|
||
|
{
|
||
|
// If the breadcrumbs have not yet been generated...
|
||
|
if (!$this->breadcrumbs) {
|
||
|
// Generate them now.
|
||
|
$this->build();
|
||
|
}
|
||
|
|
||
|
return $this->breadcrumbs;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* Build the array of breadcrumbs.
|
||
|
*
|
||
|
* The array is generated by starting at the current page and then climbing
|
||
|
* the hierarchy until the root is reached. The resulting crumbs are then
|
||
|
* stored in the $breadcrumbs instance variable.
|
||
|
*
|
||
|
* @internal
|
||
|
*/
|
||
|
protected function build()
|
||
|
{
|
||
|
// Used to hold the breadcrumbs as they are being generated.
|
||
|
$hierarchy = array();
|
||
|
|
||
|
$grav = Grav::instance();
|
||
|
$current = $grav['page'];
|
||
|
|
||
|
// If the page is not routable...
|
||
|
if (!$current) {
|
||
|
// Set up an empty array of crumbs.
|
||
|
$this->breadcrumbs = array();
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
// If we are not at the root page...
|
||
|
if (!$current->root()) {
|
||
|
|
||
|
// If we are configured to include the current page...
|
||
|
if ($this->config['include_current']) {
|
||
|
// Place the current page in the hierarchy.
|
||
|
$hierarchy[$current->url()] = $current;
|
||
|
}
|
||
|
|
||
|
$current = $current->parent();
|
||
|
|
||
|
// As long as $current does not contain the root page...
|
||
|
while ($current && !$current->root()) {
|
||
|
// Get the frontmatter of the page.
|
||
|
$header = $current->header();
|
||
|
|
||
|
// Assume we may descend unless otherwise told.
|
||
|
$may_descend = true;
|
||
|
|
||
|
// If the frontmatter contains a value for $may_descend...
|
||
|
if(isset(
|
||
|
$header->breadcrumbs,
|
||
|
$header->breadcrumbs['may_descend']
|
||
|
)) {
|
||
|
// Get that value.
|
||
|
$may_descend = $header->breadcrumbs['may_descend'];
|
||
|
}
|
||
|
|
||
|
// Then, if breadcrumbs should stop at this page...
|
||
|
if ($may_descend === false) {
|
||
|
// Empty the $hierarchy.
|
||
|
$hierarchy = [];
|
||
|
}
|
||
|
|
||
|
// Place the current page in the hierarchy.
|
||
|
$hierarchy[$current->url()] = $current;
|
||
|
|
||
|
// Get the parent of the current page.
|
||
|
$current = $current->parent();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// If we are configured to include the home page...
|
||
|
if ($this->config['include_home']) {
|
||
|
// Get the home page.
|
||
|
$home = $grav['pages']->dispatch('/');
|
||
|
|
||
|
// If the home page isn't already in the hierarchy...
|
||
|
if ($home && !array_key_exists($home->url(), $hierarchy)) {
|
||
|
// Place the home page in the hierarchy.
|
||
|
$hierarchy[] = $home;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// Reverse the array of breadcrumbs, so that they are in descending
|
||
|
// order.
|
||
|
$this->breadcrumbs = array_reverse($hierarchy);
|
||
|
}
|
||
|
}
|