1 /**
2 A manager for all the objects in the game
3 @author <a href="mailto:matthewcasperson@gmail.com">Matthew Casperson</a>
4 @class
5 */
6 function GameObjectManager()
7 {
8 /** An array of game objects
9 @type Arary
10 */
11 this.gameObjects = new Array();
12 /** An array of new game objects
13 @type Arary
14 */
15 this.addedGameObjects = new Array();
16 /** An array of removed game objects
17 @type Arary
18 */
19 this.removedGameObjects = new Array();
20 /** The time that the last frame was rendered
21 @type Date
22 */
23 this.lastFrame = new Date().getTime();
24 /** The global scrolling value of the x axis
25 @type Number
26 */
27 this.xScroll = 0;
28 /** The global scrolling value of the y axis
29 @type Number
30 */
31 this.yScroll = 0;
32 /** A reference to the canvas element
33 @type HTMLCanvasElement
34 */
35 this.canvas = null;
36 /** A reference to the 2D context of the canvas element
37 @type CanvasRenderingContext2D
38 */
39 this.context2D = null;
40 /** A reference to the in-memory canvas used as a back buffer
41 @type HTMLCanvasElement
42 */
43 this.backBuffer = null;
44 /** A reference to the backbuffer 2D context
45 @type CanvasRenderingContext2D
46 */
47 this.backBufferContext2D = null;
48 /** True if the canvas element is supported, false otherwise
49 @type Boolean
50 */
51 this.canvasSupported = false;
52 /** True if the resources supplied to the ResourceManager are all loaded, false otherwise
53 @type Boolean
54 */
55 this.resourcesLoaded = false;
56 /** The current colour of the loading screen
57 @type Number
58 */
59 this.loadingScreenCol = 0;
60 /** The direction of the changes to the loading screen colour.
61 1 = colour moving towards white
62 -1 = colour moving topwards balck
63 @type Number
64 */
65 this.loadingScreenColDirection = 1;
66 /** How quickly to change the loading screen colour per second
67 @type Number
68 */
69 this.loadingScreenColSpeed = 255;
70
71 /**
72 Initialises this object
73 @return A reference to the initialised object
74 */
75 this.startupGameObjectManager = function()
76 {
77 // set the global pointer to reference this object
78 g_GameObjectManager = this;
79
80 // watch for keyboard events
81 document.onkeydown = function(event){g_GameObjectManager.keyDown(event);}
82 document.onkeyup = function(event){g_GameObjectManager.keyUp(event);}
83
84 // get references to the canvas elements and their 2D contexts
85 this.canvas = document.getElementById('canvas');
86
87 // if the this.canvas.getContext function does not exist it is a safe bet that
88 // the current browser does not support the canvas element.
89 // in this case we don't go any further, which will save some debuggers (like
90 // the IE8 debugger) from throwing up a lot of errors.
91 if (this.canvas.getContext)
92 {
93 this.canvasSupported = true;
94 this.context2D = this.canvas.getContext('2d');
95 this.backBuffer = document.createElement('canvas');
96 this.backBuffer.width = this.canvas.width;
97 this.backBuffer.height = this.canvas.height;
98 this.backBufferContext2D = this.backBuffer.getContext('2d');
99 }
100
101 // create a new ResourceManager
102 new ResourceManager().startupResourceManager(
103 [{name: 'runLeft', src: 'run_left.png'},
104 {name: 'runRight', src: 'run_right.png'},
105 {name: 'idleLeft', src: 'idle_left.png'},
106 {name: 'idleRight', src: 'idle_right.png'},
107 {name: 'background0', src: 'jsplatformer4_b0.png'},
108 {name: 'background1', src: 'jsplatformer4_b1.png'},
109 {name: 'background2', src: 'jsplatformer4_b2.png'},
110 {name: 'block', src: 'BlockA0.png'},
111 {name: 'gem', src: 'Gem.png'},
112 {name: 'mainmenu', src: 'mainmenu.png'},
113 {name: 'portal', src: 'portal.png'}]);
114
115 // use setInterval to call the draw function
116 setInterval(function(){g_GameObjectManager.draw();}, SECONDS_BETWEEN_FRAMES);
117
118 return this;
119 }
120
121 /**
122 The render loop
123 */
124 this.draw = function ()
125 {
126 // calculate the time since the last frame
127 var thisFrame = new Date().getTime();
128 var dt = (thisFrame - this.lastFrame)/1000;
129 this.lastFrame = thisFrame;
130
131 if (!this.resourcesLoaded)
132 {
133 var numLoaded = 0;
134 for (i = 0; i < g_ResourceManager.imageProperties.length; ++i)
135 {
136 if (g_ResourceManager[g_ResourceManager.imageProperties[i]].complete)
137 {
138 ++numLoaded;
139 }
140 }
141 if ( numLoaded == g_ResourceManager.imageProperties.length )
142 {
143 // create a new ApplicationManager
144 new ApplicationManager().startupApplicationManager(this.canvas.width, this.canvas.height);
145 this.resourcesLoaded = true;
146 }
147 else
148 {
149 this.loadingScreenCol += this.loadingScreenColDirection * this.loadingScreenColSpeed * dt;
150 if (this.loadingScreenCol > 255)
151 {
152 this.loadingScreenCol = 255;
153 this.loadingScreenColDirection = -1;
154 }
155 else if (this.loadingScreenCol < 0)
156 {
157 this.loadingScreenCol = 0;
158 this.loadingScreenColDirection = 1;
159 }
160 this.context2D.fillStyle = "rgb(" + parseInt(this.loadingScreenCol) + "," + parseInt(this.loadingScreenCol) + "," + parseInt(this.loadingScreenCol) + ")";
161 this.context2D.fillRect (0, 0, this.canvas.width, this.canvas.height);
162 }
163 }
164
165 // clear the drawing contexts
166 if (this.canvasSupported && this.resourcesLoaded)
167 {
168 this.backBufferContext2D.clearRect(0, 0, this.backBuffer.width, this.backBuffer.height);
169
170 this.addNewGameObjects();
171 this.removeOldGameObjects();
172
173 // first update all the game objects
174 for (var x = 0; x < this.gameObjects.length; ++x)
175 {
176 if (this.gameObjects[x].update)
177 {
178 this.gameObjects[x].update(dt, this.backBufferContext2D, this.xScroll, this.yScroll);
179 }
180 }
181
182 // then draw the game objects
183 for (var x = 0; x < this.gameObjects.length; ++x)
184 {
185 if (this.gameObjects[x].draw)
186 {
187 this.gameObjects[x].draw(dt, this.backBufferContext2D, this.xScroll, this.yScroll);
188 }
189 }
190
191 // copy the back buffer to the displayed canvas
192 this.context2D.drawImage(this.backBuffer, 0, 0);
193 }
194 };
195
196 this.shutdownAll = function()
197 {
198 for (var x = 0; x < this.gameObjects.length; ++x)
199 {
200 if (this.gameObjects[x].shutdown)
201 {
202 this.gameObjects[x].shutdown();
203 }
204 }
205
206 this.removeOldGameObjects();
207 }
208
209 /**
210 Adds a new GameObject to the gameObjects collection
211 @param gameObject The object to add
212 */
213 this.addGameObject = function(gameObject)
214 {
215 this.addedGameObjects.push(gameObject);
216 };
217
218 this.addNewGameObjects = function()
219 {
220 if (this.addedGameObjects.length != 0)
221 {
222 for (var x = 0; x < this.addedGameObjects.length; ++x)
223 {
224 this.gameObjects.push(this.addedGameObjects[x]);
225 }
226
227 this.addedGameObjects.clear();
228 this.gameObjects.sort(function(a,b){return a.zOrder - b.zOrder;});
229 }
230 }
231
232 /**
233 Removes a GameObject from the gameObjects collection
234 @param gameObject The object to remove
235 */
236 this.removeGameObject = function(gameObject)
237 {
238 this.removedGameObjects.push(gameObject);
239 }
240
241 this.removeOldGameObjects = function()
242 {
243 if (this.removedGameObjects.length != 0)
244 {
245 for (var x = 0; x < this.removedGameObjects.length; ++x)
246 {
247 this.gameObjects.removeObject(this.removedGameObjects[x]);
248 }
249 this.removedGameObjects.clear();
250 }
251 }
252
253 this.keyDown = function(event)
254 {
255 for (var x = 0; x < this.gameObjects.length; ++x)
256 {
257 if (this.gameObjects[x].keyDown)
258 {
259 this.gameObjects[x].keyDown(event);
260 }
261 }
262 }
263
264 this.keyUp = function(event)
265 {
266 for (var x = 0; x < this.gameObjects.length; ++x)
267 {
268 if (this.gameObjects[x].keyUp)
269 {
270 this.gameObjects[x].keyUp(event);
271 }
272 }
273 }
274 }
Top