tembro 3.1.13 → 3.1.14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -2,6 +2,12 @@
2
2
 
3
3
  All notable changes to this project will be documented in this file.
4
4
 
5
+ ## 3.1.14 - 2026-07-16
6
+
7
+ - Fixed Kanban drag-and-drop by adding a native drag/drop fallback while preserving the existing `@dnd-kit` integration.
8
+ - Kept Kanban controlled and uncontrolled column updates in sync for drag, drop, and card move callbacks.
9
+ - Refreshed registry/showcase package metadata for the 3.1.14 release.
10
+
5
11
  ## 3.1.13 - 2026-07-16
6
12
 
7
13
  - Fixed `LineChart` responsive SVG height so wide dashboard cards no longer stretch line charts into oversized panels.
@@ -1,3 +1,3 @@
1
- export declare const PACKAGE_LATEST_VERSION = "3.1.13";
1
+ export declare const PACKAGE_LATEST_VERSION = "3.1.14";
2
2
  export declare const PACKAGE_LATEST_RELEASE_DATE = "July 15, 2026";
3
- export declare const PACKAGE_DEPENDENCY_RANGE = "3.1.13";
3
+ export declare const PACKAGE_DEPENDENCY_RANGE = "3.1.14";
@@ -1 +1 @@
1
- "use client";Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});const e=require("../../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/utils.cjs"),n=require("../ui/card/index.cjs"),r=require("../../../node_modules/@dnd-kit/helpers/dist/index.cjs"),i=require("../../../node_modules/@dnd-kit/react/index.cjs"),a=require("../../../node_modules/@dnd-kit/dom/sortable.cjs"),o=require("../../../node_modules/@dnd-kit/react/sortable.cjs");let s=require("react");s=e.__toESM(s,1);let c=require("lucide-react"),l=require("react/jsx-runtime");var u=`tembro-kanban-card:`,d=`tembro-kanban-column:`;function f(e){return`${u}${e}`}function p(e){return`${d}${e}`}function m(e){return e.startsWith(u)?e.slice(19):e}function h(e){let t=e===void 0?``:String(e);return t.startsWith(d)?t.slice(21):t}function g(e){return new Map(e.flatMap(e=>e.cards.map(e=>[f(e.key),e])))}function _(e,t){let n=g(e),i=r.move(Object.fromEntries(e.map(e=>[p(e.key),e.cards.map(e=>f(e.key))])),t);return e.map(e=>({...e,cards:(i[p(e.key)]??[]).map(e=>n.get(String(e))).filter(e=>!!e)}))}var v=s.forwardRef(function({label:e,disabled:t},n){return(0,l.jsx)(`button`,{ref:n,type:`button`,className:`inline-flex size-8 shrink-0 touch-none items-center justify-center rounded-md text-muted-foreground outline-none transition-colors hover:bg-muted hover:text-foreground focus-visible:ring-2 focus-visible:ring-ring disabled:cursor-not-allowed disabled:opacity-45`,"aria-label":e,disabled:t,onClick:e=>e.stopPropagation(),children:(0,l.jsx)(c.GripVerticalIcon,{className:`size-4`,"aria-hidden":`true`})})});function y({card:e,handle:t}){return(0,l.jsxs)(n.Card,{className:`transition-colors hover:bg-muted/40`,children:[(0,l.jsx)(n.CardHeader,{className:`p-3 pb-1`,children:(0,l.jsxs)(`div`,{className:`flex items-start justify-between gap-2`,children:[(0,l.jsx)(n.CardTitle,{className:`text-sm`,children:e.title}),(0,l.jsxs)(`div`,{className:`flex items-center gap-1`,children:[e.extra,t]})]})}),e.description||e.meta?(0,l.jsxs)(n.CardContent,{className:`grid gap-2 p-3 pt-0 text-xs text-muted-foreground`,children:[e.description,e.meta?(0,l.jsx)(`div`,{children:e.meta}):null]}):null]})}function b({card:e,column:n,index:r,boardDisabled:i,renderCard:a,onCardClick:s,dragHandleLabel:c,cardClassName:u}){let d=i||n.disabled===!0||e.disabled===!0,{ref:m,handleRef:h,isDragging:g,isDropTarget:_}=o.useSortable({id:f(e.key),index:r,group:p(n.key),type:`tembro-kanban-card`,accept:`tembro-kanban-card`,disabled:d,data:{cardKey:e.key,columnKey:n.key},transition:{duration:180,easing:`cubic-bezier(0.2, 0, 0, 1)`,idle:!0}}),b=(0,l.jsx)(v,{ref:h,label:c?.(e,n)??`Move ${String(e.title)}`,disabled:d}),x={index:r,isDragging:g,isDropTarget:_,handle:b};return(0,l.jsx)(`article`,{ref:m,"data-slot":`kanban-card`,"data-dragging":g||void 0,"data-drop-target":_||void 0,"data-disabled":d||void 0,role:s&&!d?`button`:void 0,tabIndex:s&&!d?0:void 0,"aria-label":typeof e.title==`string`?e.title:void 0,className:t.cn(`rounded-lg outline-none transition-[opacity,box-shadow]`,s&&!d&&`cursor-pointer focus-visible:ring-2 focus-visible:ring-ring`,_&&`ring-2 ring-primary/30`,g&&`opacity-30`,d&&`opacity-55`,u),onClick:()=>{d||s?.(e,n)},onKeyDown:t=>{t.target!==t.currentTarget||d||!s||(t.key===`Enter`||t.key===` `)&&(t.preventDefault(),s(e,n))},children:a?.(e,n,x)??(0,l.jsx)(y,{card:e,handle:b})})}function x({column:e,boardDisabled:n,renderCard:r,onCardClick:a,dragHandleLabel:o,emptyColumn:s,columnClassName:c,cardClassName:u}){let{ref:d,isDropTarget:f}=i.useDroppable({id:p(e.key),type:`tembro-kanban-column`,accept:`tembro-kanban-card`,disabled:n||e.disabled===!0,collisionPriority:1,data:{columnKey:e.key}});return(0,l.jsxs)(`section`,{ref:d,"data-slot":`kanban-column`,"data-drop-target":f||void 0,"data-disabled":e.disabled||void 0,"aria-label":typeof e.title==`string`?e.title:void 0,className:t.cn(`grid min-h-40 content-start gap-3 rounded-lg border bg-muted/35 p-3 transition-[border-color,background-color,box-shadow]`,f&&`border-primary/60 bg-primary/5 ring-2 ring-primary/15`,e.disabled&&`opacity-60`,c),children:[(0,l.jsxs)(`div`,{className:`flex items-start justify-between gap-3`,children:[(0,l.jsxs)(`div`,{className:`grid gap-0.5`,children:[(0,l.jsx)(`h3`,{className:`text-sm font-semibold text-foreground`,children:e.title}),e.description?(0,l.jsx)(`p`,{className:`text-xs text-muted-foreground`,children:e.description}):null]}),(0,l.jsx)(`div`,{className:`rounded-full bg-background px-2 py-0.5 text-xs text-muted-foreground`,children:e.count??e.cards.length})]}),(0,l.jsx)(`div`,{className:`grid min-h-16 content-start gap-2`,children:e.cards.length===0?(0,l.jsxs)(`div`,{className:`grid min-h-20 place-items-center rounded-lg border border-dashed p-3 text-center text-xs text-muted-foreground`,children:[(0,l.jsx)(`span`,{children:s}),(0,l.jsx)(`span`,{className:`sr-only`,children:`No cards yet.`})]}):e.cards.map((t,i)=>(0,l.jsx)(b,{card:t,column:e,index:i,boardDisabled:n,renderCard:r,onCardClick:a,dragHandleLabel:o,cardClassName:u},t.key))})]})}function S({columns:e,defaultColumns:n=[],onColumnsChange:r,onCardMove:o,renderCard:c,onCardClick:u,disabled:d=!1,emptyColumn:p=`Drop cards here.`,dragHandleLabel:g,columnClassName:v,cardClassName:b,overlayClassName:S,className:C,"aria-label":w=`Kanban board`,...T}){let[E,D]=s.useState(()=>n),[O,k]=s.useState(null),[A,j]=s.useState(null),M=s.useRef(null),N=e??E,P=O??N,F=e!==void 0;function I(e){let t=e.operation.source;if(!t)return;let n=String(t.id);M.current=N,k(N),j(n)}function L(e){let t=e.operation.source;if(!t||!a.isSortable(t))return;let n=_(M.current??N,e);M.current=n,k(n)}function R(e){let t=e.operation.source;if(j(null),e.canceled||!t||!a.isSortable(t)){M.current=null,k(null);return}let n=M.current??_(N,e),i=m(String(t.id)),s=h(t.initialGroup),c=h(t.group),l=N.find(e=>e.key===s),u=n.find(e=>e.key===c),d=l?.cards.find(e=>e.key===i);if(M.current=null,k(null),!d||!l||!u)return;let f={card:d,fromColumn:l,toColumn:u,fromIndex:t.initialIndex,toIndex:t.index};F||D(n),r?.(n,f),o?.(f)}let z=A?P.flatMap(e=>e.cards.map(t=>({card:t,column:e}))).find(({card:e})=>f(e.key)===A):void 0;return(0,l.jsxs)(i.DragDropProvider,{onDragStart:I,onDragOver:L,onDragEnd:R,children:[(0,l.jsx)(`div`,{...T,role:`group`,"aria-label":w,"data-slot":`kanban-board`,className:t.cn(`grid gap-4 sm:auto-cols-[minmax(280px,1fr)] sm:grid-flow-col sm:overflow-x-auto sm:pb-2`,C),children:P.map(e=>(0,l.jsx)(x,{column:e,boardDisabled:d,renderCard:c,onCardClick:u,dragHandleLabel:g,emptyColumn:p,columnClassName:v,cardClassName:b},e.key))}),(0,l.jsx)(i.DragOverlay,{children:z?(0,l.jsx)(`div`,{className:t.cn(`min-w-64 rotate-1 opacity-95 shadow-2xl`,S),children:c?.(z.card,z.column,{index:z.column.cards.findIndex(e=>e.key===z.card.key),isDragging:!0,isDropTarget:!1,handle:null})??(0,l.jsx)(y,{card:z.card,handle:null})}):null})]})}exports.KanbanBoard=S;
1
+ "use client";Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});const e=require("../../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/utils.cjs"),n=require("../ui/card/index.cjs"),r=require("../../../node_modules/@dnd-kit/helpers/dist/index.cjs"),i=require("../../../node_modules/@dnd-kit/react/index.cjs"),a=require("../../../node_modules/@dnd-kit/dom/sortable.cjs"),o=require("../../../node_modules/@dnd-kit/react/sortable.cjs");let s=require("react");s=e.__toESM(s,1);let c=require("lucide-react"),l=require("react/jsx-runtime");var u=`tembro-kanban-card:`,d=`tembro-kanban-column:`;function f(e){return`${u}${e}`}function p(e){return`${d}${e}`}function m(e){return e.startsWith(u)?e.slice(19):e}function h(e){let t=e===void 0?``:String(e);return t.startsWith(d)?t.slice(21):t}function g(e){return new Map(e.flatMap(e=>e.cards.map(e=>[f(e.key),e])))}function _(e,t){let n=g(e),i=r.move(Object.fromEntries(e.map(e=>[p(e.key),e.cards.map(e=>f(e.key))])),t);return e.map(e=>({...e,cards:(i[p(e.key)]??[]).map(e=>n.get(String(e))).filter(e=>!!e)}))}function v(e,t,n){let r=e.find(e=>e.key===t.columnKey),i=e.find(e=>e.key===n.columnKey);if(!r||!i)return null;let a=r.cards.find(e=>e.key===t.cardKey);if(!a)return null;let o=r.cards.findIndex(e=>e.key===t.cardKey);if(o<0)return null;let s=i.cards,c=n.index??s.length;if(r.key===i.key&&c>o&&--c,c=Math.max(0,Math.min(c,s.length)),r.key===i.key&&o===c)return null;let l=e.map(e=>e.key===r.key?{...e,cards:e.cards.filter(e=>e.key!==t.cardKey)}:e).map(e=>{if(e.key!==i.key)return e;let t=[...e.cards];return t.splice(c,0,a),{...e,cards:t}});return{columns:l,change:{card:a,fromColumn:r,toColumn:l.find(e=>e.key===i.key)??i,fromIndex:o,toIndex:c}}}var y=s.forwardRef(function({label:e,disabled:t},n){return(0,l.jsx)(`button`,{ref:n,type:`button`,className:`inline-flex size-8 shrink-0 touch-none items-center justify-center rounded-md text-muted-foreground outline-none transition-colors hover:bg-muted hover:text-foreground focus-visible:ring-2 focus-visible:ring-ring disabled:cursor-not-allowed disabled:opacity-45`,"aria-label":e,disabled:t,onClick:e=>e.stopPropagation(),children:(0,l.jsx)(c.GripVerticalIcon,{className:`size-4`,"aria-hidden":`true`})})});function b({card:e,handle:t}){return(0,l.jsxs)(n.Card,{className:`transition-colors hover:bg-muted/40`,children:[(0,l.jsx)(n.CardHeader,{className:`p-3 pb-1`,children:(0,l.jsxs)(`div`,{className:`flex items-start justify-between gap-2`,children:[(0,l.jsx)(n.CardTitle,{className:`text-sm`,children:e.title}),(0,l.jsxs)(`div`,{className:`flex items-center gap-1`,children:[e.extra,t]})]})}),e.description||e.meta?(0,l.jsxs)(n.CardContent,{className:`grid gap-2 p-3 pt-0 text-xs text-muted-foreground`,children:[e.description,e.meta?(0,l.jsx)(`div`,{children:e.meta}):null]}):null]})}function x({card:e,column:n,index:r,boardDisabled:i,renderCard:a,onCardClick:s,dragHandleLabel:c,cardClassName:u,onNativeDragStart:d,onNativeDragEnd:m,onNativeDrop:h}){let g=i||n.disabled===!0||e.disabled===!0,{ref:_,handleRef:v,isDragging:x,isDropTarget:S}=o.useSortable({id:f(e.key),index:r,group:p(n.key),type:`tembro-kanban-card`,accept:`tembro-kanban-card`,disabled:g,data:{cardKey:e.key,columnKey:n.key},transition:{duration:180,easing:`cubic-bezier(0.2, 0, 0, 1)`,idle:!0}}),C=(0,l.jsx)(y,{ref:v,label:c?.(e,n)??`Move ${String(e.title)}`,disabled:g}),w={index:r,isDragging:x,isDropTarget:S,handle:C};return(0,l.jsx)(`article`,{ref:_,"data-slot":`kanban-card`,"data-dragging":x||void 0,"data-drop-target":S||void 0,"data-disabled":g||void 0,role:s&&!g?`button`:void 0,tabIndex:s&&!g?0:void 0,"aria-label":typeof e.title==`string`?e.title:void 0,draggable:!g,className:t.cn(`rounded-lg outline-none transition-[opacity,box-shadow]`,s&&!g&&`cursor-pointer focus-visible:ring-2 focus-visible:ring-ring`,S&&`ring-2 ring-primary/30`,x&&`opacity-30`,g&&`opacity-55`,u),onClick:()=>{g||s?.(e,n)},onDragStart:t=>{if(g)return;let i={cardKey:e.key,columnKey:n.key,index:r};t.dataTransfer.effectAllowed=`move`,t.dataTransfer.setData(`text/plain`,JSON.stringify(i)),d?.(i)},onDragEnd:m,onDragOver:e=>{g||e.preventDefault()},onDrop:e=>{g||(e.preventDefault(),e.stopPropagation(),h?.({columnKey:n.key,index:r}))},onKeyDown:t=>{t.target!==t.currentTarget||g||!s||(t.key===`Enter`||t.key===` `)&&(t.preventDefault(),s(e,n))},children:a?.(e,n,w)??(0,l.jsx)(b,{card:e,handle:C})})}function S({column:e,boardDisabled:n,renderCard:r,onCardClick:a,dragHandleLabel:o,emptyColumn:s,columnClassName:c,cardClassName:u,onNativeDragStart:d,onNativeDragEnd:f,onNativeDrop:m}){let{ref:h,isDropTarget:g}=i.useDroppable({id:p(e.key),type:`tembro-kanban-column`,accept:`tembro-kanban-card`,disabled:n||e.disabled===!0,collisionPriority:1,data:{columnKey:e.key}});return(0,l.jsxs)(`section`,{ref:h,"data-slot":`kanban-column`,"data-drop-target":g||void 0,"data-disabled":e.disabled||void 0,"aria-label":typeof e.title==`string`?e.title:void 0,className:t.cn(`grid min-h-40 content-start gap-3 rounded-lg border bg-muted/35 p-3 transition-[border-color,background-color,box-shadow]`,g&&`border-primary/60 bg-primary/5 ring-2 ring-primary/15`,e.disabled&&`opacity-60`,c),onDragOver:t=>{n||e.disabled===!0||t.preventDefault()},onDrop:t=>{n||e.disabled===!0||(t.preventDefault(),m?.({columnKey:e.key,index:e.cards.length}))},children:[(0,l.jsxs)(`div`,{className:`flex items-start justify-between gap-3`,children:[(0,l.jsxs)(`div`,{className:`grid gap-0.5`,children:[(0,l.jsx)(`h3`,{className:`text-sm font-semibold text-foreground`,children:e.title}),e.description?(0,l.jsx)(`p`,{className:`text-xs text-muted-foreground`,children:e.description}):null]}),(0,l.jsx)(`div`,{className:`rounded-full bg-background px-2 py-0.5 text-xs text-muted-foreground`,children:e.count??e.cards.length})]}),(0,l.jsx)(`div`,{className:`grid min-h-16 content-start gap-2`,children:e.cards.length===0?(0,l.jsxs)(`div`,{className:`grid min-h-20 place-items-center rounded-lg border border-dashed p-3 text-center text-xs text-muted-foreground`,children:[(0,l.jsx)(`span`,{children:s}),(0,l.jsx)(`span`,{className:`sr-only`,children:`No cards yet.`})]}):e.cards.map((t,i)=>(0,l.jsx)(x,{card:t,column:e,index:i,boardDisabled:n,renderCard:r,onCardClick:a,dragHandleLabel:o,cardClassName:u,onNativeDragStart:d,onNativeDragEnd:f,onNativeDrop:m},t.key))})]})}function C({columns:e,defaultColumns:n=[],onColumnsChange:r,onCardMove:o,renderCard:c,onCardClick:u,disabled:d=!1,emptyColumn:p=`Drop cards here.`,dragHandleLabel:g,columnClassName:y,cardClassName:x,overlayClassName:C,className:w,"aria-label":T=`Kanban board`,...E}){let[D,O]=s.useState(()=>n),[k,A]=s.useState(null),[j,M]=s.useState(null),N=s.useRef(null),P=s.useRef(null),F=e??D,I=k??F,L=e!==void 0;function R(e){let t=e.operation.source;if(!t)return;let n=String(t.id);N.current=F,A(F),M(n)}function z(e){let t=e.operation.source;if(!t||!a.isSortable(t))return;let n=_(N.current??F,e);N.current=n,A(n)}function B(e){let t=e.operation.source;if(M(null),e.canceled||!t||!a.isSortable(t)){N.current=null,A(null);return}let n=N.current??_(F,e),i=m(String(t.id)),s=h(t.initialGroup),c=h(t.group),l=F.find(e=>e.key===s),u=n.find(e=>e.key===c),d=l?.cards.find(e=>e.key===i);if(N.current=null,A(null),!d||!l||!u)return;let f={card:d,fromColumn:l,toColumn:u,fromIndex:t.initialIndex,toIndex:t.index};L||O(n),r?.(n,f),o?.(f)}function V(e){let t=P.current;if(P.current=null,!t)return;let n=v(F,t,e);n&&(L||O(n.columns),r?.(n.columns,n.change),o?.(n.change))}let H=j?I.flatMap(e=>e.cards.map(t=>({card:t,column:e}))).find(({card:e})=>f(e.key)===j):void 0;return(0,l.jsxs)(i.DragDropProvider,{onDragStart:R,onDragOver:z,onDragEnd:B,children:[(0,l.jsx)(`div`,{...E,role:`group`,"aria-label":T,"data-slot":`kanban-board`,className:t.cn(`grid gap-4 sm:auto-cols-[minmax(280px,1fr)] sm:grid-flow-col sm:overflow-x-auto sm:pb-2`,w),children:I.map(e=>(0,l.jsx)(S,{column:e,boardDisabled:d,renderCard:c,onCardClick:u,dragHandleLabel:g,emptyColumn:p,columnClassName:y,cardClassName:x,onNativeDragStart:e=>{P.current=e},onNativeDragEnd:()=>{P.current=null},onNativeDrop:V},e.key))}),(0,l.jsx)(i.DragOverlay,{children:H?(0,l.jsx)(`div`,{className:t.cn(`min-w-64 rotate-1 opacity-95 shadow-2xl`,C),children:c?.(H.card,H.column,{index:H.column.cards.findIndex(e=>e.key===H.card.key),isDragging:!0,isDropTarget:!1,handle:null})??(0,l.jsx)(b,{card:H.card,handle:null})}):null})]})}exports.KanbanBoard=C;
@@ -33,7 +33,38 @@ function S(e, t) {
33
33
  cards: (r[v(e.key)] ?? []).map((e) => n.get(String(e))).filter((e) => !!e)
34
34
  }));
