Files
sundynix-pets/pets-fe/pages/tasks/tasks.js
T
Blizzard c72cf24f56
ci-cd / verify (push) Successful in 5s
ci-cd / deploy (push) Skipped
Complete core mini program flows
2026-10-04 09:26:58 +08:00

146 lines
3.7 KiB
JavaScript

const { secure, toast } = require("../../utils/api");
const { localDate, shiftDate } = require("../../utils/date");
Page({
data: {
pets: [],
tasks: [],
date: localDate(),
showForm: false,
editingId: "",
saving: false,
title: "",
petIndex: 0,
category: "food",
time_of_day: "08:30",
repeat_rule: "daily",
done: 0,
},
onShow() {
this.load();
},
async load() {
const date = this.data.date;
try {
const [pets, result] = await Promise.all([
secure("/pets"),
secure("/tasks?date=" + date),
]);
if (date !== this.data.date) return;
const tasks = result.items.map((t) => ({
...t,
petName: (pets.find((p) => p.id === t.pet_id) || {}).name || "宠物",
}));
this.setData({
pets,
tasks,
done: tasks.filter((t) => t.completed).length,
});
} catch (e) {
toast(e);
}
},
async toggle(e) {
const t = this.data.tasks[e.currentTarget.dataset.index];
try {
await secure("/tasks/" + t.id + "/completion", "PUT", {
date: this.data.date,
completed: !t.completed,
});
await this.load();
} catch (err) {
toast(err);
}
},
open() {
if (!this.data.pets.length) {
wx.showToast({ title: "请先添加宠物", icon: "none" });
return;
}
this.setData({
showForm: true,
editingId: "",
title: "",
petIndex: 0,
category: "food",
time_of_day: "08:30",
repeat_rule: "daily",
});
},
close() {
this.setData({ showForm: false });
},
edit(e) {
const task = this.data.tasks[e.currentTarget.dataset.index];
const petIndex = this.data.pets.findIndex((pet) => pet.id === task.pet_id);
this.setData({
showForm: true,
editingId: task.id,
title: task.title,
petIndex: Math.max(petIndex, 0),
category: task.category,
time_of_day: task.time_of_day,
repeat_rule: task.repeat_rule,
});
},
changeDay(e) {
this.setData({ date: shiftDate(this.data.date, Number(e.currentTarget.dataset.days)) });
this.load();
},
showToday() {
this.setData({ date: localDate() });
this.load();
},
field(e) {
this.setData({ [e.currentTarget.dataset.key]: e.detail.value });
},
petChange(e) {
this.setData({ petIndex: Number(e.detail.value) });
},
timeChange(e) {
this.setData({ time_of_day: e.detail.value });
},
categoryChange(e) {
this.setData({ category: e.detail.value });
},
repeatChange(e) {
this.setData({ repeat_rule: e.detail.value });
},
async save() {
if (this.data.saving) return;
if (!this.data.pets.length || !this.data.title.trim()) {
wx.showToast({ title: "请选择宠物并填写任务名", icon: "none" });
return;
}
this.setData({ saving: true });
try {
await secure(this.data.editingId ? "/tasks/" + this.data.editingId : "/tasks", this.data.editingId ? "PUT" : "POST", {
pet_id: this.data.pets[this.data.petIndex].id,
title: this.data.title.trim(),
category: this.data.category,
time_of_day: this.data.time_of_day,
repeat_rule: this.data.repeat_rule,
});
this.setData({ showForm: false, editingId: "" });
await this.load();
} catch (e) {
toast(e);
} finally {
this.setData({ saving: false });
}
},
async remove(e) {
const t = this.data.tasks[e.currentTarget.dataset.index];
const result = await wx.showModal({
title: "删除任务",
content: "确定删除「" + t.title + "」吗?",
});
if (!result.confirm) return;
try {
await secure("/tasks/" + t.id, "DELETE");
this.load();
} catch (err) {
toast(err);
}
},
});