WEB/JAVASCRIPT

[자바스크립트] 퀴즈 이펙트 : 객관식 문제 만들기

aimee418 2023. 3. 25. 16:04

“ 지연되는 프로젝트에 인력을 더 투입하면 오히려 더 늦어진다. ”

- Frederick Philips Brooks
Mythical Man-Month 저자
728x90
반응형

퀴즈 이펙트 : 객관식 문제 만들기

 

 

✈. 정보처리기능사 60문제 시험으로 만들어 보았습니다.

      같이 풀어볼까요?

 

 

 

 

✈. HTML

    <header id="header">
        <h1><a href="../javascript14.html">Quiz</a><em> 주관식 확인하기 유형</em></h1>
        <ul>
            <li><a href="quizEffect01.html">1</a></li>
            <li><a href="quizEffect02.html">2</a></li>
            <li><a href="quizEffect03.html">3</a></li>
            <li><a href="quizEffect04.html">4</a></li>
            <li class="active"><a href="quizEffect05.html">5</a></li>
        </ul>     
    </header> 
    <!-- //header -->
    <main id="main">
        <div class="quiz__wrap">
    </main>
    <!-- //main -->
    <footer id="footer">
        <a href="mailto:aimee00418@gmail.com">aimee00418@gmail.com</a>
    </footer>

🏁.POINT

 - 문제정보는 자바스크립트로 작성할 예정 입니다.

 

✈. CSS

