146 lines
4.9 KiB
JavaScript
146 lines
4.9 KiB
JavaScript
var __typeError = (msg) => {
|
|
throw TypeError(msg);
|
|
};
|
|
var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
|
|
var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
|
|
var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
|
|
var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), setter ? setter.call(obj, value) : member.set(obj, value), value);
|
|
var __privateMethod = (obj, member, method) => (__accessCheck(obj, member, "access private method"), method);
|
|
var _data, _Kanban_instances, render_fn, initDragAndDrop_fn, moveItem_fn;
|
|
class Kanban extends HTMLElement {
|
|
constructor() {
|
|
super();
|
|
__privateAdd(this, _Kanban_instances);
|
|
__privateAdd(this, _data, []);
|
|
this.attachShadow({ mode: "open" });
|
|
}
|
|
connectedCallback() {
|
|
__privateMethod(this, _Kanban_instances, render_fn).call(this);
|
|
}
|
|
get data() {
|
|
return __privateGet(this, _data);
|
|
}
|
|
set data(value) {
|
|
__privateSet(this, _data, value);
|
|
__privateMethod(this, _Kanban_instances, render_fn).call(this);
|
|
}
|
|
}
|
|
_data = new WeakMap();
|
|
_Kanban_instances = new WeakSet();
|
|
render_fn = function() {
|
|
const style = `
|
|
:host {
|
|
display: flex;
|
|
gap: 16px;
|
|
padding: 16px;
|
|
overflow-x: auto;
|
|
font-family: system-ui, -apple-system, sans-serif;
|
|
}
|
|
.column {
|
|
background: #f1f2f4;
|
|
border-radius: 8px;
|
|
width: 280px;
|
|
min-width: 280px;
|
|
display: flex;
|
|
flex-direction: column;
|
|
max-height: 100%;
|
|
}
|
|
.column-header {
|
|
padding: 12px;
|
|
font-weight: bold;
|
|
display: flex;
|
|
justify-content: space-between;
|
|
align-items: center;
|
|
}
|
|
.items-container {
|
|
flex: 1;
|
|
padding: 8px;
|
|
min-height: 50px;
|
|
}
|
|
.item {
|
|
background: white;
|
|
border-radius: 4px;
|
|
padding: 12px;
|
|
margin-bottom: 8px;
|
|
box-shadow: 0 1px 3px rgba(0,0,0,0.1);
|
|
cursor: grab;
|
|
}
|
|
.item:active {
|
|
cursor: grabbing;
|
|
}
|
|
.item.dragging {
|
|
opacity: 0.5;
|
|
}
|
|
.items-container.drag-over {
|
|
background: rgba(0,0,0,0.05);
|
|
}
|
|
`;
|
|
this.shadowRoot.innerHTML = `
|
|
<style>${style}</style>
|
|
${__privateGet(this, _data).map((col) => `
|
|
<div class="column" data-id="${col.id}">
|
|
<div class="column-header">
|
|
<span>${col.title}</span>
|
|
</div>
|
|
<div class="items-container" data-column-id="${col.id}">
|
|
${(col.items || []).map((item) => `
|
|
<div class="item" draggable="true" data-id="${item.id}" data-column-id="${col.id}">
|
|
${item.content}
|
|
</div>
|
|
`).join("")}
|
|
</div>
|
|
</div>
|
|
`).join("")}
|
|
`;
|
|
__privateMethod(this, _Kanban_instances, initDragAndDrop_fn).call(this);
|
|
};
|
|
initDragAndDrop_fn = function() {
|
|
const items = this.shadowRoot.querySelectorAll(".item");
|
|
const containers = this.shadowRoot.querySelectorAll(".items-container");
|
|
items.forEach((item) => {
|
|
item.addEventListener("dragstart", (e) => {
|
|
item.classList.add("dragging");
|
|
e.dataTransfer.setData("text/plain", JSON.stringify({
|
|
itemId: item.dataset.id,
|
|
fromColumnId: item.dataset.columnId
|
|
}));
|
|
});
|
|
item.addEventListener("dragend", () => {
|
|
item.classList.remove("dragging");
|
|
});
|
|
});
|
|
containers.forEach((container) => {
|
|
container.addEventListener("dragover", (e) => {
|
|
e.preventDefault();
|
|
container.classList.add("drag-over");
|
|
});
|
|
container.addEventListener("dragleave", () => {
|
|
container.classList.remove("drag-over");
|
|
});
|
|
container.addEventListener("drop", (e) => {
|
|
e.preventDefault();
|
|
container.classList.remove("drag-over");
|
|
const dragData = JSON.parse(e.dataTransfer.getData("text/plain"));
|
|
__privateMethod(this, _Kanban_instances, moveItem_fn).call(this, dragData.itemId, dragData.fromColumnId, container.dataset.columnId);
|
|
});
|
|
});
|
|
};
|
|
moveItem_fn = function(itemId, fromColumnId, toColumnId) {
|
|
if (fromColumnId === toColumnId) return;
|
|
const fromCol = __privateGet(this, _data).find((c) => c.id === fromColumnId);
|
|
const toCol = __privateGet(this, _data).find((c) => c.id === toColumnId);
|
|
const itemIndex = fromCol.items.findIndex((i) => i.id === itemId);
|
|
const [item] = fromCol.items.splice(itemIndex, 1);
|
|
toCol.items.push(item);
|
|
__privateMethod(this, _Kanban_instances, render_fn).call(this);
|
|
this.dispatchEvent(new CustomEvent("@update", {
|
|
detail: __privateGet(this, _data),
|
|
bubbles: true,
|
|
composed: true
|
|
}));
|
|
};
|
|
customElements.define("web-kanban", Kanban);
|
|
export {
|
|
Kanban
|
|
};
|