-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathMain.cs
359 lines (333 loc) · 11.9 KB
/
Main.cs
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
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
using ProjetVellemanTEST.GameEngine.EntityManager;
using ProjetVellemanTEST.GameEngine.SoundManager;
using ProjetVellemanTEST.GameEngine.UiManager;
using ProjetVellemanTEST.GameEngine.SaveManager;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.Linq;
using System.Runtime.Remoting.Metadata.W3cXsd2001;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using ProjetVellemanTEST.GameEngine.K8055DManager;
namespace ProjetVellemanTEST
{
public partial class frmAppMain : Form
{
//Some stuff to help while coding
/*
* StartupUi -> gamelayer = 1
* MenuUi -> gamelayer = 2
* NewGameUi -> gamelayer = 3
* SavedGameUi -> gamelayer = 4
* SettingsUi -> gamelayer = 5
* CreditsUi -> gamelayer = 6
* ChooseDifficultyUi -> gamelayer = 7
* Game -> gamelayer = 999
*/
internal int mainCpt = 0;
//Movement speed of the player
private int velocity = 10;
//Health of the player
internal int hp = 8;
//Score of the player
internal int score = 0;
//Highscore of each levels
internal int[] highScore = [0, 0, 0, 0, 0];
//Indicator of what screen is displayed
internal int gameLayer = 0;
//Maximum projectile capacity
internal int charge = 3;
//Memorize how many projectiles are displayed
internal int currentProjectile = 0;
//Memorize how many entity are displayed
internal int currentEntity = 0;
//Stock the binary value of the digital channels of the K8055
internal int digitalChannels;
//Stock the value of each analog input
internal int data1, data2;
//Stock the value of each digital inputs after the mask
internal int[] Vbtn = [0, 0, 0, 0, 0];
//Save the name of the player
internal string pseudo;
//Initiate my classes
internal InputManager inputManager;
internal EntityManager entityManager;
internal PlayerEntity pnlPlayer;
internal UiManager uiManager;
internal SoundManager soundManager;
internal SaveManager saveManager;
internal Fctvm110 Fctvm110;
//Create a random seed
internal Random random = new Random();
//Save the status of some buttons
internal bool hold = false;
internal bool hold2 = false;
internal bool e_hold = false;
//True when the game is paused
internal bool paused = false;
//True when K8055 is detected on launch
internal bool cardMode = false;
public frmAppMain()
{
InitializeComponent();
//Givve grpMain the size of the window
grpMain.Size = Size;
//Initiate my classes
inputManager = new InputManager();
entityManager = new EntityManager(this);
uiManager = new UiManager(this);
soundManager = new SoundManager(this);
saveManager = new SaveManager(this);
pnlPlayer = new PlayerEntity();
Fctvm110 = new Fctvm110();
//Search if K8055 is detected. If yes, connect to it and clear all outputs
if (Fctvm110.SearchDevices() != 0)
{
Fctvm110.ClearAllAnalog();
data1 = Fctvm110.ReadAnalogChannel(1);
Fctvm110.OutputAnalogChannel(2, data1);
Fctvm110.ClearAllDigital();
cardMode = true;
}
//Bind some useful events
if (gameLayer == 0)
{
if (cardMode)
{
//Events that occurs when any buttons of the K8055 is pressed
Fctvm110.isAnyButtonsDown += Fctvm110_isAnyButtonsDown;
}
//Events that occurs when any buttons of the keyboard is pressed
inputManager.isAnyKeyDown += anyKeyDown;
//Create the startup Ui
uiManager.CreateUiComponents<StartupUi>();
}
//Event that occurs when the system volume value has changed
soundManager.isSystemVolumeChanged += SoundManager_isSystemVolumeChanged;
//Play the menu theme
soundManager.PlayMusicLoop(soundManager.startupTheme);
}
//Force the music to change volume by pausing and resuming the music quickly
//And send the actual value to the analog output 2
internal void SoundManager_isSystemVolumeChanged()
{
if (cardMode)
{
Fctvm110.OutputAnalogChannel(2, data1);
}
uiManager.frmAppMain.soundManager.pauseMusicLoop();
uiManager.frmAppMain.soundManager.resumeMusicLoop();
}
//If any buttons has been pressed, clear the startup Ui, display
//The Main Menu Ui and unbind useless events
private void Fctvm110_isAnyButtonsDown(int value)
{
if (gameLayer == 0)
{
uiManager.ClearUi<StartupUi>();
gameLayer = 1;
uiManager.CreateUiComponents<MenuUi>();
Fctvm110.isAnyButtonsDown -= Fctvm110_isAnyButtonsDown;
inputManager.isAnyKeyDown -= anyKeyDown;
}
}
//Same here
internal void anyKeyDown(Keys keys)
{
if (gameLayer == 0)
{
uiManager.ClearUi<StartupUi>();
gameLayer = 1;
uiManager.CreateUiComponents<MenuUi>();
Fctvm110.isAnyButtonsDown -= Fctvm110_isAnyButtonsDown;
inputManager.isAnyKeyDown -= anyKeyDown;
}
}
//gameUpdate is a events that occurs on each ticks of the game clock. The clock is set on 1 ms
//Due to limited performance of windows forms, a lot more than 1 ms are passing between each ticks
private void gameUpdate(object sender, EventArgs e)
{
if(gameLayer != 999 && cardMode)
{
//Check if any buttons is pressed
Fctvm110.isAnyButtonsPressed();
//If digital input 1 is high, focus the next element focusable in the tabindex
if (Fctvm110.ReadDigitalChannel(1) && !hold)
{
this.Select(true, true);
hold = true;
}
else if (!Fctvm110.ReadDigitalChannel(1) && hold) hold = false;
}
//Check if the system volume value has changed
soundManager.SystemVolumeChange();
if (cardMode)
{
//Read the value of each analog inputs and stock them
Fctvm110.ReadAllAnalog(ref data1, ref data2);
//Change the system volume with the valur of analog input 1
soundManager.systemVolume = data1 / 255f;
}
//Gamelayer = 999 means that the game goes on
if (gameLayer == 999)
{
if (pnlPlayer.playerEnabled)
{
if (cardMode)
{
//Get the binary value of each digital inputs in once
digitalChannels = Fctvm110.ReadAllDigital();
//Mask the value and stock the state of each digital inputs
for (int i = 0; i < 5; i++)
{
Vbtn[i] = digitalChannels % 2;
digitalChannels /= 2;
}
}
//Move the player with Z/Q/S/D, arrows or K8055 digital inputs 1 -> 4
if (pnlPlayer.mainPanel.Top >= (grpMain.Height) * 3 / 4)
{
if (inputManager.isKeyPressed(Keys.Z) || inputManager.isKeyPressed(Keys.Up) || Vbtn[2] == 1) pnlPlayer.mainPanel.Top -= velocity;
}
if (pnlPlayer.mainPanel.Bottom <= grpMain.Height - 7)
{
if (inputManager.isKeyPressed(Keys.S) || inputManager.isKeyPressed(Keys.Down) || Vbtn[3] == 1) pnlPlayer.mainPanel.Top += velocity;
}
if (pnlPlayer.mainPanel.Right <= grpMain.Width - 7)
{
if (inputManager.isKeyPressed(Keys.D) || inputManager.isKeyPressed(Keys.Right) || Vbtn[0] == 1) pnlPlayer.mainPanel.Left += velocity;
}
if (pnlPlayer.mainPanel.Left >= 7)
{
if (inputManager.isKeyPressed(Keys.Q) || inputManager.isKeyPressed(Keys.Left) || Vbtn[1] == 1) pnlPlayer.mainPanel.Left -= velocity;
}
//Throw a projectile when space or K8055's digital input 5 is pressed
if ((inputManager.isKeyPressed(Keys.Space) || Vbtn[4] == 1) && !hold && currentProjectile < charge)
{
currentProjectile++;
hold = true;
entityManager.CreateEntity<ProjectileEntity>();
}
else if (!inputManager.isKeyPressed(Keys.Space) && Vbtn[4] == 0 && hold) hold = false;
//Pause the game when escape is pressed
//Then bind a special event to unpause the game
if(inputManager.isKeyPressed(Keys.Escape) && !e_hold && !paused)
{
e_hold = true;
paused = true;
uiManager.CreateUiComponents<PauseMenuUi>();
inputManager.isEscapeDown += InputManager_isEscapeDown;
}
else if(!inputManager.isKeyPressed(Keys.Escape) && e_hold)
{
e_hold = false;
}
}
//When the game start, create the player
else
{
pnlPlayer = entityManager.CreateEntity<PlayerEntity>();
pnlPlayer.size = new Size(20, 20);
pnlPlayer.location = new Point(grpMain.Width / 2 - pnlPlayer.mainPanel.Width / 2, (grpMain.Height) * 3 / 4 + pnlPlayer.mainPanel.Height);
}
//Move each entity
entityManager.moveEntity();
//Destroy entities that have to be destroyed
entityManager.destroyEntity();
//Check for collision between entities and player
entityManager.collision();
//Check for collision between entities and projectiles
entityManager.destruction();
//Update Ui that have to be updated
uiManager.UpdateUi();
//Count each ticks
mainCpt++;
//Make entities spawn with random position
//Choose random types of entities
if (currentEntity < uiManager.mode + 3)
{
int chooseEntity = random.Next(1, uiManager.mode+1);
int position = random.Next(0, grpMain.Width - 50);
switch(chooseEntity)
{
case 1: MovingEntitiy movingEntitiy = entityManager.CreateEntity<MovingEntitiy>();
movingEntitiy.location = new Point(position, -50);
currentEntity++;
break;
case 2: MovingEntityDiagonal movingEntityDiagonal = entityManager.CreateEntity<MovingEntityDiagonal>();
movingEntityDiagonal.location = new Point(position, -50);
currentEntity++;
break;
case 3:MovingEntityPattern01 pattern01 = entityManager.CreateEntity<MovingEntityPattern01>();
pattern01.location = new Point(position, -40);
currentEntity++;
break;
case 4:MovingEntityTinyVersion movingEntityTiny = entityManager.CreateEntity<MovingEntityTinyVersion>();
movingEntityTiny.location = new Point(position, -25);
currentEntity++;
break;
case 5:MovingEntityPattern01TinyVersion pattern01TinyVersion = entityManager.CreateEntity<MovingEntityPattern01TinyVersion>();
pattern01TinyVersion.location = new Point(position, -25);
currentEntity++;
break;
}
}
//End the game when the player is dead
if (hp <= 0)
{
uiManager.CreateUiComponents<EndGameUi>();
}
}
//Animate the startup Ui
if (gameLayer == 0)
{
uiManager.StartupAnimation();
}
//Performs clicks with K8055's digital input 2
if(gameLayer != 0 && gameLayer < 999)
{
if (cardMode)
{
if (Fctvm110.ReadDigitalChannel(2)) Vbtn[1] = 1;
else Vbtn[1] = 0;
if (Vbtn[1] == 1 && !hold2)
{
hold2 = true;
List<Button> copy = new List<Button>(uiManager.buttons);
foreach (Button button in copy)
{
if (button.Focused)
{
button.PerformClick();
}
}
}
else if (hold2 && Vbtn[1] == 0) hold2 = false;
}
}
}
//Event that occurs when escape is pressed when the game is paused
private void InputManager_isEscapeDown(Keys key)
{
e_hold = true;
paused = false;
uiManager.ClearUi<PauseMenuUi>();
inputManager.isEscapeDown -= InputManager_isEscapeDown;
}
//Event that occurs when any keys are up
private void onKeyUp(object sender, KeyEventArgs e)
{
inputManager.onKeyUp(e.KeyCode);
}
//Event that occurs when any keys are down
private void onKeyDown(object sender, KeyEventArgs e)
{
inputManager.onKeyDown(e.KeyCode);
}
}
}