요즘 과제에 치이고 알바도 하느라 블로그를 안쓴지 오래된 것 같은데 나름 짬짬히 이것저것 만들긴 했다. 한 번에 포스팅하려니 막막해서 그중 하나인 mbti 테스트 먼저 포스팅 하려한다.
+ 아직 디자인은 완성되지 않았는데 포켓몬 세상을 컨셉으로 잡았다 ㅋ
mbti 테스트의 기본 알고리즘은 E와 I, N과 S 등 4가지 클래스의 성향을 판단하기 위해 질문이 필요하다. 따라서 각 클래스의 질문은 홀수여야 하고, 어떤 성향이 더 큰지 비교하여 출력한다.
완성 사이트 starlit-frangollo-737871.netlify.app
이렇게 된다면 결과는 각각 2번씩 선택된 ESTP가 출력된다.
여기서 또 문제가 생겼는데 질문을 어떻게 해야할지 문제였다. 그런데 GPT한테 간단히 설명하고 질문지를 만들어달라고 요청했는데 순식간에 만들어줘서 쉽게 해결했다.
사용 코드
html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>MBTI TEST</title>
<link rel="stylesheet" href="css.css">
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link
href="https://fonts.googleapis.com/css2?family=Black+Han+Sans&family=Bruno+Ace&family=Unna:ital@1&display=swap"
rel="stylesheet">
</head>
<body>
<div id="Title">
나와 닮은 포켓몬은?
</div>
<div id="intro">
<div id="monsterball">
<div id="ue" class="soto"></div>
<div id="shita" class="soto"></div>
<div id="center">
<div id="nakanaka">
</div>
</div>
</div>
<div id="button" onclick="btnClick()">
<div id="letter">GO!</div>
<div class="btn_top"></div>
<div class="btn_bottom"></div>
</div>
</div>
<div id="contant">
<h2 id="question"></h2>
<button class="option"></button>
<button class="option"></button>
</div>
<div id="result"></div>
</body>
<script src="app.js">
</script>
</html>
css
* { margin: 0px; padding: 0px;}
body{
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
height: 100vh;
font-family: 'Black Han Sans', sans-serif;
/* background: linear-gradient(120deg,#FFFF00,#d7d1ca ); */
}
#Title{
font-size: 40px;
}
@keyframes yureru {
0% { transform: translate(0px, 0px) rotateZ(0deg); }
10% { transform: translate(-20px, 0px) rotateZ(-10deg); }
20% { transform: translate(0px, 0px) rotateZ(0deg); }
30% { transform: translate(20px, 0px) rotateZ(10deg); }
40% { transform: translate(0px, 0px) rotateZ(0deg); }
}
#monsterball {
margin: 30px auto;
animation: yureru 1s ease infinite;
width: 200px;
height: 200px;
}
.soto {
width: 200px;
height: 100px;
border: 5px solid black;
}
#center {
border: 5px solid black;
width: 50px;
height: 50px;
border-radius: 50px;
background-color: white;
position: absolute;
top: 80px;
left: 75px;
cursor: pointer;
}
#nakanaka:hover{
transition: .5s;
box-shadow: 2px 2px 2px
}
#nakanaka{
border: 2px solid black;
width: 40px;
height: 40px;
border-radius: 50px;
position: absolute;
top: 3.25px;
left: 3.25px;
}
#ue {
background-color: red;
border-radius: 200px 200px 0px 0px;
}
#shita {
background-color: white;
border-radius: 0px 0px 200px 200px;
position: relative;
top: -5px;
}
.question{
display: inline-block;
font-weight: lighter;
}
#button{
margin-top: 20px;
margin-left: 8px;
width: 180px;
height: 60px;
font-size: large;
font-weight: bold;
text-align: center;
line-height: 60px;
cursor: pointer;
}
.btn_top{
background-color: red;
width: 100%;
height: 30px;
border: black 3px solid;
border-bottom: 0px;
border-radius: 5px 5px 0px 0px;
}
.btn_bottom{
background-color: white;
width: 100%;
height: 30px;
border : black 3px solid;
border-top: 0px;
border-radius: 0px 0px 5px 5px;
}
#letter{
position: absolute;
margin-top: 5px;
z-index: 2;
display: block;
width: 180px;
height: 60px;
font-weight: bold;
font-size: 30px;
font-family: 'Bruno Ace';
}
#contant{
position: absolute;
visibility: hidden;
margin-top: -50px;
font-family: 'Gill Sans', 'Gill Sans MT', Calibri, 'Trebuchet MS', sans-serif;
text-align: center;
}
.option{
display: inline-block;
margin: 15px;
width: 300px;
height: 150px;
border-radius: 10px;
border: 2px solid black;
cursor: pointer;
font-size: large;
font-weight: bold;
text-align: center;
line-height: 60px;
/* From https://css.glass */
background: rgba(255, 255, 255, 0.2);
border-radius: 16px;
box-shadow: 0 4px 30px rgba(0, 0, 0, 0.1);
backdrop-filter: blur(5px);
-webkit-backdrop-filter: blur(5px);
border: 1px solid rgba(255, 255, 255, 0.3);
}
.option_top{
background-color: red;
width: 100%;
height: 30px;
border: black 3px solid;
border-bottom: 0px;
border-radius: 5px 5px 0px 0px;
z-index: 2;
}
.option:hover{
box-shadow: 2px 2px 2px #ccc
}
JS
let I_count = 0;
let E_count = 0;
let S_count = 0;
let N_count = 0;
let F_count = 0;
let T_count = 0;
let P_count = 0;
let J_count = 0;
function btnClick() {
var intro = document.getElementById("intro");
var contant = document.getElementById("contant");
intro.style.visibility = "hidden";
contant.style.visibility = "visible";
}
const questions = [
{
// 여기부터 I~E 테스트
question: "당신은 포켓몬 센터에서 주로 어떤 편?",
options: [
{text: "포켓몬을 치료하고 다음 전투를 준비한다", value: "I"},
{text: "다른 트레이너들과 수다를 떨며 이야기를 나눈다", value: "E"},
],
},
{
question: "포켓몬 배틀을 할 때 나는?",
options: [
{text: "이기기 위해 전략적인 장소로 간다", value: "I"},
{text: "모두들 나 싸우는것좀 봐 많은 사람들 앞으로!", value: "E"},
],
},
{
question: "포켓몬을 트레이닝할때 나는?",
options: [
{text: "다양한 트레이너와 만나며 배틀을 한다.", value: "E"},
{text: "포켓몬과 둘이서 훈련을하며 친밀도를 높인다.", value: "I"},
],
},
// 여기부터 S~N 테스트
{
question: "새로운 포켓몬을 발견했을 때 나는?",
options: [
{text: "무슨 포켓몬인지 몰라도 일단 잡고본다.", value: "S"},
{text: "저 포켓몬은 진화하면 어떻게 될까? 내 팀과 잘 어울릴까? 하며 생각해본다.", value: "N"},
],
},
{
question: "포켓몬 전투 전략을 세울 때, 나는?",
options: [
{text: "새로운 아이디어와 창의적인 전략을 시도해 본다.", value: "N"},
{text: "실제 전투에서 효과적이었던 전략을 바탕으로 계획한다", value: "S"},
],
},
{
question: "포켓몬을 선택할 때, 나는?",
options: [
{text: "타입, 스탯 등 구체적인 정보를 기반으로 선택", value: "S"},
{text: "성격과 포켓몬의 특징을 고려하여 선택", value: "N"},
],
},
// 여기부터 F~T 테스트
{
question: "팀의 포켓몬을 선택할 때 우선 순위",
options: [
{text: "타입, 스탯 등 구체적인 정보를 기반으로 선택", value: "T"},
{text: "개인적으로 친한 포켓몬 우선!", value: "F"},
],
},
{
question: "포켓몬 배틀에서 졌을 때 나는?",
options: [
{text: "같이 열심히 싸워준 포켓몬에게 위로를 한다.", value: "F"},
{text: "왜 졌는지 진 이유에 대해 분석한다.", value: "T"},
],
},
{
question: "쓰러져있는 야생 포켓몬을 발견했다!",
options: [
{text: "현재 포켓몬의 상황을 판단하고 바로 포켓몬 센터로 간다.", value: "T"},
{text: "시간이 조금 걸리더라도 불안해하는 포켓몬을 안심시킨 후에 포켓몬 센터로 간다.", value: "F"},
],
},
// 여기부터 P~J 테스트
{
question: "포켓몬 마스터가 되기 위한 여행을 떠날 때 나는?",
options: [
{text: "경로를 먼저 짜고 출발!", value: "J"},
{text: "일단 출발!", value: "P"},
],
},
{
question: "포켓몬을 키울 때 나는?",
options: [
{text: "필요할 때 부르면 되지!", value: "P"},
{text: "어떤 식으로 기를지 미리 생각한다.", value: "J"},
],
},
{
question: "배틀을 하기 전 나는?",
options: [
{text: "일단 제일 쌘 애부터 내보낸다!", value: "P"},
{text: "상대가 내는거 보고 생각할까?", value: "J"},
],
},
];
let currentQuestionIndex = 0;
function showQuestion() {
const questionElement = document.getElementById("question");
const optionElements = document.querySelectorAll(".option");
questionElement.textContent = questions[currentQuestionIndex].question;
optionElements[0].textContent =
questions[currentQuestionIndex].options[0].text;
optionElements[0].value = questions[currentQuestionIndex].options[0].value;
optionElements[1].textContent =
questions[currentQuestionIndex].options[1].text;
optionElements[1].value = questions[currentQuestionIndex].options[1].value;
}
document.addEventListener("DOMContentLoaded", () => {
const optionButtons = document.querySelectorAll(".option");
optionButtons.forEach((button) => {
button.addEventListener("click", () => {
// I_count 또는 E_count를 증가시킵니다.
if (button.value === "I") {
I_count += 1;
console.log('I_count: ',I_count);
console.log('E_count: ',E_count);
}
else if (button.value === "E") {
E_count += 1;
console.log('I_count: ',I_count);
console.log('E_count: ',E_count);
}
else if (button.value === "S") {
S_count += 1;
console.log('S_count: ',S_count);
console.log('N_count: ',N_count);
}
else if (button.value === "N") {
N_count += 1;
console.log('S_count: ',S_count);
console.log('N_count: ',N_count);
}
else if (button.value === "T") {
T_count += 1;
console.log('T_count: ',T_count);
console.log('F_count: ',F_count);
}
else if (button.value === "F") {
F_count += 1;
console.log('T_count: ',T_count);
console.log('F_count: ',F_count);
}
else if (button.value === "P") {
P_count += 1;
console.log('P_count: ',P_count);
console.log('J_count: ',J_count);
}
else if (button.value === "J") {
J_count += 1;
console.log('I_count: ',P_count);
console.log('E_count: ',J_count);
}
// 다음 질문으로 이동
currentQuestionIndex += 1;
if (currentQuestionIndex < questions.length) {
showQuestion();
} else {
let result = "";
if (I_count > E_count) {
result += "I";
} else {
result += "E";
}
if (S_count > N_count) {
result += "S";
} else {
result += "N";
}
if (T_count > F_count) {
result += "T";
} else {
result += "F";
}
if (P_count > J_count) {
result += "P";
} else {
result += "J";
}
const resultElement = document.getElementById("result");
resultElement.textContent = result
}
});
});
// 첫 번째 질문을 표시합니다.
showQuestion();
});
html에 있는 contant 부분이 버튼을 누르면 바뀌도록 JS 코드를 만들었다
반응형
'Front end > JavaScript' 카테고리의 다른 글
[JavaScript] 구조분해 할당 (0) | 2024.11.07 |
---|---|
[JavaScript] for in과 for of (0) | 2024.11.05 |
Weather site 만들기 (2) | 2023.03.19 |
(JavaScipt) OpenWeatherAPI 사용법 (0) | 2023.03.17 |
(Java Scipt) 아날로그 시계 만들기 (0) | 2023.03.13 |
댓글