4

I found several solutions to build a dynamic, complex navigation in craft. One is described here: Adding active class to globally cached navigation. Now i would like to create a more powerfull twig filter for creating different navigation and breadcrumb types with selecting of active links. I already wrote some test code in plain php and used for this the library simplehtmldom (helper for changing dom elements in php like in jquery). A demonstration about what i want to do can be found here: http://www.bahu.ch/craft/. Now i started with creating the twig filter, but i can't include the library in my plugin. Here is a quick overview of my plugin code.

   <?php 
   namespace Craft;
   use Twig_Extension;

   use Twig_Filter_Method;

Now i need to include the library (i know, that the next line is incorrect)

   include('simple_html_dom.php');

   class k4NavigationTwigExtension extends \Twig_Extension

   {


public function getName()
{
    return 'k4Navigation';
}

public function getFilters()
{
    return array(
        'k4Navigation' => new Twig_Filter_Method($this, 'k4Navigation'),
    );
}

public function k4Navigation($navigation)
{

    $html = str_get_html($navigation);

on the next line the current url should replace the string "test.html"

    $selectElem = $html->find('a[href="test.html"]')[0];

    if (is_object($selectElem)){
       // loop li and set class active
        for ($i = 1; $i <= 20; $i++) {
            $selectElem->setAttribute("class","active");
            $selectElem =  $selectElem->parent();
            if (!is_object($selectElem)){
                break;
            }
        }    
    }

    return $html;

   }

   }

Maybe someone can give me a hint, how to includ the library and the first example? You can download the full test code and started plugin from here: https://github.com/tombauer/k4-navigation

Many thanks for any help!

Sunny regards Tom

2
  • It's a bit difficult to figure out exactly what your question is. Can you be more specific? Commented Apr 14, 2015 at 18:16
  • I updated the question and hope it's now more specific. I simple like to include my standalone php code as a twig filter.
    – Tom Bauer
    Commented Apr 14, 2015 at 19:16

2 Answers 2

2

In your plugins main file add the following:

public function addTwigExtension()
{
    Craft::import('plugins.myplugin.twigextensions.myTwigExtension');

    return new MyTwigExtension();
}

In your plugin folder, add a new folder called 'twigextensions'.

In the new 'twigextensions' folder, add your twig filter 'MyTwigExtension.php'.

<?php

namespace Craft;

use Twig_Extension;
use Twig_Filter_Method;

class MyTwigExtension extends \Twig_Extension
{

    public function getName()
    {
        return 'My Twig Extension';
    }

    public function getFilters()
    {
        $returnArray = array();
        $methods = array(
            'myfilter',
        );

        foreach ($methods as $methodName) {
            $returnArray[$methodName] = new \Twig_Filter_Method($this, $methodName);
        }

        return $returnArray;
    }

    public function myfilter($content)
    {
        // perform filter operations

        return "My Filter Result";
    }

}

You can thank Luke Holder's twig extension craft-inflect for this!

8
  • Dear Douglas thank you for the answer. Whit the code i did now my plugin setup, but it does still not work. When i try to use the filter, it ends with a error "Undefined offset: 0". Maybe there is still a problem with including the needed library? Here is the link to the PHP and Plugin-Code link. Maybe you see the problem?
    – Tom Bauer
    Commented Apr 15, 2015 at 10:15
  • 1
    @giveandfindhelp See this question for some expert opinions on how to include third party libraries/classes in Craft plugins. Commented Apr 15, 2015 at 11:37
  • @MatsMikkelRummelhoff Thanks. I updated the plugin, but it has still the same error. I added a better description in github to explain what i try to do - see github.com/tombauer/k4-navigation.
    – Tom Bauer
    Commented Apr 15, 2015 at 11:58
  • That specific error message – Undefined offset: 0 – just means that you attempted to access the first index of an array, and the array is either empty, or not an array at all. You have several calls like this in your code: $selectElem = $html->find( $selectedFilter)[0];; note that if $html->find() returns a falsey value (or an empty array), you'd get the error message above when trying to access specific indexes. You should test whatever $html->find() returns (e.g. using empty() and is_array() before attempting to access that return value's data. Commented Apr 15, 2015 at 12:10
  • 1
    I have to say though, that this is going into general PHP territory, and as such is technically outside of the scope for this site. I'd recommend looking to the main Stack Overflow site for any general PHP or Simple HTML DOM related questions or issues, as those aren't really related to Craft in any way :) Commented Apr 15, 2015 at 12:12
4

Douglas McDonald's answer is correct with one issue though. The import statement is actually case sensitive

Craft::import('plugins.myplugin.twigextensions.MyTwigExtension');

I also have 2 additional notes:

  • The getName() method is deprecated so you shouldn't bother with it
  • The getFilters() method can be written much shorter, for example:
public function getFilters()
{
    return [
        'myfilter' => new \Twig_Filter_Method($this, 'myfilter'),
    ];
}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.