박스 게임 (box.html)

help·2022년 12월 30일
0

Project 1. Catcha

목록 보기
4/7
post-thumbnail

1. 사전계획

dragmove 중 고양이와 마우스의 움직임 좌표가 같고,
같은 색상 상자에 drop 되면 성공,
다른 색 상자 또는 중간에 drop되면 실패 (제자리 돌아감)
게임이 끝나면 success 문구 띄우기

[ 필요한 값 ]

  • 고양이의 첫 위치좌표 (실패 시 돌아갈 좌표)
  • 마우스의 실시간 움직임 좌표
  • 박스 색상과 고양이의 색상을 비교할 방법
  • 게임 성공한 고양이의 마리수로 success 문구 띄우기
  • 접속기기를 판단해서 drag, touch 이벤트 실행

2. 개발과정

(간단히 소개하는 소스이므로 정확한 전체 소스는 github에서 확인해주세요!)

고양이의 첫 위치좌표 (실패 시 돌아갈 좌표) >> 시행착오에서 수정

<script>
  //드래그 시작
  'dragstart': function (e) {
      startCatX = e.pageX;
      startCatY = e.pageY;
  }
</script>

마우스의 실시간 움직임과 고양이도 같이 움직이기 >> 시행착오에서 수정

<script>
    //드래그 중
    'drag': function (e) {
        moveCatX = e.pageX - startCatX;
        moveCatY = e.pageY - startCatY;

        //고양이 실시간 위치변경
        if (moveCatX >= 0 && moveCatY >= 0) {
            $(this).offset({
                left: `${moveCatX}`,
                top: `${moveCatY}`
            });
        }
    }
</script>

고양이와 박스의 html data-id에 color 값을 각각 넣어줌

<!--고양이 예시-->
<img src="images/box_cat_1.svg" class="cat" draggable="true" data-id="gray" alt="cat">

<!--박스 예시-->
<img src="images/box_1.png" draggable="false" data-id="darkblue" alt="box">

고양이가 "박스에 drop" 됐을 때,
고양이의 data-id 값을 catColor 변수에 담기
비교대상인 박스의 data-id 도 boxColor 변수에 담아줌

<script>
	$('.box-area>img').on({
		//드롭영역에 들어옴
        'dragenter': function (e) {
            $(this).css('transform', 'scale(1.3)');
        },
        //드롭영역을 벗어남
        'dragleave': function (e) {
            $(this).css('transform', 'scale(1)');
        },
        //브라우저 표중 동작 취소
        'dragover': function (e) {
            e.preventDefault();
        },
        //드롭영역에 드롭
        'drop': function (e) {
            catColor = e.originalEvent.dataTransfer.getData('id');
            boxColor = e.target.dataset.id;
        }
	});
</script>

boxColor 와 catColor 가 같은 경우 (성공)

<script>
    //동일한 색상이면, 고양이를 박스좌표로 옮기기
    if (catColor == boxColor) {

        //박스의 위치좌표  //data-id로 태그 찾기
        let boxX = $(`[data-id='${catColor}']`).eq(1).offset().left;
        let boxY = $(`[data-id='${catColor}']`).eq(1).offset().top;

        //game-box의 위치좌표
        let gameBoxX = $('.game-box').offset().left;
        let gameBoxY = $('.game-box').offset().top;

        //박스의 가로세로 사이즈
        let boxSizeX = $(`[data-id='${catColor}']`).eq(1).width();
        let boxSizeY = $(`[data-id='${catColor}']`).eq(1).height();

        //실제로 움직일 좌표 (고양이가 박스에 앉아있는 것처럼)
        let positionX = 0;
        let positionY = 0;

        if (catColor == 'gray' || catColor == 'yellow') {
            positionX = boxX - gameBoxX + (boxSizeX * 0.1);
            positionY = boxY - gameBoxY + (boxSizeY * 0.4);
        } else {
            positionX = boxX - gameBoxX + (boxSizeX * 0.3);;
            positionY = boxY - gameBoxY + (boxSizeY * 0.3);
        }
        //움직이는 애니메이션
        currentCat.animate({
            left: `${positionX}`,
            top: `${positionY}`
        }, 500);
    } 
