티스토리 뷰
● 도입
- 하나의 class(=scene)에서 함수가 실행되는 순서
- init은 constructor function을 의미한다. / 마지막인 update function은 계속 반복해서 실행된다.
- 바로 이 update function에 사용자가 키보드를 눌렀을 때 player가 움직이도록 코드를 작성할 것이다.
● 움직이는 player 만들기
- PlayingScene.js에 update function을 만들어 캐릭터 움직임 관련 내용을 작성했다.
import Phaser from "phaser";
import Player from "../characters/Player";
import { setBackground } from "../utils/backgroundManager";
export default class PlayingScene extends Phaser.Scene {
constructor() {
super("playGame");
}
create() {
// 사용할 sound들을 추가해놓는 부분
// load function : 어떤 scene에서든 전역적으로 asset을 사용할 수 있도록 load (LoadingScene.js 참고)
// add function : 해당 scene에서 asset을 사용할 수 있도록 scene의 멤버 변수로 추가할 때 사용
// cf) this.xxxx 에서 xxxx 자리에 적힌 것들이 멤버 변수들이다.
this.sound.pauseOnBlur = false;
this.m_beamSound = this.sound.add("audio_beam");
this.m_scratchSound = this.sound.add("audio_scratch");
this.m_hitMobSound = this.sound.add("audio_hitMob");
this.m_growlSound = this.sound.add("audio_growl");
this.m_explosionSound = this.sound.add("audio_explosion");
this.m_expUpSound = this.sound.add("audio_expUp");
this.m_hurtSound = this.sound.add("audio_hurt");
this.m_nextLevelSound = this.sound.add("audio_nextLevel");
this.m_gameOverSound = this.sound.add("audio_gameOver");
this.m_gameClearSound = this.sound.add("audio_gameClear");
this.m_pauseInSound = this.sound.add("audio_pauseIn");
this.m_pauseOutSound = this.sound.add("audio_pauseOut");
// player를 m_player라는 멤버 변수로 추가
// new Player(this) --> (Player class의 인스턴스 생성, 자기 자신(PlayingScene)을 scene으로 전달)
this.m_player = new Player(this); // characters/Player.js
// PlayingScene의 background 설정
// 여기서 "background1"은 LoadingScene에서 load한 asset이다. --> this.load.image("background1", bgImg1);
setBackground(this, "background1"); // backgroundManager.js의 함수
// m_cursorKeys = 사용자 키보드 입력값을 받을 수 있는 변수
// 입력값 = (up, down, left, right, space, shift)
// ex) m_cursorKeys.left.isDown = 사용자가 왼쪽 방향키를 눌렀는지 여부
this.m_cursorKeys = this.input.keyboard.createCursorKeys();
}
// 키보드 이벤트는 매 frame 마다 탐지를 해야하기 때문에 update function을 만들었다.
update() {
// movePlayerManager = 직접 만든 함수(phaser 내장 함수 아님)
this.movePlayerManager(); // 매 순간 movePlayerManager function이 실행되는 것이다.
}
movePlayerManager() {
if (this.m_cursorKeys.left.isDown
|| this.m_cursorKeys.right.isDown
|| this.m_cursorKeys.up.isDown
|| this.m_cursorKeys.down.isDown) {
// 방향키가 눌리면 애니메이션 재생
if (!this.m_player.m_moving) { // player가 움직이면 true / 멈춰있으면 false
// "player_anim"는 LoadingScene.js의 create function에 있다.
// 방향키에 손을 떼서 멈추기 직전까지 계속해서 아래 코드가 실행된다.(한 번 play 되면 계속해서 play 된다.)
this.m_player.play("player_anim"); // player_anim를 play 할 것이다.(재생할 것이다.)
}
this.m_player.m_moving = true;
} else {
// 방향키를 떼면 애니메이션 정지
if (this.m_player.m_moving) {
// "player_idle"는 LoadingScene.js의 create function에 있다.
this.m_player.play("player_idle");
}
this.m_player.m_moving = false;
}
// vector 변수를 사용해 움직임 관리
// x좌표와 y좌표가 '얼만큼 이동했는지'가 아니라 '어디로 이동하고 있는지를 관리하는 변수'이다.
// (어디로 이동하고 있는지 = 어느 방향을 향하고 있는지)
// 이것을 이용해 방향에 따른 캐릭터의 모습을 실시간으로 변경해줄 것이다.
let vector = [0, 0]; // [x좌표 방향, y좌표 방향]
// vector[0]은 (-1, 0, 1) 중 하나의 값만 갖는다.
if(this.m_cursorKeys.left.isDown) {
vector[0] += -1;
// 이 값이 계속 누적돼서 -1, -2, -3, -4 ... 이렇게 되는게 아니다.
// update function이 실행될때마다 movePlayerManager function도 실행되므로
// vector 변수도 계속해서 [0, 0]으로 초기화 된다.
// 따라서 사용자가 왼쪽 방향키를 누를 때마다 (vector[0] = -1)로 계속해서 값이 변경되는 것이지
// -1 값이 누적되는게 아니다.
} else if(this.m_cursorKeys.right.isDown) {
vector[0] += 1;
}
// vector[1]도 (-1, 0, 1) 중 하나의 값만 갖는다.
if(this.m_cursorKeys.up.isDown) {
vector[1] += -1;
} else if(this.m_cursorKeys.down.isDown) {
vector[1] += 1;
}
// vector 변수를 player class의 move method의 parameter로 넘긴다.
this.m_player.move(vector);
}
}
- Player.js에 move function을 만들어 캐릭터 움직임 관련 내용을 작성했다.
import Phaser from "phaser";
import Config from "../Config";
// Player가 Arcade 물리엔진의 영향을 받도록 extends
export default class Player extends Phaser.Physics.Arcade.Sprite {
// 어느 scene에 Player가 나올지 정해줘야 하므로 argument로 scene을 받는다.
// 참고로 scene의 constructor는 parameter가 없다.
constructor(scene) {
// 화면의 가운데에 player를 추가
// 마지막 "player" string이 identifier(식별자)이다. by LoadingScene.js
super(scene, Config.width / 2, Config.height / 2, "player");
// scene.add.existing : scene에 오브젝트 추가
scene.add.existing(this);
// scene.physics.add.existing : scene의 물리엔진에 오브젝트를 추가
scene.physics.add.existing(this);
// scale 프로퍼티를 조절해 크기 조절(디폴트: 1)
this.scale = 2;
// depth를 조절해 어떤 오브젝트가 앞에 오고 뒤에 올지 설정
// CSS의 z-index와 비슷한 개념(디폴트: 0)
this.setDepth(20); // 10단위로 조절하는게 좋다.
// 해당 오브젝트가 물리적으로 어느정도의 면적을 차지할 지 설정하는 함수(디폴트는 이미지 사이즈)
// 하지만 디폴트는 추후 몹을 추가했을 때 잘 부딪히는 느낌이 드므로 원본 이미지보다 약간 작게 설정
this.setBodySize(28, 32);
// 걷기 애니메이션 재생 여부를 위한 멤버 변수
this.m_moving = false;
}
// player가 움직이도록 하는 함수
move(vector) {
console.log(vector);
// player의
// x좌표 = vector[0] * Player.PLAYER_SPEED 만큼,
// y좌표 = vector[1] * Player.PLAYER_SPEED 만큼 움직인다.
let PLAYER_SPEED = 10;
console.log(this.x);
this.x += vector[0] * PLAYER_SPEED; // player의 x좌표 위치 변경
this.y += vector[1] * PLAYER_SPEED; // player의 y좌표 위치 변경
// PLAYER_SPEED에서 SPEED 라는 단어 자체는 큰 의미가 없다.
// 그저 방향키를 누를 때 (x좌표, y좌표)를 한 번에 얼만큼 이동하는지 결정하는 값이다.
// 당연히 PLAYER_SPEED의 값이 클 수록 한 번에 변화되는 위치 값이 크므로 그만큼 SPEED가 빨라보이는 것이다.(그래서 변수 이름이 SPEED)
// 캐릭터 이미지 원본은 왼쪽을 바라보고 있다.
// flipX 프로퍼티는 boolean 값을 받아 x축 방향으로 뒤집혀있을지 아닐지를 설정한다.
// player가 왼쪽으로 이동할 때는 flipX = false,
// player가 오른쪽쪽으로 이동할 때는 flipX = true로 설정해 적절한 방향으로 캐릭터의 모습을 변경한다.
if(vector[0] === -1) this.flipX = false;
else if(vector[0] === 1) this.flipX = true;
}
}
cf) createCursorKeys function API docs
https://newdocs.phaser.io/docs/3.55.2/Phaser.Types.Input.Keyboard.CursorKeys
'흥미 > phaser' 카테고리의 다른 글
#13 움직이는 Player 2(무한 배경 구현) (0) | 2023.05.23 |
---|---|
#11 Scene 만들기2 - LoadingScene, PlayingScene, player, background (0) | 2023.05.14 |
#10 Scene 만들기1 (0) | 2023.05.12 |
#9 템플릿 다운 (0) | 2023.05.07 |
#8 캐릭터 움직이기 tutorial (0) | 2023.05.06 |
공지사항
최근에 올라온 글
최근에 달린 댓글
- Total
- Today
- Yesterday
링크
TAG
- 프로세스
- 빅데이터
- MySQL
- java
- Phaser3
- db
- Java8
- spring
- Spring Boot
- Advanced Stream
- 메모리
- node.js
- OS
- Stream
- SpringBoot
- 코딩테스트
- git
- 빅데이터 분석기사
- Phaser
- DART
- 프로그래머스
- jpa
- 자료구조
- API
- nosql
- SQL
- 코테
- 알고리즘
- MongoDB
- 운영체제
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
글 보관함