Welcome to Abdul Malik Ikhsan's Blog

Zend Framework 2 : Create Your Custom View Helper

Posted in Tutorial PHP, Zend Framework 2 by samsonasik on July 20, 2012

In MVC Architecture, sometimes, we have to do a “logic” to manage a view. The Logic is called by View named View Helper. Zend Framework 2 has a ton of flexibility, so, we can create a custom View Helper if we want to -that can be called by View Layer over modules.

For Example, i want to create a View Helper named Testhelper which the responsibility of this helper is to state that the string is found or not.  First of all, we create a Helper under src directory :
And the content of Testhelper is :

namespace Test\View\Helper;
use Zend\View\Helper\AbstractHelper;

class Testhelper extends AbstractHelper
{
    public function __invoke($str, $find)
    {
        if (! is_string($str)){
            return 'must be string';
        }

        if (strpos($str, $find) === false){
            return 'not found';
        }

        return 'found';
    }
}

The next step is register that in Module.php

namespace Test;

use Zend\ModuleManager\Feature\AutoloaderProviderInterface,
    Zend\ModuleManager\Feature\ConfigProviderInterface,
    Zend\ModuleManager\Feature\ViewHelperProviderInterface;    

class Module implements 
    AutoloaderProviderInterface, 
    ConfigProviderInterface, 
    ViewHelperProviderInterface
{
    public function getAutoloaderConfig(){/*common code*/}
    public function getConfig(){ /*common code */ }

    public function getViewHelperConfig()
    {
        return array(
            'factories' => array(
                'test_helper' => function($sm) {
                    $helper = new View\Helper\Testhelper ;
                    return $helper;
                }
            )
        );   
   }
}

OR, you can SIMPLIFY that by configuring it as an invokable in module.config.php as @weierophinney ( project lead for Zend Framework ) suggestion –thanks a lot for his suggestion– like this :

return array(
//.........
    'view_helpers' => array(
        'invokables'=> array(
            'test_helper' => 'Test\View\Helper\Testhelper'   
        )
    ),
//.........
);

Last step, call it in the view :

echo $this->test_helper("me","e");

81 Responses

