chore: Storage 初版 — 家庭共享物品管理 (React+TS+Vite+Express+DuckDB)
Build and Deploy / build-image (push) Failing after 2m26s
Build and Deploy / build-image (push) Failing after 2m26s
This commit is contained in:
@@ -0,0 +1,75 @@
|
||||
import { useState } from "react";
|
||||
import Modal from "./Modal";
|
||||
import { useAppStore } from "../stores/app";
|
||||
import { transferEntity } from "../api";
|
||||
import { showToast } from "../lib/toast";
|
||||
|
||||
// 跨家庭转移: 将物品/整盒转移到"自己拥有管理权限"的另一个家庭 (决策点 2)
|
||||
export default function TransferModal({
|
||||
open, type, entityId, onClose, onDone,
|
||||
}: {
|
||||
open: boolean;
|
||||
type: "item" | "box";
|
||||
entityId: string;
|
||||
onClose?: () => void;
|
||||
onDone?: () => void;
|
||||
}) {
|
||||
const sourceFamilyId = useAppStore((s) => s.currentFamilyId);
|
||||
const families = useAppStore((s) => s.families);
|
||||
const [dst, setDst] = useState<string>("");
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
if (!open) return null;
|
||||
|
||||
const eligible = families.filter((f) => f.id !== sourceFamilyId && f.role === "admin");
|
||||
|
||||
const doTransfer = async () => {
|
||||
if (!dst || !sourceFamilyId) { showToast("请选择目标家庭"); return; }
|
||||
setLoading(true);
|
||||
try {
|
||||
await transferEntity(sourceFamilyId, {
|
||||
type, entityId, dstFamilyId: dst, dstParentBoxId: null,
|
||||
});
|
||||
showToast(`已转移到目标家庭`);
|
||||
onDone?.();
|
||||
onClose?.();
|
||||
} catch (e) {
|
||||
showToast(String(e));
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
return (
|
||||
<Modal
|
||||
open={open}
|
||||
title={type === "box" ? "转移整个盒子(含全部子盒与物品)" : "转移物品"}
|
||||
onClose={onClose}
|
||||
footer={
|
||||
<div className="modal-actions">
|
||||
<button className="btn btn-outline" onClick={onClose}>取消</button>
|
||||
<button className="btn btn-primary" disabled={!dst || loading} onClick={doTransfer}>
|
||||
{loading ? "转移中..." : "转移"}
|
||||
</button>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
{eligible.length === 0 ? (
|
||||
<p style={{ color: "var(--text-tertiary)", fontSize: 13 }}>没有可转移的家庭(需要你拥有该家庭的管理权限)</p>
|
||||
) : (
|
||||
<div className="picker-tree">
|
||||
{eligible.map((f) => (
|
||||
<button
|
||||
key={f.id}
|
||||
className={"picker-option" + (dst === f.id ? " picker-option-active" : "")}
|
||||
onClick={() => setDst(f.id)}
|
||||
>
|
||||
<span>{f.icon}</span> {f.name}
|
||||
</button>
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
{dst && <p style={{ fontSize: 12, color: "var(--text-secondary)", marginTop: 10 }}>转移后将从当前家庭移除,转移到目标家庭根层。</p>}
|
||||
</Modal>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user