完成50%

This commit is contained in:
2026-07-23 08:23:59 +08:00
parent 9b0ad62df4
commit f1edc6b533
218 changed files with 24318 additions and 5514 deletions
+66 -20
View File
@@ -2,7 +2,7 @@
<template>
<view class="article-list-page" :class="{ 'article-list-state--loading': listState === 'loading', 'article-list-state--empty': listState === 'empty', 'article-list-state--error': listState === 'error' }">
<ModulePageBackground module="family" />
<view class="article-list-header"><PageHeader title="谱文" action="新建" @action="createArticle" /></view>
<view class="article-list-header"><PageHeader title="谱文" :action="hasValidContext ? '新建' : ''" @action="createArticle" /></view>
<view v-if="listState === 'loading'" class="article-list-loading">
<AppLoading text="正在整理家族谱文" description="请稍候,正在读取家训、往事与序言。" />
@@ -37,9 +37,9 @@
</template>
<view v-else class="article-list-state-card">
<text>{{ listState === 'empty' ? '还没有谱文' : '谱文列表暂不可用' }}</text>
<text>{{ listState === 'empty' ? '记录第一篇家风家训或家族往事。' : '请稍后重新查看,已有谱文不会受到影响。' }}</text>
<AppButton :type="listState === 'error' ? 'secondary' : 'primary'" block :label="listState === 'error' ? '重新查看' : '新建谱文'" @click="listState === 'error' ? restoreArticles() : createArticle()" />
<text>{{ stateCopy.title }}</text>
<text>{{ stateCopy.copy }}</text>
<AppButton :type="listState === 'error' ? 'secondary' : 'primary'" block :label="stateCopy.action" @click="handleStateAction" />
</view>
</view>
</view>
@@ -52,14 +52,16 @@ import AppButton from "@/components/AppButton.vue";
import AppLoading from "@/components/AppLoading.vue";
import ModulePageBackground from "@/components/ModulePageBackground.vue";
import PageHeader from "@/components/PageHeader.vue";
import {
getGenealogyFixtureAccess,
listFamilyArticleFixtures,
} from "@/data/mock.js";
import { goBack, openPage } from "@/utils/navigation.js";
const articleCategories = ["全部", "家风家训", "家族往事", "族谱序言"];
const baseArticles = [
{ id: "101", category: "家风家训", title: "孝友传家的日常", summary: "从敬老、睦亲与守信的小事里,看见家风如何代代相传。", author: "汤文正", updatedAt: "今天更新" },
{ id: "102", category: "家族往事", title: "祖居门前的那棵桂花树", summary: "长辈口述的旧居记忆,以及每年中秋一家人相聚的故事。", author: "汤淑华", updatedAt: "昨天更新" },
{ id: "103", category: "族谱序言", title: "续修族谱序", summary: "说明本次续修的缘起、资料来源与共同参与的家人。", author: "谱主", updatedAt: "5 月 12 日" },
];
const articles = ref([...baseArticles]);
const genealogyId = ref("");
const hasValidContext = ref(false);
const articles = ref([]);
const activeCategory = ref("全部");
const keyword = ref("");
const listState = ref("loading");
@@ -71,20 +73,64 @@ const filteredArticles = computed(() => {
return categoryMatched && keywordMatched;
});
});
const stateCopy = computed(() => ({
empty: {
title: "还没有谱文",
copy: "当前家谱尚无可读取谱文,真实写接口接入后才能新增。",
action: "填写谱文预览",
},
error: {
title: "谱文列表暂不可用",
copy: "请稍后重新查看,已有谱文不会受到影响。",
action: "重新查看",
},
invalid: {
title: "谱文入口无效",
copy: "没有找到可访问的成员家谱,页面不会展示其他家谱内容。",
action: "返回上一页",
},
}[listState.value]));
onLoad((query) => {
const count = Math.max(1, Math.min(Number(query.count) || baseArticles.length, 50));
articles.value = Array.from({ length: count }, (_, index) => ({
...baseArticles[index % baseArticles.length],
id: String(101 + index),
title: count > baseArticles.length ? `${baseArticles[index % baseArticles.length].title}(第 ${index + 1} 篇)` : baseArticles[index].title,
}));
listState.value = ["loading", "empty", "error"].includes(query.state) ? query.state : "ready";
genealogyId.value = String(query.genealogyId || "");
hasValidContext.value = ["owner", "member"].includes(
getGenealogyFixtureAccess(genealogyId.value).accessRole,
);
if (!genealogyId.value || !hasValidContext.value) {
listState.value = "invalid";
return;
}
articles.value = listFamilyArticleFixtures(genealogyId.value);
listState.value = ["loading", "empty", "error"].includes(query.state)
? query.state
: articles.value.length
? "ready"
: "empty";
});
const openArticle = (article) => uni.navigateTo({ url: `/pages/family/f05-article-detail?articleId=${article.id}` });
const createArticle = () => uni.navigateTo({ url: "/pages/family/f06-article-editor?mode=create" });
const restoreArticles = () => { listState.value = "ready"; };
const openArticle = (article) =>
openPage(
"F05",
{ genealogyId: genealogyId.value, articleId: String(article.id) },
"F04",
);
const createArticle = () =>
hasValidContext.value
? openPage(
"F06",
{ genealogyId: genealogyId.value, mode: "create" },
"F04",
)
: Promise.resolve(false);
const restoreArticles = () => {
articles.value = listFamilyArticleFixtures(genealogyId.value);
listState.value = articles.value.length ? "ready" : "empty";
};
const handleStateAction = () => {
if (listState.value === "invalid") return goBack();
if (listState.value === "error") return restoreArticles();
return createArticle();
};
const resetFilters = () => { keyword.value = ""; activeCategory.value = "全部"; };
</script>