You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Django-Bootstrap循环遍历异常:模态框仅显示首个对象属性

问题根源:重复的模态框选择器

嘿,这绝对不是Bootstrap的锅——是你代码里的一个小疏忽:循环里的所有模态框都使用了同一个类名.bd-example-modal-xl作为data-target,Bootstrap在匹配模态框时只会找到第一个符合选择器的元素,所以不管你点哪张缩略图,都会弹出第一个模态框,自然显示的是第一个画作的属性。

解决方案1:给每个模态框分配唯一ID

最简单的修复方式是利用每个painting对象的唯一标识(比如pk),给每个模态框生成独一无二的ID,让缩略图的data-target精准指向对应的模态框。修改后的代码如下:

{% for painting in artist.paintings.all %}
  <!-- 缩略图:指向当前画作的专属模态框 -->
  <img class="painting" 
       src="{{ painting.Gemälde.url }}" 
       data-toggle="modal" 
       data-target="#painting-modal-{{ painting.pk }}" />
  
  <!-- 专属模态框:ID包含当前画作的pk -->
  <div class="modal fade bd-example-modal-xl" 
       id="painting-modal-{{ painting.pk }}" 
       tabindex="-1" 
       role="dialog" 
       aria-labelledby="modal-title-{{ painting.pk }}" 
       aria-hidden="true">
    <div class="modal-dialog modal-xl" role="document">
      <div class="modal-content">
        <button type="button" class="close" data-dismiss="modal" aria-label="Close">
          <span aria-hidden="true">&times;</span>
        </button>
        <h5 class="modal-title mx-auto" id="modal-title-{{ painting.pk }}">{{ painting.Bildname }}</h5>
        <img class="painting-active" src="{{ painting.Gemälde.url }}">
        <div class="modal-footer">
          <p class="mx-auto">
            {{ painting.Bildtechnik }}, {{ painting.Erstelldatum }}, {{ painting.Bildmaße_in_cm }}cm
            {% if painting.Bildpreis != 0 %}
              , {{ painting.Bildpreis }}
            {% endif %}
          </p>
        </div>
      </div>
    </div>
  </div>
{% endfor %}

这里做了几个关键调整:

  • 把循环变量名改成单数painting(更符合语义)
  • 给每个模态框的ID加上painting.pk,确保唯一
  • 缩略图的data-target对应到当前画作的模态框ID
  • 模态框的aria-labelledby属性也用了唯一的标题ID,符合无障碍规范

解决方案2:用单个模态框动态加载内容(更高效)

如果你的画作数量很多,生成一堆模态框会增加DOM体积,推荐用一个模态框+JavaScript动态填充内容的方式,性能更好:

第一步:在循环外写一个空的模态框模板

<div class="modal fade bd-example-modal-xl" id="painting-modal" tabindex="-1" role="dialog" aria-labelledby="painting-modal-title" aria-hidden="true">
  <div class="modal-dialog modal-xl" role="document">
    <div class="modal-content">
      <button type="button" class="close" data-dismiss="modal" aria-label="Close">
        <span aria-hidden="true">&times;</span>
      </button>
      <h5 class="modal-title mx-auto" id="painting-modal-title"></h5>
      <img class="painting-active" src="">
      <div class="modal-footer">
        <p class="mx-auto" id="painting-modal-details"></p>
      </div>
    </div>
  </div>
</div>

第二步:给循环里的缩略图添加自定义数据属性

把画作的所有需要展示的属性存在图片的data-*属性里:

{% for painting in artist.paintings.all %}
  <img class="painting" 
       src="{{ painting.Gemälde.url }}" 
       data-toggle="modal" 
       data-target="#painting-modal"
       data-image-url="{{ painting.Gemälde.url }}"
       data-title="{{ painting.Bildname }}"
       data-technique="{{ painting.Bildtechnik }}"
       data-date="{{ painting.Erstelldatum }}"
       data-size="{{ painting.Bildmaße_in_cm }}"
       data-price="{% if painting.Bildpreis != 0 %}{{ painting.Bildpreis }}{% endif %}" />
{% endfor %}

第三步:用JavaScript动态填充模态框内容

监听模态框的show.bs.modal事件,从触发的图片元素里读取数据,填充到模态框中:

$('#painting-modal').on('show.bs.modal', function (event) {
  // 获取触发模态框的图片元素
  const triggerBtn = $(event.relatedTarget);
  
  // 读取自定义数据属性里的内容
  const imageUrl = triggerBtn.data('image-url');
  const title = triggerBtn.data('title');
  const technique = triggerBtn.data('technique');
  const date = triggerBtn.data('date');
  const size = triggerBtn.data('size');
  const price = triggerBtn.data('price');

  // 获取模态框元素,填充内容
  const modal = $(this);
  modal.find('#painting-modal-title').text(title);
  modal.find('.painting-active').attr('src', imageUrl);
  
  // 拼接详情文本
  let detailsText = `${technique}, ${date}, ${size}cm`;
  if (price) {
    detailsText += `, ${price}`;
  }
  modal.find('#painting-modal-details').text(detailsText);
});

这种方法只需要一个模态框,不管有多少画作都不会增加DOM负担,尤其适合大量数据的场景。


内容的提问来源于stack exchange,提问作者Dariun

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.07 08:07:34