CollapseTable.JS

Make any HTML table responsive: low-priority columns automatically collapse into a per-row details panel with a +/− toggle.

v1.2.0 No dependencies Accessible UMD / ESM / CJS

Why CollapseTable?

Quick Start (CDN)

Pinned version (recommended)

<script src="https://cdn.jsdelivr.net/npm/@codeseasy/collapsetable@1.2.0/dist/collapsetable.min.js"></script>

Always latest

<script src="https://cdn.jsdelivr.net/npm/@codeseasy/collapsetable@latest/dist/collapsetable.min.js"></script>

Initialize

<script>
  var ct = new CollapseTable();
  // Optional during setup: show helpful warnings
  // ct.setMode('development');

  // target can be: "orders" (id without #), "#orders", ".orders-table", "table.responsive", or a <table> element
  ct.set("table-id-here");
</script>

Use a local file (no CDN)

<script src="/path/to/collapsetable.min.js"></script>
<script>
  var ct = new CollapseTable({ /* mode: 'development' */ });
  ct.set("table1");
</script>
💡 Tip: Prefer a full example? See the Live Demo.

Install via npm

Install

npm i @codeseasy/collapsetable

ESM

import CollapseTable from '@codeseasy/collapsetable';

const ct = new CollapseTable({ /* mode: 'development' */ });
ct.set('#orders');

CommonJS

const CollapseTable = require('@codeseasy/collapsetable');

const ct = new CollapseTable({ /* mode: 'development' */ });
ct.set('#orders');

More (TypeScript, bundlers, frameworks)

See the dedicated guide: NPM Usage

Markup requirements

Per-column attributes (on <th>)

<th data-priority="4" data-min="160" data-label="Placed On">Date</th>

API

Constructor

const ct = new CollapseTable(globalOptions?);

Attach / Detach

ct.set(target, perTableOptions?);      // one table
ct.setAll(targets, perTableOptions?);  // many tables
ct.unset(target);                      // remove one
ct.unsetAll(targets);                  // remove many

Refresh & Controls

ct.refresh(target?);    // re-measure & refit (omit to refresh all)
ct.expandAll(target?);  // expand details rows (only if some columns are hidden)
ct.collapseAll(target?);

ct.expandRow(target, rowOrIndex);   // index across all TBODY rows or pass a <tr>
ct.collapseRow(target, rowOrIndex);

Events

ct.on('expand',   ({ table, row }) => {});
ct.on('collapse', ({ table, row }) => {});
ct.on('toggle',   ({ table, row, expanded }) => {});
ct.on('refit',    ({ table, initial, anyHidden }) => {});
ct.on('destroy',  ({ table }) => {}); // unsubscribe: ct.off('expand', handler)

Runtime mode

// Set development mode to see helpful warnings during integration:
ct.setMode('development');   // 'production' | 'development' (default: 'production')
ct.getMode();                // => 'development'

// You can also pass at construction or update globally:
const ct2 = new CollapseTable({ mode: 'development' });
ct.updateOptions({ mode: 'production' });

Options (with defaults)

{
  "mode": "production",
  "controlWidth": 46,
  "minWidthDefault": 140,
  "tableLayout": "auto",
  "deferWhenHidden": true,
  "attrs": {
    "priority": "data-priority",
    "min": "data-min",
    "label": "data-label"
  },
  "classNames": {
    "root": "ctbl",
    "control": "ctbl-control",
    "toggle": "ctbl-toggle",
    "details": "ctbl-details",
    "detailsInner": "ctbl-details-inner",
    "detail": "ctbl-detail",
    "name": "ctbl-name",
    "value": "ctbl-value",
    "hide": "ctbl-hide"
  },
  "icons": { "expand": "+", "collapse": "−" },
  "strings": { "toggleTitle": "Show more", "show": "Show details", "hide": "Hide details" },
  "detailsRender": null
}
// Per-table override
ct.set('#invoices', {
  tableLayout: 'fixed',
  icons: { expand: '▶', collapse: '▼' },
  strings: { toggleTitle: 'More', show: 'Show', hide: 'Hide' }
});

// Global helpers
ct.getOptions();                 // clone of current global options (includes mode)
ct.getMode();                    // 'production' | 'development'
ct.setMode('development');       // switch at runtime
ct.updateOptions({ tableLayout: 'fixed' }); // update globals + refresh attached tables
CollapseTable.version; // "1.2.0"

Styling & frameworks

Minimal CSS is injected by the library (scoped under .ctbl) so your design system remains in control. Using Bootstrap? Apply multiple classes to the toggle button via classNames.toggle and widen the control column slightly:

const ct = new CollapseTable();
ct.set('#table-project-list', {
  classNames: {
    root: 'ctbl',
    control: 'ctbl-control',
    toggle: 'ctbl-toggle btn btn-secondary btn-sm'
  },
  controlWidth: 56
});

Tips, limitations & troubleshooting

CDN links

File structure

src/
  CollapseTable.js
  types/
    collapsetable.d.ts
dist/
  collapsetable.min.js
  collapsetable.js
README.md
npm_usage.md
package.json

Types: Provided at src/types/collapsetable.d.ts and published with the package.

License

MIT © 2025 Vishnu (Codes Easy).