안녕하세요 PrintedLove입니다.
이번 글에서는 물리엔진을 추가해 볼 건데요
이번에도 쉬운 이해를 위해 소스코드를 먼저 올리겠습니다.
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
|
from tkinter import *
import time
window = Tk()
window.title("nemoRPG") # 게임 이름
window.resizable(0,0)
canvas = Canvas(window, width = 640, height = 640, bg ="white") # 창 생성
canvas.pack()
class Game: # 게임 클래스
global objects
objects = set() # 오브젝트 세트 생성
def __init__(self):
self.keys = set() # 버튼 세트 생성
window.bind("<KeyPress>", self.keyPressHandler)
window.bind("<KeyRelease>", self.keyReleaseHandler)
obj_main = element(310, 310, 20, 20, "black")
while(1): # 메인 루프
for key in self.keys: # 버튼 체킹
if obj_main in objects:
if key == ord('A') and obj_main.x_accel > -10: # A 버튼
obj_main.x_accel -= 1
if key == ord('D') and obj_main.x_accel < 10: # D 버튼
obj_main.x_accel += 1
if key == ord('W') and obj_main.y_accel > -10: # W 버튼
obj_main.y_accel -= 1
if key == ord('S') and obj_main.y_accel < 10: # S 버튼
obj_main.y_accel += 1
for obj in objects.copy(): # 오브젝트 스텝
obj.step()
window.update() # 업데이트
time.sleep(0.01) # 0.01초 만큼 sleep
def keyPressHandler(self, event): # 버튼 세트에 버튼추가
self.keys.add(event.keycode)
def keyReleaseHandler(self, event): # 버튼 세트에 버튼 제거
if event.keycode in self.keys:
self.keys.remove(event.keycode)
class element: # 오브젝트 원형
def __init__(self, x, y, size_x, size_y, color):
self.x, self.y = x, y # 생성 위치
self.size_x, self.size_y = size_x, size_y # 크기
self.color = color # 색
self.x_accel, self.y_accel = 0, 0 # 가속도
objects.add(self) # 오브젝트 세트에 자신 등록
self.id = canvas.create_rectangle(x, y, x + self.size_x, y + self.size_y, fill = self.color, width =0) # 캠버스 추가
def destroy(self): # 제거 함수
objects.discard(self) # 오브젝트 세트에서 자신 제거
canvas.delete(self.id) # 캠버스 제거
del self
def move(self): # 움직임 계산(이동, 가속도, 중력) 함수
x_value, y_value = self.x_accel, self.y_accel
if x_value != 0 or y_value != 0: # 좌표 갱신
if canvas.coords(self.id)[0] + x_value < 0:
x_value = -canvas.coords(self.id)[0] # 창나감 방지
self.x_accel = -self.x_accel # 튕김
if canvas.coords(self.id)[1] + y_value < 0:
y_value = -canvas.coords(self.id)[1]
self.y_accel = -self.y_accel
if canvas.coords(self.id)[2] + x_value > 640:
x_value = 640 - canvas.coords(self.id)[2]
self.x_accel = -self.x_accel
if canvas.coords(self.id)[3] + y_value > 640:
y_value = 640 - canvas.coords(self.id)[3]
self.y_accel = -self.y_accel
canvas.move(self.id, x_value, y_value) # 수치만큼 이동
self.mx, self.my = 0, 0 # 이동값 초기화
self.x_accel -= self.x_accel/100 # 가속도 감소
self.y_accel -= self.y_accel/100
def step(self):
self.move()
Game() # 게임 실행
|
cs |
전체 코드입니다.
달라진 점을 하나하나 살펴보죠.
먼저, canvas객체의 틀인 element 클래스에 x_accel 과 y_accel이라는 변수를 추가했습니다.
이 변수는 0 이 아닌 값 (ex. -15, 12)이 입력될 시 객체를 수치만큼 해당 좌표로 이동하게 하는 가속도의 역할을 합니다.
여기까진 구현은 쉽습니다. 그냥 해당 값을 canvas.move()함수에 집어넣으면 되니까요.
하지만가속도가 천천히 감소하는 마찰력 효과와 canvas가 창을 나가지 못하게 하기 위해서는 조금 복잡한 식이 필요합니다.
때문에 element 클래스에 move라는, 이동 전용 함수를 선언했습니다. 이제 이 함수로 canvas객체의 이동에 관한 모든것을 관리할 것입니다.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
|
def move(self): # 움직임 계산(이동, 가속도, 중력) 함수
x_value, y_value = self.x_accel, self.y_accel
if x_value != 0 or y_value != 0: # 좌표 갱신
if canvas.coords(self.id)[0] + x_value < 0:
x_value = -canvas.coords(self.id)[0] # 창나감 방지
self.x_accel = -self.x_accel # 튕김
if canvas.coords(self.id)[1] + y_value < 0:
y_value = -canvas.coords(self.id)[1]
self.y_accel = -self.y_accel
if canvas.coords(self.id)[2] + x_value > 640:
x_value = 640 - canvas.coords(self.id)[2]
self.x_accel = -self.x_accel
if canvas.coords(self.id)[3] + y_value > 640:
y_value = 640 - canvas.coords(self.id)[3]
self.y_accel = -self.y_accel
canvas.move(self.id, x_value, y_value) # 수치만큼 이동
self.mx, self.my = 0, 0 # 이동값 초기화
self.x_accel -= self.x_accel/100 # 가속도 감소
self.y_accel -= self.y_accel/100
|
cs |
위의 코드를 한글로 풀어 써 보면 아래와 같습니다.
x, y가속도 값을 이동 좌표x, y(지역변수)에 대입
canvas 좌표가 갱신 됬을 시:
x1 좌표 + x이동 좌표 < 0 일시:
이동 좌표 - x1 좌표
x 가속도 반전
y1 좌표 + y이동 좌표 < 0 일시:
이동 좌표 - y1 좌표
y 가속도 반전
x21 좌표 + x이동 좌표 < 640 일시:
이동 좌표 - x2 좌표
x 가속도 반전
y2 좌표 + y이동 좌표 < 640 일시:
이동 좌표 - y2 좌표
y 가속도 반전
이동좌표 값만큼 canvas 이동
x, y가속도 감소
요지는, 창나감 방지를 위해 오버된 수치만큼만 이동하고 가속도를 반전시켜준다는 것입니다.
다음에는 공격 오브젝트를 구현해 보도록 하겠습니다.
'개발 일지' 카테고리의 다른 글
파이썬 tkinter 그래픽으로 슈팅 게임 만들기 5 (0) | 2019.11.25 |
---|---|
파이썬 tkinter 그래픽으로 슈팅 게임 만들기 4 (0) | 2019.11.24 |
파이썬 tkinter 그래픽으로 슈팅 게임 만들기 2 (0) | 2019.11.22 |
파이썬 tkinter 그래픽으로 슈팅 게임 만들기 1 (5) | 2019.11.22 |
파이썬 터틀 그래픽으로 달력 만들기 (1) | 2019.11.04 |
댓글