如何使用htmx更新多个同class的目标元素?
解决htmx更新多个同class目标元素的问题
htmx 默认情况下,hx-target 只会匹配第一个符合选择器的元素,所以你点击按钮后只有第一个 .details 会更新。要实现更新所有 .details 元素,有两种实用方案:
方案一:使用 Out of Band (OOB) 交换
让后端返回的 HTML 内容中,为每个需要更新的 .details 元素添加唯一 ID 和 hx-swap-oob="true" 属性,htmx 会自动匹配页面上对应 ID 的元素并替换内容。
示例:
前端按钮保持不变:
<button hx-get="/views/users/byId/someId" hx-target=".details">Details</button> <div id="details-1" class="details">first</div> <div id="details-2" class="details">second</div>
后端返回的响应内容:
<div id="details-1" class="details" hx-swap-oob="true">用户详情内容1</div> <div id="details-2" class="details" hx-swap-oob="true">用户详情内容2</div>
这种方式需要后端明确知道要更新的每个元素的唯一 ID,适合需要给不同 .details 元素设置不同内容的场景。
方案二:通过 JavaScript 事件手动更新所有元素
利用 htmx 的 htmx:afterRequest 事件,在请求完成后手动遍历并更新所有 .details 元素。
简洁版(使用 hx-on 属性):
<button hx-get="/views/users/byId/someId" hx-target="body" hx-swap="none" hx-on::after-request=" document.querySelectorAll('.details').forEach(el => el.innerHTML = event.detail.xhr.responseText) ">Details</button> <div class="details">first</div> <div class="details">second</div>
独立脚本版(适合复杂逻辑):
<button id="get-user-details" hx-get="/views/users/byId/someId" hx-target="body" hx-swap="none">Details</button> <div class="details">first</div> <div class="details">second</div> <script> document.addEventListener('htmx:afterRequest', function(event) { // 仅处理目标按钮的请求 if (event.target.id === 'get-user-details') { const responseHtml = event.detail.xhr.responseText; // 遍历所有.details元素更新内容 document.querySelectorAll('.details').forEach(el => { el.innerHTML = responseHtml; }); } }); </script>
这里将 hx-target 设为 body、hx-swap 设为 none,是为了阻止 htmx 自动执行默认的替换操作,转而通过事件处理逻辑手动完成更新。这种方式适合所有 .details 元素需要设置相同内容的场景。
内容的提问来源于stack exchange,提问作者Sazzad Islam
相关产品推荐
相关产品推荐

