在 AnQiCMS 的模板开发中,我们经常会遇到需要列表循环展示数据的情况,比如文章列表、产品分类、导航菜单等。在这些循环中,有时我们需要对列表的第一项或最后一项进行特殊处理,例如添加独特的 CSS 样式、显示不同的内容,或者巧妙地处理列表项之间的分隔符。AnQiCMS 采用了类似 Django 模板引擎的语法,为我们提供了非常直观且强大的工具来解决这类常见的模板逻辑问题。

核心机制:forloop 对象

在 AnQiCMS 的 for 循环中,系统会为每次迭代自动生成一个特殊的 forloop 对象。这个 forloop 对象包含了当前循环状态的详细信息,其中最常用且对判断首尾项至关重要的属性是 forloop.Counterforloop.Revcounter

  • forloop.Counter: 这个属性表示当前循环的迭代次数,它的计数是从 1 开始的。如果你需要一个从 0 开始的索引,可以自行调整。
  • forloop.Revcounter: 这个属性表示从当前项开始,到循环结束还剩余多少项。换句话说,它统计的是当前项以及其后所有项的数量。例如,如果一个列表总共有 5 项,第一项的 Revcounter 是 5,第二项是 4,依此类推,最后一项的 Revcounter 则是 1

了解了这两个属性后,判断循环中的首尾项就变得非常简单了。

判断第一项

要判断当前遍历的项是否是循环中的第一项,我们只需要检查 forloop.Counter 是否等于 1。这是一种非常直接和高效的方法。

例如,我们可能想给列表的第一项添加一个特殊的背景色:

{% archiveList articles with type="list" limit="5" %}
    {% for item in articles %}
        {% if forloop.Counter == 1 %}
            <div class="article-card first-highlight">
        {% else %}
            <div class="article-card">
        {% endif %}
                <h4><a href="{{ item.Link }}">{{ item.Title }}</a></h4>
                <p>{{ item.Description|truncatechars:100 }}</p>
            </div>
    {% empty %}
        <p>暂时没有文章可供显示。</p>
    {% endfor %}
{% endarchiveList %}

在这个例子中,当循环到第一篇文章时,它会额外获得 first-highlight 这个 CSS 类,方便我们进行样式上的区分,从而在视觉上突出显示列表的首项。

判断最后一项

判断当前项是否为循环中的最后一项,我们可以利用 forloop.Revcounter 属性。正如前面所解释的,当 forloop.Revcounter 的值等于 1 时,就意味着我们正在处理列表中的最后一项。

这在处理列表项之间的分隔符时特别有用。我们往往希望除了最后一项外,其他项后面都有一个分隔符:

{% categoryList categories with moduleId="1" parentId="0" %}
    <nav class="category-nav">
        {% for category in categories %}
            <a href="{{ category.Link }}">{{ category.Title }}</a>
            {% if forloop.Revcounter != 1 %}
                <span class="category-separator"> / </span>
            {% endif %}
        {% endfor %}
    </nav>
{% empty %}
    <p>没有找到任何分类。</p>
{% endcategoryList %}

这个例子展示了一个常见场景:在导航链接之间添加分隔符。通过判断 forloop.Revcounter != 1,我们确保只有在不是最后一项的时候才显示分隔符,避免了在最后一个分类后面出现不必要的分隔符,使页面布局更加整洁。

综合示例

为了更好地理解这两个属性的实际应用,让我们看一个结合了首尾项判断的例子,同时展示 forloop 的其他一些便捷信息:

”`twig

{% archiveList latestArchives with type="list" limit="6" order="CreatedTime desc" %}
    {% for article in latestArchives %}
        <div class="list-item
            {% if forloop.Counter == 1 %} is-first {% endif %}
            {% if forloop.Revcounter == 1 %} is-last {% endif %}"
        >
            <h3 class="item-title">
                <a href="{{ article.Link }}">{{ article.Title }}</a>
            </h3>
            <p class="item-meta">
                发布于:{{ stampToDate(article.CreatedTime, "2006-01-02