639 lines
22 KiB
JavaScript
639 lines
22 KiB
JavaScript
window.kitchenAnimations = [
|
||
`<div class="kitchen-anim"><div class="fire-emoji">🔥</div><div class="pan-emoji">🍳</div></div>`,
|
||
`<div class="anim-run"><div class="chicken">🐓</div><div class="chef">👨🍳</div></div>`,
|
||
`<div class="anim-pot"><div class="chicken-head">🐓</div><div class="pot-emoji">🍲</div></div>`,
|
||
`<div class="anim-pizza"><div class="chef-pizza">👨🍳</div><div class="pizza-emoji">🍕</div></div>`,
|
||
`<div class="anim-pig"><div class="pig-emoji">🐷</div><div class="sweat-emoji">💦</div><div class="knife-emoji">🍴</div></div>`
|
||
];
|
||
window.selectedAnimationHtml = null;
|
||
|
||
const params = new URLSearchParams(location.search);
|
||
let hashParam = (params.get("h") || "").trim();
|
||
|
||
// Jeśli brak hasha w URL – zapytaj użytkownika (np. do testów)
|
||
if (!hashParam) {
|
||
const input = prompt("Podaj bezpieczny hash stolika (wymagane):");
|
||
const trimmed = (input || "").trim();
|
||
if (trimmed) {
|
||
const newUrl = new URL(location.href);
|
||
newUrl.searchParams.set("h", trimmed);
|
||
location.replace(newUrl.toString());
|
||
}
|
||
}
|
||
|
||
let tableParam = ""; // Puste, zostanie uzupełnione przez backend
|
||
|
||
// UI Elements
|
||
const loadingScreen = document.getElementById("loadingScreen");
|
||
const loaderMsg = document.getElementById("loaderMsg");
|
||
const tableLabel = document.getElementById("tableLabel");
|
||
const prepStatus = document.getElementById("prepStatus");
|
||
const progressBar = document.getElementById("progressBar");
|
||
const statusMeta = document.getElementById("statusMeta");
|
||
const itemsList = document.getElementById("itemsList");
|
||
const emptyState = document.getElementById("emptyState");
|
||
const metaFooter = document.getElementById("metaFooter");
|
||
const statusIcon = document.getElementById("statusIcon");
|
||
const storageKey = `stolik2_state_${(tableParam || "unknown").toLowerCase()}`;
|
||
const historyKey = "stolik2_global_history";
|
||
const historySection = document.getElementById("historySection");
|
||
const historyList = document.getElementById("historyList");
|
||
const SIX_MONTHS_MS = 180 * 24 * 60 * 60 * 1000;
|
||
const HOT_WINDOW_MS = 5 * 60 * 60 * 1000;
|
||
|
||
// Dynamic Loader Messages
|
||
const LOADER_MIN_MS = 10_000;
|
||
const loadStartTime = Date.now();
|
||
|
||
const msgs = ["Rozgrzewamy piece...", "Szef kuchni sprawdza składniki...", "Łączenie z sercem restauracji...", "Prawie gotowe..."];
|
||
let msgIdx = 0;
|
||
const msgInterval = setInterval(() => {
|
||
msgIdx = (msgIdx + 1) % msgs.length;
|
||
loaderMsg.textContent = msgs[msgIdx];
|
||
}, 4000);
|
||
|
||
// Initial State
|
||
if (tableParam) {
|
||
tableLabel.textContent = `Stolik ${tableParam}`;
|
||
}
|
||
|
||
function hideLoader() {
|
||
const elapsed = Date.now() - loadStartTime;
|
||
const remaining = Math.max(0, LOADER_MIN_MS - elapsed);
|
||
setTimeout(() => {
|
||
loadingScreen.classList.add("hidden");
|
||
clearInterval(msgInterval);
|
||
}, remaining);
|
||
}
|
||
|
||
function updateUI(bills) {
|
||
// Hide loader after minimum display time
|
||
hideLoader();
|
||
|
||
const allArticles = bills.flatMap(b => Array.isArray(b?.Articles) ? b.Articles : []);
|
||
const items = mergeWithPersistedItems(allArticles);
|
||
renderGlobalHistory();
|
||
|
||
if (items.length === 0) {
|
||
showEmptyState();
|
||
return;
|
||
}
|
||
|
||
renderItems(items);
|
||
updateStatus(bills, items);
|
||
}
|
||
|
||
function detectTableCandidates(bill) {
|
||
const remark = String(bill?.Remark || "");
|
||
const description = String(bill?.Description || "").trim();
|
||
|
||
// 1) klasyczny format: "STOLIK 9", "STOLIK 11A"
|
||
const stolikMatch = remark.match(/STOLIK\s*([0-9A-Z]+)/i);
|
||
const fromRemark = stolikMatch ? stolikMatch[1].toLowerCase() : "";
|
||
|
||
// 2) czasem numer bywa w samym Description
|
||
const fromDescription = description.toLowerCase();
|
||
|
||
return { fromRemark, fromDescription, remark: remark.toLowerCase() };
|
||
}
|
||
|
||
function showEmptyState() {
|
||
emptyState.classList.remove("hidden");
|
||
itemsList.innerHTML = "";
|
||
prepStatus.textContent = "Brak aktywnych zamówień";
|
||
statusIcon.textContent = "🍃";
|
||
progressBar.style.width = "0%";
|
||
statusMeta.textContent = "Zapraszamy do złożenia zamówienia u kelnera.";
|
||
// Historia może istnieć nawet gdy brak bieżących pozycji
|
||
renderGlobalHistory();
|
||
}
|
||
|
||
function normalizeArticleName(rawName) {
|
||
const name = String(rawName || "Pozycja");
|
||
|
||
// Usuwa gramatury typu: "300G", "250 G", "500/200/150G".
|
||
const withoutWeight = name.replace(
|
||
/\b\d+(?:[.,]\d+)?(?:\s*\/\s*\d+(?:[.,]\d+)?)*\s*[gG]\b/g,
|
||
""
|
||
);
|
||
|
||
return withoutWeight
|
||
.replace(/\s{2,}/g, " ")
|
||
.replace(/\s+([,.;:!?])/g, "$1")
|
||
.trim() || "Pozycja";
|
||
}
|
||
|
||
function loadPersistedItems() {
|
||
try {
|
||
const raw = localStorage.getItem(storageKey);
|
||
if (!raw) return [];
|
||
const parsed = JSON.parse(raw);
|
||
return Array.isArray(parsed) ? parsed : [];
|
||
} catch {
|
||
return [];
|
||
}
|
||
}
|
||
|
||
function savePersistedItems(items) {
|
||
try {
|
||
localStorage.setItem(storageKey, JSON.stringify(items));
|
||
} catch {
|
||
// brak miejsca/tryb prywatny
|
||
}
|
||
}
|
||
|
||
function loadGlobalHistory() {
|
||
try {
|
||
const raw = localStorage.getItem(historyKey);
|
||
if (!raw) return [];
|
||
const parsed = JSON.parse(raw);
|
||
return Array.isArray(parsed) ? parsed : [];
|
||
} catch {
|
||
return [];
|
||
}
|
||
}
|
||
|
||
function saveGlobalHistory(entries) {
|
||
const now = Date.now();
|
||
const cleaned = entries
|
||
.filter((e) => e && e.name && Number.isFinite(e.archivedAt))
|
||
.filter((e) => (now - e.archivedAt) <= SIX_MONTHS_MS);
|
||
|
||
try {
|
||
localStorage.setItem(historyKey, JSON.stringify(cleaned));
|
||
} catch {
|
||
// ignore storage errors
|
||
}
|
||
}
|
||
|
||
function addItemsToGlobalHistory(items, sourceTable) {
|
||
if (!items.length) return;
|
||
const now = Date.now();
|
||
const existing = loadGlobalHistory();
|
||
|
||
// zapobiegamy dokładnym duplikatom (ta sama nazwa + qty + stół blisko czasu)
|
||
const dedupWindowMs = 2 * 60 * 1000;
|
||
const toAdd = items.filter((item) => {
|
||
return !existing.some((h) =>
|
||
h.name === item.name &&
|
||
Number(h.qty) === Number(item.qty) &&
|
||
String(h.sourceTable || "") === String(sourceTable || "") &&
|
||
Math.abs((h.archivedAt || 0) - now) <= dedupWindowMs
|
||
);
|
||
}).map((item) => ({
|
||
name: item.name,
|
||
qty: item.qty,
|
||
sourceTable: sourceTable || "?",
|
||
archivedAt: now
|
||
}));
|
||
|
||
if (!toAdd.length) return;
|
||
saveGlobalHistory([...existing, ...toAdd]);
|
||
}
|
||
|
||
function renderGlobalHistory() {
|
||
const now = Date.now();
|
||
const history = loadGlobalHistory()
|
||
.filter((e) => (now - (e.archivedAt || 0)) <= SIX_MONTHS_MS)
|
||
.sort((a, b) => (b.archivedAt || 0) - (a.archivedAt || 0));
|
||
|
||
saveGlobalHistory(history);
|
||
|
||
if (!history.length) {
|
||
historySection.classList.add("hidden");
|
||
historyList.innerHTML = "";
|
||
return;
|
||
}
|
||
|
||
historySection.classList.remove("hidden");
|
||
historyList.innerHTML = "";
|
||
|
||
history.forEach((entry) => {
|
||
const dt = new Date(entry.archivedAt || Date.now());
|
||
const div = document.createElement("div");
|
||
div.className = "item-card archived ready";
|
||
div.innerHTML = `
|
||
<div class="item-info">
|
||
<span class="item-name">${entry.name}</span>
|
||
<span class="item-meta">Stolik ${entry.sourceTable || "?"} • ${dt.toLocaleDateString("pl-PL")} ${dt.toLocaleTimeString([], {hour:'2-digit', minute:'2-digit'})}</span>
|
||
</div>
|
||
<div class="item-qty">x${entry.qty}</div>
|
||
`;
|
||
historyList.appendChild(div);
|
||
});
|
||
}
|
||
|
||
function mergeWithPersistedItems(articles) {
|
||
const current = new Map();
|
||
|
||
articles.forEach(a => {
|
||
const name = normalizeArticleName(a.Name);
|
||
const todo = parseFloat(String(a.QuantityToDo || a.QuantitySet || "0").replace(",","."));
|
||
const done = parseFloat(String(a.QuantityDone || "0").replace(",","."));
|
||
|
||
if (!current.has(name)) {
|
||
current.set(name, { name, qty: 0, done: 0, present: true, completedByDisappear: false });
|
||
}
|
||
const curr = current.get(name);
|
||
curr.qty += Number.isFinite(todo) ? todo : 0;
|
||
curr.done += Number.isFinite(done) ? done : 0;
|
||
});
|
||
|
||
const persisted = loadPersistedItems();
|
||
const persistedMap = new Map(persisted.map(i => [i.name, i]));
|
||
const merged = [];
|
||
|
||
// Aktualnie obecne pozycje z WS
|
||
current.forEach((item) => {
|
||
merged.push({
|
||
...item,
|
||
present: true,
|
||
completedByDisappear: false,
|
||
updatedAt: Date.now()
|
||
});
|
||
});
|
||
|
||
// Pozycje, które były wcześniej, ale zniknęły z API -> przesyłamy od razu do historii globalnej
|
||
persistedMap.forEach((oldItem, name) => {
|
||
if (current.has(name)) return;
|
||
const qty = Number.isFinite(oldItem?.qty) ? oldItem.qty : 0;
|
||
|
||
// Zniknęło z bieżącego rachunku (np. rachunek został zamknięty), od razu leci do osobnego bloku historii!
|
||
addItemsToGlobalHistory([{ name, qty }], tableParam);
|
||
});
|
||
|
||
// Aktywne na górze, gotowe (zniknięte) na dole
|
||
merged.sort((a, b) => {
|
||
if (a.present !== b.present) return a.present ? -1 : 1;
|
||
return a.name.localeCompare(b.name, "pl");
|
||
});
|
||
|
||
savePersistedItems(merged);
|
||
return merged;
|
||
}
|
||
|
||
function renderItems(items) {
|
||
emptyState.classList.add("hidden");
|
||
itemsList.innerHTML = "";
|
||
|
||
items.forEach((item) => {
|
||
const isReady = item.done >= item.qty && item.qty > 0;
|
||
const div = document.createElement("div");
|
||
div.className = `item-card ${isReady ? 'ready' : ''} ${item.present ? '' : 'archived'}`;
|
||
|
||
let meta = "🔥 W przygotowaniu";
|
||
if (isReady && item.completedByDisappear) {
|
||
meta = "✅ Gotowe (zrealizowane)";
|
||
} else if (isReady) {
|
||
meta = "✅ Gotowe";
|
||
}
|
||
|
||
div.innerHTML = `
|
||
<div class="item-info">
|
||
<span class="item-name">${item.name}</span>
|
||
<span class="item-meta">${meta}</span>
|
||
</div>
|
||
<div class="item-qty">x${item.qty}</div>
|
||
`;
|
||
itemsList.appendChild(div);
|
||
});
|
||
|
||
renderGlobalHistory();
|
||
}
|
||
|
||
function updateStatus(bills, items) {
|
||
let total = 0;
|
||
let done = 0;
|
||
items.forEach(i => {
|
||
total += Number.isFinite(i.qty) ? i.qty : 0;
|
||
done += Number.isFinite(i.done) ? i.done : 0;
|
||
});
|
||
|
||
const pct = total > 0 ? (done / total) * 100 : 0;
|
||
progressBar.style.width = `${pct}%`;
|
||
|
||
if (pct >= 100) {
|
||
prepStatus.textContent = "Gotowe do podania!";
|
||
statusIcon.innerHTML = "😋";
|
||
statusMeta.textContent = "Wszystkie Twoje dania opuściły już kuchnię.";
|
||
} else if (pct > 0) {
|
||
prepStatus.textContent = "Częściowo gotowe";
|
||
statusIcon.innerHTML = "🍳";
|
||
statusMeta.textContent = "Pierwsze pyszności już na Ciebie czekają!";
|
||
} else {
|
||
prepStatus.textContent = "W przygotowaniu";
|
||
if (!window.selectedAnimationHtml) {
|
||
window.selectedAnimationHtml = window.kitchenAnimations[Math.floor(Math.random() * window.kitchenAnimations.length)];
|
||
}
|
||
statusIcon.innerHTML = window.selectedAnimationHtml;
|
||
statusMeta.textContent = "Twoje zamówienie jest właśnie tworzone przez naszych kucharzy.";
|
||
}
|
||
|
||
// Footer meta
|
||
const newest = [...bills].sort((a,b) => new Date(b?.Date || 0) - new Date(a?.Date || 0))[0];
|
||
const time = newest?.Date
|
||
? new Date(newest.Date).toLocaleTimeString([], {hour: '2-digit', minute:'2-digit'})
|
||
: "--:--";
|
||
metaFooter.textContent = `Zamówienie złożone o godzinie ${time} • Stolik ${tableParam}`;
|
||
}
|
||
|
||
// API Fetch Logic
|
||
async function fetchOrders() {
|
||
try {
|
||
if (!hashParam) {
|
||
updateUI([]);
|
||
return;
|
||
}
|
||
|
||
const response = await fetch(`../api/kds.php?h=${encodeURIComponent(hashParam)}`);
|
||
const result = await response.json();
|
||
|
||
if (result.status === 'success') {
|
||
if (result.tableName && result.tableName !== '') {
|
||
tableLabel.textContent = `Stolik ${result.tableName}`;
|
||
tableParam = result.tableName; // Aktualizacja do właściwej nazwy na poczet innych zapytań
|
||
}
|
||
|
||
// API teraz samo filtruje i zwraca tylko to co nas interesuje (za pomocą mocnego wyrażenia regularnego)
|
||
const matches = result.data;
|
||
|
||
// Grupowanie składników w główne dania
|
||
const groups = {};
|
||
matches.forEach(item => {
|
||
const groupId = item.GrupaZestawuID || item.PozycjaID;
|
||
if (!groups[groupId]) {
|
||
groups[groupId] = {
|
||
Name: item.NazwaZestawu || item.NazwaTowaru,
|
||
QuantitySet: item.GrupaZestawuID ? 1 : parseFloat(item.Ilosc),
|
||
Done: 0
|
||
};
|
||
}
|
||
// StatusRealizacji >= 2 oznacza, że kucharz wcisnął "Gotowe" na swoim ekranie
|
||
if (parseInt(item.StatusRealizacji, 10) >= 2) {
|
||
groups[groupId].Done = groups[groupId].QuantitySet;
|
||
}
|
||
});
|
||
|
||
const transformedArticles = Object.values(groups).map(g => ({
|
||
Name: g.Name,
|
||
QuantitySet: g.QuantitySet,
|
||
QuantityDone: g.Done
|
||
}));
|
||
|
||
// Najnowszy czas dodania (do pokazania w stopce)
|
||
const latestDate = matches.length > 0
|
||
? matches.sort((a,b) => new Date(b.DataDodania) - new Date(a.DataDodania))[0].DataDodania
|
||
: null;
|
||
|
||
// Przekazanie do dotychczasowej logiki aktualizującej UI (w odpowiednim formacie)
|
||
updateUI([{
|
||
Articles: transformedArticles,
|
||
Date: latestDate
|
||
}]);
|
||
|
||
} else {
|
||
loaderMsg.textContent = "Błąd API: " + result.message;
|
||
}
|
||
} catch (err) {
|
||
loaderMsg.textContent = "Problem z połączeniem. Próbujemy ponownie...";
|
||
}
|
||
}
|
||
|
||
fetchOrders();
|
||
setInterval(fetchOrders, 10000);
|
||
|
||
// --- CALL WAITER LOGIC ---
|
||
let billState = { payment: '', doc: '', nip: '', company: null };
|
||
|
||
function showToast(msg) {
|
||
const t = document.getElementById("toastMsg");
|
||
document.getElementById("toastText").textContent = msg;
|
||
|
||
t.classList.remove("active");
|
||
void t.offsetWidth; // trigger reflow
|
||
t.classList.add("active");
|
||
|
||
setTimeout(() => t.classList.remove("active"), 3500);
|
||
}
|
||
|
||
function sendApiSimulated(actionName, details) {
|
||
console.log(`[SYMULACJA API] Akcja: ${actionName}`, details);
|
||
// Przykładowe wysłanie docelowo:
|
||
// if (window.socket && window.socket.readyState === WebSocket.OPEN) {
|
||
// window.socket.send(JSON.stringify({ action: "sendUpstream", payload: { type: actionName, table: tableParam, ...details } }));
|
||
// }
|
||
}
|
||
|
||
window.callWaiter = function(type) {
|
||
if (type === 'order') {
|
||
sendApiSimulated("CallWaiter_Order", { table: tableParam });
|
||
showToast("Kelner wkrótce do Ciebie podejdzie!");
|
||
}
|
||
};
|
||
|
||
window.openWaiterDialog = function() {
|
||
document.getElementById("waiterModal").classList.add("active");
|
||
document.body.style.overflow = 'hidden';
|
||
};
|
||
|
||
window.closeWaiterDialog = function() {
|
||
document.getElementById("waiterModal").classList.remove("active");
|
||
document.body.style.overflow = '';
|
||
};
|
||
|
||
window.confirmCallWaiter = function() {
|
||
closeWaiterDialog();
|
||
callWaiter('order');
|
||
};
|
||
|
||
window.openBillDialog = async function() {
|
||
billState = { payment: '', doc: '', nip: '', company: null, selectedBillId: null };
|
||
document.getElementById("billModal").classList.add("active");
|
||
document.body.style.overflow = 'hidden'; // Zablokuj scroll tła
|
||
|
||
document.getElementById("billLoading").classList.remove("hidden");
|
||
document.getElementById("billListContainer").classList.add("hidden");
|
||
goToStep("stepBillList");
|
||
|
||
try {
|
||
const res = await fetch(`../api/bills.php?h=${encodeURIComponent(hashParam)}`);
|
||
const result = await res.json();
|
||
|
||
if (result.status === 'success' && result.data.length > 0) {
|
||
const bills = result.data;
|
||
|
||
if (bills.length === 1) {
|
||
showBillReview(bills[0]);
|
||
document.getElementById("btnBackToBills").style.display = 'none';
|
||
} else {
|
||
renderBillList(bills);
|
||
document.getElementById("btnBackToBills").style.display = 'block';
|
||
}
|
||
} else {
|
||
document.getElementById("billLoading").innerHTML = "Brak otwartych rachunków do opłacenia.";
|
||
}
|
||
} catch (err) {
|
||
document.getElementById("billLoading").innerHTML = "Błąd pobierania rachunków.";
|
||
}
|
||
};
|
||
|
||
function renderBillList(bills) {
|
||
document.getElementById("billLoading").classList.add("hidden");
|
||
document.getElementById("billListContainer").classList.remove("hidden");
|
||
|
||
const container = document.getElementById("billListItems");
|
||
container.innerHTML = "";
|
||
|
||
bills.forEach(b => {
|
||
const div = document.createElement("div");
|
||
div.className = "option-card";
|
||
div.style.flexDirection = "row";
|
||
div.style.justifyContent = "space-between";
|
||
div.style.padding = "15px";
|
||
div.onclick = () => showBillReview(b);
|
||
|
||
const numerFormat = b.numer ? `#${b.numer}` : "Rachunek";
|
||
div.innerHTML = `
|
||
<div>
|
||
<div style="font-weight:bold;">${numerFormat}</div>
|
||
<div style="font-size:12px; color:var(--text-muted);">${b.opis}</div>
|
||
</div>
|
||
<div style="font-weight:bold; color:var(--primary);">${b.suma.toFixed(2)} PLN</div>
|
||
`;
|
||
container.appendChild(div);
|
||
});
|
||
}
|
||
|
||
window.goBackToBillList = function() {
|
||
goToStep("stepBillList");
|
||
};
|
||
|
||
window.showBillReview = function(bill) {
|
||
billState.selectedBillId = bill.id;
|
||
|
||
const content = document.getElementById("billReviewContent");
|
||
content.innerHTML = "";
|
||
|
||
bill.pozycje.forEach(p => {
|
||
const div = document.createElement("div");
|
||
div.style.display = "flex";
|
||
div.style.justifyContent = "space-between";
|
||
div.style.marginBottom = "8px";
|
||
div.style.borderBottom = "1px solid rgba(255,255,255,0.05)";
|
||
div.style.paddingBottom = "8px";
|
||
|
||
div.innerHTML = `
|
||
<div style="flex:1;">
|
||
<div style="font-weight:600; font-size: 14px;">${p.nazwa}</div>
|
||
<div style="font-size:12px; color:var(--text-muted);">${p.ilosc} x ${p.cena.toFixed(2)} PLN</div>
|
||
</div>
|
||
<div style="font-weight:600;">${p.wartosc.toFixed(2)} PLN</div>
|
||
`;
|
||
content.appendChild(div);
|
||
});
|
||
|
||
document.getElementById("billTotalAmount").textContent = bill.suma.toFixed(2) + " PLN";
|
||
goToStep("stepBillReview");
|
||
};
|
||
|
||
window.closeBillDialog = function() {
|
||
document.getElementById("billModal").classList.remove("active");
|
||
document.body.style.overflow = ''; // Odblokuj scroll tła
|
||
};
|
||
|
||
window.goToStep = function(stepId) {
|
||
document.querySelectorAll(".step").forEach(s => s.classList.remove("active"));
|
||
document.getElementById(stepId).classList.add("active");
|
||
};
|
||
|
||
window.selectPayment = function(method) {
|
||
billState.payment = method;
|
||
goToStep("stepDocument");
|
||
};
|
||
|
||
window.selectDocument = function(docType) {
|
||
billState.doc = docType;
|
||
if (docType === 'paragon') {
|
||
closeBillDialog();
|
||
sendApiSimulated("CallWaiter_Bill", { table: tableParam, billId: billState.selectedBillId, payment: billState.payment, doc: 'paragon' });
|
||
showToast("Kelner przyniesie paragon do opłacenia!");
|
||
} else {
|
||
goToStep("stepNIP");
|
||
document.getElementById("nipInput").value = '';
|
||
setTimeout(() => document.getElementById("nipInput").focus(), 100);
|
||
}
|
||
};
|
||
|
||
window.fetchGUS = function() {
|
||
const nip = document.getElementById("nipInput").value.replace(/[\s-]/g, '');
|
||
if (nip.length < 10) {
|
||
alert("Wprowadź poprawny numer NIP.");
|
||
return;
|
||
}
|
||
const btn = document.getElementById("btnGUS");
|
||
btn.textContent = "Szukam...";
|
||
btn.disabled = true;
|
||
|
||
// Symulacja pobrania z GUS
|
||
setTimeout(() => {
|
||
btn.textContent = "Pobierz z GUS";
|
||
btn.disabled = false;
|
||
billState.nip = nip;
|
||
billState.company = {
|
||
name: "Przykładowa Firma Sp. z o.o.",
|
||
address: "ul. Gastronomiczna 12/4, 00-120 Warszawa",
|
||
nip: nip
|
||
};
|
||
|
||
document.getElementById("cmpName").value = billState.company.name;
|
||
document.getElementById("cmpAddress").value = billState.company.address;
|
||
document.getElementById("cmpNip").value = "NIP: " + billState.company.nip;
|
||
|
||
// reset do readonly
|
||
document.getElementById("cmpName").readOnly = true;
|
||
document.getElementById("cmpAddress").readOnly = true;
|
||
document.getElementById("btnEditCompany").textContent = "Popraw ręcznie";
|
||
|
||
goToStep("stepVerify");
|
||
}, 1200);
|
||
};
|
||
|
||
window.editCompanyData = function() {
|
||
const n = document.getElementById("cmpName");
|
||
const a = document.getElementById("cmpAddress");
|
||
const btn = document.getElementById("btnEditCompany");
|
||
|
||
if (n.readOnly) {
|
||
n.readOnly = false;
|
||
a.readOnly = false;
|
||
n.focus();
|
||
btn.textContent = "Zakończ edycję";
|
||
} else {
|
||
n.readOnly = true;
|
||
a.readOnly = true;
|
||
btn.textContent = "Popraw ręcznie";
|
||
}
|
||
};
|
||
|
||
window.confirmInvoice = function() {
|
||
billState.company.name = document.getElementById("cmpName").value;
|
||
billState.company.address = document.getElementById("cmpAddress").value;
|
||
|
||
closeBillDialog();
|
||
sendApiSimulated("CallWaiter_Bill", {
|
||
table: tableParam,
|
||
billId: billState.selectedBillId,
|
||
payment: billState.payment,
|
||
doc: 'faktura',
|
||
nip: billState.nip,
|
||
company: billState.company
|
||
});
|
||
showToast("Dziękujemy! Prośba o fakturę została wysłana.");
|
||
};
|
||
|
||
// Fallback: If no data after 25s, show empty state anyway
|
||
setTimeout(() => {
|
||
if (!loadingScreen.classList.contains("hidden")) {
|
||
updateUI([]);
|
||
}
|
||
}, 25000); |