Hx Virtual

Live Demos Hub
GitHub ↗

Hx Virtual

Interactive production-grade hypermedia component for HTMXUI.

Interactive Preview

DOM Virtualization (hx-virtual)

Windowing engine that recycles DOM elements dynamically based on scroll position. Render 50,000+ items without consuming memory or freezing browser layout threads.

Live Virtualized List (50,000 items)

60 FPS Native Windowing

Usage

<!-- Include Virtual engine -->
<script src="/htmx-virtual.js"></script>

<!-- Virtual scroll container with template -->
<div hx-virtual hx-virtual-height="44" class="h-[400px] overflow-auto border rounded-xl">
  <template hx-virtual-item>
    <div class="p-3 flex justify-between border-b">
      <span hx-text="item.name"></span>
      <span hx-text="item.price"></span>
    </div>
  </template>
</div>

HTML Source

<div class="space-y-8 max-w-5xl py-4">
  <div class="space-y-2">
    <h1 class="text-3xl font-bold tracking-tight text-foreground">DOM Virtualization (hx-virtual)</h1>
    <p class="text-sm text-muted-foreground leading-relaxed">
      Windowing engine that recycles DOM elements dynamically based on scroll position. Render 50,000+ items without consuming memory or freezing browser layout threads.
    </p>
  </div>

  <!-- Virtual List Demo -->
  <div class="space-y-4">
    <div class="flex items-center justify-between">
      <h3 class="text-base font-semibold text-foreground">Live Virtualized List (50,000 items)</h3>
      <span class="text-xs font-mono text-primary bg-primary/10 px-2 py-0.5 rounded">60 FPS Native Windowing</span>
    </div>

    <div id="virtual-demo-container" hx-virtual hx-virtual-height="44" class="h-[400px] border border-border rounded-xl bg-card divide-y divide-border">
      <template hx-virtual-item>
        <div class="px-4 py-2 flex items-center justify-between hover:bg-muted/40 transition-colors">
          <div class="flex items-center gap-3">
            <span class="w-8 h-8 rounded-full bg-primary/10 text-primary flex items-center justify-center font-bold text-xs" hx-text="index"></span>
            <div>
              <div class="font-medium text-xs text-foreground" hx-text="item.customer"></div>
              <div class="text-[10px] text-muted-foreground" hx-text="item.id"></div>
            </div>
          </div>
          <div class="text-right">
            <div class="font-mono text-xs font-semibold text-foreground">$<span hx-text="item.amount"></span></div>
            <div class="text-[10px] text-emerald-500 font-medium" hx-text="item.status"></div>
          </div>
        </div>
      </template>
    </div>
  </div>

  <script>
    document.addEventListener('DOMContentLoaded', () => {
      fetch('/api/erp-invoices.json?count=50000')
        .then(res => res.json())
        .then(data => {
          const container = document.getElementById('virtual-demo-container');
          if (container && container._hxVirtual) {
            container._hxVirtual.setItems(data);
          }
        });
    });
  </script>

  <!-- Usage Code -->
  <div class="space-y-4 pt-4 border-t border-border">
    <h2 class="text-xl font-bold text-foreground">Usage</h2>
    <div class="bg-[#1e293b] text-[#e2e8f0] rounded-xl p-4 font-mono text-xs overflow-x-auto leading-relaxed shadow-sm">
      <pre>&lt;!-- Include Virtual engine --&gt;
&lt;script src="/htmx-virtual.js"&gt;&lt;/script&gt;

&lt;!-- Virtual scroll container with template --&gt;
&lt;div hx-virtual hx-virtual-height="44" class="h-[400px] overflow-auto border rounded-xl"&gt;
  &lt;template hx-virtual-item&gt;
    &lt;div class="p-3 flex justify-between border-b"&gt;
      &lt;span hx-text="item.name"&gt;&lt;/span&gt;
      &lt;span hx-text="item.price"&gt;&lt;/span&gt;
    &lt;/div&gt;
  &lt;/template&gt;
&lt;/div&gt;</pre>
    </div>
  </div>
</div>