source: 2016/27/ohjaajat/VenienteFragore/VenienteFragore/VenienteFragore/VenienteFragore.cs @ 8014

Revision 8014, 17.1 KB checked in by sieerinn, 3 years ago (diff)

Kenttiä vähän muokkailtu ja 6 elämää laitettu alkuun

Line 
1using System;
2using System.Collections.Generic;
3using Jypeli;
4using Jypeli.Assets;
5using Jypeli.Controls;
6using Jypeli.Effects;
7using Jypeli.Widgets;
8using System.Linq;
9
10namespace VenienteFragore
11{
12    public partial class VenienteFragore : SimplePhysics.Game
13    {
14        private delegate void ObjectMethod(Vector position, double width, double height, Dictionary<string, string> properties);
15        private Dictionary<string, ObjectMethod> objectMethods;
16
17        private readonly Image dripImage = LoadImage("drip");
18        private readonly Image[] minimiiniiImages = LoadImages("minimiiniianim\\minimiiniianim", 1, 4);
19        private readonly Image[] minimiinii2Images = LoadImages("minimiinii2anim\\anim", 1, 4);
20        private readonly Image[] advenaImages = LoadImages("advenawalk\\advenawalk00", 1, 49, true);
21        private readonly Image[] advenbImages = LoadImages("advenbwalk\\advenb00", 1, 49, true);
22        private readonly string[] songNames = { "DST-IceStar", "DST-HollowBreath", "DST-PhaserSwitch", "DST-Kronos" };
23
24        private readonly Image[] advenaLiftImages = LoadImages("advenaliftingwalk\\advenaliftingwalk00", 1, 49, true);
25        private readonly Image[] advenbLiftImages = LoadImages("advenbliftingwalk\\advenbliftingwalk00", 1, 49, true);
26
27        private readonly Image advenaBlob = LoadImage("advenaBlob");
28        private readonly Image advenbBlob = LoadImage("advenbBlob");
29       
30        private readonly Image advenaCrouch = LoadImage("advenacrouch");
31        private readonly Image advenbCrouch = LoadImage("advenbcrouch");
32
33
34        // Lista kenttien nimistä, joista aluksen osa on kerätty.
35        private string currentLevelName;
36        private readonly List<string> collectedParts = new List<string>();
37        private IntMeter lives;
38        private DoubleMeter pointsCounter;
39
40        private List<Player> advenae;
41        private Vector respawnPoint;
42
43        private Vector cameraSpeed = new Vector(2.0, 4.0);
44        private Vector cameraTarget;
45
46        private SimplePhysics.Object borderleft;
47        private SimplePhysics.Object borderright;
48
49        public VenienteFragore() : base(tileSize: 50)
50        {
51        }
52
53        public override void Begin()
54        {
55            MediaPlayer.Volume = 0.35;
56            MediaPlayer.IsRepeating = true;
57            MediaPlayer.Play("DST-OrganicSpace");
58
59            IsMouseVisible = true;
60            Level.Background.CreateGradient(Color.DarkBlue, Color.Black);
61
62            Label title = new Label(Screen.Width * 0.65, Screen.Height *0.25);
63            title.Position = new Vector(0, Screen.Top - Screen.Height * 0.15);
64            title.Text = "Veniente Fragore";
65            title.TextScale = new Vector(Screen.Width * 0.004, Screen.Height * 0.003);
66            title.TextColor = new Color(50, 25, 100);
67            title.HorizontalAlignment = HorizontalAlignment.Left;
68            Add(title);
69
70            PushButton start = new PushButton(Screen.Width * 0.15, Screen.Height * 0.1);
71            start.Position = new Vector(0, Screen.Top - Screen.Height * 0.45);
72            start.Text = "Start game";
73            start.Color = Color.DarkBlue;
74            start.Clicked += StartGame;
75
76            Add(start);
77
78            PushButton exit = new PushButton(Screen.Width * 0.15, Screen.Height * 0.1);
79            exit.Position = new Vector(0, Screen.Top - Screen.Height * 0.65);
80            exit.Text = "Exit";
81            exit.Color = Color.DarkBlue;
82            exit.Clicked += Exit;
83
84            Add(exit);
85            Keyboard.Listen(Key.Enter, ButtonState.Pressed, StartGame, null);
86            Keyboard.Listen(Key.Space, ButtonState.Pressed, StartGame, null);
87
88            Keyboard.Listen(Key.Escape, ButtonState.Pressed, Exit, null);
89
90            Label credits = new Label(@"Music by DST: http://dreade.com/nosoap/");
91            credits.Position = new Vector(0, Screen.Top - Screen.Height * 0.9);
92            Add(credits);
93
94
95        }
96
97
98        private void StartGame()
99        {
100            ClearAll();
101
102            MediaPlayer.Play(RandomGen.SelectOne(songNames));
103
104            IsMouseVisible = false;
105            lives = new IntMeter(6, 0, 99);
106
107
108            pointsCounter = new DoubleMeter(0, 0, 1000000);
109            pointsCounter.Changed += PointsGained;
110
111            StartLevel("thehub");
112       
113
114            Keyboard.Listen(Key.Escape, ButtonState.Pressed, ConfirmExit, "Lopeta peli");
115        }
116
117        private void PointsGained(double oldValue, double newValue)
118        {
119            double diff = newValue - oldValue;
120            if(((int)oldValue) / 10000 < ((int)newValue / 10000))
121                {
122                lives.Value++;
123            }
124        }
125
126        private void CreateGUI()
127        {
128            Label liveMeter = new Label(Screen.Width * 0.10, Screen.Height * 0.05);
129            liveMeter.Position = new Vector(Screen.Left + Screen.Width * 0.165, Screen.Top - Screen.Height * 0.1);
130         
131           
132            liveMeter.BindTo(lives);
133            liveMeter.HorizontalAlignment = HorizontalAlignment.Center;
134            Add(liveMeter);
135
136            Label border = new Label(Screen.Width * 0.1, Screen.Height * 0.05);
137            border.Position = new Vector(Screen.Left + Screen.Width * 0.15, Screen.Top - Screen.Height * 0.1);
138            border.BorderColor = Color.Gold;
139            Add(border);
140
141            Label face = new Label(Screen.Width * 0.035, Screen.Width * 0.05);
142            face.Image = advenaImages[0];
143            face.Position = new Vector(Screen.Left + Screen.Width * 0.12, Screen.Top - Screen.Height * 0.1);
144            Add(face);
145        }
146
147        private void GameOver()
148        {
149            advenae.ForEach(x => x.Destroy());
150            ClearAll();
151
152            Level.Background.CreateGradient(Color.Black, new Color(20, 20, 115));
153            Label youLose = new Label(Screen.Width, Screen.Height);
154            youLose.Text = "You lost the game";
155            youLose.TextColor = Color.Red;
156            Add(youLose);
157
158        }
159
160        public double DistanceToNearestPlayer(Vector point)
161        {
162            return advenae.Min(p => Vector.Distance(p.Position, point));
163        }
164
165        private void StartLevel(string lvlName)
166        {
167            currentLevelName = lvlName;
168            ClearAll();
169
170            // Jos aloitetaan hubista kaikilla kamoilla, niin peli on voitettu.
171            if (collectedParts.Count == 3)
172            {
173                Action<double, string> makeLabel = (y, text) =>
174                {
175                    Add(new Label(text) { Y = y, TextColor = Color.White });
176                };
177                Level.Background.Color = Color.Black;
178                makeLabel(50, "The advenae managed to repair their ship\n          and flew to their home planet.");
179                makeLabel(-50, "Your final score is <insert score here>");
180                Keyboard.Listen(Key.Escape, ButtonState.Pressed, ConfirmExit, "Lopeta peli");
181                return;
182            }
183
184           
185            advenae = new List<Player>();
186            objectMethods = new Dictionary<string, ObjectMethod>();
187            objectMethods.Add("ball", TestBall);
188            objectMethods.Add("player", CreatePlayer);
189            objectMethods.Add("moving", CreateMovingPlatform);
190            objectMethods.Add("door", CreateDoor);
191            objectMethods.Add("goomba", CreateGoomba);
192            objectMethods.Add("goomba2", CreateGoomba2);
193            objectMethods.Add("collectible", CreateCollectible);
194            objectMethods.Add("drip", CreateWaterDrip);
195            objectMethods.Add("shippart", CreateShipPart);
196
197            string backgroundImageName = null;
198
199            var tileMap = TiledTileMap.FromLevelAsset(lvlName);
200            tileMap.SetTileMethod("Tiilet", TileMethod);
201            tileMap.SetObjectMethod("Oliot", CreateObject);
202            tileMap.SetTileMethod("Etuala", Foreground);
203            tileMap.Execute((levelProperty, value) =>
204            {
205                // Jos kentän propertyistä löytyy "background", niin asetetaan
206                // sen arvon niminen kuva taustakuvaksi.
207                // Kentän propertyjä voi säätää Tiled-editorissa valikosta
208                // Map -> Map Properties
209                if (levelProperty == "background")
210                    backgroundImageName = value;
211            });
212
213            if (backgroundImageName != null)
214            {
215                Level.Background.Image = LoadImage(backgroundImageName);
216                Level.Background.TileToLevel();
217            }
218            else Level.Background.CreateGradient(Color.Beige, Color.OrangeRed);
219
220            Gravity = new Vector(0, -1400);
221            Camera.Position = advenae[0].Position;
222            CameraInitialization();
223
224            CreateGUI();
225        }
226
227
228
229        private void CameraInitialization()
230        {
231            Camera.StayInLevel = true;
232
233            Window.Width = 1500;
234            Window.Height = 750;
235
236            borderleft = new SimplePhysics.Object(TileSize, Level.Height) { X = Camera.X + Window.Width / 2, IsVisible = false };
237            Add(borderleft);
238            borderright = new SimplePhysics.Object(TileSize, Level.Height) { X = Camera.X - Window.Width / 2, IsVisible = false };
239            Add(borderright);
240
241            Timer checkit = new Timer();
242            checkit.Interval = 0.02;
243            checkit.Timeout += () => { UpdateCameraTarget(checkit); };
244            checkit.Start();
245        }
246
247        private void UpdateCameraTarget(Timer checkit)
248        {
249            var activePlayers = advenae.FindAll(o => o.IsVisible);
250
251            switch (activePlayers.Count)
252            {
253                case 1:
254                    Player soloYolo = activePlayers[0];
255                    cameraTarget.X = soloYolo.Position.X + (soloYolo.FacingDirection.GetVector().X * (TileSize * 4));
256                    if (soloYolo.IsCrouching) cameraTarget.Y = soloYolo.Position.Y - TileSize * 4;
257                    else if (soloYolo.IsGrounded) cameraTarget.Y = soloYolo.Position.Y;
258                    break;
259                case 2:
260                    var minPosition = new Vector(activePlayers.Max(p => p.X), activePlayers.Min(p => p.Y));
261                    var maxPosition = new Vector(activePlayers.Min(p => p.X), activePlayers.Max(p => p.Y));
262                    cameraTarget = (minPosition + maxPosition) * 0.5;
263                    break;
264            }
265
266            borderleft.X = Camera.X + Window.Width / 2.0;
267            borderright.X = Camera.X - Window.Width / 2.0;
268        }
269
270        protected override void Update(Time time)
271        {
272            Camera.X += (cameraTarget.X - Camera.X) * time.SinceLastUpdate.TotalSeconds * cameraSpeed.X;
273            Camera.Y += (cameraTarget.Y - Camera.Y) * time.SinceLastUpdate.TotalSeconds * cameraSpeed.Y;
274
275            base.Update(time);
276        }
277       
278        private void SetMovementKeys(Player adven, List<Key> keys)
279        {
280            Keyboard.Listen(keys[3], ButtonState.Down, Walk, null, adven, 200.0);
281            Keyboard.Listen(keys[2], ButtonState.Down, Walk, null, adven, -200.0);
282            Keyboard.Listen(keys[0], ButtonState.Down, Jump, null, adven);
283            Keyboard.Listen(keys[1], ButtonState.Pressed, Crouch, null, adven, true);
284            Keyboard.Listen(keys[1], ButtonState.Released, Crouch, null, adven, false);
285            Keyboard.Listen(keys[4], ButtonState.Pressed, Interact, null, adven);
286            // Keyboard.Listen(keys[4], ButtonState.Pressed, SplitOrMorph, "Splits or morphs the player back to 1 player", adven);
287        }
288
289        private void Interact(Player adven)
290        {
291            //Jos kannetaan jotain, viskataan se
292            var carrying = adven.Carrying;
293            if (carrying != null) //Throw
294            {
295                adven.Carrying = null;
296                double dir = adven.FacingDirection == Direction.Left ? -1 : 1;
297                carrying.Velocity = new Vector(dir * 350, 350);
298                carrying.Position = carrying.Position + new Vector(dir * 10, 30);
299                //Pitäisiköhän oma aliohjelma tehdä
300                carrying.IgnoresGravity = false;
301                carrying.IgnoresCollisionResponse = false;
302            }
303
304            Vector pingPoint = adven.Position + (adven.FacingDirection == Direction.Left ? new Vector(-adven.Width, 0) : new Vector(adven.Width, 0));
305            List<GameObject> interactedObjects = GetObjectsAt(pingPoint);
306
307            GameObject sphere = new GameObject(1, 1);
308            sphere.Position = pingPoint;
309            sphere.Shape = Shape.Circle;
310            sphere.Color = new Color(100, 0, 100, 25);
311            Add(sphere, 1);
312
313            TimerAddons.Until(() => sphere.Width == 100.0, delegate { sphere.Width += 1; sphere.Height += 1; }, 0.01, sphere.Destroy);
314
315            foreach (GameObject item in interactedObjects)
316            {
317                var obj = item as InteractableObject;
318                obj?.InteractWith(adven);
319            }
320        }
321
322        private void Pickup(SimplePhysics.Object player, InteractableObject target)
323        {
324            var adven = player as Player;
325            if (adven != null && adven.Carrying == null)
326            {
327                adven.Carrying = target;
328                target.IgnoresGravity = true;
329                target.IgnoresCollisionResponse = true;
330                //Lentävän palikan nostaminen
331            }
332        }
333
334        private void SetGeneralKeys()
335        {
336            Keyboard.Listen(Key.R, ButtonState.Pressed, () => { ClearAll(); advenae = new List<Player>(); Begin(); }, "Lopeta peli");
337            Keyboard.Listen(Key.Escape, ButtonState.Pressed, ConfirmExit, "Lopeta peli");
338
339            Keyboard.Listen(Key.X, ButtonState.Pressed, SplitOrMorph, "Splits or morphs the player", 2);
340            Keyboard.Listen(Key.RightShift, ButtonState.Pressed, SplitOrMorph, "Splits or morphs the player", 1);
341        }
342       
343        /// <summary>
344        /// Sotku
345        /// </summary>
346        /// <param name="playerNro">Sen pelaajan numero, joka haluaa toimia</param>
347        private void SplitOrMorph(int playerNro)
348        {
349            if (!advenae[playerNro - 1].IsVisible && advenae[1 - playerNro + 1].IsVisible)
350            {
351                Split(advenae[1 - playerNro + 1]);
352            }
353            else
354            {
355                Morph(advenae[1 - playerNro + 1]);
356            }
357        }
358
359        private void Morph(Player adven)
360        {
361            if (advenae.FindAll(o => o.IsVisible == true).Count != 2) return;
362
363            if (Vector.Distance(advenae[0].Position, advenae[1].Position) < adven.Width * 1.5)
364            {
365                Player destroyable = advenae.Find(o => o.PlayerNumber != adven.PlayerNumber);
366
367                destroyable.ControlKeys.ForEach(delegate (Key key)
368                {
369                    Keyboard.Disable(key);
370                });
371
372                destroyable.Destroy();
373                destroyable.IsAlive = false;
374                lives.Value++;
375            }
376
377
378            //TODO: Eeppinen hypäytys takaisin? Samalla voisi ajastimella tarkastaa jatkuvasti, ovatko pelaajat tarpeeksi lähellä toisiaan.
379            /*
380            Vector center = new Vector();
381
382            for (int i = 0; i < advenae.Count; i++)
383            {
384                center = (advenae[i].Position - center) * 0.5;
385            }
386            foreach (Player item in advenae)
387            {
388                item.Velocity = (center - item.Position) * 3.0;
389            }
390            morphing = true;
391            Timer.SingleShot(2.0, delegate { morphing = false; });
392            */
393        }
394
395        private void Split(Player adven)
396        {
397            if (advenae.FindAll(o => o.IsVisible == true).Count == 2 || lives.Value == 0) return;
398
399            Player advenNew = new Player(adven.Width, adven.Height);
400
401           
402
403            switch (adven.PlayerNumber)
404            {
405                case 1:
406                    advenNew = CreatePlayer2(adven.Position + new Vector(adven.Width, 0), adven.Width, adven.Height);
407                    break;
408                case 2:
409                    advenNew = CreatePlayer1(adven.Position + new Vector(adven.Width, 0), adven.Width, adven.Height);
410                    break;
411            }
412
413           
414            advenNew.Position = adven.Position + new Vector(adven.Width, 0);
415
416            if (Collisions(advenNew, Vector.Zero, true).Count > 0)
417            {
418                advenNew.Destroy();
419                return;
420            }
421
422            advenNew.ControlKeys.ForEach(delegate (Key key)
423            {
424                Keyboard.Enable(key);
425            });
426
427            lives.Value--;
428        }
429
430        private void Walk(Player pelaaja, double nopeus)
431        {
432            pelaaja.Walk(nopeus);
433        }
434
435        private void Jump(SimplePlatformCharacter player)
436        {
437            ((Player)player).Jump();
438        }
439
440        private void Crouch(Player player, bool crouch)
441        {
442            player.Crouch = crouch;
443        }
444    }
445}
Note: See TracBrowser for help on using the repository browser.