diff --git a/app.json b/app.json
index 1c052d0..08b036c 100644
--- a/app.json
+++ b/app.json
@@ -1,7 +1,11 @@
{
"pages": [
"pages/home/home",
- "pages/index/index"
+ "pages/index/index",
+ "pages/knowledge/index",
+ "pages/knowledge/list",
+ "pages/knowledge/article",
+ "pages/webview/index"
],
"window": {
"navigationBarTitleText": "我的第一个小程序"
diff --git a/pages/home/home.js b/pages/home/home.js
index 6f77b34..bbb74ab 100644
--- a/pages/home/home.js
+++ b/pages/home/home.js
@@ -3,5 +3,11 @@ Page({
wx.navigateTo({
url: '/pages/index/index'
})
+ },
+
+ goToKnowledge: function () {
+ wx.navigateTo({
+ url: '/pages/knowledge/index'
+ })
}
})
diff --git a/pages/home/home.wxml b/pages/home/home.wxml
index 677121b..4e82e62 100644
--- a/pages/home/home.wxml
+++ b/pages/home/home.wxml
@@ -16,6 +16,14 @@
+
+
+ 📚
+
+ 学点塔罗
+ 了解塔罗基础知识
+
+
diff --git a/pages/knowledge/article.js b/pages/knowledge/article.js
new file mode 100644
index 0000000..c95a1f6
--- /dev/null
+++ b/pages/knowledge/article.js
@@ -0,0 +1,33 @@
+const { getArticleById } = require('../../utils/knowledgeData');
+
+Page({
+ data: {
+ article: null
+ },
+
+ onLoad(options) {
+ const id = options.id;
+ const article = getArticleById(id);
+
+ if (article) {
+ this.setData({
+ article: article
+ });
+ } else {
+ wx.showToast({
+ title: '文章不存在',
+ icon: 'none'
+ });
+ setTimeout(() => {
+ wx.navigateBack();
+ }, 1500);
+ }
+ },
+
+ // 去占卜
+ goToDivination() {
+ wx.navigateTo({
+ url: '/pages/index/index'
+ });
+ }
+});
diff --git a/pages/knowledge/article.json b/pages/knowledge/article.json
new file mode 100644
index 0000000..7d33a5f
--- /dev/null
+++ b/pages/knowledge/article.json
@@ -0,0 +1,5 @@
+{
+ "navigationBarTitleText": "文章详情",
+ "navigationBarBackgroundColor": "#1a1a2e",
+ "navigationBarTextStyle": "white"
+}
\ No newline at end of file
diff --git a/pages/knowledge/article.wxml b/pages/knowledge/article.wxml
new file mode 100644
index 0000000..09cee28
--- /dev/null
+++ b/pages/knowledge/article.wxml
@@ -0,0 +1,16 @@
+
+
+ {{article.title}}
+ {{article.summary}}
+
+
+
+ {{article.content}}
+
+
+
+
+
+
diff --git a/pages/knowledge/article.wxss b/pages/knowledge/article.wxss
new file mode 100644
index 0000000..34313a0
--- /dev/null
+++ b/pages/knowledge/article.wxss
@@ -0,0 +1,74 @@
+.container {
+ min-height: 100vh;
+ background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
+ padding: 40rpx 30rpx 120rpx;
+}
+
+.article-header {
+ margin-bottom: 50rpx;
+}
+
+.article-title {
+ display: block;
+ font-size: 44rpx;
+ font-weight: 600;
+ color: #fff;
+ line-height: 1.4;
+ margin-bottom: 24rpx;
+}
+
+.article-summary {
+ display: block;
+ font-size: 28rpx;
+ color: rgba(255, 255, 255, 0.7);
+ line-height: 1.6;
+ padding: 20rpx 24rpx;
+ background: rgba(255, 255, 255, 0.08);
+ border-radius: 12rpx;
+ border-left: 4rpx solid rgba(255, 255, 255, 0.3);
+}
+
+.article-content {
+ background: rgba(255, 255, 255, 0.05);
+ backdrop-filter: blur(10px);
+ border-radius: 16rpx;
+ padding: 40rpx 32rpx;
+ border: 1px solid rgba(255, 255, 255, 0.1);
+}
+
+.content-text {
+ display: block;
+ font-size: 30rpx;
+ color: rgba(255, 255, 255, 0.9);
+ line-height: 1.8;
+ white-space: pre-wrap;
+}
+
+.bottom-action {
+ position: fixed;
+ bottom: 0;
+ left: 0;
+ right: 0;
+ padding: 20rpx 30rpx;
+ background: linear-gradient(to top, #1a1a2e 80%, transparent);
+}
+
+.divination-btn {
+ width: 100%;
+ height: 88rpx;
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
+ border-radius: 44rpx;
+ color: #fff;
+ font-size: 32rpx;
+ font-weight: 500;
+ display: flex;
+ align-items: center;
+ justify-content: center;
+ border: none;
+ box-shadow: 0 8rpx 24rpx rgba(102, 126, 234, 0.3);
+}
+
+.btn-hover {
+ opacity: 0.8;
+ transform: scale(0.98);
+}
diff --git a/pages/knowledge/index.js b/pages/knowledge/index.js
new file mode 100644
index 0000000..48cb937
--- /dev/null
+++ b/pages/knowledge/index.js
@@ -0,0 +1,21 @@
+const { getCategories } = require('../../utils/knowledgeData');
+
+Page({
+ data: {
+ categories: []
+ },
+
+ onLoad() {
+ this.setData({
+ categories: getCategories()
+ });
+ },
+
+ // 点击分类卡片
+ goToList(e) {
+ const category = e.currentTarget.dataset.category;
+ wx.navigateTo({
+ url: `/pages/knowledge/list?category=${category}`
+ });
+ }
+});
diff --git a/pages/knowledge/index.json b/pages/knowledge/index.json
new file mode 100644
index 0000000..c1cf06e
--- /dev/null
+++ b/pages/knowledge/index.json
@@ -0,0 +1,5 @@
+{
+ "navigationBarTitleText": "塔罗知识",
+ "navigationBarBackgroundColor": "#1a1a2e",
+ "navigationBarTextStyle": "white"
+}
\ No newline at end of file
diff --git a/pages/knowledge/index.wxml b/pages/knowledge/index.wxml
new file mode 100644
index 0000000..de11cfd
--- /dev/null
+++ b/pages/knowledge/index.wxml
@@ -0,0 +1,19 @@
+
+
+
+
+
+ {{item.icon}}
+ {{item.name}}
+
+
+
diff --git a/pages/knowledge/index.wxss b/pages/knowledge/index.wxss
new file mode 100644
index 0000000..015712e
--- /dev/null
+++ b/pages/knowledge/index.wxss
@@ -0,0 +1,50 @@
+.container {
+ min-height: 100vh;
+ background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
+ padding: 40rpx 30rpx;
+}
+
+.header {
+ text-align: center;
+ margin-bottom: 60rpx;
+}
+
+.page-title {
+ font-size: 48rpx;
+ font-weight: 600;
+ color: #fff;
+ letter-spacing: 4rpx;
+}
+
+.category-list {
+ display: flex;
+ flex-direction: column;
+ gap: 30rpx;
+}
+
+.category-card {
+ background: rgba(255, 255, 255, 0.08);
+ backdrop-filter: blur(10px);
+ border-radius: 20rpx;
+ padding: 50rpx 40rpx;
+ display: flex;
+ align-items: center;
+ gap: 30rpx;
+ border: 1px solid rgba(255, 255, 255, 0.1);
+ transition: all 0.3s ease;
+}
+
+.card-hover {
+ background: rgba(255, 255, 255, 0.12);
+ transform: translateY(-4rpx);
+}
+
+.category-icon {
+ font-size: 60rpx;
+}
+
+.category-name {
+ font-size: 36rpx;
+ color: #fff;
+ font-weight: 500;
+}
diff --git a/pages/knowledge/list.js b/pages/knowledge/list.js
new file mode 100644
index 0000000..e16e267
--- /dev/null
+++ b/pages/knowledge/list.js
@@ -0,0 +1,49 @@
+const { getArticlesByCategory, getCategories } = require('../../utils/knowledgeData');
+
+Page({
+ data: {
+ category: '',
+ categoryName: '',
+ articles: []
+ },
+
+ onLoad(options) {
+ const category = options.category || 'beginner';
+ const categories = getCategories();
+ const categoryInfo = categories.find(c => c.id === category);
+
+ this.setData({
+ category: category,
+ categoryName: categoryInfo ? categoryInfo.name : '文章列表',
+ articles: getArticlesByCategory(category)
+ });
+ },
+
+ // 点击文章
+ goToArticle(e) {
+ const id = e.currentTarget.dataset.id;
+ const articles = this.data.articles;
+ const article = articles.find(a => a.id === id);
+
+ if (!article) {
+ wx.showToast({
+ title: '文章不存在',
+ icon: 'none'
+ });
+ return;
+ }
+
+ // 根据文章类型跳转
+ if (article.type === 'web') {
+ // 外链文章 → 跳转到 webview
+ wx.navigateTo({
+ url: `/pages/webview/index?url=${encodeURIComponent(article.url)}`
+ });
+ } else {
+ // 本地文章 → 跳转到 article 详情页
+ wx.navigateTo({
+ url: `/pages/knowledge/article?id=${id}`
+ });
+ }
+ }
+});
diff --git a/pages/knowledge/list.json b/pages/knowledge/list.json
new file mode 100644
index 0000000..801ad54
--- /dev/null
+++ b/pages/knowledge/list.json
@@ -0,0 +1,5 @@
+{
+ "navigationBarTitleText": "文章列表",
+ "navigationBarBackgroundColor": "#1a1a2e",
+ "navigationBarTextStyle": "white"
+}
\ No newline at end of file
diff --git a/pages/knowledge/list.wxml b/pages/knowledge/list.wxml
new file mode 100644
index 0000000..d171c2e
--- /dev/null
+++ b/pages/knowledge/list.wxml
@@ -0,0 +1,19 @@
+
+
+
+
+
+ {{item.title}}
+ {{item.summary}}
+
+
+
diff --git a/pages/knowledge/list.wxss b/pages/knowledge/list.wxss
new file mode 100644
index 0000000..6109e5e
--- /dev/null
+++ b/pages/knowledge/list.wxss
@@ -0,0 +1,52 @@
+.container {
+ min-height: 100vh;
+ background: linear-gradient(135deg, #1a1a2e 0%, #16213e 100%);
+ padding: 40rpx 30rpx;
+}
+
+.header {
+ text-align: center;
+ margin-bottom: 50rpx;
+}
+
+.page-title {
+ font-size: 44rpx;
+ font-weight: 600;
+ color: #fff;
+ letter-spacing: 2rpx;
+}
+
+.article-list {
+ display: flex;
+ flex-direction: column;
+ gap: 24rpx;
+}
+
+.article-item {
+ background: rgba(255, 255, 255, 0.08);
+ backdrop-filter: blur(10px);
+ border-radius: 16rpx;
+ padding: 36rpx 32rpx;
+ border: 1px solid rgba(255, 255, 255, 0.1);
+ transition: all 0.3s ease;
+}
+
+.item-hover {
+ background: rgba(255, 255, 255, 0.12);
+ transform: translateX(8rpx);
+}
+
+.article-title {
+ display: block;
+ font-size: 32rpx;
+ color: #fff;
+ font-weight: 500;
+ margin-bottom: 16rpx;
+}
+
+.article-summary {
+ display: block;
+ font-size: 26rpx;
+ color: rgba(255, 255, 255, 0.6);
+ line-height: 1.6;
+}
diff --git a/pages/webview/index.js b/pages/webview/index.js
new file mode 100644
index 0000000..afc031b
--- /dev/null
+++ b/pages/webview/index.js
@@ -0,0 +1,21 @@
+Page({
+ data: {
+ url: ''
+ },
+
+ onLoad(options) {
+ if (options.url) {
+ this.setData({
+ url: decodeURIComponent(options.url)
+ });
+ } else {
+ wx.showToast({
+ title: 'URL参数缺失',
+ icon: 'none'
+ });
+ setTimeout(() => {
+ wx.navigateBack();
+ }, 1500);
+ }
+ }
+});
diff --git a/pages/webview/index.json b/pages/webview/index.json
new file mode 100644
index 0000000..7d33a5f
--- /dev/null
+++ b/pages/webview/index.json
@@ -0,0 +1,5 @@
+{
+ "navigationBarTitleText": "文章详情",
+ "navigationBarBackgroundColor": "#1a1a2e",
+ "navigationBarTextStyle": "white"
+}
\ No newline at end of file
diff --git a/pages/webview/index.wxml b/pages/webview/index.wxml
new file mode 100644
index 0000000..34c346a
--- /dev/null
+++ b/pages/webview/index.wxml
@@ -0,0 +1 @@
+
diff --git a/pages/webview/index.wxss b/pages/webview/index.wxss
new file mode 100644
index 0000000..b53bcd9
--- /dev/null
+++ b/pages/webview/index.wxss
@@ -0,0 +1,2 @@
+/* webview 页面样式 */
+/* web-view 组件会自动占满整个页面,无需额外样式 */
diff --git a/utils/knowledgeData.js b/utils/knowledgeData.js
new file mode 100644
index 0000000..395d9eb
--- /dev/null
+++ b/utils/knowledgeData.js
@@ -0,0 +1,350 @@
+// 塔罗知识模块 - 本地静态数据 V1.5
+// 分类:beginner(新手必看), inspiration(提问灵感), tips(塔罗小知识)
+// 支持混合内容:type: 'local'(本地文章) | 'web'(外链文章)
+
+const knowledgeData = [
+ // ========== 新手必看 ==========
+ {
+ id: 'beginner_001',
+ category: 'beginner',
+ title: '什么是塔罗牌?',
+ summary: '了解塔罗牌的起源、结构和基本用途',
+ type: 'local',
+ content: `塔罗牌是一套由78张牌组成的占卜工具,起源于15世纪的欧洲。
+
+它分为两部分:
+• 大阿尔卡那(22张):代表人生重大主题和转折点
+• 小阿尔卡那(56张):代表日常生活的细节和事件
+
+塔罗牌不是用来"算命"的,而是一面镜子,帮助你看清内心深处的想法和感受。
+
+它通过象征性的图像,引导你思考问题的不同角度,从而做出更明智的选择。`,
+ url: ''
+ },
+ {
+ id: 'beginner_002',
+ category: 'beginner',
+ title: '塔罗占卜准吗?',
+ summary: '理解塔罗占卜的本质和正确心态',
+ type: 'local',
+ content: `塔罗牌不是"预测未来"的工具,而是"探索可能性"的方式。
+
+它的准确性取决于:
+1. 你的问题是否清晰具体
+2. 你是否真诚面对自己的内心
+3. 你是否愿意从牌面中获得启发
+
+塔罗牌反映的是当下的能量和趋势,未来始终掌握在你自己手中。
+
+把塔罗当作一个智慧的朋友,它会给你建议,但最终的决定权在你。`,
+ url: ''
+ },
+ {
+ id: 'beginner_003',
+ category: 'beginner',
+ title: '如何正确提问?',
+ summary: '掌握提问技巧,让占卜更有意义',
+ type: 'local',
+ content: `好的问题决定了占卜的质量。
+
+❌ 避免的问题类型:
+• 是非题:"他喜欢我吗?"
+• 时间预测:"我什么时候能升职?"
+• 替他人占卜:"他在想什么?"
+
+✅ 推荐的问题方式:
+• "在这段关系中,我需要注意什么?"
+• "如果我选择换工作,可能会面临哪些挑战?"
+• "我该如何改善目前的困境?"
+
+记住:问"如何"比问"会不会"更有价值。`,
+ url: ''
+ },
+ {
+ id: 'beginner_004',
+ category: 'beginner',
+ title: '正位和逆位是什么意思?',
+ summary: '理解牌面方向的含义',
+ type: 'local',
+ content: `塔罗牌在占卜时可能以两种方向出现:
+
+正位:
+• 牌面图案正向朝上
+• 通常代表该牌的直接含义
+• 能量流畅、显现明显
+
+逆位:
+• 牌面图案倒置
+• 可能代表能量受阻、内化或过度
+• 需要更深入的反思
+
+逆位不等于"坏",它只是提醒你:
+这个能量可能被压抑、延迟,或需要从另一个角度理解。`,
+ url: ''
+ },
+ {
+ id: 'web_002',
+ category: 'beginner',
+ title: '塔罗牌入门指南',
+ summary: '系统化的塔罗学习路径',
+ type: 'web',
+ content: '',
+ url: 'http://www.90000li.com/tarot/2/999d793fce9f4f3782c9b24769232942.html'
+ },
+
+ // ========== 提问灵感 ==========
+ {
+ id: 'inspiration_001',
+ category: 'inspiration',
+ title: '关于感情的提问',
+ summary: '如何更好地探索情感问题',
+ type: 'local',
+ content: `感情类问题是塔罗占卜中最常见的主题。
+
+优质提问示例:
+• "在这段关系中,我需要学习什么?"
+• "我该如何处理目前的情感困惑?"
+• "这段关系对我的成长有什么意义?"
+• "如何改善我们之间的沟通?"
+
+避免问:
+• "他/她喜欢我吗?"(过于简单)
+• "我们会结婚吗?"(预测结果)
+• "他/她现在在想什么?"(替他人占卜)
+
+把焦点放在自己身上,问题会更有力量。`,
+ url: ''
+ },
+ {
+ id: 'inspiration_002',
+ category: 'inspiration',
+ title: '关于事业的提问',
+ summary: '探索职业发展和工作选择',
+ type: 'local',
+ content: `事业问题需要更具体的角度。
+
+优质提问示例:
+• "如果我选择这份工作,可能面临哪些挑战?"
+• "我该如何提升目前的工作表现?"
+• "这个项目的潜在风险是什么?"
+• "我的职业发展方向应该关注什么?"
+
+避免问:
+• "我会升职吗?"(是非题)
+• "我什么时候能找到工作?"(时间预测)
+
+把问题聚焦在"如何做得更好",而不是"会不会成功"。`,
+ url: ''
+ },
+ {
+ id: 'inspiration_003',
+ category: 'inspiration',
+ title: '关于个人成长的提问',
+ summary: '用塔罗探索内在自我',
+ type: 'local',
+ content: `塔罗牌最擅长的,就是帮助你认识自己。
+
+优质提问示例:
+• "我目前最需要关注的内在课题是什么?"
+• "如何突破当前的心理困境?"
+• "我的潜在优势是什么?"
+• "这段经历想教会我什么?"
+
+这类问题没有"对错",只有"看见"。
+
+通过塔罗,你可以:
+• 发现盲点
+• 理解情绪
+• 找到方向
+• 获得力量`,
+ url: ''
+ },
+ {
+ id: 'inspiration_004',
+ category: 'inspiration',
+ title: '关于决策的提问',
+ summary: '在选择中寻找方向',
+ type: 'local',
+ content: `面对选择时,塔罗可以帮你看清不同路径。
+
+优质提问示例:
+• "选择A和选择B分别会带来什么影响?"
+• "做这个决定时,我需要考虑什么?"
+• "这个选择对我的长期发展有何意义?"
+
+建议使用"对比牌阵":
+• 左边:选择A的可能结果
+• 右边:选择B的可能结果
+• 中间:核心建议
+
+记住:塔罗给建议,但决定权永远在你手中。`,
+ url: ''
+ },
+ {
+ id: 'web_003',
+ category: 'inspiration',
+ title: '塔罗占卜实战技巧',
+ summary: '提升占卜准确度的方法',
+ type: 'web',
+ content: '',
+ url: 'http://www.90000li.com/tarot/2/999d793fce9f4f3782c9b24769232942.html'
+ },
+
+ // ========== 塔罗小知识 ==========
+ {
+ id: 'tips_001',
+ category: 'tips',
+ title: '为什么要"洗牌"?',
+ summary: '了解洗牌的意义和能量连接',
+ type: 'local',
+ content: `洗牌不只是打乱顺序,它是一个能量连接的过程。
+
+洗牌的作用:
+1. 清除上一次占卜的能量残留
+2. 让你的意识与牌建立连接
+3. 创造一个专注的仪式感
+
+在洗牌时:
+• 保持内心平静
+• 专注于你的问题
+• 感受手中牌的重量
+
+这个过程帮助你进入"占卜状态",让解读更准确。`,
+ url: ''
+ },
+ {
+ id: 'tips_002',
+ category: 'tips',
+ title: '同一个问题可以占卜多次吗?',
+ summary: '理解占卜频率和心态',
+ type: 'local',
+ content: `不建议短时间内反复占卜同一个问题。
+
+原因:
+• 频繁占卜会让能量混乱
+• 你可能只是在寻找"想要的答案"
+• 过度依赖会削弱你的判断力
+
+建议:
+• 同一问题至少间隔1-2周
+• 如果情况有明显变化,可以重新占卜
+• 把塔罗当作参考,而不是唯一依据
+
+记住:塔罗是工具,不是拐杖。`,
+ url: ''
+ },
+ {
+ id: 'tips_003',
+ category: 'tips',
+ title: '什么时候不适合占卜?',
+ summary: '选择合适的占卜时机',
+ type: 'local',
+ content: `并非所有时刻都适合占卜。
+
+不适合占卜的情况:
+• 情绪极度激动或崩溃时
+• 只想听"好消息"时
+• 已经有明确答案,只是不想接受时
+• 身体极度疲惫时
+
+最佳占卜时机:
+• 内心相对平静
+• 真诚想要获得启发
+• 愿意接受任何答案
+• 精神状态良好
+
+占卜需要一颗开放的心。`,
+ url: ''
+ },
+ {
+ id: 'tips_004',
+ category: 'tips',
+ title: '塔罗牌需要"养牌"吗?',
+ summary: '关于塔罗牌保养的真相',
+ type: 'local',
+ content: `网上有很多"养牌"的说法,但其实没那么复杂。
+
+真正重要的:
+• 保持牌面清洁
+• 避免潮湿和暴晒
+• 用心对待你的牌
+
+不必要的仪式:
+• 不需要"开光"
+• 不需要特定时间才能用
+• 不需要复杂的净化仪式
+
+塔罗牌是工具,你的诚意比仪式更重要。
+
+用心使用,它自然会成为你的好伙伴。`,
+ url: ''
+ },
+ {
+ id: 'tips_005',
+ category: 'tips',
+ title: '塔罗牌可以借给别人吗?',
+ summary: '关于塔罗牌的使用边界',
+ type: 'local',
+ content: `这是个人选择,没有绝对的对错。
+
+传统观点:
+• 塔罗牌是私人物品,不宜外借
+• 避免能量混杂
+
+现代观点:
+• 如果你不介意,可以分享
+• 用后可以简单整理一下
+
+建议:
+• 如果你很在意,就不要借
+• 如果借出后感觉不舒服,可以重新洗牌
+• 最重要的是尊重自己的感受
+
+你的感受才是最重要的边界。`,
+ url: ''
+ },
+ {
+ id: 'web_001',
+ category: 'tips',
+ title: '塔罗牌基础知识介绍',
+ summary: '来自外部知识库的深度解析',
+ type: 'web',
+ content: '',
+ url: 'http://www.90000li.com/tarot/2/999d793fce9f4f3782c9b24769232942.html'
+ },
+ {
+ id: 'web_004',
+ category: 'tips',
+ title: '大阿卡那与小阿卡那的奥秘',
+ summary: '探索大阿卡那与小阿卡那的神秘世界',
+ type: 'web',
+ content: '',
+ url: 'http://www.90000li.com/tarot/null/4ae0c88e9c34499485250ec9bfa58098.html'
+ }
+];
+
+// 获取所有分类
+function getCategories() {
+ return [
+ { id: 'beginner', name: '新手必看', icon: '📖' },
+ { id: 'inspiration', name: '提问灵感', icon: '💡' },
+ { id: 'tips', name: '塔罗小知识', icon: '✨' }
+ ];
+}
+
+// 根据分类获取文章列表
+function getArticlesByCategory(category) {
+ return knowledgeData.filter(item => item.category === category);
+}
+
+// 根据ID获取文章详情
+function getArticleById(id) {
+ return knowledgeData.find(item => item.id === id);
+}
+
+module.exports = {
+ knowledgeData,
+ getCategories,
+ getArticlesByCategory,
+ getArticleById
+};