source: 2013/27/JaakkoL/RampageRebellion/RampageRebellion/RampageRebellion/RRBegin.cs @ 4463

Revision 4463, 45.1 KB checked in by jaollipa, 6 years ago (diff)

RREnemySpawner slightly redesigned.

Line 
1using System;
2using System.Collections.Generic;
3using System.Linq;
4using System.Text;
5using System.Diagnostics;
6using Jypeli;
7using Jypeli.Assets;
8using Jypeli.Controls;
9using Jypeli.Effects;
10using Jypeli.Widgets;
11
12/// @author     Jaakko Lipas
13/// @version    Dev - 2.7.2013
14
15/// <summary>
16/// The main class of the game that uses all other classes in the project (except RRMain).
17/// </summary>
18public class RampageRebellion : PhysicsGame
19{
20
21    #region Tech Data
22
23    /**
24     * Tags:
25     *
26     *  B = Border
27     *  P = Player
28     *  SE = Consolidated Tag for Small-Class Enemies (small, medium)
29     *  LE = Consolidated Tag for Large-Class Enemies (large, boss)
30     *  EP = Enemy Projectile
31     *  PP = Player Projectile
32     *  LP = Player Laser Blaster Projectile
33     *  BOMB = Player Bomb
34     *  BX = Bomb Explosion
35     *  ------------
36     * Collision Ignore Groups
37     *  1 = Walls
38     *  2 = Players
39     *  3 = Projectiles
40     *  4 = Enemies
41     *  **/
42
43    #endregion
44
45    #region Attributes
46    /// <summary>
47    /// Type of controls. Valid for a keyboard and an Xbox 360 controller.
48    /// </summary>
49    public enum ControllerType { Keyboard, Xbox };
50
51    /// <summary>
52    /// Meter that gauges score.
53    /// </summary>
54    public readonly IntMeter SCOREMETER = new IntMeter(0);
55    /// <summary>
56    /// Meter that gauges the player's current power.
57    /// </summary>
58    public readonly IntMeter POWERMETER = new IntMeter(0);
59    /// <summary>
60    /// Meter that gauges the player's current health.
61    /// </summary>
62    public readonly IntMeter HEALTHMETER = new IntMeter(0);
63    /// <summary>
64    /// The player's speed (X-axis).
65    /// </summary>
66    public readonly Vector PLAYER_SPEED_X = new Vector(750.0 * 1.5, 0.0);
67    /// <summary>
68    /// The player's speed (Y-axis).
69    /// </summary>
70    public readonly Vector PLAYER_SPEED_Y = new Vector(0.0, 750.0 * 1.5);
71    /// <summary>
72    /// Position of the score meter.
73    /// </summary>
74    public readonly Vector SMETER_POSITION = new Vector(320.0, 290.0);
75    /// <summary>
76    /// Position of the power meter.
77    /// </summary>
78    public readonly Vector PMETER_POSITION = new Vector(320.0, 210.0);
79    /// <summary>
80    /// Position of the health meter.
81    /// </summary>
82    public readonly Vector HMETER_POSITION = new Vector(252.0, 150.0);
83
84    /// <summary>
85    /// Position used for the weapon selector position
86    /// </summary>
87    ///
88
89    public readonly Vector WMETER_POSITION = new Vector(320.0, -80.0);
90
91    /// <summary>
92    /// (Base position) for arsenal upgrades
93    /// </summary>
94    ///
95
96    //REMEMBER - Base screen 1024x820
97    public readonly Vector ARSENAL_BASE_POSITION = new Vector(-300, -300);
98
99
100    /// <summary>
101    /// Position used for respawning the player.
102    /// </summary>
103
104    public readonly Vector RESPAWN_POSITION = new Vector(-200.0, -300.0);
105    /// <summary>
106    /// Gravity vector.
107    /// </summary>
108    public readonly Vector GRAVITY = new Vector(0.0, -150.0);
109    /// <summary>
110    /// GameObject array that visualizes the player's current health.
111    /// </summary>
112    public readonly GameObject[] METER_RECTANGLES = new GameObject[PLAYER_HP];
113
114    /// <summary>
115    /// Shot power for the player's weapon.
116    /// </summary>
117    public const int PLAYER_WEAPONPOWER = 120;
118    /// <summary>
119    /// Small enemy health.
120    /// </summary>
121    public const double SMALLENEMY_HP = 50;
122    /// <summary>
123    /// Small enemy score value.
124    /// </summary>
125    public const double SMALLENEMY_SVALUE = 100;
126    /// <summary>
127    /// Small enemy power value.
128    /// </summary>
129    public const double SMALLENEMY_PVALUE = 1;
130    /// <summary>
131    /// Medium enemy health.
132    /// </summary>
133    public const double MEDENEMY_HP = 170;
134    /// <summary>
135    /// Medium enemy score value.
136    /// </summary>
137    public const double MEDENEMY_SVALUE = 400;
138    /// <summary>
139    /// Medium enemy power value.
140    /// </summary>
141    public const double MEDENEMY_PVALUE = 3;
142    /// <summary>
143    /// Big enemy health.
144    /// </summary>
145    public const double BIGENEMY_HP = 300;
146    /// <summary>
147    /// Big enemy score value.
148    /// </summary>
149    public const double BIGENEMY_SVALUE = 1000;
150    /// <summary>
151    /// Big enemy power value.
152    /// </summary>
153    public const double BIGENEMY_PVALUE = 6;
154    /// <summary>
155    /// Boss health.
156    /// </summary>
157    public const double BOSS_HP = 1444;
158    /// <summary>
159    /// Boss score value.
160    /// </summary>
161    public const double BOSS_SVALUE = 10000;
162    /// <summary>
163    /// Boss power value.
164    /// </summary>
165    public const double BOSS_PVALUE = 25;
166    /// <summary>
167    /// Player health. Also used as the value for determining the length of the player's health meter.
168    /// </summary>
169    public const int PLAYER_HP = 40;
170    /// <summary>
171    /// Player score value (the value to be deducted from the current score, if the player dies)
172    /// </summary>
173    public const double PLAYER_SVALUE = 4000;
174    /// <summary>
175    /// Radius of a small enemy.
176    /// </summary>
177    public const double SMALLENEMY_SIZE = 40.0;
178    /// <summary>
179    /// Radius of a medium enemy.
180    /// </summary>
181    public const double MEDENEMY_SIZE = 70.0;
182    /// <summary>
183    /// Radius of a big enemy.
184    /// </summary>
185    public const double BIGENEMY_SIZE = 110.0;
186    /// <summary>
187    /// Radius of a boss enemy.
188    /// </summary>
189    public const double BOSS_SIZE = 222.0;
190    /// <summary>
191    /// Enemy mass.
192    /// </summary>
193    public const double ENEMY_MASS = 600.0;
194    /// <summary>
195    /// Linear damping value for enemies.
196    /// </summary>
197    public const double ENEMY_DAMPING = 0.92;
198    /// <summary>
199    /// Fire rate of the player's weapon.
200    /// </summary>
201    public const double PLAYER_FIRERATE = 12;
202    /// <summary>
203    /// Length of a meter.
204    /// </summary>
205    public const double METER_LENGTH = 200.0;
206    /// <summary>
207    /// Length of a single bar in a health meter. Dependant on attribute METER_LENGTH.
208    /// </summary>
209    public const double HMETER_LENGTH = METER_LENGTH / 28;
210    /// <summary>
211    /// Height of a meter.
212    /// </summary>
213    public const double METER_HEIGHT = 25.0;
214    /// <summary>
215    /// Value to use when executing the tilemap.
216    /// </summary>
217    public const double FIELDEXEC_VALUE = 20.0;
218    /// <summary>
219    /// Interval between enemy spawns (in seconds).
220    /// </summary>
221    public const double SPAWNLOGIC_INTERVAL = 14.0;
222    /// <summary>
223    /// Sets the amount of enemy spawns to execute.
224    /// </summary>
225    public const int SPAWN_AMOUNT = 11;
226    /// <summary>
227    /// General initialization value for int variables.
228    /// </summary>
229    public const int GENERAL_INITVALUE = 0;
230
231    private static RampageRebellion gameObject;
232    private RRShip playerShip;
233    private static Object upgradeLockObject = new Object();
234
235
236    /// <summary>
237    /// Internal variable, whenever the vibration features are enabled
238    /// </summary>
239
240    public bool vibrateEnabled = false;
241
242
243    /// <summary>
244    /// Primary weapon for the player. Fast but not too efficient
245    /// </summary>
246
247    public RRWeapon primaryWeapon;
248
249    /// <summary>
250    /// Secondary weapon. Not too fast to fire or to advance, but is effective
251    /// </summary>
252    ///
253    public RRWeapon secWeapon;
254
255    /// <summary>
256    /// Third weapon. Insensibly inaccurate shooter! >:D
257    /// </summary>
258    ///
259    public RRWeapon triWeapon;
260
261    /// <summary>
262    /// Bomb, that is.
263    /// </summary>
264    ///
265    public RRWeapon bomb;
266
267    /// <summary>
268    /// Player weapon arsenal! >:D
269    /// </summary>
270
271    public volatile RRWeaponArsenal playerWeaponArsenal;
272    public volatile List<IntMeter> pwArsenalUpgrades;
273    public volatile List<Label> pwArsenalLabels;
274    #endregion
275
276    #region Initialization
277    /// <summary>
278    /// The title screen void that loads the title screen background, which contains control information.
279    /// </summary>
280    ///
281
282    public override void Begin()
283    {
284        gameObject = this;
285
286        SetWindowSize(1024, 820, false);
287        Image MenuBG = LoadImage("Title");
288        Level.Background.Image = MenuBG;
289        Level.BackgroundColor = Color.DarkGray;
290        Camera.ZoomToLevel();
291        Level.Background.ScaleToLevel();
292        ControllerOne.Listen(Button.Start, ButtonState.Pressed, delegate { ControlMethod(); ControllerOne.Disable(Button.Start); }, null);
293        ControllerOne.Listen(Button.Back, ButtonState.Pressed, ConfirmExit, null);
294        Keyboard.Listen(Key.Z, ButtonState.Pressed, delegate { ControlMethod(); Keyboard.Disable(Key.Z); }, null);
295        Keyboard.Listen(Key.Escape, ButtonState.Pressed, ConfirmExit, null);
296
297        //Reset weapon upgrades here. They should not be lost upon accessing the pause menu - only when resetting!
298
299        generateArsenalData();
300    }
301
302    /// <summary>
303    /// Sets visibility for arsenal labels
304    /// </summary>
305    /// <param name="visible"></param>
306
307    private void hideArsenalLabels()
308    {
309        for (int i = 0; i < 4; i++) {
310            pwArsenalLabels[i].Destroy();
311        }
312
313        pwArsenalLabels = null;
314    }
315
316    private void generateArsenalData()
317    {
318        pwArsenalUpgrades = new List<IntMeter>(new IntMeter[] { new IntMeter(0, 0, 3), new IntMeter(0, 0, 3), new IntMeter(0, 0, 3), new IntMeter(0, 0, 3) });
319    }
320
321    private void showArsenalLabels()
322    {
323        pwArsenalLabels = new List<Label>(new Label[] { new Label(METER_LENGTH, METER_HEIGHT), new Label(METER_LENGTH, METER_HEIGHT), new Label(METER_LENGTH, METER_HEIGHT), new Label(METER_LENGTH, METER_HEIGHT) });
324
325        for (int i = 0; i < 4; i++)
326        {
327            pwArsenalLabels[i].BindTo(pwArsenalUpgrades[i]);
328
329            //Because blah - JAKE, make that GUI!
330
331            pwArsenalLabels[i].Position = new Vector(ARSENAL_BASE_POSITION.X+i*200, ARSENAL_BASE_POSITION.Y);
332            pwArsenalLabels[i].Color = Color.AshGray;
333            pwArsenalLabels[i].TextColor = Color.Black;
334
335            Add(pwArsenalLabels[i]);
336            pwArsenalLabels[i].IsVisible = true;
337        }
338    }
339
340    /// <summary>
341    /// Reads which type of control the player wants to use - Controller or Keyboard - and passes the information to the other control settings.
342    /// </summary>
343    public void ControlMethod()
344    {
345        ClearAll();
346        Image CntrlBG = LoadImage("ControlScreen");
347        Level.Background.Image = CntrlBG;
348        Level.BackgroundColor = Color.DarkGray;
349        Level.Background.ScaleToLevel();
350        ControllerOne.Listen(Button.Start, ButtonState.Pressed, delegate { GameStart(ControllerType.Xbox, true); }, null);
351        ControllerOne.Listen(Button.Y, ButtonState.Pressed, delegate { GameStart(ControllerType.Xbox, false); }, null);
352        Keyboard.Listen(Key.Z, ButtonState.Pressed, delegate { GameStart(ControllerType.Keyboard, true); }, null);
353        Keyboard.Listen(Key.X, ButtonState.Pressed, delegate { GameStart(ControllerType.Keyboard, false); }, null);
354    }
355
356    /// <summary>
357    /// Get game object
358    /// </summary>
359    /// <returns></returns>
360
361    public static RampageRebellion getGame()
362    {
363        return gameObject;
364    }
365
366    /// <summary>
367    /// Loads a color tilemap to generate the field elements using subprograms. Zooms the camera accordingly. Adds menu controls.
368    /// </summary>
369    /// <param name="controllerType">The type of controls being used.</param>
370    public void GameStart(ControllerType controllerType, bool levelsOn)
371    {
372        Camera.ZoomToAllObjects();
373
374        vibrateEnabled = (controllerType == ControllerType.Xbox);
375
376        SCOREMETER.Reset();
377        POWERMETER.Reset();
378        HEALTHMETER.Reset();
379
380        ColorTileMap Field = ColorTileMap.FromLevelAsset("GameTilemap");
381
382        Field.SetTileMethod(new Color(0, 0, 0), CreateBorder);
383        Field.SetTileMethod(new Color(255, 0, 0), CreatePlayer, controllerType);
384        CreateScoreMeter();
385        CreatePowerMeter();
386
387        CreateHealthMeter(GENERAL_INITVALUE);
388        Field.Execute(FIELDEXEC_VALUE, FIELDEXEC_VALUE);
389
390        Image LevelUI = LoadImage("UI");
391        Level.Background.Image = LevelUI;
392
393        // Starts enemy spawning; ES.levels() for the pre-designed levels and ES.arcade() for arcade.
394        RREnemySpawner ES;
395        if (levelsOn) ES = new RREnemySpawner("levels");
396        else ES = new RREnemySpawner("arcade");
397
398        Gravity = GRAVITY;
399    }
400    #endregion
401
402    #region In-Games
403    /// <summary>
404    /// A pause menu that pops up if the pause button is pressed.
405    /// </summary>
406    /// <param name="controllerType">The type of controls being used.</param>
407    /// <param name="player">The player.</param>
408    /// <param name="primaryWeapon">The player's weapon.</param>
409    public void PauseMenu(PhysicsObject player, ControllerType controllerType, RRWeaponArsenal primaryWeapon)
410    {
411        ClearControls();
412
413        showArsenalLabels();
414
415        MediaPlayer.Pause();
416        Pause();
417        switch (controllerType)
418        {
419            case ControllerType.Keyboard:
420                Keyboard.Listen(Key.Escape, ButtonState.Pressed, delegate { Pause(); ResetGame(); }, null);
421                Keyboard.Listen(Key.P, ButtonState.Pressed, delegate { Unpause(player, controllerType, primaryWeapon); }, null);
422                //JAKE: Weapon upgrade keys here
423                Keyboard.Listen(Key.C, ButtonState.Pressed, triggerUpdateKeys, null, 0);
424                Keyboard.Listen(Key.V, ButtonState.Pressed, triggerUpdateKeys, null, 1);
425                Keyboard.Listen(Key.B, ButtonState.Pressed, triggerUpdateKeys, null, 2);
426                Keyboard.Listen(Key.N, ButtonState.Pressed, triggerUpdateKeys, null, 3);
427                break;
428
429            case ControllerType.Xbox:
430                ControllerOne.Listen(Button.Back, ButtonState.Pressed, delegate { Pause(); ResetGame(); }, null);
431                ControllerOne.Listen(Button.Start, ButtonState.Pressed, delegate { Unpause(player, controllerType, primaryWeapon); }, null);
432                break;
433        }
434    }
435
436    /// <summary>
437    /// Unpauses the game and resumes music.
438    /// </summary>
439    /// <param name="controllerType">The type of controls being used.</param>
440    /// <param name="player">The player.</param>
441    /// <param name="primaryWeapon">The player's weapon.</param>
442    public void Unpause(PhysicsObject player, ControllerType controllerType, RRWeaponArsenal primaryWeapon)
443    {
444        ClearControls();
445        MediaPlayer.Resume();
446        Pause();
447
448        hideArsenalLabels();
449
450        CreateControls(player, controllerType, primaryWeapon);
451    }
452
453    /// <summary>
454    /// Clears all game data and resets the game.
455    /// </summary>
456    public void ResetGame()
457    {
458        ClearAll();
459        Begin();
460    }
461
462    /// <summary>
463    /// Void that creates an invisible (fully transparent) border object. The playable field is visually bounded by the background image,
464    /// so there is no need to apply a visible texture or color to the borders.
465    /// </summary>
466    /// <param name="position">Vector location of the object, as specified in GameStart</param>
467    /// <param name="width">Width of the object, as specified in GameStart</param>
468    /// <param name="height">Height of the object, as specified in GameStart</param>
469    public void CreateBorder(Vector position, double width, double height)
470    {
471        PhysicsObject border = PhysicsObject.CreateStaticObject(width, height);
472        border.Position = position;
473        border.Color = new Color(0, 0, 0, 0);
474        border.CollisionIgnoreGroup = 1;
475        border.Tag = "B";
476        Add(border);
477    }
478
479    /// <summary>
480    /// Void that creates the player's collision detector box and sprite, adding controls for them.
481    /// </summary>
482    /// <param name="position">Vector location of the object, as specified in GameStart</param>
483    /// <param name="width">Width of the object, as specified in GameStart</param>
484    /// <param name="height">Height of the object, as specified in GameStart</param>
485    /// <param name="controllerType">The type of controls used</param>
486    ///
487
488    public void vibrateController()
489    {
490        if (((ControllerOne.GetType()) == typeof(GamePad)) && vibrateEnabled)
491        {
492            GamePad gp = ControllerOne as GamePad;
493            gp.Vibrate(0.5, 0.5, 0.0, 0.0, 0.1);
494        }
495    }
496
497    public void collisionHandler(RRShip collider, PhysicsObject collidee)
498    {
499        //System.Diagnostics.Debugger.Log(0, "Info", collider.Tag + "on" + collidee.Tag + "\n");
500        if ((String)collidee.Tag != "Z") vibrateController();
501    }
502
503    public void meterHandlerFunc(RRShip player)
504    {
505
506        for (int i = 0; i < METER_RECTANGLES.Length; i++)
507        {
508            METER_RECTANGLES[i].Color = ((i < player.Health) ? Color.Green : Color.Red);
509        }
510
511        if (player.Health == 0)
512        {
513            onPlayerDeath(player);
514        }
515    }
516
517    public void onPlayerDeath(RRShip player)
518    {
519        if (((ControllerOne.GetType()) == typeof(GamePad)) && vibrateEnabled)
520        {
521            GamePad gp = ControllerOne as GamePad;
522            gp.Vibrate(1, 1, 1, 1, 1);
523        }
524
525        Explosion expl = new Explosion(200);
526        expl.Position = player.Position;
527        Add(expl);
528
529        player.Destroy();
530
531        SCOREMETER.Value -= (int)player.ScoreValue;
532        POWERMETER.Reset();
533        ClearControls();
534
535        Keyboard.Listen(Key.Z, ButtonState.Pressed, delegate
536        {
537            for (int i = 0; i < METER_RECTANGLES.Length; i++)
538            {
539                METER_RECTANGLES[i].Color = Color.Green;
540            }
541            CreatePlayer(RESPAWN_POSITION, 20, 20, ControllerType.Keyboard);
542        }, null);
543        ControllerOne.Listen(Button.A, ButtonState.Pressed, delegate
544        {
545            for (int i = 0; i < METER_RECTANGLES.Length; i++)
546            {
547                METER_RECTANGLES[i].Color = Color.Green;
548            }
549            CreatePlayer(RESPAWN_POSITION, 20, 20, ControllerType.Xbox);
550        }, null);
551    }
552
553    public void resetAllWeapons()
554    {
555        //Cleanup required
556        this.playerShip.Remove(playerWeaponArsenal);
557        playerWeaponArsenal.Destroy();
558
559        GeneratePlayerWeapons(this.playerShip);
560    }
561
562
563    /// <summary>
564    /// Trigger for weapon updates. Triggered in pause menu
565    ///
566    /// DOCUMENTATION:
567    ///
568    /// 1st upgrade level: 2x size bullet
569    /// 2nd upgrade: damage OR fire rate
570    /// 3rd upgrade damage OR fire rate
571    /// 4rd upgrade (bomb only) - free bomb!
572    ///
573    /// FOR JAKE: When adding the 4th weapon - ensure that the bomb remains to be the last of the weapons in WeaponArsenal
574    ///
575    /// </summary>
576    /// <param name="i">Weapon triggering parameters</param>
577
578    //((pwArsenalUpgrades[x] >= 1) ? (2) : (1))
579
580    public void triggerUpdateKeys(int i) {
581        lock (upgradeLockObject)
582        {
583            int upgradeTo = pwArsenalUpgrades[i].Value + 1;
584            int upgradePrice = (int)(Math.Pow(2,upgradeTo)+2); //Prices: 4, 6, 10, 18
585
586            if (upgradeTo > 4) return; //No. No cake for you.
587
588            if ((POWERMETER >= upgradePrice) && (i == (playerWeaponArsenal.Weapons.Count-1)) && (upgradeTo == 4)) {
589                POWERMETER.Value -= upgradePrice; //Special case
590                playerWeaponArsenal.Weapons[i].Ammo.AddValue(1);
591                resetAllWeapons();
592            } else if ((POWERMETER.Value >= upgradePrice) && (upgradeTo < 4))
593            {
594                POWERMETER.Value -= upgradePrice;
595                pwArsenalUpgrades[i].Value++;
596                resetAllWeapons();
597            }
598            else return;
599        }
600    }
601
602    /// <summary>
603    /// Triggers the bomb - aka THE LAST of all weapons, as expected so far!
604    /// </summary>
605
606    public void triggerBomb()
607    {
608        playerWeaponArsenal.singleShoot(playerWeaponArsenal.Weapons.Count - 1);
609    }
610
611
612    public void CreatePlayer(Vector position, double width, double height, ControllerType controllerType)
613    {
614        // Replaced by RRShip
615        /*RRObject player = new RRObject(width, height);
616        player.Tag = "P";
617        player.Shape = Shape.Diamond;
618        player.Health = PLAYER_HP;
619        player.ScoreValue = PLAYER_SVALUE;
620        player.Position = position;
621        player.CanRotate = false;
622        player.Color = Color.Red;
623        player.CollisionIgnoreGroup = 2;
624        Add(player);
625        player.Add(new GameObject(LoadImage("PlayerSprite")));
626        player.IgnoresGravity = true;
627        AddCollisionHandler<RRObject, PhysicsObject>(player, PlayerCollision);*/
628
629        playerShip = new RRShip(this, width, height, PLAYER_HP, PLAYER_SVALUE, position, collisionHandler, meterHandlerFunc);
630        Add(playerShip);
631        HEALTHMETER.Value = PLAYER_HP;
632
633        //Let's generate this first..
634
635        GeneratePlayerWeapons(playerShip);
636
637        CreateControls(playerShip, controllerType, playerWeaponArsenal);
638    }
639
640    /// <summary>
641    /// Generates weapons for the player's use
642    /// </summary>
643    /// <param name="ship"></param>
644
645    private void GeneratePlayerWeapons(RRShip ship)
646    {
647        SoundEffect WeaponFire = LoadSoundEffect("Shot");
648        SoundEffect WeaponFireLarge = LoadSoundEffect("LargeShot");
649
650        //Upgrade levels. Same for each weapon for now
651        double pwSizeMultiplier = ((pwArsenalUpgrades[0] >= 1) ? (2) : (1));
652        double pwFireBonusMultiplier = 1 + (2 * ((pwArsenalUpgrades[0] >= 3) ? (1) : (0)));
653        double pwDamageBonusMultiplier = 1 + (1.5 * ((pwArsenalUpgrades[0] >= 2) ? (1) : (0)));
654
655        primaryWeapon = new RRWeapon(5, 10, true, PLAYER_WEAPONPOWER, PLAYER_FIRERATE * pwFireBonusMultiplier, new RRProjectileGenerator(20 * pwSizeMultiplier, 3 * pwSizeMultiplier, 0.1, new Color(255, 55 + pwArsenalUpgrades[0] * 10, 128, 128), 10 * pwDamageBonusMultiplier));
656        primaryWeapon.Position += new Vector(0, 30);
657        primaryWeapon.projectileGenerator.defaultCollisionIgnoreGroup = 3;
658        primaryWeapon.projectileGenerator.defaultTag = "PP";
659        primaryWeapon.projectileGenerator.canRotate = false;
660        primaryWeapon.projectileGenerator.shotSound = WeaponFire;
661        primaryWeapon.Color = new Color(0, 0, 0, 0);
662        primaryWeapon.Angle += Angle.FromDegrees(90);
663
664        //primaryWeapon.ProjectileCollision = playerCollisionHandler;
665
666        double swSizeMultiplier = ((pwArsenalUpgrades[1] >= 1) ? (2) : (1));
667        double swFireBonusMultiplier = 1 + (2 * ((pwArsenalUpgrades[1] >= 2) ? (1) : (0)));
668        double swDamageBonusMultiplier = 1 + (2.2 * ((pwArsenalUpgrades[1] >= 3) ? (1) : (0)));
669
670        //ShipWeapon secWeapon = new ShipWeapon(20, 30);
671        secWeapon = new RRWeapon(5, 10, true, PLAYER_WEAPONPOWER, PLAYER_FIRERATE * 10 * swFireBonusMultiplier, new RRProjectileGenerator(190 * swSizeMultiplier, 3 * swSizeMultiplier, 0.01, new Color(33, 211 + pwArsenalUpgrades[1] * 10, 111, 128), 1 * swDamageBonusMultiplier));
672        secWeapon.Position += new Vector(0, 100);
673        secWeapon.projectileGenerator.defaultCollisionIgnoreGroup = 3;
674        secWeapon.projectileGenerator.ignoresCollisionResponse = true;
675        secWeapon.projectileGenerator.defaultTag = "LP";
676        secWeapon.projectileGenerator.canRotate = false;
677        secWeapon.projectileGenerator.shotSound = WeaponFire;
678        secWeapon.Color = new Color(0, 0, 0, 0);
679        secWeapon.Angle += Angle.FromDegrees(90);
680
681        double triSizeMultiplier = ((pwArsenalUpgrades[2] >= 1) ? (2) : (1));
682        double triFireBonusMultiplier = 1 + (5.2 * ((pwArsenalUpgrades[2] >= 3) ? (1) : (0)));
683        double triDamageBonusMultiplier = 1 + (4.2 * ((pwArsenalUpgrades[2] >= 2) ? (1) : (0)));
684
685        //Third weapon
686
687        triWeapon = new RRWeapon(5, 10, true, PLAYER_WEAPONPOWER, PLAYER_FIRERATE * 5 * triFireBonusMultiplier, new RRProjectileGenerator(30 * triSizeMultiplier, 3 * triSizeMultiplier, 0.1, new Color(222, 222 - pwArsenalUpgrades[2] * 40, 11, 28), 1.5 * triDamageBonusMultiplier));
688        triWeapon.Position += new Vector(0, 35);
689        triWeapon.projectileGenerator.defaultCollisionIgnoreGroup = 3;
690        triWeapon.projectileGenerator.defaultTag = "PP";
691        triWeapon.projectileGenerator.canRotate = false;
692        triWeapon.projectileGenerator.shotSound = WeaponFire;
693        triWeapon.Color = new Color(0, 0, 0, 0);
694        triWeapon.Angle += Angle.FromDegrees(90);
695        triWeapon.setBaseAngle(triWeapon.Angle);
696        triWeapon.randomizedAngleSlate = 14 + pwArsenalUpgrades[2].Value*10.9;
697
698
699        double bombSizeMultiplier = ((pwArsenalUpgrades[3] >= 1) ? (2) : (1));
700        double bombFireBonusMultiplier = 1 + (1 * ((pwArsenalUpgrades[3] >= 3) ? (1) : (0)));
701        double bombDamageBonusMultiplier = 1 + (3 * ((pwArsenalUpgrades[3] >= 2) ? (1) : (0)));
702
703        //And the BOMB!
704
705        bomb = new RRWeapon(30, 30, true, PLAYER_WEAPONPOWER * 2, PLAYER_FIRERATE / 10 * bombFireBonusMultiplier, new RRProjectileGenerator(30 * bombSizeMultiplier, 30 * bombSizeMultiplier, 0.2, new Color(111, 111 + pwArsenalUpgrades[2] * 10, 111, 128), 50 * bombDamageBonusMultiplier));
706        bomb.projectileGenerator.projectileShape = Shape.Circle;
707        bomb.projectileGenerator.defaultCollisionIgnoreGroup = 3;
708        bomb.projectileGenerator.defaultTag = "BOMB";
709        bomb.projectileGenerator.canRotate = false;
710        bomb.projectileGenerator.shotSound = WeaponFireLarge;
711        bomb.Color = new Color(0, 0, 0, 0);
712        bomb.Angle += Angle.FromDegrees(90);
713        bomb.countInWeaponArsenal = false;
714
715        this.playerWeaponArsenal = new RRWeaponArsenal(primaryWeapon);
716        //rP = primaryWeapon;
717        this.playerWeaponArsenal.ProjectileCollision = playerCollisionHandler;
718        this.playerWeaponArsenal.addNewWeapon(secWeapon);
719        this.playerWeaponArsenal.addNewWeapon(triWeapon);
720        this.playerWeaponArsenal.addNewWeapon(bomb);
721        ship.Add(playerWeaponArsenal);
722       
723
724        CreateWeaponMeter();
725    }
726
727    public void shiftWeapons()
728    {
729        //Attempt to shift a weapon
730        playerWeaponArsenal.setNextWeapon();
731    }
732
733    /// <summary>
734    /// Creates controls for the player depending on the chosen control method.
735    /// </summary>
736    /// <param name="player">The player to be moved</param>
737    /// <param name="controllerType">The current control type</param>
738    /// <param name="primaryWeapon">The player's weapon</param>
739    private void CreateControls(PhysicsObject player, ControllerType controllerType, RRWeaponArsenal primaryWeapon)
740    {
741        ClearControls();
742        vibrateEnabled = (controllerType == ControllerType.Xbox);
743        switch (controllerType)
744        {
745            case ControllerType.Keyboard:
746                Keyboard.Listen(Key.Up, ButtonState.Down, MovePlayer, null, PLAYER_SPEED_Y, player);
747                Keyboard.Listen(Key.Up, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
748                Keyboard.Listen(Key.Down, ButtonState.Down, MovePlayer, null, -PLAYER_SPEED_Y, player);
749                Keyboard.Listen(Key.Down, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
750                Keyboard.Listen(Key.Left, ButtonState.Down, MovePlayer, null, -PLAYER_SPEED_X, player);
751                Keyboard.Listen(Key.Left, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
752                Keyboard.Listen(Key.Right, ButtonState.Down, MovePlayer, null, PLAYER_SPEED_X, player);
753                Keyboard.Listen(Key.Right, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
754                Keyboard.Listen(Key.P, ButtonState.Pressed, delegate { PauseMenu(player, controllerType, primaryWeapon); }, null);
755                Keyboard.Listen(Key.Z, ButtonState.Down, FireWeapon, null, primaryWeapon);
756                Keyboard.Listen(Key.X, ButtonState.Pressed, triggerBomb, null);
757                Keyboard.Listen(Key.LeftShift, ButtonState.Pressed, shiftWeapons, null);
758
759
760
761                break;
762            case ControllerType.Xbox:
763                ControllerOne.Listen(Button.DPadUp, ButtonState.Down, MovePlayer, null, PLAYER_SPEED_Y, player);
764                ControllerOne.Listen(Button.DPadUp, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
765                ControllerOne.Listen(Button.DPadDown, ButtonState.Down, MovePlayer, null, -PLAYER_SPEED_Y, player);
766                ControllerOne.Listen(Button.DPadDown, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
767                ControllerOne.Listen(Button.DPadLeft, ButtonState.Down, MovePlayer, null, -PLAYER_SPEED_X, player);
768                ControllerOne.Listen(Button.DPadLeft, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
769                ControllerOne.Listen(Button.DPadRight, ButtonState.Down, MovePlayer, null, PLAYER_SPEED_X, player);
770                ControllerOne.Listen(Button.DPadRight, ButtonState.Released, MovePlayer, null, Vector.Zero, player);
771                ControllerOne.ListenAnalog(AnalogControl.LeftStick, 0.1, movePlayerAnalog, null, player);
772                ControllerOne.Listen(Button.Start, ButtonState.Pressed, delegate { PauseMenu(player, controllerType, primaryWeapon); }, null);
773                ControllerOne.Listen(Button.RightTrigger, ButtonState.Down, FireWeapon, null, primaryWeapon);
774                ControllerOne.Listen(Button.Y, ButtonState.Pressed, shiftWeapons, null);
775                break;
776            default:
777                break;
778        }
779    }
780
781    public void movePlayerAnalog(AnalogState al, PhysicsObject player)
782    {
783        double xPos = al.StateVector.X;
784        double yPos = al.StateVector.Y;
785        Vector pPushVector = new Vector((xPos) * PLAYER_SPEED_X.X, (yPos) * PLAYER_SPEED_Y.Y);
786        player.Push(pPushVector);
787
788        double maxVibration = 0.15;
789        double maxBias = 0.5;
790
791        double prcBias = (0.5 * Math.Abs((xPos + yPos / 2))) +
792                         (0.5 * Math.Max(0, Math.Min(1, (1 - Math.Abs((player.Velocity.Magnitude / 100))))));
793
794        //Bias the control
795        double rightControllerVibr = ((maxVibration / 2) - ((maxVibration / 2 * maxBias) * xPos)) * prcBias;
796        double leftControllerVibr = ((maxVibration / 2) + ((maxVibration / 2 * maxBias) * xPos)) * prcBias;
797
798        if (((ControllerOne.GetType()) == typeof(GamePad)) && vibrateEnabled)
799        {
800            GamePad gp = ControllerOne as GamePad;
801            gp.Vibrate(leftControllerVibr, rightControllerVibr, 0, 0, 0.1);
802        }
803
804        //player.Velocity = pPushVector;
805    }
806
807    /// <summary>
808    /// Fires the primary weapon of the player.
809    /// </summary>
810    /// <param name="weapon">The weapon to be fired</param>
811    public void FireWeapon(RRWeaponArsenal weapon)
812    {
813        //TODO - Clean up FireWeapon, and the superflous "weapon" clause.
814        PhysicsObject projectile = playerWeaponArsenal.Shoot();
815    }
816
817    /// <summary>
818    /// Applies the force vector specified in the controls to the player object.
819    /// </summary>
820    /// <param name="force">The force vector to be applied, specified in a previous Listen method</param>
821    /// <param name="player">The player that the force vector is to be applied to, specified in a previous Listen method</param>
822    public void MovePlayer(Vector force, PhysicsObject player)
823    {
824        player.Push(force);
825        //player.Velocity = force;
826    }
827
828
829    public void CreateWeaponMeter()
830    {
831        Label weaponMeter = new Label(METER_LENGTH, METER_HEIGHT);
832        weaponMeter.Position = WMETER_POSITION;
833        weaponMeter.Color = Color.Azure;
834        weaponMeter.BindTo(playerWeaponArsenal.currentWeaponIndexMeter);
835        Add(weaponMeter);
836    }
837
838    /// <summary>
839    /// Creates a score meter on the screen. Value represented by the attribute SCOREMETER.
840    /// </summary>
841    public void CreateScoreMeter()
842    {
843        Label scoreMeter = new Label(METER_LENGTH, METER_HEIGHT);
844        scoreMeter.Position = SMETER_POSITION;
845        scoreMeter.TextColor = Color.Green;
846        scoreMeter.BindTo(SCOREMETER);
847        Add(scoreMeter);
848    }
849
850    /// <summary>
851    /// Creates a power meter on the screen. Value represented by the attribute POWERMETER.
852    /// </summary>
853    public void CreatePowerMeter()
854    {
855        Label powerMeter = new Label(METER_LENGTH, METER_HEIGHT);
856        powerMeter.Position = PMETER_POSITION;
857        powerMeter.TextColor = Color.BloodRed;
858        powerMeter.BindTo(POWERMETER);
859        Add(powerMeter);
860    }
861
862    /// <summary>
863    /// Creates a health meter on the screen recursively. Length of the health meter is dependant on player maximum health.
864    /// </summary>
865    /// <param name="i"></param>
866    public void CreateHealthMeter(int i)
867    {
868        if (i >= PLAYER_HP) return;
869        METER_RECTANGLES[i] = new GameObject(HMETER_LENGTH, METER_HEIGHT);
870        METER_RECTANGLES[i].Position = new Vector(HMETER_POSITION.X + (HMETER_LENGTH * i), HMETER_POSITION.Y);
871        METER_RECTANGLES[i].Color = Color.Green;
872        Add(METER_RECTANGLES[i]);
873        CreateHealthMeter(i + 1);
874    }
875
876    public void UpgradeMenu()
877    {
878    }
879
880    #endregion
881
882    #region Colliders
883    /// <summary>
884    /// Handles collisions between player projectiles and other objects.
885    /// </summary>
886    /// <param name="projectile">A projectile fired by the player (collider)</param>
887    /// <param name="target">Target of collision</param>
888    public void playerCollisionHandler(PhysicsObject projectile, PhysicsObject target)
889    {
890        if (target.Tag.ToString() == "B" & projectile.Tag.ToString() != "BX") projectile.Destroy(); // If the bullet hits the top wall, destroy it
891        else if (target.Tag.ToString() == "EP" || target.Tag.ToString() == "PP")
892        {
893            if (projectile.Tag.ToString() != "BOMB" || projectile.Tag.ToString() != "BE") projectile.Destroy();
894            target.Destroy();
895        }
896
897        else if (target.Tag.ToString().EndsWith("E"))
898        {
899            RREnemy enemy = target as RREnemy;
900            RRProjectile proj = projectile as RRProjectile;
901            if (enemy.Health >= 0) enemy.Health -= proj.Damage;
902            if (enemy.Health <= 0)
903            {
904                //System.Diagnostics.Debugger.Log(0, "Info", Convert.ToString(enemy.ScoreValue) + "\n");
905                SCOREMETER.Value += (int)enemy.ScoreValue;
906                POWERMETER.Value += (int)enemy.PowerValue;
907                enemy.Destroy();
908            }
909            if ((projectile.Tag.ToString() == "LP" & target.Tag.ToString() != "LE") || projectile.Tag.ToString() == "BX" || projectile.Tag.ToString() == "BS") return;
910            else if (projectile.Tag.ToString() == "BOMB" & (target.Tag.ToString().EndsWith("E") || target.Tag.ToString() == "B")) BombExplosion(projectile);
911            projectile.Destroy();
912        }
913    }
914
915    public void BombExplosion(PhysicsObject bomb)
916    {
917        SoundEffect BombExplosion = LoadSoundEffect("Bomb");
918        BombExplosion.Play();
919
920        RRProjectile bombExplosion = new RRProjectile(5.0, 999999999999, "explosion");
921        bombExplosion.Position = bomb.Position;
922        bombExplosion.Damage = 150;
923        bombExplosion.Tag = "BX";
924        bombExplosion.IgnoresCollisionResponse = true;
925        bombExplosion.IgnoresGravity = true;
926        AddCollisionHandler<RRProjectile, RREnemy>(bombExplosion, playerCollisionHandler);
927        Add(bombExplosion);
928
929        RRProjectile bombShockwave = new RRProjectile(5.0, 999999999999, new Color(212, 0, 52, 30));
930        bombShockwave.Position = bomb.Position;
931        bombShockwave.Damage = 0.1;
932        bombShockwave.Tag = "BS";
933        bombShockwave.IgnoresCollisionResponse = true;
934        bombShockwave.IgnoresGravity = true;
935        AddCollisionHandler<RRProjectile, RREnemy>(bombShockwave, playerCollisionHandler);
936        Add(bombShockwave);
937
938        Timer growExplosion = new Timer();
939        growExplosion.Interval = 0.02;
940        growExplosion.Start();
941        growExplosion.Timeout += delegate 
942        {
943            if (bombExplosion.Width >= 2500 & bombExplosion.Height >= 2500) { growExplosion.Reset(); bombExplosion.Destroy(); bombShockwave.Destroy(); }
944            else { bombExplosion.Width = bombExplosion.Width * 1.05; bombExplosion.Height = bombExplosion.Height * 1.05; bombShockwave.Width = bombShockwave.Width * 2.5; bombShockwave.Height = bombShockwave.Height * 2.5; }
945        };
946    }
947
948    #endregion
949
950    #region Enemy Logic
951
952
953    /// <summary>
954    /// After a successfully ran game, opens score screen and starts the program over after closing it.
955    /// </summary>
956    public void GameEnd()
957    {
958        Pause();
959        ScoreList scoreList = new ScoreList(10, false, 2500);
960        scoreList = DataStorage.TryLoad<ScoreList>(scoreList, "scorelist.xml");
961        HighScoreWindow scoreWindow = new HighScoreWindow("High Scores", "You have made the high scores! Please enter your name: ", scoreList, SCOREMETER.Value);
962        scoreWindow.Closed += delegate { DataStorage.Save<ScoreList>(scoreList, "scorelist.xml"); Pause(); ClearAll(); Begin(); };
963        Add(scoreWindow);
964    }
965    #endregion
966
967    #region Legacy
968    // Below: legacy code to document previous logic errors
969
970    //Old enemy generator code. Replaced by RREnemySpawner!
971
972    /** /// <summary>
973    /// Creates an enemy on the field with the given parameters. Returns the created enemy.
974    /// </summary>
975    /// <param name="position">Position to create enemy in</param>
976    /// <param name="radius">Radius of the enemy</param>
977    /// <param name="hp">Health of the enemy</param>
978    /// <param name="powerValue">Power given by the enemy on death</param>
979    /// <param name="scoreValue">Score given by the enemy on death</param>
980    /// <returns>The created enemy.</returns>
981    public RRObject CreateEnemy(Vector position, double radius, ushort hp, ushort powerValue, ushort scoreValue)
982    {
983        RRObject enemy = new RRObject(radius, radius);
984        enemy.Tag = "E";
985        enemy.Position = position;
986        enemy.Color = Color.HotPink;
987        enemy.CollisionIgnoreGroup = 3;
988        enemy.Mass = ENEMY_MASS;
989        enemy.LinearDamping = ENEMY_DAMPING;
990        enemy.CanRotate = false;
991        enemy.Health = hp;
992        enemy.ScoreValue = scoreValue;
993        enemy.PowerValue = powerValue;
994        Add(enemy);
995        return enemy;
996    } **/
997
998    /// <summary>
999    /// Main process for enemy spawns. If this isn't called in GameStart, no enemies will spawn.
1000    /// REPLACED BY RREnemySpawner
1001    /// </summary>
1002    /*public void MainEnemyProcess(int spawnLogic)
1003    {
1004        for (int i = 0; i < SPAWN_COUNT.Length; i++)
1005        {
1006            SPAWN_COUNT[i] = i;
1007        }
1008        Timer spawns = new Timer();
1009        spawns.Interval = SPAWNLOGIC_INTERVAL;
1010        spawns.Start();
1011        spawns.Timeout += delegate
1012        {
1013            if (spawnLogic == SPAWN_COUNT[0] || spawnLogic == SPAWN_COUNT[2] || spawnLogic == SPAWN_COUNT[4] || spawnLogic == SPAWN_COUNT[5])
1014            {
1015                for (int i = 0; i < ENEMY_SPAWNS1.Length; i++)
1016                {
1017                    CreateEnemy(ENEMY_SPAWNS1[i], SMALLENEMY_SIZE, SMALLENEMY_HP, SMALLENEMY_PVALUE, SMALLENEMY_SVALUE);
1018                }
1019            }
1020            else if (spawnLogic == SPAWN_COUNT[1] || spawnLogic == SPAWN_COUNT[3] || spawnLogic == SPAWN_COUNT[6] || spawnLogic == SPAWN_COUNT[10])
1021            {
1022                for (int i = 0; i < ENEMY_SPAWNS2.Length; i++)
1023                {
1024                    CreateEnemy(ENEMY_SPAWNS2[i], MEDENEMY_SIZE, MEDENEMY_HP, MEDENEMY_PVALUE, MEDENEMY_SVALUE);
1025                }
1026            }
1027            else if (spawnLogic >= SPAWN_COUNT[7] & spawnLogic < SPAWN_COUNT[10])
1028            {
1029                for (int i = 0; i < ENEMY_SPAWNS3.Length; i++)
1030                {
1031                    CreateEnemy(ENEMY_SPAWNS3[i], BIGENEMY_SIZE, BIGENEMY_HP, BIGENEMY_PVALUE, BIGENEMY_SVALUE);
1032                }
1033            }
1034            else if (spawnLogic == 11)
1035            {
1036                RRObject boss = CreateEnemy(BOSS_SPAWN, BOSS_SIZE, BOSS_HP, BOSS_PVALUE, BOSS_SVALUE);
1037                boss.Destroyed += delegate { GameEnd(); };
1038            }
1039            spawnLogic++;
1040        };
1041    }*/
1042
1043    /// <summary>
1044    /// Handles collisions between the player and objects that can damage the player.
1045    /// </summary>
1046    /// <param name="player">The player (collider)</param>
1047    /// <param name="target">Target of collision</param>
1048    /* public void PlayerCollision(RRObject player, PhysicsObject target)
1049     {
1050         if (player.Velocity.X + player.Velocity.Y > 200.0)
1051         {
1052             if (target.Tag.ToString() == "B")
1053             {
1054                 if (player.Health == 1) METER_RECTANGLES[0].Color = Color.Red;
1055                 else METER_RECTANGLES[player.Health - 1].Color = Color.Red;
1056                 player.Health -= 1;
1057             }
1058             else if (target.Tag.ToString() == "E")
1059             {
1060                 target.Destroy();
1061                 if (player.Health == 1)
1062                 {
1063                     METER_RECTANGLES[0].Color = Color.Red;
1064                     player.Health -= 1;
1065                 }
1066                 else METER_RECTANGLES[player.Health - 1].Color = Color.Red;
1067                 if (player.Health > 1)
1068                 {
1069                     METER_RECTANGLES[player.Health - 2].Color = Color.Red;
1070                     player.Health -= 2;
1071                 }
1072             }
1073             if (player.Health == 0)
1074             {
1075                 player.Destroy();
1076                 SCOREMETER.Value -= player.ScoreValue;
1077                 POWERMETER.Reset();
1078                 ClearControls();
1079                 Keyboard.Listen(Key.Z, ButtonState.Pressed, delegate
1080                 {
1081                     for (int i = 0; i < METER_RECTANGLES.Length; i++)
1082                     {
1083                         METER_RECTANGLES[i].Color = Color.Green;
1084                     }
1085                     CreatePlayer(RESPAWN_POSITION, 20, 20, ControllerType.Keyboard);
1086                 }, null);
1087                 ControllerOne.Listen(Button.A, ButtonState.Pressed, delegate
1088                 {
1089                     for (int i = 0; i < METER_RECTANGLES.Length; i++)
1090                     {
1091                         METER_RECTANGLES[i].Color = Color.Green;
1092                     }
1093                     CreatePlayer(RESPAWN_POSITION, 20, 20, ControllerType.Xbox);
1094                 }, null);
1095             }
1096         }
1097     } */
1098
1099    /*
1100    /// <summary>
1101    /// Void that adds an invisible PhysicsObject entity to an
1102    /// existing PhysicsObject, to serve as an origin point for Bullet entities.
1103    /// </summary>
1104    /// <param name="shooter">The entity that the origin object is to be attached to</param>
1105    /// <param name="controllerType">The type of controls used</param>
1106    public void AddWeapons(PhysicsObject shooter)
1107    {
1108        PhysicsObject origin = new PhysicsObject(shooter.Width, shooter.Height, Shape.Rectangle);
1109        origin.IgnoresCollisionResponse = true;
1110        shooter.Add(origin);
1111    }
1112
1113    /// <summary>
1114    /// Uses a timer delegate to set the rate-of-fire for the player's weapon. Allows "rapid fire" controls.
1115    /// </summary>
1116    /// <param name="origin">The object to originate shots from</param>
1117    /// <param name="weapon">The timer to set. The timer is created in a previous Listen method</param>
1118    /// <param name="controlType">The type of controls used (Controller true/Keyboard false)</param>
1119    public void WeaponRate(PhysicsObject origin, Timer weapon, bool controlType)
1120    {
1121        weapon.Interval = 0.225;
1122        weapon.Timeout += delegate { FireWeapon(origin, Shape.Rectangle); };
1123        weapon.Start();
1124        if (controlType == true) {
1125            ControllerOne.Listen(Button.RightTrigger, ButtonState.Released, StopRate, null, weapon);
1126        }
1127        else { Keyboard.Listen(Key.Z, ButtonState.Released, StopRate, null, weapon); }
1128    }
1129
1130    /// <summary>
1131    /// Stops the weapon timer from cycling the next shot.
1132    /// </summary>
1133    /// <param name="weapon">The timer to stop</param>
1134    public void StopRate(Timer weapon)
1135    {
1136        weapon.Stop();
1137    }
1138
1139    /// <summary>
1140    /// Calls a subprogram which creates a Bullet at the specified location and sends it off flying.
1141    /// </summary>
1142    /// <param name="origin">The object to set origin point for</param>
1143    /// <param name="shape">Shape of the bullet's collision detector</param>
1144    public void FireWeapon(PhysicsObject origin, Shape shape)
1145    {
1146        CreateBullet(origin.X + 5, origin.Y + 10, 15.0, 4.0, shape);
1147        CreateBullet(origin.X - 5, origin.Y + 10, 15.0, 4.0, shape);
1148    }
1149
1150    public void CreateBullet(double x, double y, double width, double height, Shape shape)
1151    {
1152        Bullet Weapon1 = new Bullet(width, height);
1153        Weapon1.Damage = 5;
1154        Weapon1.X = x;
1155        Weapon1.Y = y;
1156        Weapon1.Shape = shape;
1157        Weapon1.Hit(new Vector(0.0, 600.0));
1158    }
1159    */
1160    #endregion
1161}
Note: See TracBrowser for help on using the repository browser.