/* header */
#header {
    background-color: #d3d3d3;
    color: #fff;
    padding: 10px;
    position: fixed;
    left: 0;
    top: 0;
    width: 100%;
    display: flex;
    justify-content: space-between;
}
#header::before {
    content: '';
    border: 4px ridge #ccc;
    position: absolute;
    left: 5px;
    top: 5px;
    width: calc(100% - 10px);
    height: calc(100% - 10px);
}
#header h1{
    font-size: 28px;
    padding: 5px 5px 5px 10px;
    font-family: 'DungGeunMo';
    z-index: 10;
    position: relative;
}
#header h1 a {
    color: #fff;
}
#header h1 em{
    font-size: 0.5em;
}
#header ul {
  padding: 5px;
}
#header li {
  display: inline;
  z-index: 10;
  position: relative;;
}
#header li a {
    color: #fff;
    font-family: 'DungGeunMo';
    border: 1px dashed #fff;
    display: inline-block;
    padding: 5px;
}
#header li.active a,
#header li a:hover {
    background-color: #fff;
    color: #666;
} 
/* footer */
#footer {
    position: fixed;
    left: 0;
    bottom: 0;
    width: 100%;
    background-color: #d3d3d3;
    text-align: center;
}
#footer a{
    color: #fff;
    padding: 20px;
    display: block;
    font-family: 'DungGeunMo';
    z-index: 10;
    position: relative;
}
#footer ::before{
    content: '';
    border: 4px ridge #333;
    position: absolute;
    left: 5px;
    top: 5px;
    width: calc(100% - 16px);
    height: calc(100% - 12px);  
}
#main {
    padding: 100px 0;
}
/* quiz__wrap */
.quiz__wrap {
    display: flex;
    justify-content: center;
    flex-wrap: wrap;
}
.quiz__wrap .quiz{
    width: 500px;
    background-color: #fff;
    border: 8px ridge #d3d3d3;
    margin: 10px;
}
.quiz__header{}
.quiz__title{
    background-color: #d3d3d3;
    border: 3px ridge #ccc;
    border-bottom-width: 6px;
    padding: 5px;
    font-family: 'DungGeunMo';
    font-size: 16px;
    color: #ffffff;
    text-align: center;
}
.quiz__main{}
.quiz__question {
    color: #3b3b3b;
    padding: 20px;
    font-size: 24px;
    font-family: 'NanumSquareNeo';
    font-weight: bold;
    line-height: 1.5;
    border-bottom: 6px ridge #ccc;
}
.quiz__question em {
    color : #333;
}
.quiz__answer {
    font-family: 'NanumSquareNeo';
    padding: 20px;
    text-align: center;
    font-size: 24px;
    /* border-bottom: 6px ridge #05e658; */
}
.quiz__answer .confirm {
    cursor: pointer;
    background-color: #f5f5f5;
    border: 3px ridge #ccc;
    width: 100%;
    font-family: 'NanumSquareNeo';
    padding: 10px 20px;
    font-size: 22px;
    transition: all 0.3s;
    text-shadow: 1px 1px 0 #c2c2c2;
    font-weight: 700;
}
.quiz__answer .confirm:hover{
    background-color: #e2e2e2;
}
.quiz__answer .result {
    /* display: none; */
    background-color: #fff;
    border: 3px ridge #ccc;
    width: 100%;
    font-family: 'NanumSquareNeo';
    padding: 10px 20px;
    font-size: 22px;
}
.quiz__answer .input {
  /* display: none; */
    background-color: #fff;
    border: 3px groove #ccc;
    width: 100%;
    font-family: 'NanumSquareNeo';
    padding: 10px 20px;
    font-size: 22px;
    margin-bottom: 10px;
}
.quiz__view {
    border-bottom: 6px ridge #cacaca;
}
/* 문제해설 */
.quiz__desc {
  border-top: 6px ridge #cacaca;
  padding: 20px;
  font-family: 'NanumSquareNeo';
}
.quiz__desc::before {
  content:'🎁Tip ';
  color: #cb001c;
  font-weight: bold;
}
.quiz__choice {
  padding: 20px;
  border-bottom: 6px ridge #cacaca;
  font-family: 'NanumSquareNeo';
}
.quiz__choice label {
    display: flex;
}
.quiz__choice label input {
    /* position: absolute; */
    /* left: -9999px; */
    clip: rect(0 0 0 0 );
    width: 1px;
    height: 1px;
    margin: -1px;
    overflow: hidden;
}
.quiz__choice label span {
    font-size: 20px;
    line-height: 1.4;
    padding: 6px;
    display: flex;
    cursor: pointer;
    margin: 2px 0;
}
.quiz__choice label span::before{
    content:'';
    width: 26px;
    height: 26px;
    margin-right: 15px;
    border-radius: 50%;
    background-color: #fff;
    box-shadow: inset 0 0 0 4px #6fa30b;
    transition: all 0.2s;
    flex-shrink: 0;
    /* flex 일정이상 작아지지 않도록 */
}
.quiz__check {
    position: fixed;
    right: 20px;
    bottom: 80px;
    width: 130px;
    height: 130px;
    text-align: center;
    line-height: 130px;
    border-radius: 50%;
    z-index: 1000;
    background: #222;
    color: #fff;
    font-family: 'NanumSquareNeo';
    cursor: pointer;
}
/* 모달창 쓰지 않음
.quiz__modal {
    width: 100%;
    height: 100%;
    position: fixed;
    left: 0;
    top: 0;
    z-index: 2000;
    background-color: rgba(0,0,0,0.2);
    display: flex;
    align-items: center;
    justify-content: center;
  }
.quiz__modal .modal {
    width: 500px;
    height: 500px;
    background-color: #fff;

} */
.quiz__check a:hover {
}
.quiz__choice label input:checked + span {
    background-color: #f5ffe7;
}
.quiz__choice label input:checked + span::before {
  box-shadow: inset 0 0 0 8px #6fa30b;
}
.quiz__footer{
    border-top: 6px ridge #cacaca;
    padding: 20px;
    font-family: 'NanumSquareNeo';
    display: none;
}
.quiz__footer::before {
     content:'🎁Tip';
     color: #ff3c3c;
     font-weight: bold;
}
.quiz__info {
  position: fixed;
  right: 20px;
  bottom: 220px;
  background-color: #cb001c;
  text-align: center;
  width: 130px;
  height: 50px;
  line-height: 50px;
  border-radius: 10px;
  color: #FEFEFE;
}
/* 말풍선모양 역삼각형만들기 */
.quiz__info::after {
  content: '';
  position: absolute;
  left: 50%;
  bottom: -10px;
  margin-left: -10px;
  border-top: 10px solid #cb001c;
  border-left: 10px solid transparent;
  border-right: 10px solid transparent;
}
/* dog__wrap */
.dog .tail, 
.dog .chin, 
.dog .tongue::before, 
.dog .tongue::after, 
.dog .mouth, 
.dog .nose, 
.dog .teardrop, 
.dog .eyes, 
.dog .face::before, 
.dog .face::after, 
.dog .ears::before, 
.dog .ears::after, 
.dog__wrap {
    transition: 0.2s ease-in;
}
.dog__wrap {
  position: relative;
  flex-wrap: wrap;
  align-items: flex-start;
}
.dog__wrap .true {
  width: 120px;
  height: 120px;
  line-height: 120px;
  background-color: #549561;
  border-radius: 50%;
  color: #fff;
  position: absolute;
  left: 70%;
  top: 100px;
  text-align: center;
  font-family: 'NanumSquareNeo';
  opacity: 0;
}
.dog__wrap .false {  
  width: 120px;
  height: 120px;
  line-height: 120px;
  background-color: #dda852;
  border-radius: 50%;
  color: #fff;
  position: absolute;
  right: 70%;
  top: 100px;
  text-align: center;
  font-family: 'NanumSquareNeo';
  opacity: 0;
}
.dog__wrap.like .true {
  opacity: 1;
  animation: wobble .6s;
}
.dog__wrap.dislike .false {
  opacity: 1;
  animation: wobble .6s;
}
@keyframes wobble {
  0% {transform: translateX(0) rotate(0deg);}
  15% {transform: translateX(-25%) rotate(-5deg);}
  30% {transform: translateX(20%) rotate(3deg);}
  45% {transform: translateX(-15%) rotate(-3deg);}
  60% {transform: translateX(10%) rotate(2deg);}
  75% {transform: translateX(-5%) rotate(-1deg);}
  100% {transform: translateX(0%) rotate(0deg);}
}
.card-container {
    position: relative;
    width: 360px;
    height: 378px;
    margin: auto;
    padding-top: 125px;
    border-radius: 3%;
    z-index: 0;
}
.card-container::before {
    top: 3%;
    width: 93%;
    background: rgba(255, 255, 255, 0.7);
}
.card-container::after {
    top: 5.5%;
    width: 85%;
    background: rgba(255, 255, 255, 0.35);
}
.dog .head,
.dog .body {
    position: relative;
    width: 115px;
}
.dog .head {
    height: 115px;
    border-radius: 50% 50% 0 0;
    margin: 0 auto;
}
.dog .ears {
    position: relative;
    top: -14%;
    width: 100%;
}
.dog .ears::before, .dog .ears::after {
  content: "";
  position: absolute;
  top: 0;
  width: 35px;
  height: 70px;
  background: #CB7A1D;
  border-top: 11px solid #F7AA2B;
  border-left: 7px solid #F7AA2B;
  border-right: 7px solid #F7AA2B;
}
.dog .ears::before {
  left: 0;
  border-radius: 50% 45% 0 0;
}
.dog .ears::after {
  right: 0;
  border-radius: 45% 50% 0 0;
}
.dog .face {
  position: absolute;
  background: #F7AA2B;
  width: 100%;
  height: 100%;
  border-radius: 50% 50% 0 0;
}
.dog .face::before, .dog .face::after {
  content: "";
  display: block;
  margin: auto;
  background: #FEFEFE;
}
.dog .face::before {
  width: 15px;
  height: 35px;
  margin-top: 24px;
  border-radius: 20px 20px 0 0;
}
.dog .face::after {
  position: absolute;
  bottom: -1px;
  left: 0;
  right: 0;
  width: 60px;
  height: 65px;
  border-radius: 45% 45% 0 0;
}
.dog .eyes {
  position: relative;
  top: 29%;
  text-align: center;
}
.dog .eyes::before, .dog .eyes::after {
  content: "";
  display: inline-block;
  width: 12px;
  height: 12px;
  border-radius: 100%;
  background: #451d1c;
  margin: 0 14.5%;
}
.dog .teardrop {
  position: absolute;
  top: 125%;
  left: 19%;
  width: 6px;
  height: 6px;
  border-radius: 0 50% 50% 50%;
  transform: rotate(45deg);
  background: #FEFEFE;
  visibility: hidden;
}
.dog .nose {
  position: relative;
  top: 35%;
  width: 16px;
  height: 8px;
  border-radius: 35px 35px 65px 65px;
  background: #451d1c;
  margin: auto;
}
.dog .mouth {
  position: relative;
  top: 34.5%;
  width: 4px;
  height: 6px;
  margin: 0 auto;
  text-align: center;
  background: #451d1c;
}
.dog .mouth::before, .dog .mouth::after {
  content: "";
  position: absolute;
  top: -4px;
  width: 18px;
  height: 18px;
  border-radius: 50%;
  border: 4px solid #451d1c;
  border-left-color: transparent;
  border-top-color: transparent;
  z-index: 2;
}
.dog .mouth::before {
  transform: translateX(-89%) rotate(45deg);
}
.dog .mouth::after {
  transform: translateX(-2px) rotate(45deg);
}
.dog .tongue {
  position: relative;
  z-index: 1;
}
.dog .tongue::before, .dog .tongue::after {
  content: "";
  position: absolute;
}
.dog .tongue::before {
  top: 10px;
  left: -7px;
  width: 18px;
  height: 0;
  border-radius: 50%;
  background: #451d1c;
  z-index: -1;
}
.dog .tongue::after {
  top: 14px;
  left: -4px;
  width: 12px;
  height: 0;
  border-radius: 20px;
  background: #F5534F;
  z-index: 5;
}
.dog .chin {
  position: relative;
  top: 47.5%;
  margin: 0 auto;
  width: 12px;
  height: 12px;
  border-top: 10px solid #e8e7ec;
  border-left: 5px solid transparent;
  border-right: 5px solid transparent;
  border-radius: 2px;
  z-index: 0;
}
.dog .body {
  position: relative;
  height: 139px;
  margin: auto;
  z-index: 0;
}
.dog .body::before, .dog .body::after {
  content: "";
  position: absolute;
  top: -1px;
  left: 0;
  right: 0;
  bottom: 0;
  display: block;
  width: 100%;
  margin: auto;
  background: #F7AA2B;
}
.dog .body::after {
  top: -2px;
  bottom: -1px;
  width: 60px;
  background: #FEFEFE;
}
.dog .tail {
  position: absolute;
  left: -60%;
  bottom: 1px;
  background: #F7AA2B;
  width: 93px;
  height: 15px;
  transform: rotate(45deg);
  transform-origin: 100% 50%;
  border-radius: 25px 0 0 25px;
  z-index: -2;
}
.dog .legs {
  position: absolute;
  bottom: 0;
  left: -10%;
  width: 120%;
  height: 15%;
  background: #F7AA2B;
  border-radius: 10px 10px 0 0;
}
.dog .legs::before, .dog .legs::after {
  content: "";
  position: absolute;
  bottom: 1px;
  background: #CB7A1D;
  z-index: -1;
}
.dog .legs::before {
  left: -7.5%;
  width: 115%;
  height: 55%;
  border-radius: 5px 5px 0 0;
}
.dog .legs::after {
  left: -3.5%;
  width: 107%;
  height: 250%;
  border-radius: 20px 20px 35px 35px;
}
@keyframes movetongue {
  100% {
    height: 27px;
  }
}
@keyframes movetail {
  0% {
    transform: rotate(37deg);
  }
  100% {
    transform: rotate(52deg);
  }
}
@keyframes cry {
  100% {
    visibility: visible;
  }
}

