From abe51739547f0766c1b2495996eb78b43c096093 Mon Sep 17 00:00:00 2001 From: eric Date: Wed, 11 Mar 2026 11:00:37 -0500 Subject: [PATCH] 'init2' --- src/composables/useKnowledge.js | 20 + src/config/app.js | 45 ++ src/data/mockData.js | 58 +-- src/views/CourseDetail.vue | 33 +- src/views/EbookDetail.vue | 17 +- src/views/Home.vue | 792 ++++++++++++++++++++++++++++++-- 6 files changed, 871 insertions(+), 94 deletions(-) diff --git a/src/composables/useKnowledge.js b/src/composables/useKnowledge.js index d3cd477..29952d4 100644 --- a/src/composables/useKnowledge.js +++ b/src/composables/useKnowledge.js @@ -4,6 +4,7 @@ import { mockEbooks, mockEbookChapters, } from '@/data/mockData.js' +import { ACCESS_LEVEL } from '@/utils/access.js' export async function fetchEbooks() { return [...mockEbooks] @@ -35,3 +36,22 @@ export async function fetchCourse(courseId) { const list = await fetchCourses() return list.find((item) => String(item.id) === String(courseId)) || null } + +/** 获取各课程的首个免费试看章节 */ +export async function fetchFreeTrialChapters() { + const courses = await fetchCourses() + const result = [] + for (const course of courses) { + const chapters = mockCourseChapters[course.id] || [] + const freeChapter = chapters.find((ch) => ch.access_level === ACCESS_LEVEL.FREE) + if (freeChapter) { + result.push({ + courseId: course.id, + courseTitle: course.title, + chapterId: freeChapter.id, + chapterTitle: freeChapter.title, + }) + } + } + return result +} diff --git a/src/config/app.js b/src/config/app.js index 7620a29..880a3a8 100644 --- a/src/config/app.js +++ b/src/config/app.js @@ -8,3 +8,48 @@ export const NAV_ITEMS = [ { path: '/', label: '首页' }, { path: '/vip', label: '会员' }, ] + +/** 网盘配置 - 多个独立资源 */ +export const NETDISK_CONFIG = { + enabled: true, + items: [ + { id: 1, name: '大模型', desc: 'GPT、Claude、国产大模型资源包', url: 'https://pan.baidu.com', icon: 'fire-o' }, + { id: 2, name: '懒人安装包', desc: '一键安装,开箱即用', url: 'https://pan.baidu.com', icon: 'down' }, + { id: 3, name: '课程讲义', desc: '配套 PPT、思维导图', url: 'https://pan.baidu.com', icon: 'notes-o' }, + { id: 4, name: '源码合集', desc: '课程示例代码与项目', url: 'https://pan.baidu.com', icon: 'records-o' }, + ], +} + +/** 限时优惠配置 */ +export const PROMO_CONFIG = { + enabled: false, + title: '限时优惠', + desc: '报名立享 8 折,仅限本周', + endAt: null, // 如 '2025-03-18 23:59:59' 可显示倒计时 + href: '/vip', +} + +/** 免费试看配置 */ +export const FREE_TRIAL_CONFIG = { + enabled: false, +} + +/** 课程预告配置 */ +export const COMING_SOON_CONFIG = { + enabled: true, + items: [ + { id: 'soon-1', title: '多模态 AI 实战', desc: '图文理解、语音识别、视频生成', eta: '即将上线' }, + { id: 'soon-2', title: 'AI 副业变现', desc: '从 0 到 1 打造 AI 产品', eta: '筹备中' }, + ], +} + +/** 学习群配置 - 仅展示 QQ 群,微信群隐藏 */ +export const STUDY_GROUP_CONFIG = { + enabled: true, + title: '加入学习群', + desc: '与 AI 学习者一起交流,获取最新资料与答疑', + items: [ + { id: 'wechat', name: '微信学习群', icon: 'chat-o', desc: '扫码加入,每日更新', href: '#', type: 'wechat', hidden: true }, + { id: 'qq', name: 'QQ 交流群', icon: 'friends-o', desc: '群号 123456789', href: '#', type: 'qq' }, + ], +} diff --git a/src/data/mockData.js b/src/data/mockData.js index 7ad43f8..880c87b 100644 --- a/src/data/mockData.js +++ b/src/data/mockData.js @@ -1,24 +1,27 @@ import { getCourseMarkdownRef, getEbookMarkdownRef } from '@/markdown/config.js' import { ACCESS_LEVEL } from '@/utils/access.js' -export const mockEbooks = [ - { - id: 1, - title: 'Prompt 工程实战手册', - cover: 'https://picsum.photos/400/300?random=ai1', - description: '从零到精通:提示词设计、Few-shot、思维链,让大模型听懂你的需求。', - category_id: 'ai', - sort_order: 1, - }, - { - id: 2, - title: 'AI Agent 开发指南', - cover: 'https://picsum.photos/400/300?random=ai2', - description: 'RAG、Function Calling、多 Agent 协作,打造可落地的智能体应用。', - category_id: 'ai', - sort_order: 2, - }, +/** 本地封面占位图(SVG data URI,含标题文字,无网络请求) */ +function localCover(title, gradient = 0, scale = 1) { + const gradients = [ + ['#059669', '#047857'], + ['#0891b2', '#0e7490'], + ['#6366f1', '#4f46e5'], + ['#8b5cf6', '#7c3aed'], + ] + const [c1, c2] = gradients[gradient % gradients.length] + const baseSize = String(title).length > 12 ? 18 : 22 + const fontSize = Math.round(baseSize * scale) + const safe = String(title).replace(/&/g, '&').replace(//g, '>').replace(/"/g, '"') + const svg = `${safe}` + return 'data:image/svg+xml,' + encodeURIComponent(svg) +} + +const ebookData = [ + { id: 1, title: 'Prompt 工程实战手册', description: '从零到精通:提示词设计、Few-shot、思维链,让大模型听懂你的需求。', category_id: 'ai', sort_order: 1 }, + { id: 2, title: 'AI Agent 开发指南', description: 'RAG、Function Calling、多 Agent 协作,打造可落地的智能体应用。', category_id: 'ai', sort_order: 2 }, ] +export const mockEbooks = ebookData.map((item, i) => ({ ...item, cover: localCover(item.title, i) })) export const mockEbookChapters = { 1: [ @@ -67,24 +70,11 @@ export const mockEbookChapters = { ], } -export const mockCourses = [ - { - id: 1, - title: 'ChatGPT 与大模型实战', - cover: 'https://picsum.photos/400/300?random=ai3', - description: 'GPT-4、Claude、国产大模型 API 调用,从 Prompt 到 RAG 全流程实战。', - category_id: 'ai', - sort_order: 1, - }, - { - id: 2, - title: 'AI Agent 从 0 到 1', - cover: 'https://picsum.photos/400/300?random=ai4', - description: 'LangChain、AutoGPT、多 Agent 协作,打造能自主完成任务的智能体。', - category_id: 'ai', - sort_order: 2, - }, +const courseData = [ + { id: 1, title: 'ChatGPT 与大模型实战', description: 'GPT-4、Claude、国产大模型 API 调用,从 Prompt 到 RAG 全流程实战。', category_id: 'ai', sort_order: 1 }, + { id: 2, title: 'AI Agent 从 0 到 1', description: 'LangChain、AutoGPT、多 Agent 协作,打造能自主完成任务的智能体。', category_id: 'ai', sort_order: 2 }, ] +export const mockCourses = courseData.map((item, i) => ({ ...item, cover: localCover(item.title, i, 2) })) export const mockCourseChapters = { 1: [ diff --git a/src/views/CourseDetail.vue b/src/views/CourseDetail.vue index 295872f..0fef8e7 100644 --- a/src/views/CourseDetail.vue +++ b/src/views/CourseDetail.vue @@ -11,8 +11,8 @@