Subscribe to comments with RSS.

  1. Juanito Perez said, on September 27, 2012 at 7:11 am

    Excelent tutorial bro!! I’m learning ZF2 and your site is very good.

  2. samsonasik said, on October 5, 2012 at 11:31 am

    Thank you 😉

  3. Dragan Menoski said, on October 16, 2012 at 3:41 pm

    Great job !
    Thank you

  4. samsonasik said, on October 16, 2012 at 4:32 pm

    You’re welcome 😉

  5. loktheprince said, on December 5, 2012 at 1:58 pm

    $this->paginationControl($albums, ‘Sliding’, ‘pager.phtml’, array(‘lang’=>’en’)) is not working for me.
    $this->pageCount dont have any value
    $this->getRequest()->getServer()->get(‘QUERY_STRING’) is not returning anything

    Please suggest me

  6. […] post about creating Controller pLugin in ZF2. For what have to do to create a View Helper , see : my post about creating view helper or EvanDotPro’s […]

  7. Guilhem said, on January 10, 2013 at 5:07 am

    Thanks for that and happy new year 🙂

  8. piasek said, on January 25, 2013 at 8:50 pm

    Hi
    I’m trying to create my View Helper where i will create IMG tag
    so far i have this:

    <?php
    
    // module/Photo/src/Photo/View/Helper/ImgHelper.php
    
    namespace Photo\View\Helper;
    
    use Zend\View\Helper\AbstractHelper;
    
    class Imghelper extends AbstractHelper
      {
        protected $_baseUrl = null;
        protected $_exists = array();
    
        public function __construct ()
          {
            $url = PUBLIC_PATH;
            $root = '/' . trim($url, '/');
    
            if ($root == "/")
              {$root = "";}
    
            $this->_baseUrl = $root . "/";
          }
    
        public function img($path, $params = array())
          {
            $plist = array();
            $str = null;
    
            $imgpath = $this->_baseUrl . ltrim($path);
    
            if (!isset($this->_exists[$path]))
              {$this->_exists[$path] = file_exists(realpath($imgpath));}
    
            if (!isset($params['alt']))
              {$params['alt'] = '';}
    
            foreach ($params as $param => $value)
              {$plist[] = $param . '="' . $this->view->escape($value) . '"';}
    
                    $str = " ".join(" ", $plist);
            $p = ($this->_exists[$path]) ? $this->_baseUrl.ltrim($path,'/') : null;
    
            if (isset($p))
              {return '<img src="'.$p.'" '.$str.' />';}
          }
    
      } 
    

    But i have an error on line with $this->view->escape($value)
    and the question is how i can get function escape to work here?

    Error message
    “Fatal error: Uncaught exception ‘Zend\ServiceManager\Exception\ServiceNotFoundException’ with message ‘Zend\ServiceManager\ServiceManager::get was unable to fetch or create an instance for escape’ in ”

    thx

    • samsonasik said, on January 26, 2013 at 12:52 am

      You should extends

      Zend\View\Helper\Escaper\AbstractHelper; 
      

      which Escaper is placed., so the code should be :

      namespace Photo\View\Helper;
      
      use Zend\View\Helper\Escaper\AbstractHelper;
      
      class Imghelper extends AbstractHelper
      {
          protected $_baseUrl = null;
          protected $_exists = array();
      
          public function __construct ()
          {
              $url = PUBLIC_PATH;
              $root = '/' . trim($url, '/');
      
              if ($root == "/")
                {$root = "";}
      
              $this->_baseUrl = $root . "/";
          }
          
          public function escape($value)
          {
             return $this->getEscaper()->escapeHtml($value);
          }
      
          public function __invoke($path, $params = array())
          {
                     $plist = array();
              $str = null;
      
              $imgpath = $this->_baseUrl . ltrim($path);
      
              if (!isset($this->_exists[$path]))
                {$this->_exists[$path] = file_exists(realpath($imgpath));}
      
              if (!isset($params['alt']))
                {$params['alt'] = '';}
      
              foreach ($params as $param => $value)
                {$plist[] = $param . '="' . $this->escape($value) . '"';}
      
                      $str = " ".join(" ", $plist);
              $p = ($this->_exists[$path]) ? $this->_baseUrl.ltrim($path,'/') : null;
      
              if (isset($p))
                {return '<img src="'.$p.'" '.$str.' />';}
          }
        } 
      

      and use $this->getEscaper()->escapeHtml() to escape the html.
      do escapeJs() or other depend on your need.

      so, in the view, you can call :

       echo $this->yourimghelper($path, array());
      
  9. Ioan Katalin said, on February 14, 2013 at 7:14 pm

    use Zend\ModuleManager\Feature\AutoloaderProviderInterface,
    Zend\ModuleManager\Feature\ConfigProviderInterface,
    Zend\ModuleManager\Feature\ViewHelperProviderInterface;

    class Module implements
    AutoloaderProviderInterface,
    ConfigProviderInterface,
    ViewHelperProviderInterface
    {//..
    public function getViewHelperConfig()
    {
    return array(
    ‘factories’ => array(
    ‘Ie9’ => function ($sm) {
    $locator = $sm->getServiceLocator();
    $viewHelper = new View\Helper\Ie9;
    return $viewHelper;
    }
    ),
    );
    }
    //…
    }

  10. Rid Zeal said, on February 24, 2013 at 12:23 am

    Tanya sedikit mas Iksan, kalo untuk dipakai semua module berarti harus di register di invocables di module.config nya ya?

    Apa memungkinkan kalau dibuat di library eksternal, jadi bisa ambil dari situ, tidak perlu register2 lagi.
    Trims.

  11. Juan Rojas said, on March 18, 2013 at 11:43 pm

    Hi, I tried this but get the following error and my application crashes:

    Warning: Class ‘Zend\Stdlib\ArrayObject\PhpReferenceCompatibility’ not found in C:\Program Files (x86)\Zend\ZendServer\data\apps\http\__default__\MT5_0\1.0.0\vendor\zendframework\zendframework\library\Zend\Stdlib\ArrayObject.php on line 24

    Fatal error: Class ‘Zend\Stdlib\AbstractArrayObject’ not found in C:\Program Files (x86)\Zend\ZendServer\data\apps\http\__default__\MT5_0\1.0.0\vendor\zendframework\zendframework\library\Zend\Stdlib\ArrayObject.php on line 33

    Any Ideas? i really like your tutorials by the way.

    • samsonasik said, on March 19, 2013 at 6:00 am

      use ZendSkeletonApplication to be a skeleton project. clone this : https://github.com/zendframework/ZendSkeletonApplication and update your ZF library to the latest master.

      • vikas said, on March 19, 2013 at 6:17 pm

        hello samsonasik i want put search box in my form for search data but i’dont get any easy solution for same and also i am new in zend so can you put tutorial step by step for my help..

      • samsonasik said, on March 20, 2013 at 5:05 pm

        you can create a form to accomodate it. thanks for the suggestion.

  12. Sasha said, on March 26, 2013 at 12:23 am

    Hello, please advice how to use url() helper in custom view helper. Thank you for your time.

    • samsonasik said, on March 26, 2013 at 12:25 am

      you can do something like this :

          public function __invoke()
          {
              $urlHelper = $this->view->plugin('url');
              
              //do other thing...
          }
      
      • Sasha said, on March 26, 2013 at 2:39 am

        Thank you.

      • samsonasik said, on March 26, 2013 at 5:20 pm

        you’re welcome 😉

  13. hhh said, on April 27, 2013 at 12:39 am

    how to add a helper to specified module?

    this will apply to all modules ..
    ‘view_helpers’ => array(
    ‘invokables’=> array(
    ‘test_helper’ => ‘Test\View\Helper\Testhelper’
    )
    ),

    • samsonasik said, on April 27, 2013 at 5:12 am

      all module config are merged, and the view helper should only called if that called, there is no concept like you mentioned :p

  14. Sumit said, on May 28, 2013 at 8:00 pm

    Good work mate! your expertise and this blog has really been helpful. I just have suggestion if you can put a demo link of the sample code it would be great as people can see the actual working of the code bits. Cheers!

  15. teolateo said, on June 7, 2013 at 2:53 pm

    help me!

    Database
    CREATE TABLE IF NOT EXISTS `Menu` (
    `idmenu` int(2) NOT NULL AUTO_INCREMENT,
    `NameMenu` varchar(255) NOT NULL,
    PRIMARY KEY (`idmenu`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=8 ;

    NSERT INTO `Menu` (`idmenu`, `NameMenu`, ) VALUES
    (1, ‘Home’),
    (2, ‘Who we are’),
    (3, ‘Products’),
    (4, ‘Downloads’),
    (5, ‘Search’),
    (6, ‘Logon’),
    (7, ‘Contact us’);

    Module
    Ema
    –config
    –module.config.php
    –src
    –ema\view\helper\
    –MenuHelper.php
    –view
    –layout
    –layout.phtml
    –Module.php
    –autoload_classmap.php

    1.File module.config.php
    array(
    ‘invokables’=> array(
    ‘menus’ => ‘Ema\View\Helper\MenuHelper’,
    )
    ),
    );

    2.MenuHelper.php
    namespace Ema\View\Helper;
    use Zend\View\Helper\AbstractHelper;
    use Zend\Db\Adapter\Adapter;
    class MenuHelper extends AbstractHelper {
    Protected $adapter;
    public function __construct(Adapter $adapter) {
    $this->adapter = $adapter;
    }
    public function __invoke()
    { $result = $this->adapter->query(‘SELECT * FROM `Menu` ‘);
    return $result->toArray(); }
    }

    3.layout.phtml

    $menus as $menu){
    ?>

    error lauoyt.php foreach($this->$menus as $menu)

    • teolateo said, on June 7, 2013 at 2:57 pm

      Database
      CREATE TABLE IF NOT EXISTS `Menu` (
      `idmenu` int(2) NOT NULL AUTO_INCREMENT,
      `NameMenu` varchar(255) NOT NULL,
      PRIMARY KEY (`idmenu`)
      ) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=8 ;

      NSERT INTO `Menu` (`idmenu`, `NameMenu`, ) VALUES
      (1, ‘Home’),
      (2, ‘Who we are’),
      (3, ‘Products’),
      (4, ‘Downloads’),
      (5, ‘Search’),
      (6, ‘Logon’),
      (7, ‘Contact us’);

      Module
      Ema
      –config
      –module.config.php
      –src
      –ema\view\helper\
      –MenuHelper.php
      –view
      –layout
      –layout.phtml
      –Module.php
      –autoload_classmap.php
      1.File module.config.php
      array(
      ‘invokables’=> array(
      ‘menus’ => ‘Ema\View\Helper\MenuHelper’,
      )
      ),
      );

      2.MenuHelper.php
      namespace Ema\View\Helper;
      use Zend\View\Helper\AbstractHelper;
      use Zend\Db\Adapter\Adapter;
      class MenuHelper extends AbstractHelper {
      Protected $adapter;
      public function __construct(Adapter $adapter)
      {
      $this->adapter = $adapter;
      }
      public function __invoke()
      {
      $result = $this->adapter->query(‘SELECT * FROM `Menu` ‘);
      return $result->toArray();
      }
      }
      3.layout.phtml

      $menus as $menu){
      ?>

  16. Beneetha TA said, on July 11, 2013 at 7:11 pm

    hi

    I am trying to do navigation with menu and sub menu but not getting……Could you please help me

  17. […] Weißt du denn, wie eigene View-Helper eingebunden werden? Ansonsten verweise ich einfach mal auf Zend Framework 2 : Create Your Custom View Helper | Welcome to Abdul Malik Ikhsan's Blog An die __invoke-Methode übergibst du dann die Formular-Elemente. In dieser baust du dann einfach […]

  18. Lom said, on October 6, 2013 at 10:32 pm

    Great tutorial! One question: How to get the translator working / conform inside a view helper? Possible?

    • samsonasik said, on October 6, 2013 at 10:34 pm

      you can call $this->view->viewhelpername() inside the view helper class.

  19. Lom said, on October 6, 2013 at 11:40 pm

    Thanks for your really quick reply :-). Sorry, maybe my question was not good.

    How can i use the translator->translate(); within a view helper to translate some needed strings? And does it has an impact on the performance if I se the translator inside a view helper.

    • samsonasik said, on October 6, 2013 at 11:47 pm

      call via :

      $this->view->translate("somestring");
      

      inside view helper.

  20. Lom said, on October 6, 2013 at 11:50 pm

    You’re the best! Thanks a lot! Now I’m even more think that the ZF2 is really awesome. Getting more and more comfortable with it. And still a lot to learn and discover :-).

  21. Arvind Kumar said, on October 8, 2013 at 2:08 pm

    Hello samsonasik,
    Thanks for sharing this grate tutorial. Can I make multiple function in Testhelper.php file like sortString,uppercase,lowercase etc. If It is possible then how will I use.
    Thanks in advenced.

    • samsonasik said, on October 8, 2013 at 3:11 pm

      ofcourse, as far as the access modifier of that function is public. you can do

      $this->yourhelper()->somefunction();
      
  22. Arvind Kumar said, on October 8, 2013 at 7:19 pm

    How to define and access multiple function from one helper class

    test_helper->calculatetotal(20);
    $this->test_helper->calculatearea(30);

    Thanks in advance for reply 🙂

    • Arvind Kumar said, on October 8, 2013 at 7:21 pm

      class Testhelper extends AbstractHelper
      {
      public $sum;
      public function __invoke()
      {
      return $this;
      }

      public function calculatetotal($sum)
      {
      return $sum+$sum;
      }
      public function calculatearea($sum)
      {
      return $sum*$sum;
      }

      }

    • samsonasik said, on October 8, 2013 at 8:53 pm

      $this->test_helper()->calculatearea(30);

      you missed () to get the __invoke()/__construct() function first.

      • Arvind Kumar said, on October 8, 2013 at 9:20 pm

        Thanks got it 🙂

        $this->test_helper()->setUserName(‘test’)

  23. hungbuit said, on October 26, 2013 at 3:11 pm

    thank so much!

  24. Juan D said, on November 28, 2013 at 5:39 am

    I’m having problems trying to create my own FormRow based on Zend2 with just few changes on how render create the layout and where errors are placed. I’ve created my own FormRow class, adding this class to invokables

    public function getViewHelperConfig()
    {
    return array(
    ‘invokables’ => array(‘formelementerrors’ => ‘Events\Form\View\Helper\FormElementErrors’,
    ‘formrow’ => ‘Events\Form\View\Helper\FormRow’),
    );

    But getting this error and I’m a little bit lost. Can you give me a little bit of your zend2 wisdom to guide me?

    Argument 1 passed toXXXXX\\FormRow::render() must be an instance of Events\\Form\\View\\Helper\\ElementInterface, instance of Zend\\Form\\Element\\Select given, called in XXXX/vendor/zendframework/zendframework/library/Zend/Form/View/Helper/FormRow.php on line 107

    Thanks

  25. […] post about creating Controller pLugin in ZF2. For what have to do to create a View Helper , see : my post about creating view helper or EvanDotPro’s […]

  26. Mohammad Nomaan Patel said, on January 23, 2014 at 8:40 pm

    Hi,
    I would like to create view helper for setting attributes for select options
    For example

    128 x 128

    64 x 64


    This width & height attribute would be set on runtime.
    Plz Help

  27. Mohammad Nomaan Patel said, on January 23, 2014 at 8:50 pm
    <select>
    	<option value="1" width="128" height="128">
    		128 x 128
    	</option>
    	<option value="2" width="64" height="64">
    		64 x 64
    	</option>
    </select>
    

    Sorry for posting this replies multiple times…….

  28. Flavio Portela said, on March 8, 2014 at 4:34 am

    Reblogged this on Flavio's Blog and commented:
    Ejemplo para crear Views Helpers en ZF2

  29. Iwan said, on May 6, 2014 at 11:27 am

    Om, mau tanya.. kalau mau buat fungsi tanggal, hari ,bulan versi Indonesia, harus pake view helper kah om??
    boleh kasih sedikit tips ga sama ane.. masih baru belajar om… 🙂

    Makasih banyak om…

  30. Amit said, on July 22, 2014 at 4:05 pm

    Hello Samsonasik,
    I need your help .
    I want to show some data from model to footer.phtml/layout.phtml .
    I am trying it with custom view helper but there is problem of database connectivity .
    is there another way to do this .

    If i seprate header.phtml ,footer.phtml and menu.phtml and want to some data module wise then how shoild i approach please help.

  31. දිනුක තිලංග said, on October 22, 2014 at 8:53 pm

    Thanks. It is works for me.

  32. Ashim said, on January 6, 2015 at 7:03 pm

    I am trying to create a custom view helper in zf2 for testing

    I created it as below…
    inside Application\Application\View\Helper\LiveStreaming.php

    inside Application\Module.php

    array(

    ‘liveStreaming’ => function($name) {
    return new View\Helper\LiveStreaming($name);
    },
    ),
    );
    }
    ?>

    Now I am calling that view inside different model call News

    News\view\news\news\index.phtml

    liveStreaming(‘Ivan Gospodinow’); ?>

    its not giving any response. Can you please tell me where I am doing mistake. I have checked almost all your post example, but not getting my answer.

    Thank you in advance.

  33. Kamatchi panneer selvam said, on February 11, 2015 at 5:51 pm

    thank you samsonasik. very nice it’s very helpful to me

  34. may saghira said, on March 12, 2015 at 10:51 pm

    Hi samsonasik , first thanks for the tuto ,
    it worked perfectly with one viewHelper , plz how can we add an other view helper and add declare it in the Module.php under factories , i tried my best but can’t get it ….
    public function getViewHelperConfig()
    {
    return array(
    ‘factories’ => array(
    ‘test_helper’ => function($sm) {
    $helper = new View\Helper\Testhelper ;
    return $helper;
    }
    )
    );
    }

    • samsonasik said, on March 13, 2015 at 12:33 am

      add more view helper in different key with different name

      • may saghira said, on March 13, 2015 at 12:38 am

        is it like this :
        return array(
        ‘factories’ => array(
        test_helper=> function() {
        $helper = new View\Helper\Testhelper () ;
        return $helper;
        },
        ‘enabling’ => function() {
        $helper = new View\Helper\Enabling ();
        return $helper;
        },
        )
        );

        waiting for your answer … thanks

      • samsonasik said, on March 13, 2015 at 1:21 am

        that should work, but remember that if you don’t need dependency when creating an instance, you don’t need factories, use invokables instead, read https://samsonasik.wordpress.com/2013/01/02/zend-framework-2-cheat-sheet-service-manager/

    • may saghira said, on March 13, 2015 at 4:08 pm

      yeah , it works …. i know that there ‘s two ways to declare view helpers in ZF2 under invokables and factories.
      thanks a lot

  35. Madhav Subedi said, on June 24, 2015 at 11:53 am

    Hey,
    I need to access session from main layout file. please suggest

  36. Khunshan Ahmad said, on July 19, 2015 at 10:57 pm

    Can I use a variable in ViewModel array in view helper also like I use in view $this->someVariableFromController? If No then how.

    • samsonasik said, on July 21, 2015 at 4:04 pm

      view helper is not intended to grab viewHelper variable, if you need, you could just pass the variable to view helper method. $viewhelper->method($viewModelVariables); and proceed inside the method body.

  37. Manoel Filho said, on August 12, 2015 at 9:55 am

    I learn a lot from your blog. Very good

  38. Fernando Jr said, on September 4, 2015 at 7:02 am

    Very Thanks!!!!!!!!!!!!!!!!!!!!!!! ‘-‘

  39. Cyrilb said, on November 30, 2015 at 8:05 pm

    You’re the best bro!
    Thanks a lot for all your tutorials.
    They really help me

  40. Tan said, on June 19, 2016 at 12:20 am

    great !:)

  41. krupal patel said, on October 22, 2016 at 12:48 pm

    Grt Job 😀

    As per this code helper is used for particular module. Is it possible global helper for all module or helper in autoload like Codeiigniter.

  42. Madeline said, on April 22, 2017 at 11:57 pm

    Trank you for made this example (Y)


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

%d bloggers like this: