is it possible to add multiple filters in twig ?
for example i have this single filter
$app->twig->addFilter('_bah',new Twig_Filter_Function('_bah'));
if i want to add all my functions ill do this
$app->twig->addFilter('_bah1',new Twig_Filter_Function('_bah1'));
$app->twig->addFilter('_bah2',new Twig_Filter_Function('_bah2'));
..... etc
if i have many functions i want to use inside Twig template but without calling them by class name like {{ classname.method }} , i want to call them as a filter like {{ "bla bla bla"|trim_me}} is it possible ?
You can create an extension in Twig...
The main motivation for writing an extension is to move often used
code into a reusable class like adding support for
internationalization. An extension can define tags, filters, tests,
operators, global variables, functions, and node visitors.
Creating an extension also makes for a better separation of code that
is executed at compilation time and code needed at runtime. As such,
it makes your code faster.
Most of the time, it is useful to create a single extension for your
project, to host all the specific tags and filters you want to add to
Twig.
http://twig.sensiolabs.org/doc/advanced.html#creating-an-extension
Then you just need one line...
$twig->addExtension(new My_Twig_Extension_Class());
Related
For instance in the Timber Documentation we have lots of examples like the following:
{% for item in menu.items %}
{{ post.author.name }}
Now the "item" and the "menu" etc. are all predefined, and nowhere defined by a user in the files (otherwise by my understanding Timber and TWIG would not make much sense).
What I do not understand is where I can find out a list these. In the Docs of Timber, there are a bunch of examples, then when I compare them to the Timber Starter Theme for Wordpress, I see a bunch of them, which aren't even mentioned in the documentations.
Where do I find a list of all available items?
What is the logic behind these items?
Don’t feel dumb, because you’re not! We’ve all been there. I had the same questions, when I started out with Timber. We’re trying to improve the documentation constantly, so questions like these help us to find out what we can do better 👍.
Whenever you see a variable in Twig, it can actually come from a couple of different places:
Variables from the global context
There’s a filter that most of us use to make a variable globally available whenever you set up your context through Timber::get_context(). When you see {% for item in menu.items %}, then it’s probably from the section of the docs about «Setting up a menu globally». I have to admit that we explain the filter through this example only, which is not ideal. But we’re changing this. In the next version of Timber, we try to explain the global context better (make sure to only read the section about the global context, because the part about «Template Contexts» describes functionality that is not available yet.)
Variables from the template
Consider the following example:
$context = Timber::get_context();
$context['post'] = new Timber\Post();
Timber::render( 'single.twig', $context );
Here you set up your context through Timber::get_context(). When you use Timber::get_context(), you’ll get a bunch of variables that make sense globally, but not for every template.
The $context variable is an array, holding all the variables you want to pass to your Twig template, in this case single.twig. When can add our own variables, like in the example above, where we add post that hold a Timber\Post object of the currently displayed post.
Variables from Timber’s classes
In the template, when you see {{ post.author.name }}, then author can be different things:
A property of the Timber\Post object that holds a value. These are all the variables that you’d see when you do {{ dump(post) }}.
A method of the Timber\Post object, that will be excecuted. This might be confusing at first, because in PHP, you always need to add braces to call a function, but in Twig, you don’t need to. When you call $post->author() in PHP, you would use post.author in Twig. To see a list of all the methods that are available for Timber\Post, you need to look into the Reference section for Timber\Post in the docs.
So if you would write the example {{ post.author.name }} in PHP, it would look like this:
$post->author()->name()
So author is a method of Timber\Post, which returns a Timber\User object. The Timber\User object has a method called name, which returns «the human-friendly name of the user».
But! When you just look at {{ post.author.name }}, it could also be a multi-dimensional array that you defined yourself:
$context['post'] = array(
'author' => array(
'name' => 'Tom Riddle',
),
);
You wouldn’t know that just from looking at it in Twig.
Variables from the Twig syntax
When you see {% for item in menu.items %}, then you’re looping over the variable menu.items. The variable menu probably comes from the global context (a Timber\Menu object), and items is a property of this object. The item variable is a new variable that is created to access the current loop item in the for loop. In this example, it’s the current menu item. You can choose any name for item you want.
Variables from includes
You can pass down a variable in Twig through the include statement. For example, if you defined post through your template file and wanted to use a different name in the template that you include, you could use it like this:
{% include 'teaser.twig' with { teaser: post } %}
Coming back to your specific questions:
Where do I find a list of all available items?
What is the logic behind these items?
I’m afraid there isn’t a definitive list, because what a variable is can be very dynamic. It’s mostly a combination of the global context, variables you set from the template, methods and properties from Timber’s classes as well as variables you define yourself in Twig.
If you have more question, add the to this answer as comments and I can update this answer accordingly.
I come from the procedural PHP and am learning OOP with Laravel. What I learned so far is very interesting and will ease my developer's life (it's not my job btw).
So, for all my websites, I am using a slug property for all articles, categories, and so on.
I started to use the "str_slug" provided by Laravel which seems to do the job at 99%. The issue I get is when I have such title (in french): "J'ai mangé une pomme", the slug string I get is: "jai-mange-une-pomme" which, in french, is not correct. I would like "j-ai-mange-une-pomme".
It's not really an issue. I can do:
$slug = str_replace('\'','_',$input['name']);
$slug = str_slug($slug, '-');
It suits me well but I wonder how to use anytime I want to use it. I don't want to write it again and again and again.
In procedural, it's easy, I would write a function, such as thePerfectSlug(){} in a helpers.php file (still an example) and will use an include at the top of my index.php. That would do the job.
But in OOP and especially in Laravel (5.1), how can I do that?
Thanks
You still can achieve it with normal function. Laravel uses his own function which are stored in helpers.php file. You can make your own helpers.php file and add it to your main composer.json file at autoload.files.
If you would like to do it in OOP way, create a trait like App\Traits\Sluggify with your method and use it in any class that needs it.
I have a template which calls a number of built in macros which I am including this template from several other places.
Sometimes, I need all of the macros to be called like this:
{{ Form::label('foo', 'Foo') }}
Other times I need them all to be called like this:
{{{ Form::label('foo', 'Foo') }}}
At the moment, I have two separate templates which are identical except for the extra { }, which means I have to edit two files every time I want to change anything.
Is there a way to switch the auto escaping on/off, so that I can use the same file for both situations?
Thanks
No, there's no feature in Laravel that would allow you to do that -- additionally, it'd probably be a bad idea from a code maintenance/security-audit point of view. Looking at a template a few weeks later and not knowing which variables were or were not escaped would be madness.
If you need to do this, "The Right" way would be to extend Blade with your own directive -- something like #escapeIsConfigIsOn and then put your logic for when to escape content in there. The top level function e is what blade uses internally for escaping.
#File: login/vendor/laravel/framework/src/Illuminate/Support/helpers.php
function e($value)
{
return htmlentities($value, ENT_QUOTES, 'UTF-8', false);
}
in smarty Smarty_Compiler.class.php performed some operation between two tags like {if}{/if}
if i want to get text within the new tag then how to proceedi tried inside
function _compile_tag($template_tag)
{
....
switch ($tag_command) {
-----
case 'newtag':
break;
case '/newtag':
break;
}
How can i get the content of tpl within the new tag
You should create a Smarty plugin. You can read documentations here (about extending Smarty) and here (more specific, about create block functions plugins).
Basically, you have to create your smarty_make_pdf() PHP function (see parameters in the second link I gave you), place it in a file called block.make_pdf.php (see here) and tell Smarty to search for plugins in the folder you created that file using $smarty->addPluginsDir() (see here).
PS: I'm supposing you are using Smarty 3.
You really shouldn't be editing the core Smarty code to achieve this.
Look into registerPlugin() if you're using Smarty 3 (or register_block() if you're on Smarty 2).
These methods will allow you to create your own Smarty tags and write handler functions that implement them.
I'm using CodeIgniter, and will likely use their template library as I want to keep things extremely simple to use. The content for the template variables will come from the database, but I want the business admins to know what content areas are available. Basically the names of the parameters when they choose a specific template. For instance, Joomla uses an extra XML file that defines each area, whereas Wordpress uses comments within a page template to inform the system that the PHP file is a template. I like the Joomla approach because you don't have to parse the PHP file to find the areas, but I like the Wordpress approach because you don't have an extra XML file associated with every template. Are there other approaches that I'm missing?
I think the nicest way would be to add a small hack to the template parser class. The code looks quite readable and clean in system/libraries/Parser.php. You could insert a hook in that class that can be used to keep track of the variables. I don't know, if it works, but here's a snippet:
class CI_Parser {
var $varCallback;
function setVarCallback($callbackFunction) {
$this->varCallback = $callbackFunction;
}
...
function _parse_single(...) {
$callback = $this->varCallback;
$callback($key);
}
...
//Somewhere in your code
function storeVarName($variableName) {
// Persist the variable name wherever you want here
}
$this->parser->setVarCallback('storeVarName');
You could do this directly in the controller:
// in the controller
print_r($data);
$this->load->view("main", $data);
Or a little more rudimentary, but you could pass to the template a PHP array of variables (or an object):
// in the controller
$data = array();
$data["namespace"] = array(
"title" => "My website",
"posts" => array("hi", "something else")
);
$this->load->view("main", $data);
And then in the view, have a flag to print_r the namespace to show all the vars available, so that business admins know exactly what to use.
// in the view
if(isset($namespace["showAllVars"])) print_r($namespace);
One option would be to call token_get_all on the PHP file (only when your business admins are loading it up), and parse the output of that.
The best approach, in my opinion, is to keep the variable definitions in another place (such as a database table, or a separate file). This will help with testing (i.e., a programmer can't just remove a tag and it's gone) and making sure things are still working as you move on with the application development in time.
Another advantage is that your application logic will be independent from the templating engine.
On a side note, if you expect a lot of traffic, you may consider using smarty instead. We have done extensive testing with most of the templating engines around and smarty is the fastest.