10.2. Pages

10.2. Pages

There are two types of pages built-in in Zym_Navigation:

  • MVC pages – using the class Zym_Navigation_Page_Mvc

  • URI pages – using the class Zym_Navigation_Page_Uri

MVC pages are meant to be "internal" pages, and are defined using MVC parameters like action and controller, while the URI pages are generally considered to be off-site, for example if you want it to link to another site/domain, or you want to have some other special logic to it by using e.g. href="/docs/reference".

10.2.1. Common page features

All page classes must extend Zym_Navigation_Abstract, and will thus share a common set of features and properties. Most notably they share the options in the table below, and are forced to use the same initialization process.

[Note] Note

Read more on extending Zym_Navigation_Page in Creating custom page types.

[Note] Note

All option keys are translated to their according set methods. This means that the option position maps to the method setPosition(), and reset_params maps to the method setResetParams().

Table 10.1. Common page options

Key Type Default Description
label string null A page label, such as Home or Blog. This is the only required common page option.
id string | int null An id tag/attribute that may be used for the page, typically in an anchor element.
class string null A CSS class that may be used for the page, typically in an anchor element.
title string null A succinct page description, typically for using as the title attribute in an anchor.
target string null Specifies a target that may be used for the page, typically in an anchor element.
position string | int | null null Works like order for elements in Zend_Form. If specified, the page will be iterated in a specific order, meaning you can force a page to be iterated first by setting position to something like -100. If a string is given, it must parse to a valid int. If null is given, it will be reset, meaning the order in which the page was added to the container will be used.
resource string | Zend_Acl_Resource_Interface | null null ACL resource to associate with the page. Read more in the section on ACL integration in view helpers..
privilege string | null null ACL privilege to associate with the page. Read more in the section on ACL integration in view helpers..
active bool false Whether the page should be considered active for the current request. If active is false or not given, MVC pages will check its properties against the request object upon calling $page->isActive().
visible bool true Whether page should be visible for the user, or just be a part of the structure. Invisible pages are skipped by view helpers.
pages array | Zend_Config | null null Sub pages of the page. This could be an array or Zend_Config object containing either page options that can be passed to Zym_Navigation_Page::factory(), actual Zym_Navigation_Page instances, or a mixture of those.

[Note] Custom properties

All pages support setting and getting of custom properties, by using the magic methods __set($name, $value), __get($name), __isset($name) and __unset($name).Custom properties will also be included in $page->toArray().

Example 10.2. Custom page properties

This is an example of how custom properties can be used. Custom properties will also be included inf $page->toArray().

<?php
 
$page = new Zym_Navigation_Page_Mvc(array('label' => 'Lorem ipsum'));
$page->foo = 'bar';
$page->meaning = 42;
 
echo $page->foo;
 
if ($page->meaning != 42) {
    // action should be taken
}

10.2.2. Zym_Navigation_Page_Mvc

MVC pages are defined using MVC parameters from the Zend Framework terminology. An MVC page will use Zend_Controller_Action_Helper_Url internally in the getHref() method to generate hrefs, and in isActive() it will intersect the the Zend_Controller_Request_Abstract params with its own params to determine if the page is active.

Table 10.2. MVC page options

Key Type Default Description
action string null Action name to use when generating href to the page.
controller string null Controller name to use when generating href to the page.
module string null Module name to use when generating href to the page.
params array array User params to use when generating href to the page.
route string default Route name to use when generating href to the page.
reset_params bool true Whether user params should be reset when generating href to the page.

Example 10.3. getHref() generates the page URL

These examples show that MVC pages use Zend_Controller_Action_Helper_Url internally to generate URLs when calling $page->getHref().

[Note] Note

All examples assume a regular MVC setup with default being the default module name, and that the route named default has not been modified.

The URL/URI returned is relative to your application's baseUrl. In the examples, the base is '/' for simplicity.

<?php
 
// getHref() returns /
$page = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'index',
    'controller' => 'index'
));
 
// getHref() returns /blog/post/view
$page = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'view',
    'controller' => 'post',
    'module'     => 'blog'
));
 
// getHref() returns /blog/post/view/id/1337
$page = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'view',
    'controller' => 'post',
    'module'     => 'blog',
    'id'         => 1337
));

Example 10.4. isActive() determines if page is active

These examples show that MVC pages determine whether they are active by using the params found in the request object.

[Note] Note

All examples assume a regular MVC setup with default being the default module name, and that the route named default has not been modified.

<?php
 
/*
 * Dispatched request:
 * - module:     default
 * - controller: index
 * - action:     index
 */
 
$page1 = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'index',
    'controller' => 'index'
));
 
$page2 = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'bar',
    'controller' => 'index'
));
 
$page1->isActive(); // returns true
$page2->isActive(); // returns false 
 
