<?php if (!defined('PmWiki')) exit();

/*
 * DESCRIPTION:  The Cluster recipe adds group-clustering
 * functionality to PmWiki, in a pseudo-hierarchical way.
 * For info, see http://www.pmwiki.org/wiki/Cookbook/Cluster
 * Based on Hg by Dan Vis  <editor àt fast döt st>, Copyright 2007.
 * 	see http://www.pmwiki.org/wiki/Cookbook/Hg
 * Modified by: Kathryn Andersen v'2007-02-12'
 * ----
 * Modified by: Feral v'2007-02-14'
 *	I added (:nl:)s next to the (:include:) statements as [[PmWiki/LayoutVariables#GroupFooterFmt]] denotes that a (:nl:) after the (:include:) is default. However, in my tests I found a (:nl:) before the (:include:) was also necessary to arrive at the same output.
 *	I also added code for a (:clusterbreadcrumbs:) directive that will output a clickable 'breadcrumbs' style trail.
 * ----
 * Feral's v'2007-02-21' -- RightBar support
 *	* Replaced hardcoded 'Site' with $SiteGroup.
 *	* Added $ClusterRightBar page variable.
 *	* Added support function ClusterRightBarName($group), which is just a
 *	  slight tweak of ClusterSideBarName(), nothing more.
 *	* Added variable $clustersrightbarname for skins to use to determine if
 *	  they should show their rightbar; (I needed this to make triad work as
 *	  expected.)
 * ----
 */

/*
 * Set up various variables
 */
$RecipeInfo['Cluster']['Version'] = '2007-02-21';
SDV($ClusterSeparator, '-');
SDV($ClusterMaxLevels, 7);

/* ================================================================
 * Page Variables
 */
$FmtPV['$g0'] = 'ClusterCountLevels($group)';
$FmtPV['$n0'] = 'ClusterCountLevels($name)';
for ($i=0; $i < $ClusterMaxLevels; $i++) {
	$hg = "g" . ($i + 1);
	$hn = "n" . ($i + 1);
	$FmtPV['$' . $hg] = 'ClusterSplitName($group, ' . $i . ')';
	$FmtPV['$' . $hn] = 'ClusterSplitName($name, ' . $i . ')';
}
$FmtPV['$SideBar'] = 'ClusterSideBarName($group)';
$FmtPV['$GroupTitle'] = 'ClusterGroupTitle($pn, $var)';
$FmtPV['$GroupTitlespaced'] = 'ClusterGroupTitle($pn, $var)';
$FmtPV['$ClusterRightBar'] = 'ClusterRightBarName($group)'; // [Feral:052/07@17:32] v2007-02-21 -- RightBar support



/* ================================================================
 * Markup for link shortcuts
 */
Markup('[[cluster','<var','/\\[\\[(-|[\\*\\^]+)(.*?)\\]\\]/e', 'ClusterLinks($pagename, "$1", "$2")');

/* ================================================================
 * Set up clustered configurations
 */
$pagename = ResolvePageName($pagename);
$EnablePGCust = 0;
$m = preg_split('/[.\\/]/', $pagename);
$group = $m[0];
$name = $m[1];

$found_config = false;
$found_grouphead = false;
$found_groupfoot = false;
$found_attr = false;
if (file_exists("$LocalDir/$group.$name.php")) {
	include_once("$LocalDir/$group.$name.php");
	$found_config = true;
}
$PageCSSListFmt["pub/css/$group.$name.css"] = "$PubDirUrl/css/$group.$name.css"; 
$groups = explode($ClusterSeparator, $group);
while (count($groups) != 0) {
	$cluster_group = implode ($ClusterSeparator, $groups);
	if (!$found_config && file_exists("$LocalDir/$cluster_group.php")) {
		include_once("$LocalDir/$cluster_group.php");
		$found_config = true;
	}
	if (!$found_grouphead && PageExists("$cluster_group.GroupHeader")) {
		$GroupHeaderFmt = "(:nl:)(:include $cluster_group.GroupHeader:)(:nl:)";
		$found_grouphead = true;
	}
	if (!$found_groupfoot && PageExists("$cluster_group.GroupFooter")) {
		$GroupFooterFmt = "(:nl:)(:include $cluster_group.GroupFooter:)(:nl:)";
		$found_groupfoot = true;
	}
	if (!$found_attr && PageExists("$cluster_group.GroupAttributes")) {
		$GroupAttributesFmt = "$cluster_group.GroupAttributes";
		$found_groupfoot = true;
	}
	$PageCSSListFmt["pub/css/$cluster_group.css"] = "$PubDirUrl/css/$cluster_group.css"; 
	array_pop($groups);
}
// set the defaults for those that haven't been found
if (!$found_config && file_exists("$LocalDir/$default.php")) {
	include_once("$LocalDir/$default.php");
}
if (!$found_grouphead && PageExists("$SiteGroup.GroupHeader")) {
	$GroupHeaderFmt = "(:nl:)(:include $SiteGroup.GroupHeader:)(:nl:)";
}
if (!$found_groupfoot && PageExists("$SiteGroup.GroupFooter")) {
	$GroupFooterFmt = "(:nl:)(:include $SiteGroup.GroupFooter:)(:nl:)";
}
$PageCSSListFmt["pub/css/local.css"] = "$PubDirUrl/css/local.css";
$PageCSSListFmt = array_reverse($PageCSSListFmt, true);

