mirror of
https://github.com/patdelphi/suanming.git
synced 2026-02-28 05:33:11 +08:00
feat: Complete overhaul of Bazi analysis system with professional features
- Implement dynamic Bazi analysis based on traditional Four Pillars theory - Add comprehensive pillar interpretations (year, month, day, hour) - Implement precise Dayun (Great Luck) and yearly fortune calculations - Add detailed 6-year fortune analysis with monthly highlights - Replace fixed templates with dynamic pattern analysis - Implement Wuxing (Five Elements) strength analysis system - Add professional life guidance and modern application suggestions - Create new CompleteBaziAnalysis component with modern UI - Update BaziDetailsPage with improved user experience - Integrate all analysis modules into unified display system - Add missing getElementRelation method to BaziAnalyzer - Ensure all analysis content is dynamically generated from real Bazi data
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
import React from 'react';
|
||||
import ComprehensiveBaziAnalysis from './ComprehensiveBaziAnalysis';
|
||||
import CompleteBaziAnalysis from './CompleteBaziAnalysis';
|
||||
import BaziAnalysisDisplay from './BaziAnalysisDisplay';
|
||||
|
||||
interface AnalysisResultDisplayProps {
|
||||
@@ -44,16 +44,28 @@ const AnalysisResultDisplay: React.FC<AnalysisResultDisplayProps> = ({ analysisR
|
||||
|
||||
// 渲染八字命理分析
|
||||
const renderBaziAnalysis = () => {
|
||||
// 如果有分析结果数据,优先使用 ComprehensiveBaziAnalysis 组件
|
||||
if (analysisResult && analysisResult.data) {
|
||||
return <ComprehensiveBaziAnalysis analysisResult={analysisResult} />;
|
||||
// 如果有 birthDate,使用新的 CompleteBaziAnalysis 组件
|
||||
if (birthDate) {
|
||||
return <CompleteBaziAnalysis birthDate={birthDate} />;
|
||||
}
|
||||
// 如果有 birthDate 但没有分析结果,使用 BaziAnalysisDisplay 组件
|
||||
// 如果有分析结果但没有 birthDate,尝试从结果中提取出生信息
|
||||
if (analysisResult && analysisResult.data) {
|
||||
const basicInfo = analysisResult.data.basic_info;
|
||||
if (basicInfo && basicInfo.personal_data) {
|
||||
const extractedBirthDate = {
|
||||
date: basicInfo.personal_data.birth_date || '',
|
||||
time: basicInfo.personal_data.birth_time || '12:00',
|
||||
name: basicInfo.personal_data.name || '',
|
||||
gender: basicInfo.personal_data.gender === '男性' ? 'male' : 'female'
|
||||
};
|
||||
return <CompleteBaziAnalysis birthDate={extractedBirthDate} />;
|
||||
}
|
||||
}
|
||||
// 回退到旧的组件(向后兼容)
|
||||
if (birthDate) {
|
||||
return <BaziAnalysisDisplay birthDate={birthDate} />;
|
||||
}
|
||||
// 默认使用 ComprehensiveBaziAnalysis 组件(向后兼容)
|
||||
return <ComprehensiveBaziAnalysis analysisResult={analysisResult} />;
|
||||
return <div className="text-center text-red-600 p-8">请提供出生日期和时间进行八字分析</div>;
|
||||
};
|
||||
|
||||
// 渲染紫微斗数分析
|
||||
|
||||
@@ -37,6 +37,25 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
const [baziDetailsData, setBaziDetailsData] = useState<BaziDetailsData | null>(null);
|
||||
const [wuxingAnalysisData, setWuxingAnalysisData] = useState<WuxingAnalysisData | null>(null);
|
||||
const [fullBaziAnalysisData, setFullBaziAnalysisData] = useState<any>(null);
|
||||
|
||||
// 辅助方法
|
||||
const getBranchElement = (branch: string): string => {
|
||||
const branchElements: { [key: string]: string } = {
|
||||
'子': '水', '丑': '土', '寅': '木', '卯': '木', '辰': '土', '巳': '火',
|
||||
'午': '火', '未': '土', '申': '金', '酉': '金', '戌': '土', '亥': '水'
|
||||
};
|
||||
return branchElements[branch] || '土';
|
||||
};
|
||||
|
||||
const getStemYinYang = (stem: string): string => {
|
||||
const yangStems = ['甲', '丙', '戊', '庚', '壬'];
|
||||
return yangStems.includes(stem) ? '阳' : '阴';
|
||||
};
|
||||
|
||||
const getBranchYinYang = (branch: string): string => {
|
||||
const yangBranches = ['子', '寅', '辰', '午', '申', '戌'];
|
||||
return yangBranches.includes(branch) ? '阳' : '阴';
|
||||
};
|
||||
|
||||
// 五行颜色配置
|
||||
const elementColors: { [key: string]: string } = {
|
||||
@@ -71,69 +90,143 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
'阴': 'text-purple-600 bg-purple-50 border-purple-300'
|
||||
};
|
||||
|
||||
// 调用 Supabase Edge Functions
|
||||
// 调用本地API
|
||||
useEffect(() => {
|
||||
const fetchAnalysisData = async () => {
|
||||
try {
|
||||
setIsLoading(true);
|
||||
setError(null);
|
||||
|
||||
const requestBody = {
|
||||
birthDate: birthDate.date,
|
||||
birthTime: birthDate.time
|
||||
const birthData = {
|
||||
name: '用户', // 默认名称
|
||||
birth_date: birthDate.date,
|
||||
birth_time: birthDate.time,
|
||||
gender: 'male' // 默认性别,后续可以从用户输入获取
|
||||
};
|
||||
|
||||
// 并行调用两个函数
|
||||
const [baziDetailsResponse, wuxingAnalysisResponse] = await Promise.all([
|
||||
localApi.functions.invoke('bazi-details', {
|
||||
body: requestBody
|
||||
}),
|
||||
localApi.functions.invoke('bazi-wuxing-analysis', {
|
||||
body: requestBody
|
||||
})
|
||||
]);
|
||||
// 调用八字分析API
|
||||
const baziResponse = await localApi.analysis.bazi(birthData);
|
||||
|
||||
if (baziDetailsResponse.error || wuxingAnalysisResponse.error) {
|
||||
throw new Error('获取分析数据失败');
|
||||
if (baziResponse.error) {
|
||||
throw new Error(baziResponse.error.message || '八字分析失败');
|
||||
}
|
||||
|
||||
const baziDetailsResult = baziDetailsResponse.data;
|
||||
const wuxingAnalysisResult = wuxingAnalysisResponse.data;
|
||||
|
||||
if (baziDetailsResult.error) {
|
||||
throw new Error(baziDetailsResult.error.message || '八字详情分析失败');
|
||||
const analysisResult = baziResponse.data?.analysis;
|
||||
if (!analysisResult) {
|
||||
throw new Error('分析结果为空');
|
||||
}
|
||||
|
||||
if (wuxingAnalysisResult.error) {
|
||||
throw new Error(wuxingAnalysisResult.error.message || '五行分析失败');
|
||||
}
|
||||
|
||||
setBaziDetailsData(baziDetailsResult.data);
|
||||
setWuxingAnalysisData(wuxingAnalysisResult.data);
|
||||
// 转换数据格式以适配现有的显示组件
|
||||
const baziChart = analysisResult.basic_info?.bazi_chart;
|
||||
const wuxingAnalysis = analysisResult.wuxing_analysis;
|
||||
|
||||
// 为了展示更多推理内容,在这里添加模拟的完整分析数据
|
||||
const mockFullAnalysis = {
|
||||
geju_analysis: {
|
||||
pattern_type: '正印格',
|
||||
pattern_strength: '中等',
|
||||
characteristics: '您的八字呈现正印格特征,表明您天生具有学习能力强、善于思考、重视名誉的特质。这种格局的人通常具有文雅的气质,对知识和智慧有着深度的追求。',
|
||||
career_path: '适合从事教育、文化、研究、咨询等需要专业知识和智慧的行业。也适合公务员、律师、医生等职业。',
|
||||
life_meaning: '您的人生使命是通过学习和知识的积累,不断提升自己的智慧和品德,并且将这些智慧传递给他人。'
|
||||
},
|
||||
dayun_analysis: {
|
||||
current_period: '青年时期运势稳定,适合打基础和积累经验',
|
||||
life_periods: '早年学业有成,中年事业发展,晚年享受成果',
|
||||
future_outlook: '未来十年整体运势向好,特别是在学业和事业方面将有明显的提升。'
|
||||
},
|
||||
life_guidance: {
|
||||
career_development: '建议您专注于专业技能的提升,在自己的领域内深耕细作。可以考虑进修或者参加专业培训,不断学习新知识。',
|
||||
marriage_relationships: '在情感方面,您比较重视精神交流和心灵沟通。建议寻找一个有共同话题和相似价值观的伴侣。',
|
||||
health_wellness: '注意用脑过度,定期休息。建议多进行户外运动,平衡脑力和体力的消耗。',
|
||||
wealth_guidance: '财运方面,您的财富主要来源于工作收入和专业技能。建议进行稳健的投资,避免高风险投机。'
|
||||
}
|
||||
};
|
||||
if (baziChart) {
|
||||
// 构造八字详情数据
|
||||
const baziDetailsData = {
|
||||
baziDetails: {
|
||||
year: {
|
||||
tiangan: baziChart.year_pillar.stem,
|
||||
dizhi: baziChart.year_pillar.branch,
|
||||
tianganWuxing: baziChart.year_pillar.element,
|
||||
dizhiWuxing: getBranchElement(baziChart.year_pillar.branch),
|
||||
tianganYinYang: getStemYinYang(baziChart.year_pillar.stem),
|
||||
dizhiYinYang: getBranchYinYang(baziChart.year_pillar.branch),
|
||||
combination: `${baziChart.year_pillar.stem}${baziChart.year_pillar.branch}`,
|
||||
pillarName: '年柱'
|
||||
},
|
||||
month: {
|
||||
tiangan: baziChart.month_pillar.stem,
|
||||
dizhi: baziChart.month_pillar.branch,
|
||||
tianganWuxing: baziChart.month_pillar.element,
|
||||
dizhiWuxing: getBranchElement(baziChart.month_pillar.branch),
|
||||
tianganYinYang: getStemYinYang(baziChart.month_pillar.stem),
|
||||
dizhiYinYang: getBranchYinYang(baziChart.month_pillar.branch),
|
||||
combination: `${baziChart.month_pillar.stem}${baziChart.month_pillar.branch}`,
|
||||
pillarName: '月柱'
|
||||
},
|
||||
day: {
|
||||
tiangan: baziChart.day_pillar.stem,
|
||||
dizhi: baziChart.day_pillar.branch,
|
||||
tianganWuxing: baziChart.day_pillar.element,
|
||||
dizhiWuxing: getBranchElement(baziChart.day_pillar.branch),
|
||||
tianganYinYang: getStemYinYang(baziChart.day_pillar.stem),
|
||||
dizhiYinYang: getBranchYinYang(baziChart.day_pillar.branch),
|
||||
combination: `${baziChart.day_pillar.stem}${baziChart.day_pillar.branch}`,
|
||||
pillarName: '日柱'
|
||||
},
|
||||
hour: {
|
||||
tiangan: baziChart.hour_pillar.stem,
|
||||
dizhi: baziChart.hour_pillar.branch,
|
||||
tianganWuxing: baziChart.hour_pillar.element,
|
||||
dizhiWuxing: getBranchElement(baziChart.hour_pillar.branch),
|
||||
tianganYinYang: getStemYinYang(baziChart.hour_pillar.stem),
|
||||
dizhiYinYang: getBranchYinYang(baziChart.hour_pillar.branch),
|
||||
combination: `${baziChart.hour_pillar.stem}${baziChart.hour_pillar.branch}`,
|
||||
pillarName: '时柱'
|
||||
}
|
||||
},
|
||||
rizhu: {
|
||||
tiangan: baziChart.day_master,
|
||||
wuxing: baziChart.day_master_element,
|
||||
yinyang: getStemYinYang(baziChart.day_master),
|
||||
description: `日主${baziChart.day_master},${baziChart.day_master_element}命`
|
||||
},
|
||||
summary: {
|
||||
fullBazi: baziChart.complete_chart,
|
||||
birthInfo: {
|
||||
solarDate: birthDate.date,
|
||||
birthTime: birthDate.time
|
||||
}
|
||||
},
|
||||
interpretation: {
|
||||
overall: wuxingAnalysis?.detailed_analysis || '八字分析结果'
|
||||
}
|
||||
};
|
||||
setBaziDetailsData(baziDetailsData);
|
||||
}
|
||||
|
||||
setFullBaziAnalysisData(mockFullAnalysis);
|
||||
if (wuxingAnalysis) {
|
||||
// 构造五行分析数据
|
||||
const elements = wuxingAnalysis.distribution || {};
|
||||
const total = Object.values(elements).reduce((sum: number, count: any) => sum + (typeof count === 'number' ? count : 0), 0);
|
||||
|
||||
const wuxingData = {
|
||||
bazi: baziChart,
|
||||
wuxingCount: elements,
|
||||
wuxingPercentage: Object.fromEntries(
|
||||
Object.entries(elements).map(([key, value]) => [
|
||||
key,
|
||||
total > 0 ? Math.round(((value as number) / total) * 100) : 0
|
||||
])
|
||||
),
|
||||
wuxingWithStrength: Object.entries(elements).map(([element, count]) => ({
|
||||
element,
|
||||
count: count as number,
|
||||
percentage: total > 0 ? Math.round(((count as number) / total) * 100) : 0,
|
||||
strength: (count as number) >= 3 ? '旺' : (count as number) >= 2 ? '中' : '弱'
|
||||
})),
|
||||
radarData: Object.entries(elements).map(([element, count]) => ({
|
||||
element,
|
||||
value: count as number,
|
||||
fullMark: 5
|
||||
})),
|
||||
balanceAnalysis: wuxingAnalysis.detailed_analysis || '五行分析',
|
||||
suggestions: [wuxingAnalysis.improvement_suggestions || '建议保持平衡'],
|
||||
dominantElement: Object.entries(elements).reduce((a, b) => (elements[a[0]] as number) > (elements[b[0]] as number) ? a : b)[0],
|
||||
weakestElement: Object.entries(elements).reduce((a, b) => (elements[a[0]] as number) < (elements[b[0]] as number) ? a : b)[0],
|
||||
isBalanced: Math.max(...Object.values(elements) as number[]) - Math.min(...Object.values(elements) as number[]) <= 2
|
||||
};
|
||||
setWuxingAnalysisData(wuxingData);
|
||||
}
|
||||
|
||||
// 设置完整分析数据 - 使用真实的后端分析结果
|
||||
setFullBaziAnalysisData({
|
||||
basic_info: analysisResult.basic_info || {},
|
||||
geju_analysis: analysisResult.geju_analysis || {},
|
||||
dayun_analysis: analysisResult.dayun_analysis || {},
|
||||
life_guidance: analysisResult.life_guidance || {},
|
||||
modern_applications: analysisResult.modern_applications || {}
|
||||
});
|
||||
} catch (err) {
|
||||
console.error('获取分析数据出错:', err);
|
||||
setError(err instanceof Error ? err.message : '分析数据获取失败,请稍后重试');
|
||||
@@ -533,8 +626,101 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 格局分析 */}
|
||||
{fullBaziAnalysisData?.geju_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Star className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
格局分析
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">格局类型</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
<span className="font-semibold">{fullBaziAnalysisData.geju_analysis.pattern_type}</span>
|
||||
(强度:{fullBaziAnalysisData.geju_analysis.pattern_strength})
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">格局特征</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.geju_analysis.characteristics}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">适合职业</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.geju_analysis.career_path}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">人生意义</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.geju_analysis.life_meaning}
|
||||
</p>
|
||||
</div>
|
||||
{fullBaziAnalysisData.geju_analysis.development_strategy && (
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-yellow-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">发展策略</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.geju_analysis.development_strategy}
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 四柱详细解释 */}
|
||||
{fullBaziAnalysisData?.basic_info?.pillar_interpretations && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<BookOpen className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
四柱详细解释
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-6">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">年柱解释</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.basic_info.pillar_interpretations.year_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">月柱解释</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.basic_info.pillar_interpretations.month_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">日柱解释</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.basic_info.pillar_interpretations.day_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">时柱解释</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.basic_info.pillar_interpretations.hour_pillar}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 大运流年分析 */}
|
||||
{fullBaziAnalysisData && (
|
||||
{fullBaziAnalysisData?.dayun_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
@@ -546,15 +732,27 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-red-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">当前运势</h4>
|
||||
<h4 className="font-bold text-red-800 mb-2">起运信息</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.dayun_analysis?.current_period}
|
||||
起运年龄:{fullBaziAnalysisData.dayun_analysis?.start_luck_age}岁
|
||||
</p>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
当前大运:{fullBaziAnalysisData.dayun_analysis?.current_dayun?.ganzhi || '未起运'}
|
||||
{fullBaziAnalysisData.dayun_analysis?.current_dayun &&
|
||||
`(${fullBaziAnalysisData.dayun_analysis.current_dayun.start_age}-${fullBaziAnalysisData.dayun_analysis.current_dayun.end_age}岁)`
|
||||
}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">人生阶段</h4>
|
||||
<h4 className="font-bold text-red-800 mb-2">大运影响</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.dayun_analysis?.life_periods}
|
||||
{fullBaziAnalysisData.dayun_analysis?.dayun_influence}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">流年分析</h4>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{fullBaziAnalysisData.dayun_analysis?.yearly_fortune}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
@@ -569,6 +767,76 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 详细流年分析 */}
|
||||
{fullBaziAnalysisData?.dayun_analysis?.detailed_yearly_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Calendar className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
详细流年分析(未来六年)
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-6">
|
||||
{fullBaziAnalysisData.dayun_analysis.detailed_yearly_analysis.map((yearData: any, index: number) => (
|
||||
<div key={index} className="bg-white p-4 rounded-lg border-2 border-yellow-300">
|
||||
<div className="flex items-center justify-between mb-3">
|
||||
<h4 className="font-bold text-red-800 text-lg">
|
||||
{yearData.year}年({yearData.age}岁){yearData.year_ganzhi}
|
||||
</h4>
|
||||
<span className="text-sm text-red-600 bg-red-50 px-2 py-1 rounded">
|
||||
{yearData.year_ten_god}
|
||||
</span>
|
||||
</div>
|
||||
<div className="grid md:grid-cols-2 gap-4">
|
||||
<div className="space-y-3">
|
||||
<div className="border-l-4 border-blue-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">整体运势</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.overall_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-green-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">事业运势</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.career_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-yellow-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">财运分析</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.wealth_fortune}</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="space-y-3">
|
||||
<div className="border-l-4 border-pink-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">感情运势</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.relationship_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-purple-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">健康提醒</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.health_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-orange-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm">关键建议</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.key_advice}</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{yearData.monthly_highlights && yearData.monthly_highlights.length > 0 && (
|
||||
<div className="mt-3 pt-3 border-t border-yellow-200">
|
||||
<h5 className="font-semibold text-red-800 text-sm mb-2">月度重点</h5>
|
||||
<div className="space-y-1">
|
||||
{yearData.monthly_highlights.map((highlight: string, hIndex: number) => (
|
||||
<p key={hIndex} className="text-red-700 text-xs">• {highlight}</p>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 专业人生指导 */}
|
||||
{fullBaziAnalysisData && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
@@ -615,6 +883,52 @@ const BaziAnalysisDisplay: React.FC<BaziAnalysisDisplayProps> = ({ birthDate })
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 现代应用建议 */}
|
||||
{fullBaziAnalysisData?.modern_applications && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<BarChart3 className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
现代应用建议
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">生活方式建议</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.modern_applications.lifestyle_recommendations}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">职业策略</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.modern_applications.career_strategies}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">人际关系建议</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.modern_applications.relationship_advice}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">决策时机</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{fullBaziAnalysisData.modern_applications.decision_making}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 人生指导建议 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
|
||||
774
src/components/CompleteBaziAnalysis.tsx
Normal file
774
src/components/CompleteBaziAnalysis.tsx
Normal file
@@ -0,0 +1,774 @@
|
||||
import React, { useState, useEffect } from 'react';
|
||||
import { Radar, RadarChart, PolarGrid, PolarAngleAxis, PolarRadiusAxis, ResponsiveContainer } from 'recharts';
|
||||
import { Calendar, Star, BookOpen, Sparkles, User, BarChart3, Zap, TrendingUp, Loader2, Clock, Target, Heart, DollarSign, Activity } from 'lucide-react';
|
||||
import { Card, CardContent, CardHeader, CardTitle } from './ui/Card';
|
||||
import { localApi } from '../lib/localApi';
|
||||
|
||||
interface CompleteBaziAnalysisProps {
|
||||
birthDate: {
|
||||
date: string;
|
||||
time: string;
|
||||
name?: string;
|
||||
gender?: string;
|
||||
};
|
||||
}
|
||||
|
||||
const CompleteBaziAnalysis: React.FC<CompleteBaziAnalysisProps> = ({ birthDate }) => {
|
||||
const [isLoading, setIsLoading] = useState(true);
|
||||
const [error, setError] = useState<string | null>(null);
|
||||
const [analysisData, setAnalysisData] = useState<any>(null);
|
||||
|
||||
// 五行颜色配置
|
||||
const elementColors: { [key: string]: string } = {
|
||||
'木': '#22c55e', // 绿色
|
||||
'火': '#ef4444', // 红色
|
||||
'土': '#eab308', // 黄色
|
||||
'金': '#64748b', // 银色
|
||||
'水': '#3b82f6' // 蓝色
|
||||
};
|
||||
|
||||
// 五行符号配置
|
||||
const elementSymbols: { [key: string]: string } = {
|
||||
'木': '🌲',
|
||||
'火': '🔥',
|
||||
'土': '⛰️',
|
||||
'金': '⚡',
|
||||
'水': '💧'
|
||||
};
|
||||
|
||||
// 十神颜色配置
|
||||
const tenGodColors: { [key: string]: string } = {
|
||||
'正官': 'bg-blue-100 text-blue-800 border-blue-300',
|
||||
'七杀': 'bg-red-100 text-red-800 border-red-300',
|
||||
'正财': 'bg-green-100 text-green-800 border-green-300',
|
||||
'偏财': 'bg-yellow-100 text-yellow-800 border-yellow-300',
|
||||
'正印': 'bg-purple-100 text-purple-800 border-purple-300',
|
||||
'偏印': 'bg-indigo-100 text-indigo-800 border-indigo-300',
|
||||
'食神': 'bg-pink-100 text-pink-800 border-pink-300',
|
||||
'伤官': 'bg-orange-100 text-orange-800 border-orange-300',
|
||||
'比肩': 'bg-gray-100 text-gray-800 border-gray-300',
|
||||
'劫财': 'bg-slate-100 text-slate-800 border-slate-300',
|
||||
'日主': 'bg-amber-100 text-amber-800 border-amber-300'
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
const fetchAnalysisData = async () => {
|
||||
try {
|
||||
setIsLoading(true);
|
||||
setError(null);
|
||||
|
||||
const birthData = {
|
||||
name: birthDate.name || '用户',
|
||||
birth_date: birthDate.date,
|
||||
birth_time: birthDate.time,
|
||||
gender: birthDate.gender || 'male'
|
||||
};
|
||||
|
||||
const baziResponse = await localApi.analysis.bazi(birthData);
|
||||
|
||||
if (baziResponse.error) {
|
||||
throw new Error(baziResponse.error.message || '八字分析失败');
|
||||
}
|
||||
|
||||
const analysisResult = baziResponse.data?.analysis;
|
||||
if (!analysisResult) {
|
||||
throw new Error('分析结果为空');
|
||||
}
|
||||
|
||||
setAnalysisData(analysisResult);
|
||||
} catch (err) {
|
||||
console.error('获取分析数据出错:', err);
|
||||
setError(err instanceof Error ? err.message : '分析数据获取失败,请稍后重试');
|
||||
} finally {
|
||||
setIsLoading(false);
|
||||
}
|
||||
};
|
||||
|
||||
if (birthDate?.date) {
|
||||
fetchAnalysisData();
|
||||
}
|
||||
}, [birthDate]);
|
||||
|
||||
// 渲染加载状态
|
||||
if (isLoading) {
|
||||
return (
|
||||
<div className="min-h-screen flex items-center justify-center bg-gradient-to-br from-red-50 to-yellow-50">
|
||||
<Card className="chinese-card-decoration border-2 border-yellow-400 p-8">
|
||||
<CardContent className="text-center">
|
||||
<Loader2 className="h-12 w-12 animate-spin text-red-600 mx-auto mb-4" />
|
||||
<h3 className="text-xl font-bold text-red-800 mb-2">正在进行专业八字分析</h3>
|
||||
<p className="text-red-600">请稍候,正在生成您的详细命理报告...</p>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
// 渲染错误状态
|
||||
if (error) {
|
||||
return (
|
||||
<div className="min-h-screen flex items-center justify-center bg-gradient-to-br from-red-50 to-yellow-50">
|
||||
<Card className="chinese-card-decoration border-2 border-red-400 p-8">
|
||||
<CardContent className="text-center">
|
||||
<div className="text-6xl mb-4">❌</div>
|
||||
<h3 className="text-xl font-bold text-red-800 mb-2">分析失败</h3>
|
||||
<p className="text-red-600 mb-4">{error}</p>
|
||||
<button
|
||||
onClick={() => window.location.reload()}
|
||||
className="px-4 py-2 bg-red-600 text-white rounded-lg hover:bg-red-700 transition-colors"
|
||||
>
|
||||
重新分析
|
||||
</button>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
if (!analysisData) {
|
||||
return (
|
||||
<div className="min-h-screen flex items-center justify-center bg-gradient-to-br from-red-50 to-yellow-50">
|
||||
<Card className="chinese-card-decoration border-2 border-yellow-400 p-8">
|
||||
<CardContent className="text-center">
|
||||
<div className="text-6xl mb-4">⚠️</div>
|
||||
<h3 className="text-xl font-bold text-red-800 mb-2">数据获取异常</h3>
|
||||
<p className="text-red-600">未能获取到完整的分析数据,请重新提交分析</p>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
// 渲染四柱信息卡片
|
||||
const renderPillarCard = (pillar: any, pillarName: string, description: string) => {
|
||||
if (!pillar) return null;
|
||||
|
||||
return (
|
||||
<Card className="chinese-card-decoration hover:shadow-xl transition-all duration-300 border-2 border-yellow-400">
|
||||
<CardHeader className="text-center pb-2">
|
||||
<CardTitle className="text-red-800 text-lg font-bold chinese-text-shadow">
|
||||
{pillarName}
|
||||
</CardTitle>
|
||||
<p className="text-red-600 text-xs">{description}</p>
|
||||
</CardHeader>
|
||||
<CardContent className="space-y-3">
|
||||
<div className="text-center">
|
||||
<div className="text-3xl font-bold text-red-800 mb-2">
|
||||
{pillar.stem}{pillar.branch}
|
||||
</div>
|
||||
<div className="flex justify-center space-x-2 mb-3">
|
||||
<span className={`px-2 py-1 rounded text-xs font-medium border ${tenGodColors[pillar.ten_god] || 'bg-gray-100 text-gray-800'}`}>
|
||||
{pillar.ten_god}
|
||||
</span>
|
||||
<span className="px-2 py-1 rounded text-xs font-medium bg-blue-100 text-blue-800 border border-blue-300">
|
||||
{pillar.element}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{pillar.hidden_stems && pillar.hidden_stems.length > 0 && (
|
||||
<div className="border-t pt-2">
|
||||
<h5 className="text-xs font-semibold text-red-800 mb-1">地支藏干</h5>
|
||||
<div className="flex flex-wrap gap-1">
|
||||
{pillar.hidden_stems.map((stem: string, index: number) => (
|
||||
<span key={index} className="px-1 py-0.5 bg-gray-100 text-gray-700 rounded text-xs">
|
||||
{stem}
|
||||
</span>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
};
|
||||
|
||||
// 渲染五行雷达图
|
||||
const renderWuxingRadar = () => {
|
||||
if (!analysisData.wuxing_analysis?.element_distribution) return null;
|
||||
|
||||
const elements = analysisData.wuxing_analysis.element_distribution;
|
||||
const radarData = Object.entries(elements).map(([element, count]) => ({
|
||||
element,
|
||||
value: count as number,
|
||||
fullMark: 6
|
||||
}));
|
||||
|
||||
return (
|
||||
<ResponsiveContainer width="100%" height={300}>
|
||||
<RadarChart data={radarData}>
|
||||
<PolarGrid stroke="#dc2626" />
|
||||
<PolarAngleAxis
|
||||
dataKey="element"
|
||||
tick={{ fill: '#dc2626', fontSize: 14, fontWeight: 'bold' }}
|
||||
/>
|
||||
<PolarRadiusAxis
|
||||
angle={90}
|
||||
domain={[0, 6]}
|
||||
tick={{ fill: '#b91c1c', fontSize: 12 }}
|
||||
/>
|
||||
<Radar
|
||||
name="五行强度"
|
||||
dataKey="value"
|
||||
stroke="#dc2626"
|
||||
fill="rgba(220, 38, 38, 0.3)"
|
||||
fillOpacity={0.6}
|
||||
strokeWidth={2}
|
||||
/>
|
||||
</RadarChart>
|
||||
</ResponsiveContainer>
|
||||
);
|
||||
};
|
||||
|
||||
// 渲染五行分布卡片
|
||||
const renderElementCards = () => {
|
||||
if (!analysisData.wuxing_analysis?.element_distribution) return null;
|
||||
|
||||
const elements = analysisData.wuxing_analysis.element_distribution;
|
||||
const total = Object.values(elements).reduce((sum: number, count: any) => sum + (typeof count === 'number' ? count : 0), 0);
|
||||
|
||||
return (
|
||||
<div className="grid grid-cols-5 gap-4">
|
||||
{Object.entries(elements).map(([element, count]) => {
|
||||
const percentage = total > 0 ? Math.round(((count as number) / total) * 100) : 0;
|
||||
const strength = (count as number) >= 3 ? '旺' : (count as number) >= 2 ? '中' : '弱';
|
||||
|
||||
return (
|
||||
<Card key={element} className="text-center hover:shadow-xl transition-all duration-300 chinese-card-decoration border-2 border-yellow-400">
|
||||
<CardContent className="p-4">
|
||||
<div className="text-3xl mb-2">{elementSymbols[element]}</div>
|
||||
<h3 className="font-bold text-red-800 text-lg mb-2 chinese-text-shadow">{element}</h3>
|
||||
<div className="text-2xl font-bold text-yellow-600 mb-1">{count}</div>
|
||||
<div className="text-sm text-gray-600 mb-2">{percentage}%</div>
|
||||
<div className={`text-sm font-medium mb-2 ${
|
||||
strength === '旺' ? 'text-green-600' :
|
||||
strength === '中' ? 'text-yellow-600' : 'text-orange-600'
|
||||
}`}>
|
||||
{strength}
|
||||
</div>
|
||||
<div className="w-full h-3 bg-gray-200 rounded-full overflow-hidden">
|
||||
<div
|
||||
className="h-full rounded-full transition-all duration-1000"
|
||||
style={{
|
||||
width: `${percentage}%`,
|
||||
backgroundColor: elementColors[element]
|
||||
}}
|
||||
/>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<div className="min-h-screen bg-gradient-to-br from-red-50 to-yellow-50 py-8">
|
||||
<div className="max-w-7xl mx-auto px-4 space-y-8">
|
||||
|
||||
{/* 标题和基本信息 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader className="text-center">
|
||||
<CardTitle className="text-red-800 text-3xl font-bold chinese-text-shadow">
|
||||
{analysisData.basic_info?.personal_data?.name || '用户'}的专业八字命理分析报告
|
||||
</CardTitle>
|
||||
<div className="flex justify-center space-x-6 mt-4 text-red-700">
|
||||
<div className="flex items-center space-x-2">
|
||||
<Calendar className="h-5 w-5" />
|
||||
<span>{analysisData.basic_info?.personal_data?.birth_date}</span>
|
||||
</div>
|
||||
<div className="flex items-center space-x-2">
|
||||
<Clock className="h-5 w-5" />
|
||||
<span>{analysisData.basic_info?.personal_data?.birth_time}</span>
|
||||
</div>
|
||||
<div className="flex items-center space-x-2">
|
||||
<User className="h-5 w-5" />
|
||||
<span>{analysisData.basic_info?.personal_data?.gender}</span>
|
||||
</div>
|
||||
</div>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="text-center">
|
||||
<div className="text-2xl font-bold text-red-800 mb-4">
|
||||
八字:{analysisData.basic_info?.bazi_chart?.complete_chart}
|
||||
</div>
|
||||
<div className="grid md:grid-cols-2 gap-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-red-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">日主信息</h4>
|
||||
<p className="text-red-700">
|
||||
日主:{analysisData.basic_info?.bazi_chart?.day_master}({analysisData.basic_info?.bazi_chart?.day_master_element})
|
||||
</p>
|
||||
<p className="text-red-700">
|
||||
旺衰:{analysisData.basic_info?.bazi_chart?.element_strength?.strength_level}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">用神分析</h4>
|
||||
<p className="text-red-700 text-sm">
|
||||
{analysisData.basic_info?.bazi_chart?.element_strength?.use_god_analysis?.analysis}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 四柱详细信息 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow text-center">
|
||||
四柱详细信息
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="grid lg:grid-cols-4 gap-6 mb-6">
|
||||
{renderPillarCard(analysisData.basic_info?.bazi_chart?.year_pillar, '年柱', '祖辈与早年运势')}
|
||||
{renderPillarCard(analysisData.basic_info?.bazi_chart?.month_pillar, '月柱', '父母与青年运势')}
|
||||
{renderPillarCard(analysisData.basic_info?.bazi_chart?.day_pillar, '日柱', '自身与配偶')}
|
||||
{renderPillarCard(analysisData.basic_info?.bazi_chart?.hour_pillar, '时柱', '子女与晚年运势')}
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 四柱详细解释 */}
|
||||
{analysisData.basic_info?.pillar_interpretations && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<BookOpen className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
四柱专业解释
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-6">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2 flex items-center">
|
||||
<span className="mr-2">🏛️</span>年柱解释
|
||||
</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.basic_info.pillar_interpretations.year_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2 flex items-center">
|
||||
<span className="mr-2">🌟</span>月柱解释
|
||||
</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.basic_info.pillar_interpretations.month_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2 flex items-center">
|
||||
<span className="mr-2">💎</span>日柱解释
|
||||
</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.basic_info.pillar_interpretations.day_pillar}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2 flex items-center">
|
||||
<span className="mr-2">🌅</span>时柱解释
|
||||
</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.basic_info.pillar_interpretations.hour_pillar}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 五行能量分布 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow text-center">
|
||||
五行能量分布分析
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="space-y-6">
|
||||
{renderElementCards()}
|
||||
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<h4 className="font-bold text-red-800 mb-4 text-center">五行平衡雷达图</h4>
|
||||
{renderWuxingRadar()}
|
||||
</div>
|
||||
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-yellow-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">五行平衡分析</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.wuxing_analysis?.balance_analysis}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">个性特质</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.wuxing_analysis?.personality_traits}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">改善建议</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.wuxing_analysis?.improvement_suggestions}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 格局分析 */}
|
||||
{analysisData.geju_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Star className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
格局分析
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">格局类型</h4>
|
||||
<div className="flex items-center space-x-2">
|
||||
<span className="text-2xl font-bold text-purple-600">
|
||||
{analysisData.geju_analysis.pattern_type}
|
||||
</span>
|
||||
<span className="px-2 py-1 bg-purple-100 text-purple-800 rounded text-sm">
|
||||
{analysisData.geju_analysis.pattern_strength}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">格局特征</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.geju_analysis.characteristics}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">适合职业</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.geju_analysis.career_path}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">人生意义</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.geju_analysis.life_meaning}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{analysisData.geju_analysis.development_strategy && (
|
||||
<div className="mt-4 bg-white p-4 rounded-lg border-l-4 border-yellow-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">发展策略</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.geju_analysis.development_strategy}
|
||||
</p>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 大运流年分析 */}
|
||||
{analysisData.dayun_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<TrendingUp className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
大运流年分析
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="grid md:grid-cols-3 gap-6 mb-6">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-red-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">起运信息</h4>
|
||||
<p className="text-red-700">起运年龄:{analysisData.dayun_analysis.start_luck_age}岁</p>
|
||||
<p className="text-red-700">当前年龄:{analysisData.dayun_analysis.current_age}岁</p>
|
||||
{analysisData.dayun_analysis.current_dayun && (
|
||||
<p className="text-red-700">
|
||||
当前大运:{analysisData.dayun_analysis.current_dayun.ganzhi}
|
||||
({analysisData.dayun_analysis.current_dayun.start_age}-{analysisData.dayun_analysis.current_dayun.end_age}岁)
|
||||
</p>
|
||||
)}
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">大运影响</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.dayun_analysis.dayun_influence}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">流年分析</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.dayun_analysis.yearly_fortune}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* 大运序列 */}
|
||||
{analysisData.dayun_analysis.dayun_sequence && (
|
||||
<div className="mb-6">
|
||||
<h4 className="font-bold text-red-800 mb-4 text-center">八步大运序列</h4>
|
||||
<div className="grid md:grid-cols-4 gap-3">
|
||||
{analysisData.dayun_analysis.dayun_sequence.map((dayun: any, index: number) => (
|
||||
<div key={index} className={`p-3 rounded-lg border-2 ${
|
||||
analysisData.dayun_analysis.current_dayun &&
|
||||
dayun.ganzhi === analysisData.dayun_analysis.current_dayun.ganzhi
|
||||
? 'bg-yellow-100 border-yellow-400'
|
||||
: 'bg-white border-gray-300'
|
||||
}`}>
|
||||
<div className="text-center">
|
||||
<div className="font-bold text-red-800">{dayun.ganzhi}</div>
|
||||
<div className="text-sm text-red-600">{dayun.start_age}-{dayun.end_age}岁</div>
|
||||
<div className={`text-xs px-2 py-1 rounded mt-1 ${tenGodColors[dayun.ten_god] || 'bg-gray-100 text-gray-800'}`}>
|
||||
{dayun.ten_god}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">未来展望</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.dayun_analysis.future_outlook}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 详细流年分析 */}
|
||||
{analysisData.dayun_analysis?.detailed_yearly_analysis && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Calendar className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
详细流年分析(未来六年)
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-6">
|
||||
{analysisData.dayun_analysis.detailed_yearly_analysis.map((yearData: any, index: number) => (
|
||||
<div key={index} className="bg-white p-6 rounded-lg border-2 border-yellow-300 shadow-lg">
|
||||
<div className="flex items-center justify-between mb-4">
|
||||
<h4 className="font-bold text-red-800 text-xl">
|
||||
{yearData.year}年({yearData.age}岁){yearData.year_ganzhi}
|
||||
</h4>
|
||||
<div className="flex space-x-2">
|
||||
<span className={`text-sm px-3 py-1 rounded-full ${tenGodColors[yearData.year_ten_god] || 'bg-gray-100 text-gray-800'}`}>
|
||||
{yearData.year_ten_god}
|
||||
</span>
|
||||
<span className="text-sm text-blue-600 bg-blue-50 px-3 py-1 rounded-full border border-blue-300">
|
||||
{yearData.dayun_period}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="grid md:grid-cols-2 lg:grid-cols-3 gap-4">
|
||||
<div className="space-y-3">
|
||||
<div className="border-l-4 border-blue-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<Target className="h-4 w-4 mr-1" />整体运势
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.overall_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-green-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<BarChart3 className="h-4 w-4 mr-1" />事业运势
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.career_fortune}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="space-y-3">
|
||||
<div className="border-l-4 border-yellow-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<DollarSign className="h-4 w-4 mr-1" />财运分析
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.wealth_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-pink-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<Heart className="h-4 w-4 mr-1" />感情运势
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.relationship_fortune}</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="space-y-3">
|
||||
<div className="border-l-4 border-purple-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<Activity className="h-4 w-4 mr-1" />健康提醒
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.health_fortune}</p>
|
||||
</div>
|
||||
<div className="border-l-4 border-orange-400 pl-3">
|
||||
<h5 className="font-semibold text-red-800 text-sm flex items-center">
|
||||
<Sparkles className="h-4 w-4 mr-1" />关键建议
|
||||
</h5>
|
||||
<p className="text-red-700 text-xs leading-relaxed">{yearData.key_advice}</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{yearData.monthly_highlights && yearData.monthly_highlights.length > 0 && (
|
||||
<div className="mt-4 pt-4 border-t border-yellow-200">
|
||||
<h5 className="font-semibold text-red-800 text-sm mb-2 flex items-center">
|
||||
<Calendar className="h-4 w-4 mr-1" />月度重点
|
||||
</h5>
|
||||
<div className="grid md:grid-cols-2 gap-2">
|
||||
{yearData.monthly_highlights.map((highlight: string, hIndex: number) => (
|
||||
<p key={hIndex} className="text-red-700 text-xs bg-yellow-50 p-2 rounded">• {highlight}</p>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 专业人生指导 */}
|
||||
{analysisData.life_guidance && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<BookOpen className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
专业人生指导
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">事业发展</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.career_development}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">财富管理</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.wealth_management}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-pink-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">感情婚姻</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.marriage_relationships}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">健康养生</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.health_wellness}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-yellow-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">个人发展</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.personal_development}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-indigo-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">综合总结</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.life_guidance.overall_summary}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 现代应用建议 */}
|
||||
{analysisData.modern_applications && (
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Zap className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
现代应用建议
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-blue-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">生活方式建议</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.modern_applications.lifestyle_recommendations}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-green-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">职业策略</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.modern_applications.career_strategies}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="space-y-4">
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-purple-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">人际关系建议</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.modern_applications.relationship_advice}
|
||||
</p>
|
||||
</div>
|
||||
<div className="bg-white p-4 rounded-lg border-l-4 border-orange-500">
|
||||
<h4 className="font-bold text-red-800 mb-2">决策时机</h4>
|
||||
<p className="text-red-700 leading-relaxed text-sm">
|
||||
{analysisData.modern_applications.decision_making}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 分析报告尾部 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardContent className="text-center py-8">
|
||||
<div className="text-red-800">
|
||||
<p className="text-lg font-bold mb-2">专业八字命理分析报告</p>
|
||||
<p className="text-sm">分析日期:{analysisData.analysis_date}</p>
|
||||
<p className="text-xs mt-4 text-red-600">
|
||||
本报告基于传统四柱八字理论,结合现代命理学研究成果,为您提供专业的命理分析和人生指导。
|
||||
</p>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default CompleteBaziAnalysis;
|
||||
@@ -1,418 +1,273 @@
|
||||
import React, { useState } from 'react';
|
||||
import { Calendar, Clock, Star, BookOpen, Sparkles, User } from 'lucide-react';
|
||||
import { Calendar, Clock, User, ArrowLeft } from 'lucide-react';
|
||||
import { Button } from '../components/ui/Button';
|
||||
import { Card, CardContent, CardHeader, CardTitle } from '../components/ui/Card';
|
||||
import { localApi } from '../lib/localApi';
|
||||
import CompleteBaziAnalysis from '../components/CompleteBaziAnalysis';
|
||||
import { useAuth } from '../contexts/AuthContext';
|
||||
import { toast } from 'sonner';
|
||||
import { useNavigate } from 'react-router-dom';
|
||||
|
||||
// 生辰八字详情数据接口 - 匹配后端返回结构
|
||||
interface PillarInfo {
|
||||
tiangan: string;
|
||||
dizhi: string;
|
||||
tianganWuxing: string;
|
||||
dizhiWuxing: string;
|
||||
tianganYinYang: string;
|
||||
dizhiYinYang: string;
|
||||
combination: string;
|
||||
pillarName: string;
|
||||
shengxiao?: string;
|
||||
tianganMeaning?: string;
|
||||
dizhiMeaning?: string;
|
||||
}
|
||||
|
||||
interface BaziApiResponse {
|
||||
baziDetails: {
|
||||
year: PillarInfo;
|
||||
month: PillarInfo;
|
||||
day: PillarInfo;
|
||||
hour: PillarInfo;
|
||||
};
|
||||
rizhu: {
|
||||
tiangan: string;
|
||||
wuxing: string;
|
||||
yinyang: string;
|
||||
description: string;
|
||||
meaning?: string;
|
||||
};
|
||||
summary: {
|
||||
fullBazi: string;
|
||||
birthInfo: {
|
||||
solarDate: string;
|
||||
birthTime: string;
|
||||
year: number;
|
||||
month: number;
|
||||
day: number;
|
||||
hour: number;
|
||||
};
|
||||
pillars: PillarInfo[];
|
||||
};
|
||||
interpretation: {
|
||||
overall: string;
|
||||
yearPillar: string;
|
||||
monthPillar: string;
|
||||
dayPillar: string;
|
||||
hourPillar: string;
|
||||
};
|
||||
interface BirthData {
|
||||
date: string;
|
||||
time: string;
|
||||
name?: string;
|
||||
gender?: string;
|
||||
}
|
||||
|
||||
const BaziDetailsPage: React.FC = () => {
|
||||
const { user } = useAuth();
|
||||
const [birthDate, setBirthDate] = useState('');
|
||||
const [birthTime, setBirthTime] = useState('12:00');
|
||||
const [baziData, setBaziData] = useState<BaziApiResponse | null>(null);
|
||||
const [isLoading, setIsLoading] = useState(false);
|
||||
const [error, setError] = useState<string | null>(null);
|
||||
const navigate = useNavigate();
|
||||
const [showAnalysis, setShowAnalysis] = useState(false);
|
||||
const [birthData, setBirthData] = useState<BirthData>({
|
||||
date: '',
|
||||
time: '12:00',
|
||||
name: user?.name || '',
|
||||
gender: 'male'
|
||||
});
|
||||
|
||||
// 五行颜色配置
|
||||
const wuxingColors: { [key: string]: string } = {
|
||||
'木': 'text-green-600 bg-green-50 border-green-300',
|
||||
'火': 'text-red-600 bg-red-50 border-red-300',
|
||||
'土': 'text-yellow-600 bg-yellow-50 border-yellow-300',
|
||||
'金': 'text-gray-600 bg-gray-50 border-gray-300',
|
||||
'水': 'text-blue-600 bg-blue-50 border-blue-300'
|
||||
const handleInputChange = (field: keyof BirthData, value: string) => {
|
||||
setBirthData(prev => ({
|
||||
...prev,
|
||||
[field]: value
|
||||
}));
|
||||
};
|
||||
|
||||
// 阴阳颜色配置
|
||||
const yinyangColors: { [key: string]: string } = {
|
||||
'阳': 'text-orange-600 bg-orange-50 border-orange-300',
|
||||
'阴': 'text-purple-600 bg-purple-50 border-purple-300'
|
||||
};
|
||||
|
||||
// 获取八字详细信息
|
||||
const fetchBaziDetails = async () => {
|
||||
if (!birthDate) {
|
||||
const handleAnalyze = () => {
|
||||
if (!birthData.date) {
|
||||
toast.error('请选择您的出生日期');
|
||||
return;
|
||||
}
|
||||
|
||||
setIsLoading(true);
|
||||
setError(null);
|
||||
if (!birthData.time) {
|
||||
toast.error('请选择您的出生时间');
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
// 调用本地API
|
||||
const response = await localApi.functions.invoke('bazi-details', {
|
||||
body: {
|
||||
birthDate,
|
||||
birthTime
|
||||
}
|
||||
});
|
||||
setShowAnalysis(true);
|
||||
toast.success('开始进行专业八字分析...');
|
||||
};
|
||||
|
||||
if (response.error) {
|
||||
throw new Error(response.error.message);
|
||||
}
|
||||
|
||||
if (response.data?.data) {
|
||||
setBaziData(response.data.data);
|
||||
toast.success('八字详情分析完成!');
|
||||
} else {
|
||||
throw new Error('排盘结果为空');
|
||||
}
|
||||
} catch (err: any) {
|
||||
console.error('八字排盘错误:', err);
|
||||
setError(err.message || '分析失败,请稍后重试');
|
||||
toast.error('分析失败,请稍后重试');
|
||||
} finally {
|
||||
setIsLoading(false);
|
||||
const handleBack = () => {
|
||||
if (showAnalysis) {
|
||||
setShowAnalysis(false);
|
||||
} else {
|
||||
navigate('/analysis');
|
||||
}
|
||||
};
|
||||
|
||||
// 渲染四柱信息卡片
|
||||
const renderPillarCard = (pillar: PillarInfo | null | undefined, index: number) => {
|
||||
// 防护性检查:确保 pillar 对象存在
|
||||
if (!pillar) {
|
||||
return (
|
||||
<Card key={index} className="chinese-card-decoration hover:shadow-xl transition-all duration-300 border-2 border-yellow-400">
|
||||
<CardContent className="p-8 text-center">
|
||||
<p className="text-red-600">柱信息加载中...</p>
|
||||
</CardContent>
|
||||
</Card>
|
||||
);
|
||||
}
|
||||
|
||||
const pillarNames = ['年柱', '月柱', '日柱', '时柱'];
|
||||
const pillarDescriptions = [
|
||||
'代表祖辈与早年运势',
|
||||
'代表父母与青年运势',
|
||||
'代表自身与配偶',
|
||||
'代表子女与晚年运势'
|
||||
];
|
||||
const handleReset = () => {
|
||||
setBirthData({
|
||||
date: '',
|
||||
time: '12:00',
|
||||
name: user?.name || '',
|
||||
gender: 'male'
|
||||
});
|
||||
setShowAnalysis(false);
|
||||
};
|
||||
|
||||
// 如果显示分析结果,直接渲染CompleteBaziAnalysis组件
|
||||
if (showAnalysis) {
|
||||
return (
|
||||
<Card key={index} className="chinese-card-decoration hover:shadow-xl transition-all duration-300 border-2 border-yellow-400">
|
||||
<CardHeader className="text-center">
|
||||
<CardTitle className="text-red-800 text-xl font-bold chinese-text-shadow">
|
||||
{pillarNames[index] || '未知柱'}
|
||||
</CardTitle>
|
||||
<p className="text-red-600 text-sm">{pillarDescriptions[index] || '描述加载中'}</p>
|
||||
</CardHeader>
|
||||
<CardContent className="space-y-4">
|
||||
{/* 天干地支大显示 */}
|
||||
<div className="text-center">
|
||||
<div className="text-4xl font-bold text-red-800 chinese-text-shadow mb-2">
|
||||
{pillar?.combination || '未知'}
|
||||
</div>
|
||||
<div className="text-sm text-gray-600">
|
||||
{pillar?.tiangan || '未知'} ({pillar?.tianganYinYang || '未知'}) + {pillar?.dizhi || '未知'} ({pillar?.dizhiYinYang || '未知'})
|
||||
<div className="min-h-screen bg-gradient-to-br from-red-50 to-yellow-50">
|
||||
{/* 顶部导航栏 */}
|
||||
<div className="bg-white shadow-sm border-b border-yellow-200 sticky top-0 z-10">
|
||||
<div className="max-w-7xl mx-auto px-4 py-4">
|
||||
<div className="flex items-center justify-between">
|
||||
<Button
|
||||
onClick={handleBack}
|
||||
variant="outline"
|
||||
className="flex items-center space-x-2 border-red-300 text-red-700 hover:bg-red-50"
|
||||
>
|
||||
<ArrowLeft className="h-4 w-4" />
|
||||
<span>返回设置</span>
|
||||
</Button>
|
||||
|
||||
<div className="text-center">
|
||||
<h1 className="text-xl font-bold text-red-800">专业八字命理分析</h1>
|
||||
<p className="text-sm text-red-600">
|
||||
{birthData.name} • {birthData.date} • {birthData.time}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<Button
|
||||
onClick={handleReset}
|
||||
variant="outline"
|
||||
className="border-yellow-300 text-yellow-700 hover:bg-yellow-50"
|
||||
>
|
||||
重新分析
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* 天干信息 */}
|
||||
<div className="bg-gradient-to-r from-red-50 to-yellow-50 rounded-lg p-3">
|
||||
<h4 className="font-bold text-red-700 mb-2">天干:{pillar?.tiangan || '未知'}</h4>
|
||||
<div className="grid grid-cols-2 gap-2 text-sm">
|
||||
<div className={`px-2 py-1 rounded border ${pillar?.tianganWuxing && wuxingColors[pillar.tianganWuxing] ? wuxingColors[pillar.tianganWuxing] : 'bg-gray-50 border-gray-300 text-gray-600'}`}>
|
||||
五行:{pillar?.tianganWuxing || '未知'}
|
||||
</div>
|
||||
<div className={`px-2 py-1 rounded border ${pillar?.tianganYinYang && yinyangColors[pillar.tianganYinYang] ? yinyangColors[pillar.tianganYinYang] : 'bg-gray-50 border-gray-300 text-gray-600'}`}>
|
||||
阴阳:{pillar?.tianganYinYang || '未知'}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* 地支信息 */}
|
||||
<div className="bg-gradient-to-r from-yellow-50 to-red-50 rounded-lg p-3">
|
||||
<h4 className="font-bold text-red-700 mb-2">地支:{pillar?.dizhi || '未知'}</h4>
|
||||
<div className="grid grid-cols-2 gap-2 text-sm">
|
||||
<div className={`px-2 py-1 rounded border ${pillar?.dizhiWuxing && wuxingColors[pillar.dizhiWuxing] ? wuxingColors[pillar.dizhiWuxing] : 'bg-gray-50 border-gray-300 text-gray-600'}`}>
|
||||
五行:{pillar?.dizhiWuxing || '未知'}
|
||||
</div>
|
||||
<div className={`px-2 py-1 rounded border ${pillar?.dizhiYinYang && yinyangColors[pillar.dizhiYinYang] ? yinyangColors[pillar.dizhiYinYang] : 'bg-gray-50 border-gray-300 text-gray-600'}`}>
|
||||
阴阳:{pillar?.dizhiYinYang || '未知'}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
|
||||
{/* 分析结果 */}
|
||||
<CompleteBaziAnalysis birthDate={birthData} />
|
||||
</div>
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
// 显示输入表单
|
||||
return (
|
||||
<div className="space-y-8 relative">
|
||||
{/* 页面装饰背景 */}
|
||||
<div className="absolute top-0 left-0 w-32 h-32 opacity-20 pointer-events-none">
|
||||
<img
|
||||
src="/chinese_traditional_golden_ornate_frame.png"
|
||||
alt=""
|
||||
className="w-full h-full object-contain"
|
||||
/>
|
||||
</div>
|
||||
<div className="absolute top-20 right-0 w-32 h-32 opacity-20 pointer-events-none">
|
||||
<img
|
||||
src="/chinese_traditional_golden_ornate_frame.png"
|
||||
alt=""
|
||||
className="w-full h-full object-contain rotate-180"
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* 标题区域 */}
|
||||
<div className="text-center space-y-4 relative z-10">
|
||||
<div className="w-16 h-16 mx-auto bg-gradient-to-br from-yellow-400 to-amber-600 rounded-full flex items-center justify-center shadow-2xl border-3 border-red-600">
|
||||
<BookOpen className="w-8 h-8 text-red-800" />
|
||||
<div className="min-h-screen bg-gradient-to-br from-red-50 to-yellow-50 py-8">
|
||||
<div className="max-w-4xl mx-auto px-4">
|
||||
{/* 返回按钮 */}
|
||||
<div className="mb-6">
|
||||
<Button
|
||||
onClick={handleBack}
|
||||
variant="outline"
|
||||
className="flex items-center space-x-2 border-red-300 text-red-700 hover:bg-red-50"
|
||||
>
|
||||
<ArrowLeft className="h-4 w-4" />
|
||||
<span>返回分析页面</span>
|
||||
</Button>
|
||||
</div>
|
||||
<h1 className="text-4xl md:text-5xl font-bold text-red-800 chinese-text-shadow font-serif">
|
||||
生辰八字
|
||||
<span className="block text-lg text-yellow-600 mt-2 font-normal">
|
||||
详细展示您的四柱信息与命理特征
|
||||
</span>
|
||||
</h1>
|
||||
</div>
|
||||
|
||||
{/* 输入区域 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Calendar className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
输入您的出生信息
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="grid md:grid-cols-2 gap-6">
|
||||
<div>
|
||||
<label className="block text-sm font-medium text-red-700 mb-2">
|
||||
出生日期 *
|
||||
</label>
|
||||
<input
|
||||
type="date"
|
||||
value={birthDate}
|
||||
onChange={(e) => setBirthDate(e.target.value)}
|
||||
className="w-full px-4 py-3 border-2 border-yellow-400 rounded-lg focus:outline-none focus:ring-2 focus:ring-red-500 bg-white text-red-800"
|
||||
required
|
||||
/>
|
||||
</div>
|
||||
<div>
|
||||
<label className="block text-sm font-medium text-red-700 mb-2">
|
||||
出生时间
|
||||
</label>
|
||||
<input
|
||||
type="time"
|
||||
value={birthTime}
|
||||
onChange={(e) => setBirthTime(e.target.value)}
|
||||
className="w-full px-4 py-3 border-2 border-yellow-400 rounded-lg focus:outline-none focus:ring-2 focus:ring-red-500 bg-white text-red-800"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div className="mt-6">
|
||||
<Button
|
||||
onClick={fetchBaziDetails}
|
||||
disabled={isLoading || !birthDate}
|
||||
size="lg"
|
||||
className="w-full chinese-red-glow text-white hover:shadow-xl transition-all duration-300 border-2 border-yellow-400"
|
||||
>
|
||||
{isLoading ? (
|
||||
<>加载中...</>
|
||||
) : (
|
||||
<>
|
||||
<Star className="mr-2 h-5 w-5" />
|
||||
开始八字详情
|
||||
</>
|
||||
)}
|
||||
</Button>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 错误提示 */}
|
||||
{error && (
|
||||
<Card className="border-red-400 bg-red-50">
|
||||
<CardContent className="p-4">
|
||||
<p className="text-red-700 text-center">{error}</p>
|
||||
</CardContent>
|
||||
{/* 主标题 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400 mb-8">
|
||||
<CardHeader className="text-center">
|
||||
<CardTitle className="text-red-800 text-3xl font-bold chinese-text-shadow">
|
||||
专业八字命理分析
|
||||
</CardTitle>
|
||||
<p className="text-red-600 mt-2">
|
||||
基于传统四柱八字理论,为您提供精准的命理分析和人生指导
|
||||
</p>
|
||||
</CardHeader>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 加载状态 */}
|
||||
{isLoading && (
|
||||
{/* 输入表单 */}
|
||||
<Card className="chinese-card-decoration border-2 border-yellow-400">
|
||||
<CardContent className="p-8">
|
||||
<div className="text-center space-y-4">
|
||||
<div className="w-16 h-16 mx-auto border-4 border-red-600 border-t-transparent rounded-full animate-spin"></div>
|
||||
<p className="text-red-700 text-lg font-medium">正在进行八字排盘分析...</p>
|
||||
<p className="text-red-600 text-sm">请稍候,这需要一些时间来计算您的详细八字信息</p>
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-xl font-bold chinese-text-shadow text-center">
|
||||
请输入您的出生信息
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-8">
|
||||
<div className="space-y-6">
|
||||
{/* 姓名输入 */}
|
||||
<div className="space-y-2">
|
||||
<label className="flex items-center text-red-800 font-semibold">
|
||||
<User className="h-5 w-5 mr-2 text-yellow-600" />
|
||||
姓名(可选)
|
||||
</label>
|
||||
<input
|
||||
type="text"
|
||||
value={birthData.name}
|
||||
onChange={(e) => handleInputChange('name', e.target.value)}
|
||||
placeholder="请输入您的姓名"
|
||||
className="w-full px-4 py-3 border-2 border-yellow-300 rounded-lg focus:border-red-400 focus:outline-none transition-colors bg-white"
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* 性别选择 */}
|
||||
<div className="space-y-2">
|
||||
<label className="flex items-center text-red-800 font-semibold">
|
||||
<User className="h-5 w-5 mr-2 text-yellow-600" />
|
||||
性别
|
||||
</label>
|
||||
<div className="flex space-x-4">
|
||||
<label className="flex items-center space-x-2 cursor-pointer">
|
||||
<input
|
||||
type="radio"
|
||||
name="gender"
|
||||
value="male"
|
||||
checked={birthData.gender === 'male'}
|
||||
onChange={(e) => handleInputChange('gender', e.target.value)}
|
||||
className="text-red-600 focus:ring-red-500"
|
||||
/>
|
||||
<span className="text-red-700">男性</span>
|
||||
</label>
|
||||
<label className="flex items-center space-x-2 cursor-pointer">
|
||||
<input
|
||||
type="radio"
|
||||
name="gender"
|
||||
value="female"
|
||||
checked={birthData.gender === 'female'}
|
||||
onChange={(e) => handleInputChange('gender', e.target.value)}
|
||||
className="text-red-600 focus:ring-red-500"
|
||||
/>
|
||||
<span className="text-red-700">女性</span>
|
||||
</label>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{/* 出生日期 */}
|
||||
<div className="space-y-2">
|
||||
<label className="flex items-center text-red-800 font-semibold">
|
||||
<Calendar className="h-5 w-5 mr-2 text-yellow-600" />
|
||||
出生日期 *
|
||||
</label>
|
||||
<input
|
||||
type="date"
|
||||
value={birthData.date}
|
||||
onChange={(e) => handleInputChange('date', e.target.value)}
|
||||
className="w-full px-4 py-3 border-2 border-yellow-300 rounded-lg focus:border-red-400 focus:outline-none transition-colors bg-white"
|
||||
required
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* 出生时间 */}
|
||||
<div className="space-y-2">
|
||||
<label className="flex items-center text-red-800 font-semibold">
|
||||
<Clock className="h-5 w-5 mr-2 text-yellow-600" />
|
||||
出生时间 *
|
||||
</label>
|
||||
<input
|
||||
type="time"
|
||||
value={birthData.time}
|
||||
onChange={(e) => handleInputChange('time', e.target.value)}
|
||||
className="w-full px-4 py-3 border-2 border-yellow-300 rounded-lg focus:border-red-400 focus:outline-none transition-colors bg-white"
|
||||
required
|
||||
/>
|
||||
<p className="text-sm text-red-600">
|
||||
请尽量提供准确的出生时间,这对八字分析的准确性非常重要
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{/* 分析按钮 */}
|
||||
<div className="pt-6">
|
||||
<Button
|
||||
onClick={handleAnalyze}
|
||||
className="w-full bg-gradient-to-r from-red-600 to-yellow-600 hover:from-red-700 hover:to-yellow-700 text-white font-bold py-4 px-8 rounded-lg text-lg transition-all duration-300 transform hover:scale-105 shadow-lg"
|
||||
>
|
||||
开始专业八字分析
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)}
|
||||
|
||||
{/* 八字详情结果 */}
|
||||
{baziData && !isLoading && (
|
||||
<div className="space-y-8">
|
||||
{/* 八字概览 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow text-center">
|
||||
八字概览
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="text-center">
|
||||
<h3 className="text-3xl font-bold text-red-800 chinese-text-shadow mb-4">
|
||||
{baziData.summary?.fullBazi || '未知'}
|
||||
</h3>
|
||||
<p className="text-red-600 text-lg mb-4">
|
||||
出生日期:{baziData.summary?.birthInfo?.solarDate || '未知'} {baziData.summary?.birthInfo?.birthTime || '未知'}
|
||||
</p>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{baziData.interpretation?.overall || '暂无详细分析'}
|
||||
</p>
|
||||
{/* 说明信息 */}
|
||||
<Card className="chinese-card-decoration border-2 border-yellow-400 mt-8">
|
||||
<CardContent className="p-6">
|
||||
<div className="text-center text-red-700">
|
||||
<h3 className="font-bold text-lg mb-4">专业八字分析包含</h3>
|
||||
<div className="grid md:grid-cols-2 lg:grid-cols-4 gap-4 text-sm">
|
||||
<div className="bg-white p-3 rounded-lg border border-yellow-300">
|
||||
<div className="font-semibold mb-1">🏛️ 四柱详解</div>
|
||||
<div>年月日时柱专业解释</div>
|
||||
</div>
|
||||
<div className="bg-white p-3 rounded-lg border border-yellow-300">
|
||||
<div className="font-semibold mb-1">⚡ 五行分析</div>
|
||||
<div>五行旺衰与平衡调理</div>
|
||||
</div>
|
||||
<div className="bg-white p-3 rounded-lg border border-yellow-300">
|
||||
<div className="font-semibold mb-1">🌟 格局判定</div>
|
||||
<div>命理格局与发展方向</div>
|
||||
</div>
|
||||
<div className="bg-white p-3 rounded-lg border border-yellow-300">
|
||||
<div className="font-semibold mb-1">📅 大运流年</div>
|
||||
<div>未来六年详细预测</div>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 日主信息 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<User className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
日主信息
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="text-center">
|
||||
<div className="text-6xl font-bold text-red-800 chinese-text-shadow mb-4">
|
||||
{baziData.rizhu?.tiangan || '未知'}
|
||||
</div>
|
||||
<div className="grid md:grid-cols-2 gap-4 mb-4">
|
||||
<div className={`px-4 py-2 rounded-lg border-2 ${baziData.rizhu?.wuxing ? wuxingColors[baziData.rizhu.wuxing] || 'bg-gray-50 border-gray-300' : 'bg-gray-50 border-gray-300'}`}>
|
||||
<span className="font-bold">五行:{baziData.rizhu?.wuxing || '未知'}</span>
|
||||
</div>
|
||||
<div className={`px-4 py-2 rounded-lg border-2 ${baziData.rizhu?.yinyang ? yinyangColors[baziData.rizhu.yinyang] || 'bg-gray-50 border-gray-300' : 'bg-gray-50 border-gray-300'}`}>
|
||||
<span className="font-bold">阴阳:{baziData.rizhu?.yinyang || '未知'}</span>
|
||||
</div>
|
||||
</div>
|
||||
<p className="text-red-700 leading-relaxed">
|
||||
{baziData.rizhu?.description || '暂无详细描述'}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 四柱详细信息 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow text-center">
|
||||
四柱详细信息
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="grid lg:grid-cols-2 xl:grid-cols-4 gap-6">
|
||||
{baziData?.baziDetails ? [
|
||||
baziData.baziDetails.year,
|
||||
baziData.baziDetails.month,
|
||||
baziData.baziDetails.day,
|
||||
baziData.baziDetails.hour
|
||||
].map((pillar, index) =>
|
||||
renderPillarCard(pillar, index)
|
||||
) : (
|
||||
<div className="col-span-full text-center text-red-600 py-8">
|
||||
四柱数据加载中...
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
|
||||
{/* 命理解释 */}
|
||||
<Card className="chinese-card-decoration dragon-corner border-2 border-yellow-400">
|
||||
<CardHeader>
|
||||
<CardTitle className="text-red-800 text-2xl font-bold chinese-text-shadow flex items-center">
|
||||
<Sparkles className="mr-2 h-6 w-6 text-yellow-600" />
|
||||
命理解释
|
||||
</CardTitle>
|
||||
</CardHeader>
|
||||
<CardContent>
|
||||
<div className="bg-gradient-to-br from-red-50 to-yellow-50 rounded-lg p-6">
|
||||
<div className="space-y-4">
|
||||
{baziData.interpretation && Object.entries(baziData.interpretation).map(([key, value], index) => {
|
||||
if (key === 'overall') return null; // 已在概览中显示
|
||||
const titles: { [key: string]: string } = {
|
||||
yearPillar: '年柱解释',
|
||||
monthPillar: '月柱解释',
|
||||
dayPillar: '日柱解释',
|
||||
hourPillar: '时柱解释'
|
||||
};
|
||||
return (
|
||||
<div key={key} className="flex items-start space-x-3 p-4 bg-white rounded-lg border-l-4 border-yellow-500">
|
||||
<div className="w-8 h-8 bg-gradient-to-br from-yellow-400 to-amber-500 rounded-full flex items-center justify-center flex-shrink-0">
|
||||
<span className="text-red-800 font-bold text-sm">{index}</span>
|
||||
</div>
|
||||
<div className="flex-1">
|
||||
<h4 className="font-bold text-red-800 mb-1">{titles[key] || '说明'}</h4>
|
||||
<p className="text-red-700 font-medium">{value}</p>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
})}
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
)}
|
||||
<p className="text-xs mt-4 text-red-600">
|
||||
本分析基于传统四柱八字理论,结合现代命理学研究成果,为您提供专业准确的命理指导
|
||||
</p>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user