</script>

boxColor 와 catColor 가 다른 경우 (실패, 제자리 돌아감) >> 시행착오에서 수정

<script>
	currentCat.offset({
		left: `${startCatX}`,
		top: `${startCatY}`
	});
</script>

게임 성공 고양이는 successBox배열에 추가, 6마리 채워지면 "success!" 띄우기

<script>
    let successBox = [];

    //게임완료 배열에 추가
    successBox.push($(this));
    if (successBox.length == 5) {
        successAlert();
    }

    //성공문구 띄우기
    function successAlert() {
        setTimeout(() => {
            $('.success-txt').addClass('success-effect');
        }, 500);
    }
</script>

접속 기기 확인 후, drag 또는 touch 함수 실행

<script>
    //접속기기 판별 후 실행
    var isMobile = /Android|webOS|iPhone|iPad|iPod|BlackBerry/i.test(navigator.userAgent) ? true : false;
    function checkMobile() {
        if (isMobile) { //모바일접속시
            catTouch();
        } else { //web접속시
            catDrag();
        }
    }
    checkMobile();
</script>

3. 시행착오

고양이의 첫 위치좌표 : dragstart 위치는 계속 바뀐다!
그래서 dragstart시 '무조건 click'을 걸어주고
click 함수를 이용하여 일정한 첫 위치좌표를 얻는다

<script>
    //드래그 시작 (요소 data-id 저장)
    'dragstart': function (e) {
        e.originalEvent.dataTransfer.setData('id', e.target.dataset.id);
        $(this).css('transform', 'scale(1.3)');
        e.target.click(); //-----드래그 시작 시 자동클릭
        startCatX = e.pageX;
        startCatY = e.pageY;
    },

    'click': function (e) {
    //첫 시작 x, y 좌표 - 고정좌표 얻기!
        startClickX = $(this).offset().left;
        startClickY = $(this).offset().top;
    },
</script>

마우스의 실시간 움직임과 고양이도 같이 움직이기 :
drag 하는 중에 클릭 좌표(고정된 첫좌표)와 dragstart좌표(매번 변동되는 좌표)의 차이 만큼
고양이의 잔상이 남아서 제거해줌

<script>
    //드래그 중
    'drag': function (e) {

        moveCatX = e.pageX - (startCatX - startClickX);
        moveCatY = e.pageY - (startCatY - startClickY);

        //고양이 실시간 위치변경
        if (moveCatX >= 0 && moveCatY >= 0) {
            $(this).offset({
                left: `${moveCatX}`,
                top: `${moveCatY}`
            });
        }
    },
</script>

boxColor 와 catColor 가 다른 경우 (제자리 돌아감) :
dragstart 때 고양이의 사이즈를 1.3배 해주었더니
startClick값이 1.3배 커진 고양이 기준으로 측정되므로
catSizeWidth(Height) * 0.3 / 2 더해줘야함(=returnPlace)

<script>
    //영역에 도달하지 못하거나 색상이 다른 경우

    let catSizeWidth = $(e.target).width();
    let catSizeHeight = $(e.target).height();
    let returnPlaceWidth = catSizeWidth * 0.3 / 2;
    let returnPlaceHeight = catSizeHeight * 0.3 / 2;

    currentCat.offset({ 
        left: `${startClickX + returnPlaceWidth}`,
        top: `${startClickY + returnPlaceHeight}`
    });
</script>

4. 결과물

5. 개인적 코멘트

각 이미지의 위치값과 실시간 값등을 정확하게 확인하기 위해
콘솔창을 달고 살았던 프로젝트!

scale(1.3)으로 인해서 나온 나비효과들과
드래그 시작시의 좌표가 항상 같지 않았고, 생각했던 싱크로율이 맞지않아 당황했지만
열심히 찾아내어 더 확실하고 정확한 방법으로 고쳤고,
왜 이렇게 움직이는지 왜 이런 값들이 나오는지 더 자세히 알아보는 계기가 되어
재밌었던 프로젝트였다

profile
프론트 개발자

0개의 댓글