New tile based platform engine – part 3

In this 3rd step I introduced the gravity.

Now the hero starts on the top of the screen and he can walk “downhill” thanks to gravity.

During next step I’ll introduce jumps, then a massive explication will follow.

And AS3 version, of course.

I have to say, making a platform engine is funny and a little harder than I expected.

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
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
tile_size = 20;
ground_acceleration = 1;
ground_friction = 0.8;
air_acceleration = 0.1;
air_friction = 0.7;
ice_acceleration = 0.15;
ice_friction = 0.95;
treadmill_speed = 2;
max_speed = 3;
xspeed = 0;
yspeed = 0;
falling = false;
gravity = 0.5;
level = new Array();
level[0] = [1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0];
level[1] = [1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1];
level[2] = [1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1];
level[3] = [1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1];
level[4] = [1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 1, 3, 3, 3, 3, 1, 1, 4, 4, 4, 4, 1, 1];
player = [1, 0];
function create_level(l) {
	_root.createEmptyMovieClip("level_container", 1);
	level_height = l.length;
	level_width = l[0].length;
	for (y=0; y<level_height; y++) {
		for (x=0; x<level_width; x++) {
			if (l[y][x] != 0) {
				t = level_container.attachMovie("tile", "t"+y+"_"+x, _root.level_container.getNextHighestDepth(), {_x:x*tile_size, _y:y*tile_size});
				t.gotoAndStop(l[y][x]);
			}
		}
	}
	x_pos = player[0]*tile_size+tile_size/2;
	y_pos = player[1]*tile_size+tile_size/2+1;
	level_container.attachMovie("hero", "hero", _root.level_container.getNextHighestDepth(), {_x:x_pos, _y:y_pos});
}
create_level(level);
_root.onEnterFrame = function() {
	ground_under_feet();
	walking = false;
	if (Key.isDown(Key.LEFT)) {
		xspeed -= speed;
		walking = true;
	}
	if (Key.isDown(Key.RIGHT)) {
		xspeed += speed;
		walking = true;
	}
	if (!walking) {
		xspeed *= friction;
		if (Math.abs(xspeed)<0.5) {
			xspeed = 0;
		}
	}
	if (xspeed>max_speed) {
		xspeed = max_speed;
	}
	if (xspeed<-max_speed) {
		xspeed = -max_speed;
	}
	if (falling) {
		yspeed += gravity;
	}
	xspeed += bonus_speed;
	x_pos += xspeed;
	y_pos += yspeed;
	check_collisions();
	level_container.hero._x = x_pos;
	level_container.hero._y = y_pos;
	xspeed -= bonus_speed;
};
function ground_under_feet() {
	bonus_speed = 0;
	left_foot_x = Math.floor((x_pos-6)/tile_size);
	right_foot_x = Math.floor((x_pos+5)/tile_size);
	foot_y = Math.floor((y_pos+9)/tile_size);
	left_foot = level[foot_y][left_foot_x];
	right_foot = level[foot_y][right_foot_x];
	if (left_foot != 0) {
		current_tile = left_foot;
	} else {
		current_tile = right_foot;
	}
	switch (current_tile) {
	case 0 :
		speed = air_acceleration;
		friction = air_friction;
		falling = true;
		break;
	case 1 :
		over = "ground";
		speed = ground_acceleration;
		friction = ground_friction;
		break;
	case 2 :
		over = "ice";
		speed = ice_acceleration;
		friction = ice_friction;
		break;
	case 3 :
		over = "treadmill";
		speed = ground_acceleration;
		friction = ground_friction;
		bonus_speed = -treadmill_speed;
		break;
	case 4 :
		over = "treadmill";
		speed = ground_acceleration;
		friction = ground_friction;
		bonus_speed = treadmill_speed;
		break;
	}
}
function check_collisions() {
	get_edges();
	// collision to the bottom 
	if (yspeed>0) {
		if ((level[bottom][right] != 0) or (level[bottom][left] != 0)) {
			y_pos = bottom*tile_size-9;
			yspeed = 0;
			falling = false;
			get_edges();
		}
	}
	// collision to the left 
	if (xspeed<0) {
		if ((level[top][left] != 0) or (level[bottom][left] != 0)) {
			x_pos = (left+1)*tile_size+6;
			xspeed = 0;
		}
	}
	// collision to the right          
	if (xspeed>0) {
		if ((level[top][right] != 0) or (level[bottom][right] != 0)) {
			x_pos = right*tile_size-6;
			xspeed = 0;
		}
	}
}
function get_edges() {
	// right edge
	right = Math.floor((x_pos+5)/tile_size);
	// left edge   
	left = Math.floor((x_pos-6)/tile_size);
	// bottom edge
	bottom = Math.floor((y_pos+8)/tile_size);
	// top edge
	top = Math.floor((y_pos-9)/tile_size);
}

Download source code and enjoy.

Rate this post: 1 Star2 Stars3 Stars4 Stars5 Stars (17 votes, average: 4.94 out of 5)
Loading ... Loading ...
Flash Templates provided by Template Monster are pre-made web design products developed using Flash technology.
They can be easily customized to meet the unique requirements of your project.
Be my fan on Facebook and follow me on Twitter! Exclusive content for my Facebook fans and Twitter followers

This post has 5 comments

  1. David D

    on September 18, 2008 at 8:52 pm

    Really good! And very fast posting. I really like this and it’s helping me alot

  2. Brian Yamabe

    on September 18, 2008 at 11:23 pm

    Great stuff! There is an inconsistency in that if the player gets on the conveyor belt throws you off. A related inconsistency is that the -> conveyor belt doesn’t affect you until you are on all the way but the <- conveyor belt starts as soon as you touch it.

  3. LanoG

    on September 19, 2008 at 8:50 am

    Yeah.. I agreed. Very useful and fun. Almost everyday I check this blog to see new post by Emanuele. Good job…!!

  4. Arxanas

    on September 19, 2008 at 12:20 pm

    Awesome tutorials, like always! Heck, I made this website my homepage so that I could see if new ones are up!

    I can’t wait to make him jump!

  5. Marre2795

    on September 19, 2008 at 3:50 pm

    It’s a good tutorial, but I wonder how do I make him jump.