Давайте рассмотрим ещё одну новую возможность, появившуюся в Laravel 5.3.
Что такое директивы Blade?
Язык шаблонов Laravel Blade предоставляет нечто, называемое «директивы», которые представляют собой настраиваемые теги для часто используемых управляющих структур, начинающиеся с символа @. Если вы когда-нибудь писали шаблоны в Blade, то скорее всего знаете @if, @foreach и т.д.
Вообще, эти директивы управляющих структур просто эмулируют соотвествующие PHP-аналоги. Например, PHP@if(condition)
— это то же самое, что и PHP<?php if (condition):
.
Знакомство с переменной PHP$loop
В версии 5.3 директива PHP@foreach
обрела немного суперсилы в виде переменной PHP$loop
, которая доступна в каждом цикле PHP@foreach
.
Переменная PHP$loop
— объект stdClass, предоставляющий метаданные того цикла, в котором вы сейчас находитесь. Посмотрите на её свойства:
- index — индекс текущего элемента в цикле от нуля; 0 означает «первый элемент»
- iteration — индекс текущего элемента в цикле от единицы; 1 означает «первый элемент»
- remaining — сколько элементов осталось в цикле; если текущий элемент первый из трёх, то вернётся 2
- count — число элементов в цикле
- first — логическое; первый ли это элемент в цикле
- last — логическое; последний ли это элемент в цикле
- depth — целое число; на каком уровне вложенности данный цикл; вернёт 1 для цикла, 2 для цикла в цикле, и т.д.
- parent — если данный цикл находится внутри другого цикла
PHP@foreach
, вернёт ссылку на переменнуюPHP$loop
для элемента родительского цикла; иначе вернёт null
Большинство из них довольно очевидны, а значит вы можете делать вот так:
<ul>
@foreach ($pages as $page)
<li>{{ $page->title }} ({{ $loop->iteration }} / {{ $loop->count }})</li>
@endforeach
</ul>
Но также вы получаете ссылку на родительские переменные PHP$loop
, когда работаете с вложенными циклами. Вы можете использовать depth, чтобы определить, вложен ли цикл, и parent для получения переменной PHP$loop
его родителя. Это открывает подобные возможности для использования шаблонов:
<ul>
@foreach ($pages as $page)
<li>{{ $loop->iteration }}: {{ $page->title }}
@if ($page->hasChildren())
<ul>
@foreach ($page->children() as $child)
<li>{{ $loop->parent->iteration }}.{{ $loop->iteration }}:
{{ $child->title }}</li>
@endforeach
</ul>
@endif
</li>
@endforeach
</ul>
Комментарии (11)
Зачем таким образом пародировать программный код? Не лучше ли сочинить его в контроллере и кинуть в представление как параметр?
P.S. А я так и знал — не получится в MVC по-человечески разнести логику и оформление.
Контроллер имеет минимум логики, от вытягивает данные из модели и передает в представление. Представление — это не только оформление. Перечислять (итерировать) данные ты в контроллере будешь?
Ну да. Раз уж пришлось работать в MVC (мне больше нравится мои собственные паттерны, но что делать — не кормят они...) — то очень поможет порядок: где что искать.
В моделях — ищем работу с базой(-ами).
В контрололерах — всю логику.
В представлениях — всё, что относится к вёрстке.
Птоэтому у меня представления короткие и почти лишенные логики. В них — верстка страницы.
Я поддерживабю проект, написанный другими разработчиками. Там представление — это «ад каннибалов». Вот чего я стараюсь избегать.
Это не MVC.
И ты не ответил, ты в контроллере данные будешь итерировать? Т.е. ты в контроллере будешь лепить что-то вроде:
по мне проще, если контроллер делегирует данные в переменную посредством функций, которые определенны в отдельном файле типа main_functions
а во view уже кидать отдельные массивы данных
У вас все посты совершенно в одном духе — как раньше было хорошо, как сейчас плохо. Причём без фактов и примеров, просто слова в вакууме.
Какая разница между представлением и логикой, если они пересекаются? Смысл их делить? Тогда уж писать всё в одном файле, как в WordPress, и не заморачиваться модными концепциями.
У вас все посты совершенно в одном духе — как раньше было хорошо, как сейчас плохо
Да ладно. Ничего подобного в моём комментарии нет.
Какая разница между представлением и логикой, если они пересекаются?
Никакой. От себя добавлю — они всегда пересекаются. Ну кроме каких-то совершенно «учебных» случаев.
Смысл их делить?
Никакого.
Тогда уж писать всё в одном файле, как в WordPress
Я никогда в жизни не агитировал за WordPress.
и не заморачиваться модными концепциями
Ну почему. Просто модные концепции нужно пробовать на зуб.
Кстати, хочу поделиться очень полезным сниппетом, показывающим насколько $loop - полезная переменная. Перечисление данных массива, разделенных запятой, когда запятую в конце ставить не нужно:
Только есть проблема с пробелами — т.к. у тебя там переводы строки и отступы, то в запятой + пробеле нет смысла, т.к. они и так подставляются. А вот убрать пробелы до запятой ты убрать не сможешь (если не ставить
cssfont-size: 0
и т.д.).Если контекст позволяет, то лучше решать через CSS (исчезает возможность копировать запятую, но иногда это даже полезно):
Если нет, то нужно ставить запятую после блока, причём без пробелов/новой строки перед ней, а вот это уже не так красиво.
Проблем с пробелами «почти нет», много использовал в реальном проекте (не только с запятой). Где-то помню проблема была. Решил тем, что в span обернул. За пример с CSS спасибо.
ОБЪЯСНИТЕ, ПОЖАЛУЙСТА ! Не понимаю до конца кусок вот этого кода:
<
ul> @foreach ($pages as $page)
Откуда title и почему к нему обращение через "->" ? И потом, в документации с директивами @contenu и @break Там в условиях обращение к каким-то type и number
Откуда они взялись, какую роль играют. Я пробовал этот код, приведённый в документации, но у меня не работает.
Вот, что написано в документации, но нифига не понятно как ограничить вывод при итерациях.
При работе с циклами вы также можете закончить цикл или пропустить текущую итерацию:
@foreach ($users as $user)
@if ($user->type == 1) @continue
@endif
{{ $user->name }}
@if ($user->number == 5)
@endif
@endforeach