35
35
  }
36
- var C = d.forwardRef(function({ label: e, disabled: t }, n) {
36
+ function C(e, t, n) {
37
+ let r = e.find((e) => e.key === t.columnKey), i = e.find((e) => e.key === n.columnKey);
38
+ if (!r || !i) return null;
39
+ let a = r.cards.find((e) => e.key === t.cardKey);
40
+ if (!a) return null;
41
+ let o = r.cards.findIndex((e) => e.key === t.cardKey);
42
+ if (o < 0) return null;
43
+ let s = i.cards, c = n.index ?? s.length;
44
+ if (r.key === i.key && c > o && --c, c = Math.max(0, Math.min(c, s.length)), r.key === i.key && o === c) return null;
45
+ let l = e.map((e) => e.key === r.key ? {
46
+ ...e,
47
+ cards: e.cards.filter((e) => e.key !== t.cardKey)
48
+ } : e).map((e) => {
49
+ if (e.key !== i.key) return e;
50
+ let t = [...e.cards];
51
+ return t.splice(c, 0, a), {
52
+ ...e,
53
+ cards: t
54
+ };
55
+ });
56
+ return {
57
+ columns: l,
58
+ change: {
59
+ card: a,
60
+ fromColumn: r,
61
+ toColumn: l.find((e) => e.key === i.key) ?? i,
62
+ fromIndex: o,
63
+ toIndex: c
64
+ }
65
+ };
66
+ }
67
+ var w = d.forwardRef(function({ label: e, disabled: t }, n) {
37
68
  return /* @__PURE__ */ p("button", {
38
69
  ref: n,
39
70
  type: "button",
@@ -47,7 +78,7 @@ var C = d.forwardRef(function({ label: e, disabled: t }, n) {
47
78
  })
48
79
  });
49
80
  });
50
- function w({ card: e, handle: a }) {
81
+ function T({ card: e, handle: a }) {
51
82
  return /* @__PURE__ */ m(t, {
52
83
  className: "transition-colors hover:bg-muted/40",
53
84
  children: [/* @__PURE__ */ p(r, {
@@ -68,14 +99,14 @@ function w({ card: e, handle: a }) {
68
99
  }) : null]
69
100
  });
70
101
  }
71
- function T({ card: t, column: n, index: r, boardDisabled: i, renderCard: a, onCardClick: o, dragHandleLabel: s, cardClassName: c }) {
72
- let l = i || n.disabled === !0 || t.disabled === !0, { ref: d, handleRef: f, isDragging: m, isDropTarget: h } = u({
102
+ function E({ card: t, column: n, index: r, boardDisabled: i, renderCard: a, onCardClick: o, dragHandleLabel: s, cardClassName: c, onNativeDragStart: l, onNativeDragEnd: d, onNativeDrop: f }) {
103
+ let m = i || n.disabled === !0 || t.disabled === !0, { ref: h, handleRef: g, isDragging: y, isDropTarget: b } = u({
73
104
  id: _(t.key),
74
105
  index: r,
75
106
  group: v(n.key),
76
107
  type: "tembro-kanban-card",
77
108
  accept: "tembro-kanban-card",
78
- disabled: l,
109
+ disabled: m,
79
110
  data: {
80
111
  cardKey: t.key,
81
112
  columnKey: n.key
@@ -85,40 +116,60 @@ function T({ card: t, column: n, index: r, boardDisabled: i, renderCard: a, onCa
85
116
  easing: "cubic-bezier(0.2, 0, 0, 1)",
86
117
  idle: !0
87
118
  }
88
- }), g = /* @__PURE__ */ p(C, {
89
- ref: f,
119
+ }), x = /* @__PURE__ */ p(w, {
120
+ ref: g,
90
121
  label: s?.(t, n) ?? `Move ${String(t.title)}`,
91
- disabled: l
92
- }), y = {
122
+ disabled: m
123
+ }), S = {
93
124
  index: r,
94
- isDragging: m,
95
- isDropTarget: h,
96
- handle: g
125
+ isDragging: y,
126
+ isDropTarget: b,
127
+ handle: x
97
128
  };
98
129
  return /* @__PURE__ */ p("article", {
99
- ref: d,
130
+ ref: h,
100
131
  "data-slot": "kanban-card",
101
- "data-dragging": m || void 0,
102
- "data-drop-target": h || void 0,
103
- "data-disabled": l || void 0,
104
- role: o && !l ? "button" : void 0,
105
- tabIndex: o && !l ? 0 : void 0,
132
+ "data-dragging": y || void 0,
133
+ "data-drop-target": b || void 0,
134
+ "data-disabled": m || void 0,
135
+ role: o && !m ? "button" : void 0,
136
+ tabIndex: o && !m ? 0 : void 0,
106
137
  "aria-label": typeof t.title == "string" ? t.title : void 0,
107
- className: e("rounded-lg outline-none transition-[opacity,box-shadow]", o && !l && "cursor-pointer focus-visible:ring-2 focus-visible:ring-ring", h && "ring-2 ring-primary/30", m && "opacity-30", l && "opacity-55", c),
138
+ draggable: !m,
139
+ className: e("rounded-lg outline-none transition-[opacity,box-shadow]", o && !m && "cursor-pointer focus-visible:ring-2 focus-visible:ring-ring", b && "ring-2 ring-primary/30", y && "opacity-30", m && "opacity-55", c),
108
140
  onClick: () => {
109
- l || o?.(t, n);
141
+ m || o?.(t, n);
142
+ },
143
+ onDragStart: (e) => {
144
+ if (m) return;
145
+ let i = {
146
+ cardKey: t.key,
147
+ columnKey: n.key,
148
+ index: r
149
+ };
150
+ e.dataTransfer.effectAllowed = "move", e.dataTransfer.setData("text/plain", JSON.stringify(i)), l?.(i);
151
+ },
152
+ onDragEnd: d,
153
+ onDragOver: (e) => {
154
+ m || e.preventDefault();
155
+ },
156
+ onDrop: (e) => {
157
+ m || (e.preventDefault(), e.stopPropagation(), f?.({
158
+ columnKey: n.key,
159
+ index: r
160
+ }));
110
161
  },
111
162
  onKeyDown: (e) => {
112
- e.target !== e.currentTarget || l || !o || (e.key === "Enter" || e.key === " ") && (e.preventDefault(), o(t, n));
163
+ e.target !== e.currentTarget || m || !o || (e.key === "Enter" || e.key === " ") && (e.preventDefault(), o(t, n));
113
164
  },
114
- children: a?.(t, n, y) ?? /* @__PURE__ */ p(w, {
165
+ children: a?.(t, n, S) ?? /* @__PURE__ */ p(T, {
115
166
  card: t,
116
- handle: g
167
+ handle: x
117
168
  })
118
169
  });
119
170
  }
120
- function E({ column: t, boardDisabled: n, renderCard: r, onCardClick: i, dragHandleLabel: a, emptyColumn: o, columnClassName: s, cardClassName: l }) {
121
- let { ref: u, isDropTarget: d } = c({
171
+ function D({ column: t, boardDisabled: n, renderCard: r, onCardClick: i, dragHandleLabel: a, emptyColumn: o, columnClassName: s, cardClassName: l, onNativeDragStart: u, onNativeDragEnd: d, onNativeDrop: f }) {
172
+ let { ref: h, isDropTarget: g } = c({
122
173
  id: v(t.key),
123
174
  type: "tembro-kanban-column",
124
175
  accept: "tembro-kanban-card",
@@ -127,12 +178,21 @@ function E({ column: t, boardDisabled: n, renderCard: r, onCardClick: i, dragHan
127
178
  data: { columnKey: t.key }
128
179
  });
129
180
  return /* @__PURE__ */ m("section", {
130
- ref: u,
181
+ ref: h,
131
182
  "data-slot": "kanban-column",
132
- "data-drop-target": d || void 0,
183
+ "data-drop-target": g || void 0,
133
184
  "data-disabled": t.disabled || void 0,
134
185
  "aria-label": typeof t.title == "string" ? t.title : void 0,
135
- className: e("grid min-h-40 content-start gap-3 rounded-lg border bg-muted/35 p-3 transition-[border-color,background-color,box-shadow]", d && "border-primary/60 bg-primary/5 ring-2 ring-primary/15", t.disabled && "opacity-60", s),
186
+ className: e("grid min-h-40 content-start gap-3 rounded-lg border bg-muted/35 p-3 transition-[border-color,background-color,box-shadow]", g && "border-primary/60 bg-primary/5 ring-2 ring-primary/15", t.disabled && "opacity-60", s),
187
+ onDragOver: (e) => {
188
+ n || t.disabled === !0 || e.preventDefault();
189
+ },
190
+ onDrop: (e) => {
191
+ n || t.disabled === !0 || (e.preventDefault(), f?.({
192
+ columnKey: t.key,
193
+ index: t.cards.length
194
+ }));
195
+ },
136
196
  children: [/* @__PURE__ */ m("div", {
137
197
  className: "flex items-start justify-between gap-3",
138
198
  children: [/* @__PURE__ */ m("div", {
@@ -156,7 +216,7 @@ function E({ column: t, boardDisabled: n, renderCard: r, onCardClick: i, dragHan
156
216
  className: "sr-only",
157
217
  children: "No cards yet."
158
218
  })]
159
- }) : t.cards.map((e, o) => /* @__PURE__ */ p(T, {
219
+ }) : t.cards.map((e, o) => /* @__PURE__ */ p(E, {
160
220
  card: e,
161
221
  column: t,
162
222
  index: o,
@@ -164,33 +224,36 @@ function E({ column: t, boardDisabled: n, renderCard: r, onCardClick: i, dragHan
164
224
  renderCard: r,
165
225
  onCardClick: i,
166
226
  dragHandleLabel: a,
167
- cardClassName: l
227
+ cardClassName: l,
228
+ onNativeDragStart: u,
229
+ onNativeDragEnd: d,
230
+ onNativeDrop: f
168
231
  }, e.key))
169
232
  })]
170
233
  });
171
234
  }
172
- function D({ columns: t, defaultColumns: n = [], onColumnsChange: r, onCardMove: i, renderCard: a, onCardClick: c, disabled: u = !1, emptyColumn: f = "Drop cards here.", dragHandleLabel: h, columnClassName: g, cardClassName: v, overlayClassName: x, className: C, "aria-label": T = "Kanban board", ...D }) {
173
- let [O, k] = d.useState(() => n), [A, j] = d.useState(null), [M, N] = d.useState(null), P = d.useRef(null), F = t ?? O, I = A ?? F, L = t !== void 0;
174
- function R(e) {
235
+ function O({ columns: t, defaultColumns: n = [], onColumnsChange: r, onCardMove: i, renderCard: a, onCardClick: c, disabled: u = !1, emptyColumn: f = "Drop cards here.", dragHandleLabel: h, columnClassName: g, cardClassName: v, overlayClassName: x, className: w, "aria-label": E = "Kanban board", ...O }) {
236
+ let [k, A] = d.useState(() => n), [j, M] = d.useState(null), [N, P] = d.useState(null), F = d.useRef(null), I = d.useRef(null), L = t ?? k, R = j ?? L, z = t !== void 0;
237
+ function B(e) {
175
238
  let t = e.operation.source;
176
239
  if (!t) return;
177
240
  let n = String(t.id);
178
- P.current = F, j(F), N(n);
241
+ F.current = L, M(L), P(n);
179
242
  }
180
- function z(e) {
243
+ function V(e) {
181
244
  let t = e.operation.source;
182
245
  if (!t || !l(t)) return;
183
- let n = S(P.current ?? F, e);
184
- P.current = n, j(n);
246
+ let n = S(F.current ?? L, e);
247
+ F.current = n, M(n);
185
248
  }
186
- function B(e) {
249
+ function H(e) {
187
250
  let t = e.operation.source;
188
- if (N(null), e.canceled || !t || !l(t)) {
189
- P.current = null, j(null);
251
+ if (P(null), e.canceled || !t || !l(t)) {
252
+ F.current = null, M(null);
190
253
  return;
191
254
  }
192
- let n = P.current ?? S(F, e), a = y(String(t.id)), o = b(t.initialGroup), s = b(t.group), c = F.find((e) => e.key === o), u = n.find((e) => e.key === s), d = c?.cards.find((e) => e.key === a);
193
- if (P.current = null, j(null), !d || !c || !u) return;
255
+ let n = F.current ?? S(L, e), a = y(String(t.id)), o = b(t.initialGroup), s = b(t.group), c = L.find((e) => e.key === o), u = n.find((e) => e.key === s), d = c?.cards.find((e) => e.key === a);
256
+ if (F.current = null, M(null), !d || !c || !u) return;
194
257
  let f = {
195
258
  card: d,
196
259
  fromColumn: c,
@@ -198,23 +261,29 @@ function D({ columns: t, defaultColumns: n = [], onColumnsChange: r, onCardMove:
198
261
  fromIndex: t.initialIndex,
199
262
  toIndex: t.index
200
263
  };
201
- L || k(n), r?.(n, f), i?.(f);
264
+ z || A(n), r?.(n, f), i?.(f);
265
+ }
266
+ function U(e) {
267
+ let t = I.current;
268
+ if (I.current = null, !t) return;
269
+ let n = C(L, t, e);
270
+ n && (z || A(n.columns), r?.(n.columns, n.change), i?.(n.change));
202
271
  }
203
- let V = M ? I.flatMap((e) => e.cards.map((t) => ({
272
+ let W = N ? R.flatMap((e) => e.cards.map((t) => ({
204
273
  card: t,
205
274
  column: e
206
- }))).find(({ card: e }) => _(e.key) === M) : void 0;
275
+ }))).find(({ card: e }) => _(e.key) === N) : void 0;
207
276
  return /* @__PURE__ */ m(o, {
208
- onDragStart: R,
209
- onDragOver: z,
210
- onDragEnd: B,
277
+ onDragStart: B,
278
+ onDragOver: V,
279
+ onDragEnd: H,
211
280
  children: [/* @__PURE__ */ p("div", {
212
- ...D,
281
+ ...O,
213
282
  role: "group",
214
- "aria-label": T,
283
+ "aria-label": E,
215
284
  "data-slot": "kanban-board",
216
- className: e("grid gap-4 sm:auto-cols-[minmax(280px,1fr)] sm:grid-flow-col sm:overflow-x-auto sm:pb-2", C),
217
- children: I.map((e) => /* @__PURE__ */ p(E, {
285
+ className: e("grid gap-4 sm:auto-cols-[minmax(280px,1fr)] sm:grid-flow-col sm:overflow-x-auto sm:pb-2", w),
286
+ children: R.map((e) => /* @__PURE__ */ p(D, {
218
287
  column: e,
219
288
  boardDisabled: u,
220
289
  renderCard: a,
@@ -222,21 +291,28 @@ function D({ columns: t, defaultColumns: n = [], onColumnsChange: r, onCardMove:
222
291
  dragHandleLabel: h,
223
292
  emptyColumn: f,
224
293
  columnClassName: g,
225
- cardClassName: v
294
+ cardClassName: v,
295
+ onNativeDragStart: (e) => {
296
+ I.current = e;
297
+ },
298
+ onNativeDragEnd: () => {
299
+ I.current = null;
300
+ },
301
+ onNativeDrop: U
226
302
  }, e.key))
227
- }), /* @__PURE__ */ p(s, { children: V ? /* @__PURE__ */ p("div", {
303
+ }), /* @__PURE__ */ p(s, { children: W ? /* @__PURE__ */ p("div", {
228
304
  className: e("min-w-64 rotate-1 opacity-95 shadow-2xl", x),
229
- children: a?.(V.card, V.column, {
230
- index: V.column.cards.findIndex((e) => e.key === V.card.key),
305
+ children: a?.(W.card, W.column, {
306
+ index: W.column.cards.findIndex((e) => e.key === W.card.key),
231
307
  isDragging: !0,
232
308
  isDropTarget: !1,
233
309
  handle: null
234
- }) ?? /* @__PURE__ */ p(w, {
235
- card: V.card,
310
+ }) ?? /* @__PURE__ */ p(T, {
311
+ card: W.card,
236
312
  handle: null
237
313
  })
238
314
  }) : null })]
239
315
  });
240
316
  }
241
317
  //#endregion
242
- export { D as KanbanBoard };
318
+ export { O as KanbanBoard };
@@ -1 +1 @@
1
- Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});var e=`3.1.13`,t=`July 15, 2026`,n=e;exports.PACKAGE_DEPENDENCY_RANGE=n,exports.PACKAGE_LATEST_RELEASE_DATE=t,exports.PACKAGE_LATEST_VERSION=e;
1
+ Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});var e=`3.1.14`,t=`July 15, 2026`,n=e;exports.PACKAGE_DEPENDENCY_RANGE=n,exports.PACKAGE_LATEST_RELEASE_DATE=t,exports.PACKAGE_LATEST_VERSION=e;
@@ -1,4 +1,4 @@
1
1
  //#region src/showcase/package-meta.ts
2
- var e = "3.1.13", t = "July 15, 2026", n = e;
2
+ var e = "3.1.14", t = "July 15, 2026", n = e;
3
3
  //#endregion
4
4
  export { n as PACKAGE_DEPENDENCY_RANGE, t as PACKAGE_LATEST_RELEASE_DATE, e as PACKAGE_LATEST_VERSION };