/home/coolpkct/www/websites/cake3.cool.rocks/admin/classes/nav.php
<?php
/**
 * Part of SimpleViewer.net portfolio web site package.
 *
 * @package Showkase
 * @author Jack Hardie {@link http://www.jhardie.com}
 * @copyright Copyright (c) 2012, SimpleViewer Inc.
 */
defined('SK_ACCESS')||die('<h1>403: Forbidden</h1>');
 
/**
 * Site Navigation
 *
 * @package Showkase
 */
Class Nav
{
    /**
     * @var object singleton
     */
    private $config;
    
    /**
     * @var object DOM document
     */
    private $navDom;
  
    /**
     * Constructs Nav
     *
     */
    public function __construct(PageFactory $pageFactory, PageSet $pageSet)
    {
        $this->config = SkConfig::getInstance();
        $this->navDom = $this->makeDom($pageFactory, $pageSet);
    }
    
    /**
     * Returns current value of nav html
     *
     * @param string page reference
     * @param boolean include inactive subnav
     * @return string
     */
    public function getHtml($pageRef, $subnav = true)
    {
      if (!$this->navDom->hasChildNodes()) return '';
      $dom = clone $this->navDom;
      $dom->formatOutput = true;
      $xpath = new DOMXPath($dom);
      // Note space delimiters to distinguish sk-page-1 and sk-page-11
      $activeChildren = $xpath->query("/ul/li/ul/li[contains(concat(' ', @class, ' '), ' sk-page-$pageRef ')]");
      if ($activeChildren->length > 0) {
          $activeChild = $activeChildren->item(0);
          $activeChild->setAttribute('class', $activeChild->getAttribute('class').' active');
          $activeParent = $activeChild->parentNode->parentNode;
          $activeParent->setAttribute('class', $activeParent->getAttribute('class').' active');
      }
      $activeAdults = $xpath->query("/ul/li[contains(concat(' ', @class, ' '), ' sk-page-$pageRef ')]");
      if ($activeAdults->length > 0) {
          $activeAdult = $activeAdults->item(0);
          $activeAdult->setAttribute('class', $activeAdult->getAttribute('class').' active');
      }
      if ($subnav) return $dom->saveXML($dom->firstChild);
      $inactiveSubnav = $xpath->query("/ul/li[not(contains(@class, 'active'))]/ul");
      foreach ($inactiveSubnav as $ul) {
          $removed = $ul->parentNode->removeChild($ul);
      }
      return $dom->saveXML($dom->firstChild);
    }
  
    /**
     * Returns current value of nav html
     * Old code retained in case of problems with XPath
     *
     * @param string page reference
     * @return string
     */
    /*
    public function getHtml($pageRef)
    {
      $dom = clone $this->navDom;
      $dom->formatOutput = true;
      foreach ($dom->getElementsByTagName('li') as $li)
      { 
          $active = (strpos($li->getAttribute('class'), 'sk-page-'.$pageRef) !== false);
          $grandParent = $li->parentNode->parentNode;
          $isChild = ($grandParent->nodeName == 'li');
          if ($active) {
              $li->setAttribute('class', $li->getAttribute('class').' active');
              if ($isChild) {
                  $grandParent->setAttribute('class', $grandParent->getAttribute('class').' active');
              }
          }  
      }
      return $dom->saveXML($dom->firstChild);
    }
    */
  
    /**
     * Returns page html
     *
     * @return object DOM document
     */ 
    private function makeDom(PageFactory $pageFactory, PageSet $pageSet)
    {
        $weights = array();
        $navLi = array();
        $navA = array();
        $navLiUl = array();
        $navName = array();
        $navParent = array();
        $pagesData = $pageSet->getPagesData();
        $navDom = new DOMDocument('1.0', 'utf-8');
        $navDom->formatOutput = true;
        $navRoot = $navDom->createElement('ul');
        $navRoot->setAttribute('class', 'nav');
        foreach ($pagesData as $key=>$pageData) {
            $weights[] = isset($pageData['navWeight']) ? $pageData['navWeight'] : $pageData['pageRef'];
        }
        array_multisort($weights, $pagesData);
        $last = count($pagesData) - 1;
        $contentUrl = $this->config->getContentUrl();
        foreach ($pagesData as $key=>$pageData) {
            if (strtolower($pageData['navShow']) == 'false') continue;
            if (isset($pageData['supported']) && strtolower($pageData['supported']) == 'false') continue;
            $url = $contentUrl.'/'.basename($pageData['path']).'/';
            $target = '';
            if ($pageData['pageType'] == 'link') {
                $page = $pageFactory->make($pageData['pageType'], $pageData['pageRef'], $pageData['path']);
                $url = $page->getLayerVar('ss_customNavUrl');
                $target = $page->getLayerVar('ss_customNavTarget');
            }
            $ref = $pageData['pageRef'];
            $navLi[$ref] = $navDom->createElement('li');
            $cssGroup = ($pageData['parentPage'] > 0) ? 'sk-group sk-group-'.$pageData['parentPage'].' ' : '';
            $cssClass = $cssGroup.'sk-type-'.$pageData['pageType'].' sk-page-'.$pageData['pageRef'];
            $navLi[$ref]->setAttribute('class', $cssClass);
            $navA[$ref] = $navDom->createElement('a');
            $navA[$ref]->setAttribute('href', $url);
            if ($target != '') {
                $navA[$ref]->setAttribute('target', $target);
            }
            $navLi[$ref]->appendChild($navA[$ref]);
            $navName[$ref] = $navDom->createTextNode($pageData['navName']);
            $navA[$ref]->appendChild($navName[$ref]);
            $navParent[$ref] = $pageData['parentPage'];
        }
        unset($ref, $key, $pageData);
        foreach ($navLi as $ref=>$li) {
            $parentRef = $navParent[$ref];
            if ($parentRef == 0) {
                $navRoot->appendChild($li);
                continue;
            }
            if (!isset($navLi[$parentRef])) {
                continue;
            }
            if (!isset($navLiUl[$parentRef])) {
                $navLiUl[$parentRef] = $navDom->createElement('ul');
                $navLiUl[$parentRef]->setAttribute('class', 'subnav');
                $navLi[$parentRef]->appendChild($navLiUl[$parentRef]);
            }
            $navLiUl[$parentRef]->appendChild($li);
        }
        if ($navRoot->hasChildNodes()) {
            $navDom->appendChild($navRoot);
        }
        $uls = $navDom->getElementsByTagName('ul');
        foreach ($uls as $ul) {
            if (!$ul->hasChildNodes()) continue;
            $node = $ul->firstChild;
            $cssClass = $node->getAttribute('class');
            $node->setAttribute('class', $cssClass.' sk-first');
            $node = $ul->lastChild;
            $cssClass = $node->getAttribute('class');
            $node->setAttribute('class', $cssClass.' sk-last');
        }
        return $navDom;
    }
}