diff --git a/src/controllers/custom/setBoosterController.ts b/src/controllers/custom/setBoosterController.ts index b3109a2e..9acb25b8 100644 --- a/src/controllers/custom/setBoosterController.ts +++ b/src/controllers/custom/setBoosterController.ts @@ -1,44 +1,19 @@ import { getAccountIdForRequest } from "../../services/loginService.ts"; import { getInventory } from "../../services/inventoryService.ts"; import type { RequestHandler } from "express"; -import { ExportBoosters } from "warframe-public-export-plus"; +import type { IBooster } from "../../types/inventoryTypes/inventoryTypes.ts"; import { broadcastInventoryUpdate } from "../../services/wsService.ts"; -const I32_MAX = 0x7fffffff; - export const setBoosterController: RequestHandler = async (req, res) => { const accountId = await getAccountIdForRequest(req); - const requests = req.body as { ItemType: string; ExpiryDate: number }[]; + const requests = req.body as IBooster[]; const inventory = await getInventory(accountId, "Boosters"); - const boosters = inventory.Boosters; - if ( - requests.some(request => { - if (typeof request.ItemType !== "string") return true; - if (Object.entries(ExportBoosters).find(([_, item]) => item.typeName === request.ItemType) === undefined) - return true; - if (typeof request.ExpiryDate !== "number") return true; - if (request.ExpiryDate < 0 || request.ExpiryDate > I32_MAX) return true; - return false; - }) - ) { - res.status(400).send("Invalid ItemType provided."); - return; - } - const now = Math.trunc(Date.now() / 1000); - for (const { ItemType, ExpiryDate } of requests) { - if (ExpiryDate <= now) { - // remove expired boosters - const index = boosters.findIndex(item => item.ItemType === ItemType); - if (index !== -1) { - boosters.splice(index, 1); - } + for (const request of requests) { + const index = inventory.Boosters.findIndex(item => item.ItemType === request.ItemType); + if (index !== -1) { + inventory.Boosters[index].ExpiryDate = request.ExpiryDate; } else { - const boosterItem = boosters.find(item => item.ItemType === ItemType); - if (boosterItem) { - boosterItem.ExpiryDate = ExpiryDate; - } else { - boosters.push({ ItemType, ExpiryDate }); - } + inventory.Boosters.push(request); } } await inventory.save(); diff --git a/static/webui/index.html b/static/webui/index.html index b3facf05..cfe5afd1 100644 --- a/static/webui/index.html +++ b/static/webui/index.html @@ -476,9 +476,9 @@
-
+
-
+
diff --git a/static/webui/script.js b/static/webui/script.js index bf971cf8..8b732e15 100644 --- a/static/webui/script.js +++ b/static/webui/script.js @@ -1007,6 +1007,67 @@ function updateInventory() { document.getElementById("EvolutionProgress-list").appendChild(tr); }); + document.getElementById("Boosters-list").innerHTML = ""; + data.Boosters.forEach(item => { + if (item.ExpiryDate < Math.floor(Date.now() / 1000)) { + // Booster has expired, skip it + return; + } + const tr = document.createElement("tr"); + { + const td = document.createElement("td"); + td.textContent = itemMap[item.ItemType]?.name ?? item.ItemType; + tr.appendChild(td); + } + { + const td = document.createElement("td"); + td.classList = "text-end text-nowrap"; + { + const form = document.createElement("form"); + form.style.display = "inline-block"; + form.onsubmit = function (event) { + event.preventDefault(); + const maxDate = new Date(input.max); + const selectedDate = new Date(input.value); + if (selectedDate > maxDate) { + input.value = maxDate.toISOString().slice(0, 16); + } + doChangeBoosterExpiry(item.ItemType, input); + }; + + const input = document.createElement("input"); + input.type = "datetime-local"; + input.classList = "form-control form-control-sm"; + input.value = formatDatetime("%Y-%m-%d %H:%M:%s", item.ExpiryDate * 1000); + input.max = "2038-01-19T03:14"; + input.onblur = function () { + const maxDate = new Date(input.max); + const selectedDate = new Date(input.value); + if (selectedDate > maxDate) { + input.value = maxDate.toISOString().slice(0, 16); + } + doChangeBoosterExpiry(item.ItemType, input); + }; + + form.appendChild(input); + td.appendChild(form); + } + { + const a = document.createElement("a"); + a.href = "#"; + a.onclick = function (event) { + event.preventDefault(); + setBooster(item.ItemType, 0); + }; + a.title = loc("code_remove"); + a.innerHTML = ``; + td.appendChild(a); + } + tr.appendChild(td); + } + document.getElementById("Boosters-list").appendChild(tr); + }); + document.getElementById("FlavourItems-list").innerHTML = ""; data.FlavourItems.forEach(item => { const datalist = document.getElementById("datalist-FlavourItems"); @@ -1619,63 +1680,6 @@ function updateInventory() { } document.getElementById("changeSyndicate").value = data.SupportedSyndicate ?? ""; - document.getElementById("Boosters-list").innerHTML = ""; - const now = Math.floor(Date.now() / 1000); - data.Boosters.forEach(({ ItemType, ExpiryDate }) => { - if (ExpiryDate < now) { - // Booster has expired, skip it - return; - } - const tr = document.createElement("tr"); - { - const td = document.createElement("td"); - td.textContent = itemMap[ItemType]?.name ?? ItemType; - tr.appendChild(td); - } - { - const td = document.createElement("td"); - td.classList = "text-end text-nowrap"; - const timeString = formatDatetime("%Y-%m-%d %H:%M:%s", ExpiryDate * 1000); - const inlineForm = document.createElement("form"); - const input = document.createElement("input"); - - inlineForm.style.display = "inline-block"; - inlineForm.onsubmit = function (event) { - event.preventDefault(); - doChangeBoosterExpiry(ItemType, input); - }; - input.type = "datetime-local"; - input.classList.add("form-control"); - input.classList.add("form-control-sm"); - input.value = timeString; - let changed = false; - input.onchange = function () { - changed = true; - }; - input.onblur = function () { - if (changed) { - doChangeBoosterExpiry(ItemType, input); - } - }; - inlineForm.appendChild(input); - - td.appendChild(inlineForm); - - const removeButton = document.createElement("a"); - removeButton.title = loc("code_remove"); - removeButton.innerHTML = ``; - removeButton.href = "#"; - removeButton.onclick = function (event) { - event.preventDefault(); - setBooster(ItemType, 0); - }; - td.appendChild(removeButton); - - tr.appendChild(td); - } - document.getElementById("Boosters-list").appendChild(tr); - }); - if (single.getCurrentPath().startsWith("/webui/guildView")) { const guildReq = $.get("/custom/getGuild?guildId=" + window.guildId); guildReq.done(guildData => { @@ -3542,7 +3546,7 @@ function handleModularSelection(category) { }); } -function setBooster(ItemType, ExpiryDate, callback) { +function setBooster(ItemType, ExpiryDate) { revalidateAuthz().then(() => { $.post({ url: "/custom/setBooster?" + window.authz, @@ -3555,33 +3559,27 @@ function setBooster(ItemType, ExpiryDate, callback) { ]) }).done(function () { updateInventory(); - if (callback) callback(); }); }); } -function doAcquireBoosters() { +function doAcquireBooster() { const uniqueName = getKey(document.getElementById("acquire-type-Boosters")); if (!uniqueName) { $("#acquire-type-Boosters").addClass("is-invalid").focus(); return; } - const ExpiryDate = Date.now() / 1000 + 3 * 24 * 60 * 60; // default 3 days - setBooster(uniqueName, ExpiryDate, () => { - $("#acquire-type-Boosters").val(""); - }); + setBooster(uniqueName, Math.floor(Date.now() / 1000 + 3 * 24 * 60 * 60)); + document.getElementById("acquire-type-Boosters").value = ""; } function doChangeBoosterExpiry(ItemType, ExpiryDateInput) { - console.log("Changing booster expiry for", ItemType, "to", ExpiryDateInput.value); - // cast local datetime string to unix timestamp - const ExpiryDate = Math.trunc(new Date(ExpiryDateInput.value).getTime() / 1000); + const ExpiryDate = Math.floor(new Date(ExpiryDateInput.value).getTime() / 1000); if (isNaN(ExpiryDate)) { ExpiryDateInput.addClass("is-invalid").focus(); - return false; + return; } setBooster(ItemType, ExpiryDate); - return true; } function formatDatetime(fmt, date) { diff --git a/static/webui/translations/de.js b/static/webui/translations/de.js index c4618cbd..588f4df9 100644 --- a/static/webui/translations/de.js +++ b/static/webui/translations/de.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `Moas`, inventory_kubrowPets: `Bestien`, inventory_evolutionProgress: `Incarnon-Entwicklungsfortschritte`, - inventory_Boosters: `Booster`, + inventory_boosters: `Booster`, inventory_flavourItems: `Sammlerstücke`, inventory_shipDecorations: `Schiffsdekorationen`, inventory_bulkAddSuits: `Fehlende Warframes hinzufügen`, diff --git a/static/webui/translations/en.js b/static/webui/translations/en.js index c948ef9c..28af5370 100644 --- a/static/webui/translations/en.js +++ b/static/webui/translations/en.js @@ -108,7 +108,7 @@ dict = { inventory_moaPets: `Moas`, inventory_kubrowPets: `Beasts`, inventory_evolutionProgress: `Incarnon Evolution Progress`, - inventory_Boosters: `Boosters`, + inventory_boosters: `Boosters`, inventory_flavourItems: `Flavour Items`, inventory_shipDecorations: `Ship Decorations`, inventory_bulkAddSuits: `Add Missing Warframes`, diff --git a/static/webui/translations/es.js b/static/webui/translations/es.js index a53e1cbc..2098a4fd 100644 --- a/static/webui/translations/es.js +++ b/static/webui/translations/es.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `Moas`, inventory_kubrowPets: `Bestias`, inventory_evolutionProgress: `Progreso de evolución Incarnon`, - inventory_Boosters: `Potenciadores`, + inventory_boosters: `Potenciadores`, inventory_flavourItems: `Ítems estéticos`, inventory_shipDecorations: `Decoraciones de nave`, inventory_bulkAddSuits: `Agregar Warframes faltantes`, diff --git a/static/webui/translations/fr.js b/static/webui/translations/fr.js index 2df0c925..f08248b9 100644 --- a/static/webui/translations/fr.js +++ b/static/webui/translations/fr.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `Moas`, inventory_kubrowPets: `Bêtes`, inventory_evolutionProgress: `Progrès de l'évolution Incarnon`, - inventory_Boosters: `Boosters`, + inventory_boosters: `Boosters`, inventory_flavourItems: `[UNTRANSLATED] Flavour Items`, inventory_shipDecorations: `Décorations du vaisseau`, inventory_bulkAddSuits: `Ajouter les Warframes manquantes`, diff --git a/static/webui/translations/ru.js b/static/webui/translations/ru.js index 3e225e93..5e648379 100644 --- a/static/webui/translations/ru.js +++ b/static/webui/translations/ru.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `МОА`, inventory_kubrowPets: `Звери`, inventory_evolutionProgress: `Прогресс эволюции Инкарнонов`, - inventory_Boosters: `Бустеры`, + inventory_boosters: `Бустеры`, inventory_flavourItems: `Уникальные предметы`, inventory_shipDecorations: `Украшения корабля`, inventory_bulkAddSuits: `Добавить отсутствующие Варфреймы`, diff --git a/static/webui/translations/uk.js b/static/webui/translations/uk.js index 754c1f57..0c6c7665 100644 --- a/static/webui/translations/uk.js +++ b/static/webui/translations/uk.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `МОА`, inventory_kubrowPets: `Тварини`, inventory_evolutionProgress: `Прогрес еволюції Інкарнонів`, - inventory_Boosters: `Посилення`, + inventory_boosters: `Посилення`, inventory_flavourItems: `Унікальні предмети`, inventory_shipDecorations: `Прикраси судна`, inventory_bulkAddSuits: `Додати відсутні Ворфрейми`, diff --git a/static/webui/translations/zh.js b/static/webui/translations/zh.js index 6ec6bc89..29cb3e68 100644 --- a/static/webui/translations/zh.js +++ b/static/webui/translations/zh.js @@ -109,7 +109,7 @@ dict = { inventory_moaPets: `恐鸟`, inventory_kubrowPets: `动物同伴`, inventory_evolutionProgress: `灵化之源进度`, - inventory_Boosters: `加成器`, + inventory_boosters: `加成器`, inventory_flavourItems: `装饰物品`, inventory_shipDecorations: `飞船装饰`, inventory_bulkAddSuits: `添加缺失战甲`,