feat: rebuild pet app and backend around core care flows
This commit is contained in:
@@ -0,0 +1,165 @@
|
||||
const { secure, toast } = require("../../utils/api");
|
||||
Page({
|
||||
data: {
|
||||
pets: [],
|
||||
selected: [],
|
||||
walk: null,
|
||||
points: [],
|
||||
polyline: [],
|
||||
latitude: 31.23,
|
||||
longitude: 121.47,
|
||||
duration: "00:00",
|
||||
distance: "0.00",
|
||||
share: false,
|
||||
},
|
||||
onShow() {
|
||||
this.load();
|
||||
this.clock = setInterval(() => this.tick(), 1000);
|
||||
},
|
||||
onHide() {
|
||||
this.stopTimers();
|
||||
},
|
||||
onUnload() {
|
||||
this.stopTimers();
|
||||
},
|
||||
stopTimers() {
|
||||
clearInterval(this.clock);
|
||||
clearInterval(this.tracker);
|
||||
},
|
||||
async load() {
|
||||
try {
|
||||
const [pets, walks] = await Promise.all([
|
||||
secure("/pets"),
|
||||
secure("/walks"),
|
||||
]);
|
||||
const selected = (wx.getStorageSync("walk_pet_ids") || []).filter((id) =>
|
||||
pets.some((p) => p.id === id),
|
||||
);
|
||||
const walk =
|
||||
walks.find((w) => w.status === "active" || w.status === "paused") ||
|
||||
null;
|
||||
this.setData({ pets, selected, walk });
|
||||
if (walk) {
|
||||
this.renderWalk(walk);
|
||||
this.track();
|
||||
}
|
||||
} catch (e) {
|
||||
toast(e);
|
||||
}
|
||||
},
|
||||
pick(e) {
|
||||
if (this.data.walk) return;
|
||||
this.setData({ selected: e.detail.selected });
|
||||
wx.setStorageSync("walk_pet_ids", e.detail.selected);
|
||||
},
|
||||
async start() {
|
||||
if (!this.data.selected.length) {
|
||||
wx.showToast({ title: "请选择同行的狗狗", icon: "none" });
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const walk = await secure("/walks", "POST", {
|
||||
pet_ids: this.data.selected,
|
||||
});
|
||||
this.setData({ walk });
|
||||
this.track();
|
||||
this.point();
|
||||
} catch (e) {
|
||||
toast(e);
|
||||
}
|
||||
},
|
||||
track() {
|
||||
clearInterval(this.tracker);
|
||||
this.tracker = setInterval(() => this.point(), 15000);
|
||||
},
|
||||
async point() {
|
||||
if (!this.data.walk || this.data.walk.status !== "active") return;
|
||||
try {
|
||||
const pos = await wx.getLocation({ type: "gcj02" });
|
||||
const walk = await secure(
|
||||
"/walks/" + this.data.walk.id + "/points",
|
||||
"POST",
|
||||
{ latitude: pos.latitude, longitude: pos.longitude },
|
||||
);
|
||||
this.renderWalk(walk);
|
||||
} catch (e) {
|
||||
console.warn(e);
|
||||
}
|
||||
},
|
||||
renderWalk(walk) {
|
||||
const pts = (walk.points || []).map((p) => ({
|
||||
latitude: p.latitude,
|
||||
longitude: p.longitude,
|
||||
}));
|
||||
const last = pts[pts.length - 1];
|
||||
this.setData({
|
||||
walk,
|
||||
points: pts,
|
||||
polyline:
|
||||
pts.length > 1 ? [{ points: pts, color: "#268e6a", width: 5 }] : [],
|
||||
latitude: last ? last.latitude : this.data.latitude,
|
||||
longitude: last ? last.longitude : this.data.longitude,
|
||||
distance: (walk.distance_meters / 1000).toFixed(2),
|
||||
share: walk.share_enabled,
|
||||
});
|
||||
this.tick();
|
||||
},
|
||||
tick() {
|
||||
const walk = this.data.walk;
|
||||
if (!walk) return;
|
||||
const end = walk.ended_at
|
||||
? new Date(walk.ended_at)
|
||||
: walk.status === "paused"
|
||||
? new Date(walk.paused_at || Date.now())
|
||||
: new Date();
|
||||
const sec = Math.max(
|
||||
0,
|
||||
Math.floor((end - new Date(walk.started_at)) / 1000) -
|
||||
(walk.paused_seconds || 0),
|
||||
);
|
||||
this.setData({
|
||||
duration:
|
||||
String(Math.floor(sec / 60)).padStart(2, "0") +
|
||||
":" +
|
||||
String(sec % 60).padStart(2, "0"),
|
||||
});
|
||||
},
|
||||
async action(e) {
|
||||
const kind = e.currentTarget.dataset.kind;
|
||||
try {
|
||||
const walk = await secure(
|
||||
"/walks/" + this.data.walk.id + "/" + kind,
|
||||
"POST",
|
||||
);
|
||||
this.renderWalk(walk);
|
||||
if (kind === "finish") {
|
||||
clearInterval(this.tracker);
|
||||
wx.showToast({ title: "今天的快乐已记录", icon: "success" });
|
||||
}
|
||||
} catch (err) {
|
||||
toast(err);
|
||||
}
|
||||
},
|
||||
async shareChange(e) {
|
||||
try {
|
||||
const walk = await secure(
|
||||
"/walks/" + this.data.walk.id + "/share",
|
||||
"PUT",
|
||||
{ enabled: e.detail.value },
|
||||
);
|
||||
this.renderWalk(walk);
|
||||
} catch (err) {
|
||||
toast(err);
|
||||
}
|
||||
},
|
||||
onShareAppMessage() {
|
||||
const walk = this.data.walk;
|
||||
return {
|
||||
title: "肉垫计划 · 看看我们遛到哪儿了 🐾",
|
||||
path:
|
||||
walk && walk.share_enabled
|
||||
? "/pages/share/share?token=" + walk.share_token
|
||||
: "/pages/home/home",
|
||||
};
|
||||
},
|
||||
});
|
||||
Reference in New Issue
Block a user