.like {
  background: #ffdcd0;
}

.like .face::before {
  margin-top: 10px;
}

.like .face::after {
  height: 85px;
}

.like .eyes {
  top: 13%;
}

.like .eyes::before,
.like .eyes::after {
  width: 18px;
  height: 5px;
  margin: 0px 12.5%;
  transform: rotate(-37.5deg);
  border-radius: 20px;
}

.like .eyes::after {
  transform: rotate(37.5deg);
}

.like .nose {
  top: 18%;
}

.like .mouth {
  top: 16.5%;
}

.like .tongue::before {
  height: 12px;
}

.like .tongue::after {
  height: 24px;
          animation: movetongue 0.1s linear 0.35s infinite alternate forwards;
}

.like .chin {
  top: 34%;
}

.tail {
  animation: movetail 0.1s linear infinite alternate forwards;
}


.dislike {
  background: #9879d0;
}

.dislike .ears::before {
  transform: rotate(-50deg) translate(-7px, 2px);
}

.dislike .ears::after {
  transform: rotate(50deg) translate(7px, 2px);
}

.dislike .face::before {
  margin-top: 28px;
}

.dislike .face::after {
  height: 55px;
}

.dislike .eyes {
  top: 38%;
}

.dislike .eyes::before,
.dislike .eyes::after {
  width: 18px;
  height: 5px;
  margin: 0px 14.5%;
  transform: rotate(-37.5deg);
  border-radius: 20px;
}
.dislike .eyes::after {
  transform: rotate(37.5deg);
}
.dislike .teardrop {
  animation: cry 0.1s ease-in 0.25s forwards;
}
.dislike .nose {
  top: 44%;
}
.dislike .mouth {
  top: 42%;
}
.dislike .chin {
  top: 52%;
}
.dislike .tail {
  transform: rotate(0);
}

