picocms / Pico

Pico is a stupidly simple, blazing fast, flat file CMS.
http://picocms.org/
MIT License
3.83k stars 617 forks source link

Adding Twig functions to use in themes #424

Closed wlabarron closed 6 years ago

wlabarron commented 6 years ago

Hi there.

I'm trying to add a custom function to Twig which I can use on any of my theme pages.

Twig supports this through extensions (relevant Twig documentation + various other webpages about it) but I don't know how to implement this into Pico without modifying the core, which is both probably not a good idea and even when I tried to I couldn't make it work.

Has anyone tried anything like this? How can I add custom Twig functions to use in my Pico themes?

PhrozenByte commented 6 years ago

Pico uses a event-based system that allows you to hook into Pico's processing. Have a look at Pico's plugins/DummyPlugin.php, Pico's class docs and the developer docs (still WIP, help is highly appreciated).

Specifically refer to the $twig parameter of the onPageRendering event - this is the Twig_Environment object you need to register your custom filters, functions, tests, tags or extensions.

wlabarron commented 6 years ago

Thanks for the quick response!

I've duplicated DummyPlugin, set $enabled to true and written this:

public function onPageRendering(Twig_Environment &$twig, array &$twigVariables, &$templateName)
    {
      $testFunction = new Twig_Function('testFunction', function () {
        return "Test works!";
      });
      $twig->addFunction($testFunction);
    }

When I open a page in my browser I get a totally blank page - I'm not even calling the function anywhere. What am I doing wrong? The PHP I'm familiar with is a lot simpler than this so sorry if this is something totally straightforward I'm missing.

PhrozenByte commented 6 years ago

Check your server's error.log, you likely got an PHP Parse Error somewhere :wink:

wlabarron commented 6 years ago

Aha! Error logged was PHP Fatal error: Uncaught Error: Cannot instantiate abstract class Twig_Function. I went into vendor/twig/twig/lib/Twig/Function.php which says that Twig_Function is deprecated and Twig_SimpleFunction should be used instead. Swap that over, works perfectly! Thank you for your help, @PhrozenByte.

So for anyone looking to add a custom Twig function using a Pico plugin, this is what I ended up with in my plugin:

public function onPageRendering(Twig_Environment &$twig, array &$twigVariables, &$templateName)
    {
      $testFunction = new Twig_SimpleFunction('testFunction', function () {
        return "Test works!";
      });
      $twig->addFunction($testFunction);
    }
wlabarron commented 6 years ago

Would this be something useful for the developer docs? If so, I’m happy to do a little write-up.

PhrozenByte commented 6 years ago

Sure! :+1: :smiley: You can find the developer docs in the _development directory of the picocms/picocms.github.io repo: https://github.com/picocms/picocms.github.io/tree/master/_development