Search code examples
loopsforeachrowrangetemplate-toolkit

Template Toolkit - Render ranges of same loop in different rows


I'm trying to get a Template Toolkit [% FOREACH %] loop to split and render the items within a certain range into different rows.

What I've got so far:

<ul>
    <ul class="row-top">
    [% FOREACH news IN newsfeeds %]
    [% IF loop.index() < 3 %]
        [% INCLUDE content_news/news_item.tt %]
    [% END %]
    [% END %]
    </ul>
    [% FOREACH news IN newsfeeds %]
        [% IF loop.index() > 3 %]
            [% INCLUDE content_news/news_item.tt %]
        [% END %]
    [% END %]
</ul>

The output so far (got the first row right):

<ul>
    <ul class="row-top">
        <li class="item featured"></li>
        <li class="item"></li>
        <li class="item last"></li>
    </ul>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
</ul>

The ideal output markup:

<ul class="top-row">
    <li class="item featured"></li>
    <li class="item"></li>
    <li class="item last"></li>
</ul>
<ul class="row">
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item last"></li>
</ul>
<ul class="row">
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item last"></li>
</ul>
<ul class="row">
    <li class="item"></li>
    <li class="item"></li>
    <li class="item"></li>
    <li class="item last"></li>
</ul>

The situation:

Because list items might have different heights, they can't just float left. They need to be rendered in different rows. The foreach loop should open and close the tags as shown in the markup above.

Because the featured item is twice as wide as a default item (think 4 columns grid), the first row (.top-row) has only three items.

All this should preferably be rendered from the same foreach loop, since the data is coming from the same source.

The intention is to get this done in Template Toolkit, but any method that shows the logic behind the idea would be appreciated!

Cheers, W.


Solution

  • I would slice the list:

    [% featured_items = newsfeeds.slice(0,2) %]
    [% normal_items  = newsfeeds.slice(3) %]
    
    <ul class="row-top">
        [% FOREACH news IN featured_items %]
            [% INCLUDE content_news/news_item.tt %]
        [% END %]
    </ul>
    <ul class="row">
        [% FOREACH news IN normal_items %]
            [% INCLUDE content_news/news_item.tt %]
            [% IF ( loop.count % 4 ) == 0 %]</ul><ul class="row>[%END%]
        [% END %]
    </ul>