Вопрос

В настоящее время я предлагаю свою функцию в классе и передаю экземпляр этого класса в шаблон и вызовете мою необходимую функцию в качестве метода класса.

{{ unneededclass.blah() }}

Мне нужно сделать как ниже

{{ blah() }}

Является ли это возможным?

Это было полезно?

Решение

Обновление 5/14/2015

Комментаторы указывают, что я в основном неправ. Если вам действительно нужна функция, а не фильтр или макрос, вы можете сделать это как предложен в документах Twig:

$twig = new Twig_Environment($loader);
$function = new Twig_SimpleFunction('blah', function () {
   // ...
});
$twig->addFunction($function);

И использовать вроде

{{ blah() }}

Короче говоря, нет, это невозможно.

Однако надежда не потеряна!

Фильтры

Если эта функция blah() ваших предназначен для изменения существующей переменной, то это фильтр.

Пример:

//in your PHP
function format_date($date_string,$format_string) {
    return date($format_string,strtotime($date_string));
}
$twig_env->addFilter('format_date',new Twig_Filter_Function('format_date'));

{# in your template #}
{{ some_date|format_date('n/j/Y') }}

(Первый аргумент - это переменная, которую вы фильтруете, второй поставляется нормальным средством)

Макрос

Если, как вы указали выше, ваша функция просто выводит HTML, то это хороший кандидат на макрос.

Пример:

{# in your template #}
{% macro say_hello() %}
<p>Oh! Hello, world!</p>
{% endmacro %}

{# ... later on ... #}
{{ _self.say_hello() }}

Или с параметрами:

{% macro input(name,value,type) %}
<input type="{{ type|default('text') }}" name="{{ name }}" value="{{ value }}">
{% endmacro %}

{{ _self.input('phone_number','867-5309') }}
{{ _self.input('subscribe','yes','checkbox') }}

Почему?

То, что нужно помнить, это то, что шаблоны веточки представляют собой Посмотреть, с точки зрения MVC. Это означает, что они изолированы в терминах их окружающей среды и могут только представлять контекст вы передаете их через массив данных, которые вы проходите в $template->render() метод.

Это хорошая вещь, так как он каникует вашу презентацию от вашей логики и данных. Если вы можете произвольно вызывать функции, вы вдруг увеличиваете эту связь, что является плохой предмет.

Другая причина для этого - это способ обратных обратных вызовов PHP. Подумайте о том, как вам придется пройти эту функцию в свой шаблон ... наверное что-то подобное:

function blah() {
    return "<p>Oh! Hello, world!</p>";
}

$template = $twig_env->loadTemplate('template.html');
echo $template->render(array('blah'=>'blah'));

В вашем шаблоне переменная контекста blah теперь просто строка, содержащая 'blah'.

В Vanilla PHP, когда вы используете переменные функции, такие как это (попробуйте использовать строку переменной, такой как функция), она (более или менее) выполняет поиск для этой функции, затем вызывает его. Ты нет Передача функции, просто это имя.

Дело в том, что вы не можете передавать функцию в шаблон, потому что только механизм PHP для этого является строкой имени, и один раз внутри шаблона, это имя больше не является именем функции и просто строка.

Немного давно завещал, но я надеюсь, что помогает!

Если вы хотите больше документирования, официальные документы здесь.

Другие советы

Я был таким потерян, как вы были, мой друг, но после поиска в Интернете за ответ и не нашел ничего, я решил посмотреть, смогу ли я сделать это сам. Поэтому я хотел опубликовать свое решение здесь (хотя я знаю, что этот пост старый), потому что это первый удар в Google, если вы ищете эту проблему.

Вот идет, это довольно просто на самом деле:

Я сделал класс, который содержит мои функции и переменные, например:

class functionContainer{
        function getRandomNumber()
        {
                return rand();
        }
}
$values = array(
'functions'=> new functionContainer()
);

Итак, теперь у нас есть $ значения как массив, который содержит этот объект с функцией «getrandomnumber ()».

При рендеринге файла шаблона включите этот класс в качестве значения:

$twig->render('random.html', $values);

Таким образом, внутри файла шаблона вы можете просто позвонить в этот метод, чтобы вызвать функцию и получить свой результат:

{{ functions.getRandomNumber }}

Хотя вы не можете PHP Callable напрямую, Twig расширяется. Вы можете добавить Callable Filter, поэтому вы можете применить к функциям PHP, передаваемые шаблону.

namespace My\Twig\Extension;

class LambdaFilter extends \Twig_Extension {

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

    public function getFilters() {
        return array(
            new \Twig_SimpleFilter('call', array($this, 'doCall'))
        );
    }

    public function doCall() {
        $arguments = func_get_args();
        $callable = array_shift($arguments);
        if(!is_callable($callable)) {
            throw new InvalidArgumentException();
        }
        return call_user_func_array($callable, $arguments);
    }

}

Теперь, если вы проходите переменную my_func шаблон, вы можете сделать my_func|call(arg1, arg2). Отказ Вы можете даже сделать функции высшего порядка "array_filter"|call(my_array, my_func) И вы всегда можете сделать больше вещей в фильтре, как принятие массива в качестве параметров и так далее.

Полный ответ:http://twig.sensiolabs.org/doc/advanced.html#id2.

Я предпочитаю использовать расширение Twig, как это:

namespace Some\Twig\Extensions;

class MenuExtensions extends \Twig_Extension
{
    public function getFunctions()
    {
        return array(
            new \Twig_SimpleFunction('sidebar_menu', [$this, 'generate_sidebar_menu']),
        );
    }

    public function generate_sidebar_menu($menu){
        return $menu;
    }

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

В шаблоне:

{{ sidebar_menu('some text') }}

С использованием Анонимный класс

Создать анонимный класс в Manager / Controller / Service ..

     $functions = new class($router)
    {
        public function __construct($router)
        {
            $this->router = $router;
        }

    public function getRowUrl(FileManager $fileManager)
    {
        if ($fileManager->isNode()) {
            return $this->router->generate('...', ['parent' => ...]);
        }
        return $this->router->generate('...', ['entity' => ...]);
    }
};

Вставить параметр в просмотр

$params=[
            'functions' => $functions

        ];



    return new Response($this->twig->render('...:index.html.twig', $params));

Использовать функцию ввиду

 {% set rowUrl = functions.rowUrl(entity) %}
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top