Cute Apple
본문 바로가기
개발/HTML&JS

html 플랫포머 게임

by 미댕댕 2021. 4. 4.

작업 결과물

 

 

body, CSS, script 작업

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
<style>
body{margin:0px;}
#wrapper{
    width: 1280px;
    height: 960px;
    background-image:url(./png/BG.png);
    margin: auto;
    position: relative;
    overflow: hidden;
}
</style>
<script src="./js/GameObject.js"></script>
<script src="./js/Block.js"></script>
<script src="./js/Hero.js"></script>
<script src="./js/lib.js"></script>
<script>
var hero;
var blockArray=[]; //벽돌을 담아놓을 배열
 
function init(){
    createBlock();
    createHero();
 
    //키보드 이벤트 구현
    window.addEventListener("keydown"function(e){ //이벤트 객체가 익명함수의 매개변수로 전달됨
        
        switch(e.keyCode){
            case 32: jump(); break;
            case 37: hero.velX=-3break;
            case 39: hero.velX=3break;
 
        }
    });
    window.addEventListener("keyup"function(e){ //이벤트 객체가 익명함수의 매개변수로 전달됨
 
        switch(e.keyCode){
            case 37: hero.velX=0break;
            case 39: hero.velX=0break;
 
        }
    });
}
//블럭생성
function createBlock(){
    // constructor(container, src, width, height, x, y, velX, velY)
    for(var i=0;i<10;i++){
        var block=new Block(document.getElementById("wrapper"), 
        "./png/StoneBlock.png"70,70,50+(70*i),60000);
        blockArray.push(block); //배열에 추가
    }
 
}
function createHero(){
    // constructor(container, src, width, height, x, y, velX, velY)
    hero=new Hero(document.getElementById("wrapper"), "./png/ninja.png"5585100,500,1)
    
}
//점프 처리
function jump(){
    if(hero.jump==false && hero.velY==0){
        hero.velY=-10//순간적으로 음수로 전환(하지만 곧 g때문에 양수로 전환됨)
        hero.jump=true;
    }
}
function gameLoop(){
    //주인공의 tick, render
    hero.tick();
    hero.render();
}
window.addEventListener("load"function(){
    init();
    setInterval("gameLoop()"10);
});
</script>
</head>
<body>
    <div id="wrapper"></div>
</body>
</html>
cs

 

 

class 작업

1. GameObject

- 공통으로 사용하는 생성자를 미리 생성해두어 부모 요소로 사용한다.

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
/*
객체지향에서는 현실에서의 상속의 개념을 코드로 구현이 가능하다.
즉, 모든 자식이 보유해야할 공통 코드를, 자식 객체마다 코드를 중복
시키지 않고, 부모객체에 공통코드를 작성할 수 있다.
이러한 코드기법을 지원하는이유는 코드의재사용성과 유지보수성이다.( 시간, 돈 save)
 
이 클래스는 게임에 등장할 모든 객체의 최상위 객체이다
*/ 
class GameObject{
    constructor(container, src, width, height, x, y, velX, velY){
        this.container=container;
        this.img=document.createElement("img");
        this.src=src;
        this.width=width;
        this.height=height;
        this.x=x;
        this.y=y; 
        this.velX=velX;
        this.velY=velY;
        this.init();
    }
    init(){
        this.img.src=this.src;
        this.img.style.width=this.width+"px";
        this.img.style.height=this.height+"px";
 
        this.img.style.position="absolute";
        this.img.style.left=this.x+"px"
        this.img.style.top=this.y+"px"
         //부착
         this.container.appendChild(this.img);
    }
    tick(){
        //누구를 염두해두고 코드를 넣어두어야하나
        //자식이 누구일지, 그리고 어떤 움직임을 가질지 알수없으므로, 코드를 작성할 수 없다.
        // 이렇게 부모클래스가 내용없이(즉 몸체없이) 작성한 메소드를 가리켜, 추상메서드라하면,
        // 추상 메서드의 본 목적은 자신이 불완전하게 남겨놓는다.
        //기능을 자식에게 구현할 것을 강제하기 위함이다
    }
    render(){
 
    }
}
cs

 

 