/*
 * Dispatched request:
 * - module:     blog
 * - controller: post
 * - action:     view
 * - id:         1337
 */
 
$page = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'view',
    'controller' => 'post',
    'module'     => 'blog'
));
 
// returns true, because request has the same module, controller and action
$page->isActive(); 
 
/*
 * Dispatched request:
 * - module:     blog
 * - controller: post
 * - action:     view
 */
 
$page = new Zym_Navigation_Page_Mvc(array(
    'label'      => 'foo',
    'action'     => 'view',
    'controller' => 'post',
    'module'     => 'blog',
    'id'         => null
));
 
// returns false, because page requires the id param to be set in the request
$page->isActive(); // returns false

Example 10.5. Using routes

MVC pages are aware of routes. Setting what route should be used when generating the URL is done by specifying the route option when constructing, or by calling $page->setRoute('routeName') on a page instance.

<?php
 
// the following route is added to the ZF router 
Zend_Controller_Front::getInstance()->getRouter()->addRoute(
    'article_view', // route name
    new Zend_Controller_Router_Route(
        'a/:id',
        array(
            'module'     => 'news',
            'controller' => 'article',
            'action'     => 'view',
            'id'         => null
        )
    )
);
 
// a page is created with a 'route' option
$page = new Zym_Navigation_Page_Mvc(array(
    'label'  => 'A news article',
    'route'  => 'article_view',
    'params' => array(
        'id' => 42
    )
));
 
// returns: /a/42
$page->getHref();

10.2.3. Zym_Navigation_Page_Uri

Pages of type Zym_Navigation_Page_Uri can be used to link to pages on other domains or sites, or to implement custom logic for the page. URI pages are really simple; in addition to the common page options, an URI page only takes one option, the uri option. The uri will be returned when using $page->getHref().

[Note] Note

Zym_Navigation_Page_Uri will not try to determine whether it should be active when calling $page->isActive(). It merely returns what currently is set, so to make a URI page active you have to manually call $page->setActive().

Table 10.3. URI page options

Key Type Default Description
uri string null URI to page. This can be any string.

10.2.4. Creating custom page types

When extending Zym_Navigation_Page, the child class cannot override the constructor. This is used to force every page class to accept only an array or a Zend_Config object as the only argument to the constructor, so that all page types can created using the page factory method.

Example 10.6. The most simple custom page

The only thing you need to add to a custom page is the getHref() method.

<?php
require_once 'Zym/Navigation/Page.php';
 
class My_Simple_Page extends Zym_Navigation_Page
{
    public function getHref()
    {
        return 'something-completely-different';
    }
}

There is no need to override the setOptions() and setConfig() when extending the abstract page class, even if the new child class have properties that are not in the abstract class. setOptions() will translate the given option name to a potential method name and use method_exists() to determine if there is matching set method for the option.

Example 10.7. Adding properties

When adding properties to an extended page, there is no need to override/modify setOptions() or setConfig().

<?php
require_once 'Zym/Navigation/Page.php';
 
class My_Navigation_Page extends Zym_Navigation_Page
{
    protected $_foo;
    protected $_fooBar;
 
    public function setFoo($foo)
    {
        $this->_foo = $foo;
    }
 
    public function setFooBar($fooBar)
    {
        $this->_fooBar = $fooBar;
    }
}
 
// can now construct using
$page = new My_Navigation_Page(array(
    'label'   => 'Property names are translated',
    'foo'     => 'bar',
    'foo_bar' => 'baz'
));
 
// ...or
$page = Zym_Navigation_Page::factory(array(
    'type'    => 'My_Navigation_Page',
    'label'   => 'Property names are translated',
    'foo'     => 'bar',
    'foo_bar' => 'baz'
));

By default, Zym_Navigation_Page will validate that a label is set when the page is being constructed. If you want to add extra validation to be done when constructing, to ensure that a page cannot be in an invalid state, you should overload the _validate() method and add whatever validation you need there.

Example 10.8. Adding custom validation

This is an example of a more strict version of Zym_Navigation_Page_Mvc. Most of the code is left out to focus on the point; adding validation.

<?php
class My_Strict_Page extends Zym_Navigation_Page_Mvc
{
    /**
     * An MVC page must have controller and action set
     *
     * @return void
     * @throws Zym_Navigation_Page_InvalidException  if page is invalid
     */
    protected function _validate()
    {
        if (!isset($this->_controller)) {
            $msg = 'Page controller is not set';
        } elseif (!isset($this->_action)) {
            $msg = 'Page action is not set';
        }
 
        if (isset($msg)) {
            require_once 'Zym/Navigation/Page/InvalidException.php';
            throw new Zym_Navigation_Page_InvalidException($msg);
        } else {
            parent::_validate();
        }
    }
}