98 lines
3.5 KiB
TypeScript
98 lines
3.5 KiB
TypeScript
type EnneagramType = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9;
|
|
|
|
const directKeys: Record<number, EnneagramType> = {
|
|
1: 1, 10: 1, 19: 1, 28: 1,
|
|
2: 2, 11: 2, 20: 2, 29: 2,
|
|
3: 3, 12: 3, 21: 3, 30: 3,
|
|
4: 4, 13: 4, 22: 4, 31: 4,
|
|
5: 5, 14: 5, 23: 5, 32: 5,
|
|
6: 6, 15: 6, 24: 6, 33: 6,
|
|
7: 7, 16: 7, 25: 7, 34: 7,
|
|
8: 8, 17: 8, 26: 8, 35: 8,
|
|
9: 9, 18: 9, 27: 9, 36: 9,
|
|
};
|
|
|
|
const bipolarKeys: Record<number, { left?: EnneagramType[]; right?: EnneagramType[] }> = {
|
|
37: { left: [8], right: [6] },
|
|
38: { left: [1], right: [4, 7] },
|
|
39: { left: [9], right: [3] },
|
|
40: { left: [7], right: [5] },
|
|
41: { left: [1], right: [7] },
|
|
42: { left: [2], right: [5] },
|
|
43: { left: [7, 8], right: [9] },
|
|
44: { left: [5], right: [2, 4] },
|
|
45: { left: [8], right: [2, 9] },
|
|
46: { right: [1] },
|
|
47: { right: [2] },
|
|
48: { left: [3] },
|
|
49: { right: [4] },
|
|
50: { right: [5] },
|
|
51: { right: [6] },
|
|
52: { left: [7] },
|
|
53: { left: [8] },
|
|
54: { left: [9] },
|
|
};
|
|
|
|
export const enneagramTypeInfo: Record<EnneagramType, { name: string; shortName: string; description: string }> = {
|
|
1: { name: '1号 改革者', shortName: '改革者', description: '追求正确、负责、自律和改进。' },
|
|
2: { name: '2号 助人者', shortName: '助人者', description: '重视关系、照顾他人和被需要。' },
|
|
3: { name: '3号 成就者', shortName: '成就者', description: '重视目标、效率、表现和认可。' },
|
|
4: { name: '4号 自我型', shortName: '自我型', description: '重视真实、独特、情绪深度和个人意义。' },
|
|
5: { name: '5号 探索者', shortName: '探索者', description: '重视知识、理解、独立和能力感。' },
|
|
6: { name: '6号 忠诚者', shortName: '忠诚者', description: '重视安全、支持、可靠性和风险预判。' },
|
|
7: { name: '7号 享乐者', shortName: '享乐者', description: '重视自由、可能性、新体验和快乐。' },
|
|
8: { name: '8号 挑战者', shortName: '挑战者', description: '重视力量、直接、掌控和保护边界。' },
|
|
9: { name: '9号 调停者', shortName: '调停者', description: '重视和谐、稳定、舒适和避免冲突。' },
|
|
};
|
|
|
|
function addScore(
|
|
scores: Record<EnneagramType, { total: number; count: number }>,
|
|
type: EnneagramType,
|
|
value: number,
|
|
) {
|
|
scores[type].total += value;
|
|
scores[type].count += 1;
|
|
}
|
|
|
|
export function calculateOEPSResults(answers: string[]) {
|
|
const scores = Object.fromEntries(
|
|
([1, 2, 3, 4, 5, 6, 7, 8, 9] as EnneagramType[]).map((type) => [
|
|
type,
|
|
{ total: 0, count: 0 },
|
|
]),
|
|
) as Record<EnneagramType, { total: number; count: number }>;
|
|
|
|
answers.forEach((answer, index) => {
|
|
const questionId = index + 1;
|
|
const value = Number(answer || 0);
|
|
if (!value) return;
|
|
|
|
const directType = directKeys[questionId];
|
|
if (directType) {
|
|
addScore(scores, directType, value);
|
|
return;
|
|
}
|
|
|
|
const key = bipolarKeys[questionId];
|
|
if (!key) return;
|
|
|
|
key.left?.forEach((type) => addScore(scores, type, 6 - value));
|
|
key.right?.forEach((type) => addScore(scores, type, value));
|
|
});
|
|
|
|
const ranked = (Object.entries(scores) as [string, { total: number; count: number }][])
|
|
.map(([type, score]) => ({
|
|
type: Number(type) as EnneagramType,
|
|
total: score.total,
|
|
count: score.count,
|
|
average: score.count ? score.total / score.count : 0,
|
|
...enneagramTypeInfo[Number(type) as EnneagramType],
|
|
}))
|
|
.sort((a, b) => b.average - a.average);
|
|
|
|
return {
|
|
ranked,
|
|
top: ranked[0],
|
|
};
|
|
}
|