2. Block

1
2
3
4
5
6
// 블럭을 정의한다.
class Block extends GameObject{
    constructor(container, src, width, height, x, y, velX, velY){
        super(container, src, width, height, x, y, velX, velY);
    }
}
cs

 

 

 

 

3. Hero

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
/*
    예전에 작성한 코드를 재사용해보자!
*/
class Hero extends GameObject{
    constructor(container, src, width, height, x, y, velX, velY){
        //부모의 생성자 메서드를 호출하자!!(매개변수 빠짐없이)
        super(container, src, width, height, x, y, velX, velY)
        this.g=0.5//중력 가속도 효과를 내기 위한 변수
        this.jump=false;
        
    }
    //히어로는 움직임이 있다! 따라서 메서드 정의가 요구된다!
    //그렇지만, 부모에게 물려받은 메서드가, 현재 나의 상황에는 맞지 않을 경우
    //업그레이드할 필요가 있다!!!(java, C# 등 oop언어에서는 이러한 메서드 재정의기법을
    //가리켜 오버라이딩(overriding)이라 한다)
    tick(){
        //코드에서는 보이지 않지만, 현재 클래스는 GameObject의 모든것을 다 가지고
        //있는 것과 마찬가지이다!! 즉, 내것 처럼 접근할 수 있다
        this.velY+=this.g; //중력을 표현하기 위해 가속도로 처리
        this.y=this.y+this.velY;
        this.x=this.x+this.velX;
 
        //현재 화면에 존재하는 모든 벽돌들을 대상으로, 주인공의 발바닥과 닿았는지 체크
        for(var i=0;i<blockArray.length; i++){
            var onBlock=collisionCheck(this.img, blockArray[i].img);
 
            /*onBlock이 true 라면 벽돌에 닿은거임
            1) 속도를 없애고
            2) 1번의 조건은 무조건 수행하지 말고, 우리가 원할 때만 수행
 
            */
            if(onBlock && this.jump==false){
                this.velY=0//점프버튼을 누르면, velY 값을 묶어놓지 말자
                //나의 위치를 벽돌위에 고정(벽돌의 y 값보다 키만큼 위로 올라가게)
                this.y=blockArray[i].y-this.height;
            }
 
 
            //주인공이 점프한 이후, 다시 하강하는 순간을 포착하여 벽돌위에 서있을 수 있는
            //핵심 변수인 this.jump를 다시 false로 돌려놓자
            if(this.velY>0){
                this.jump=false;
            }
 
        }
 
    }
    render(){
        this.img.style.left=this.x+"px"
        this.img.style.top=this.y+"px"
    }
}
cs

 

 

lib 작업

 

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
function collisionCheck(me, target) {
    //두물체간 충돌 여부 판단 
    me_x= parseInt(me.style.left);
    me_y= parseInt(me.style.top);
    me_width=parseInt(me.style.width);
    me_height=parseInt(me.style.height);
 
    target_x= parseInt(target.style.left);
    target_y= parseInt(target.style.top);
    target_width=parseInt(target.style.width);
    target_height=parseInt(target.style.height);
 
 
    var result1=(me_x >= target_x) && (me_x <= (target_x+target_width));//나의 x좌표위치가 타겟의 x range 내에 있는지 판단 
    var result2=(me_x+me_width >= target_x) && (me_x+me_width <= (target_x+target_width));  //나의 가로폭이 타겟의 가로폭 내에 있는지 판단
    var result3=(me_y >= target_y) && (me_y <= (target_y+target_height));//나의 y좌표위치가 타겟의 세로폭 내에 있는지 판단
    var result4=(me_y+me_height >= target_y) && (me_y+me_height <= (target_y+target_height));//나의 y폭이 타겟의 세로폭 내에 있는지 판단
    
    return (result1 || result2) && (result3 || result4);
}
 
cs
반응형

'개발 > HTML&JS' 카테고리의 다른 글

html JSON 활용  (0) 2021.03.30
htm 슈팅게임  (0) 2021.03.25
html 충돌검사  (0) 2021.03.24
html 객체와 class  (0) 2021.03.23
html 다차원 배열2  (0) 2021.03.18

댓글