/* ================================================================
 * Vars, mostly to help the skins know we have pieces they do not realize.
 * [Feral:052/07@16:54] Inserted for clever skins, such as triad, so they can determin if we have a right bar they do not know about.
 */
$clustersrightbarname = ClusterRightBarName($group); // [Feral:052/07@16:53] Needed for clever skins

/* ================================================================
 * Functions
 */
function ClusterCountLevels($name) {
	global $ClusterSeparator;
	$parts = explode($ClusterSeparator, $name);
	return count($parts);
}

function ClusterSplitName($name, $ind) {
	global $ClusterSeparator;
	$parts = explode($ClusterSeparator, $name);
	if ($ind < 0 || $ind >= count($parts)) return '';
	else return $parts[$ind];
}

function ClusterGroupTitle($pagename, $var, $fmt = NULL) {
	global $DefaultName, $SpaceWikiWords, $AsSpacedFunction;
	// look for a group-title for this specific group, first
	if (is_null($fmt)) {
		SDV($GroupTitlePathFmt,
			array(
				'$Group.GroupAttributes', '$Group.GroupHeader', 
				'$Group.GroupFooter', '$Group.$Group', "\$Group.$DefaultName"));
		$fmt = $GroupTitlePathFmt;
	}
	foreach((array)$fmt as $f) {
		$pn = FmtPageName($f, $pagename);
		$page = ReadPage($pn, READPAGE_CURRENT);
		if ($page['title']) { return $page['title']; }
	}

	// okay, didn't find one
	$num_parts = PageVar($pagename, '$g0');
	if ($num_parts == 1)
	{
		$grouptitle = PageVar($pagename, '$Group');
	}
	else {
		// get the last part of the group
		$grouptitle = PageVar($pagename, '$g' . PageVar($pagename, '$g0'));
	}
	return ($var == '$GroupTitlespaced' || $SpaceWikiWords)
		? $AsSpacedFunction($grouptitle) : $grouptitle;
}

function ClusterSideBarName($group) {
	global $ClusterSeparator;
	global $SiteGroup;
	$groups = explode($ClusterSeparator, $group);
	while (count($groups) != 0) {
		$cluster_group = implode ($ClusterSeparator, $groups);
		if (PageExists("$cluster_group.SideBar")) {
			// short-circuit return!
			return "$cluster_group.SideBar";
		}
		array_pop($groups);
	}
	return "$SiteGroup.SideBar";
}

// ----
// [Feral:052/07@15:38] Blockcopied/substituted from ClusterSideBarName()
function ClusterRightBarName($group) {
	global $ClusterSeparator;
	global $SiteGroup;
	$groups = explode($ClusterSeparator, $group);
	while (count($groups) != 0) {
		$cluster_group = implode ($ClusterSeparator, $groups);
		if (PageExists("$cluster_group.RightBar")) {
			// short-circuit return!
			return "$cluster_group.RightBar";
		}
		array_pop($groups);
	}
	return "$SiteGroup.RightBar";
}


function ClusterLinks($pagename, $prefix, $inlink) {
	global $ClusterSeparator;
	$group = FmtPageName('$Group', $pagename);
	if ($prefix == "-") {
		return "[[$group$ClusterSeparator$inlink]]";
	}
	$groups = explode($ClusterSeparator, $group);
	$c = strlen($prefix);
	$i = 0;
	while ($i < $c) {
		if (substr($prefix, 0, 1) == "*") $link = $link . $groups[$i] . $ClusterSeparator;
		if (substr($prefix, 0, 1) == "^") array_pop($groups);
		$i = $i + 1;
	}
	if (substr($prefix, 0, 1) == "*") $link = substr ($link, 0, -1);
	if (substr($prefix, 0, 1) == "^") $link = implode($ClusterSeparator, $groups);
	return "[[$link$inlink]]";
}


// ----
// Blame the following on Feral...
Markup('clusterbreadcrumbs','directives',"/\(:clusterbreadcrumbs:\)/e", "ClusterBreadCrumbs()");
function ClusterBreadCrumbs()
{
	global $ClusterSeparator;
	global $pagename;

	$pagename = ResolvePageName($pagename);
	$EnablePGCust = 0;
	$m = preg_split('/[.\\/]/', $pagename);
	$group = $m[0];
	$name = $m[1];

	$out = "";
	$groups = explode($ClusterSeparator, $group);


	$number = count($groups);
	for ($i=0; $i < $number; $i++)
	{
		if	(	$i != 0)
		{
			$out.= " $ClusterSeparator ";
		}

//		$out.= "$i:";
		$out.= "[[";

		for	($num = 0; $num <= $i; $num++)
		{
			if	(	$num != 0)
			{
				$out.= $ClusterSeparator;
			}

			$out.= $groups[$num];
		}
		$out.= "|";
		$out.= $groups[$i];
		$out.= "]]";
//		$out.= " !! ";
	}

//	$out.= "<br/>\n";
	return $out;
}


//
///EOF