🏁. POINT

 

 

✈. JAVASCRIPT

//문제정보 //<br><img style='width:300px' src=''> 이렇게 이미지 넣기
        const quizInfo = [
            {
                infoType: "정보처리 기능사",
                infoTime: "2009년 7월 12일 5회",
                infoNumber: "20090501",
                infoQuestion: "명령어(Instruction)형식에서 첫 번째 바이트의 기능이 아닌 것은?",
                infoChoice: {
                    1: "자료의 주소지정 기능",
                    2: "제어 기능",
                    3: "자료 전달 기능",
                    4: "함수 연산 기능",
                },
                infoAnswer: "1",
                infoDesc: "명령어 = 명령어 코드부 + 명령어 주소부 Instruction = Op_Code + Operand 연산자의(명령어 코드) 4가지 기능 1.제어기능 2.입출력기능 3.전달기능 4.함수연산기능"            
            },{
                infoType: "정보처리 기능사",
                infoTime: "2009년 7월 12일 5회",
                infoNumber: "20090502",
                infoQuestion: "다음 불대수(Boolean algebra)의 기본법칙을 바르게 표현한 것은?<br>A+(B+C) = (A+B)+C",
                infoChoice: {
                    1: "교환법칙",
                    2: "분배법칙",
                    3: "흡수법칙",
                    4: "결합법칙",
                },
                infoAnswer: "4",
                infoDesc: "연산자가 모두 동일할 경우 앞으로 괄호로 결합하거나 뒤로 괄호로 결합하거나 하는 것은 결국 같다는 것이 결합 법칙 입니다."
            }
//선택자
        const quizWrap = document.querySelector(".quiz__wrap");
        // const quizTitle = quizWrap.querySelector(".quiz__title");
        // quizTitle.innerHTML = quizInfo[0].infoQuestion; //선택자 quizTitle안에html넣기
        // console.log(quizInfo[2].infoChoice[1])
        let quizScore = 0;

🏁. POINT

이런 방식으로 60문제를 작성하였습니다.

 

✈ . 문제출력을 위한 스크립트 입니다. 

        //문제출력
        const updateQuiz = () => {
            const exam = []; //exam은 배열이다 : 선언

            quizInfo.forEach((question, number) => { //quizInfo == question : forEach함수
                //exam배열에 객체를 push한다. 방법은 백틱(``)태그 안에 넣는 것 =>템플릿 리터럴 (리터럴 : 데이터 그자체)
                exam.push(`
                    <div class="quiz">
                    <div class="quiz__header">
                        <h2 class="quiz__title">${question.infoType} ${question.infoTime}</h2>
                    </div>
                    <div class="quiz__main">
                        <div class="quiz__question">
                            <em>${number+1}.</em>
                            ${question.infoQuestion}
                        </div>
                        <div class="quiz__view">
                            <div class="dog__wrap">
                                <div class="true">정답입니다!</div>
                                <div class="false">틀렸습니다!</div>
                                <div class="card-container">
                                    <div class="dog">
                                        <div class="head">
                                            <div class="ears"></div>
                                            <div class="face"></div>
                                            <div class="eyes">
                                                <div class="teardrop"></div>
                                            </div>
                                            <div class="nose"></div>
                                            <div class="mouth">
                                                <div class="tongue"></div>
                                            </div>
                                            <div class="chin"></div>
                                        </div>
                                        <div class="body">
                                        <div class="tail"></div>
                                        <div class="legs"></div>
                                        </div>
                                    </div>
                                </div>
                            </div>                        
                        </div>
                        <div class="quiz__choice">                           
                            <label for="choice1${number}">
                                <input type="radio" id="choice1${number}" name="choice${number}" value="1">
                                <span class="choice">${question.infoChoice[1]}</span>
                            </label>
                            <label for="choice2${number}">
                                <input type="radio" id="choice2${number}" name="choice${number}" value="2">
                                <span class="choice">${question.infoChoice[2]}</span>
                            </label>
                            <label for="choice3${number}">
                                <input type="radio" id="choice3${number}" name="choice${number}" value="3">
                                <span class="choice">${question.infoChoice[3]}</span>
                            </label>
                            <label for="choice4${number}">
                                <input type="radio" id="choice4${number}" name="choice${number}" value="4">
                                <span class="choice">${question.infoChoice[4]}</span>
                            </label>
                        </div>                       
                        <div class="quiz__desc">정답은<em>${question.infoAnswer}</em>번 입니다<br> ${question.infoDesc}</div>
                    </div>
                </div>
                `);
            });

            // console.log(exam)
            exam.push(`
                <div class="quiz__info">??</div>
                <div class="quiz__check">정답확인하기</div> 
            `);

            quizWrap.innerHTML = exam.join('');

            //설명숨기기 : 선택자 쓸수 없음
            // document.querySelectorAll(".quiz__desc").forEach(function(el){
            //     el.style.display = "none"
            // })
            //화살표함수
            document.querySelectorAll(".quiz__desc").forEach(el => el.style.display = "none");


        }
        updateQuiz();

🏁. POINT 

01. join()메서드 

배열의 모든 요소를 하나의 문자열로 합쳐서 반환합니다.

이 때, 각 요소는 구분자(separator)로 구분됩니다. 구분자는 선택적으로 지정할 수 있으며, 지정하지 않으면 기본값으로 쉼표(,)가 사용됩니다.

const arr = ["apple", "banana", "orange"];
const str = arr.join(", "); // "apple, banana, orange"

위 예제에서는 join() 메서드에 , 를 인수로 전달하여 각 요소를 쉼표와 공백으로 구분한 문자열을 생성했습니다.

또한, join() 메서드는 배열의 길이가 1인 경우에는 구분자 없이 요소 하나만 반환합니다

const arr2 = ["hello"];
const str2 = arr2.join(", "); // "hello"

위 예제에서는 join() 메서드가 구분자 없이 "hello" 하나만 반환합니다.

join() 메서드는 문자열이 아닌 다른 데이터 타입의 요소도 문자열로 변환하여 합칩니다. 따라서, 배열 요소가 객체, 배열, 함수 등의 경우에는 문자열로 변환된 결과를 합쳐서 반환합니다.

 

 

02. 템플릿 리터럴

 

템플릿 리터럴(Template literals)은 ES6(ECMAScript 2015)에서 도입된 새로운 문자열 표기법입니다. 이전에는 문자열을 표현할 때 작은 따옴표(')나 큰 따옴표(")를 사용했지만, 템플릿 리터럴에서는 백틱(`)을 사용합니다.

템플릿 리터럴을 사용하면 문자열 안에서 변수나 표현식을 간단하게 삽입할 수 있습니다. 이를 위해서는 ${} 형태로 변수나 표현식을 감싸주면 됩니다. 예를 들어, 다음과 같이 사용할 수 있습니다.

const name = "ChatGPT";
const greeting = `Hello, ${name}!`;
console.log(greeting); // 출력: "Hello, ChatGPT!"

템플릿 리터럴에서는 줄바꿈도 그대로 유지됩니다. 이전에는 줄바꿈을 위해서 \n을 사용해야 했지만, 템플릿 리터럴에서는 그냥 엔터를 입력하면 됩니다.

const message = `여러 줄에 걸쳐
작성할 수 있습니다.
이렇게 줄바꿈도 그대로 유지됩니다.`;
console.log(message);
// 출력:
// "여러 줄에 걸쳐
// 작성할 수 있습니다.
// 이렇게 줄바꿈도 그대로 유지됩니다."

템플릿 리터럴은 보다 간결하고 가독성이 높은 코드를 작성할 수 있도록 도와줍니다.

 

✈. 정답확인 / 설명보이기/ 점수보이기 / 정답클릭 스크립트 입니다.

//정답확인
        const answerQuiz = () => {
            const quizChoices = document.querySelectorAll(".quiz__choice");
           //
            quizScore = 0;
            //사용자가 체크한 답 == 문제 정답
            quizInfo.forEach((question, number) => { //속성선택자 :input[name=choice${number}] 
                const userSelector = `input[name=choice${number}]:checked`;//사용자가 체크한 답 6개 찾기
                const quizSelectorWrap = quizChoices[number];//quizChoice를 번호대로 묶은 것
                const userAnswer = (quizSelectorWrap.querySelector(userSelector) || {}).value;//||(or)을 넣어 빈답안에도 
                const dogWrap = quizWrap.querySelectorAll(".dog__wrap");

                if(userAnswer == question.infoAnswer){
         //           alert("정답");
                    dogWrap[number].classList.remove("dislike");
                    dogWrap[number].classList.add("like");
                    quizScore++;
                }else {
         //           alert("오답");
                    dogWrap[number].classList.remove("like");
                    dogWrap[number].classList.add("dislike");
                    //
                }
            });
            alert(quizScore)
        //설명 보이기
        document.querySelectorAll(".quiz__desc").forEach(el => el.style.display = "block");

        //점수보이기
        document.querySelector(".quiz__info").innerHTML = Math.ceil((quizScore / quizInfo.length) * 100) + "점";
        document.querySelector(".quiz__info").style.display = "block";
        }

        
        //정답클릭
        document.querySelector(".quiz__check").addEventListener("click", answerQuiz);

 

🏁. 

math()메서드

Math 객체는 자바스크립트에서 제공하는 수학 관련 메서드와 상수들을 모아놓은 전역 객체입니다. Math 객체를 사용하면 산술 연산, 삼각 함수, 로그 함수, 지수 함수 등의 다양한 수학 연산을 수행할 수 있습니다.

Math.abs(x) x의 절댓값을 반환합니다.
Math.ceil(x) x보다 크거나 같은 최소의 정수를 반환합니다.
Math.floor(x) x보다 작거나 같은 최대의 정수를 반환합니다.
Math.round(x) x를 반올림한 값을 반환합니다.
Math.max(x1, x2, ..., xn) 주어진 인수 중 가장 큰 값을 반환합니다.
Math.min(x1, x2, ..., xn) 주어진 인수 중 가장 작은 값을 반환합니다.
Math.random() 0 이상 1 미만의 난수를 반환합니다.
Math.pow(x, y) x의 y제곱을 반환합니다
Math.sqrt(x) x의 제곱근을 반환합니다.
Math.exp(x) e의 x승을 반환합니다.