/* * PhotonTorpedo.cs * Authors: August Zinsser * * Copyright Matthew Belmonte 2007 */ using System; using System.Collections.Generic; using System.Text; using Microsoft.Xna.Framework; using Microsoft.Xna.Framework.Audio; using Microsoft.Xna.Framework.Content; using Microsoft.Xna.Framework.Graphics; using Microsoft.Xna.Framework.Input; using Microsoft.Xna.Framework.Storage; using Pina3D.Particles; using tAC_Engine; namespace Astropolis { /// /// The lasers that the player fires at meteors or other ships /// class PhotonTorpedo : Entity { protected Emitter mTrailEmitter; // Particle effect protected Emitter mHeadEmitter; // '' protected float mSpawnDepth; // Depth that the lasers spawn at (should be the same as the player ship) protected float mKillDepth; // How far the laser travels before fizzling out protected bool mAlive = true; // If the laser is alive or not protected bool mIsGoingAway; // Used to determine whether the lasers are travelling away from the player or towards it protected bool mFriendly = true; // Friendly lasers are fired from the player, non-friendly lasers can damage the player protected int mDamage = 0; // How much damage is dealt to a ship that collides with this laser protected Vector3 mSpace3DSize; // Size of this entity in space3D coordinates protected int mLevel = 0; // Levels 1 and 2 look cooler public bool Friendly { set { mFriendly = value; } get { return mFriendly; } } public int Damage { set { mDamage = value; } get { return mDamage; } } public bool Alive { set { mAlive = value; mTrailEmitter.Alive = value; mHeadEmitter.Alive = value; } get { return mAlive; } } public override float Width { set { mSpace3DSize.X = value; } get { return mSpace3DSize.X; } } public override float Height { set { mSpace3DSize.Y = value; } get { return mSpace3DSize.Y; } } public override Vector3 Size { get { return mSpace3DSize; } } public virtual Vector3 CollisionSize { get { return mSpace3DSize; } } /// /// Constructor /// /// If the torpedo should rotate clockwise /// Color of the photon /// In Space3D units /// In Space3D units /// In Spacw3D units /// Level 0 is standard, levels 1 and 2 look cooler /// Space3D units/second /// Initial Z position /// Maximum Z position public PhotonTorpedo(bool clockwise, Color color, int level, Vector3 spawnLocation, float width, float height, float depth, float speed, float spawnDepth, float killDepth) : base((Texture2D)null) { mSpace3DSize = new Vector3(width, height, depth); mLevel = level; mPos = spawnLocation; mVel.Z = speed; mSize.Z = width * 2; // Extra width allows us to calculate collisions more cheaply mSpawnDepth = spawnDepth; mKillDepth = killDepth; // Load and move the particle effects mTrailEmitter = Sparx.LoadParticleEffect(@"Content\Particle Effects\PhotonTorpedoTrail.spx"); if (mLevel == 1) { mHeadEmitter = Sparx.LoadParticleEffect(@"Content\Particle Effects\PhotonTorpedoSpinningHead.spx"); mHeadEmitter.Position3D = new Vector3(0, -100, 0); mHeadEmitter.RegularEmissionType.Modifiers[0].InitialTint = Color.LightGoldenrodYellow; mHeadEmitter.RegularEmissionType.Modifiers[0].FinalTint = color; mTrailEmitter.RegularEmissionType.Modifiers[0].InitialTint = new Color( (byte)(color.R + 128), (byte)(color.G + 0), (byte)(color.B - 32), color.A); mTrailEmitter.RegularEmissionType.Modifiers[0].FinalTint = color; mTrailEmitter.RenderScale = 4f; mSpace3DSize.X *= 2f; mSpace3DSize.Y *= 2f; } else if (mLevel >= 2) { mHeadEmitter = Sparx.LoadParticleEffect(@"Content\Particle Effects\PhotonTorpedoHead.spx"); mHeadEmitter.Position3D = Vector3.Zero; mHeadEmitter.RegularEmissionType.Modifiers[0].InitialTint = Color.Orange; mHeadEmitter.RegularEmissionType.Modifiers[0].FinalTint = color; mHeadEmitter.RegularEmissionType.Modifiers[0].FinalScale *= 10f; mTrailEmitter = Sparx.LoadParticleEffect(@"Content\Particle Effects\PhotonTorpedoTrail2.spx"); mTrailEmitter.RegularEmissionType.Modifiers[0].InitialTint = color; mTrailEmitter.RegularEmissionType.Modifiers[0].FinalTint = Color.Orange; mVel.Z *= 2f; mSize.Z *= 2f; mSpace3DSize.X *= 2f; mSpace3DSize.Y *= 2f; mSpace3DSize.Z *= 2f; } else // Default { mHeadEmitter = Sparx.LoadParticleEffect(@"Content\Particle Effects\PhotonTorpedoHead.spx"); mHeadEmitter.Position3D = Vector3.Zero; mHeadEmitter.RegularEmissionType.Modifiers[0].InitialTint = color; mHeadEmitter.RegularEmissionType.Modifiers[0].FinalTint = color; mTrailEmitter.RegularEmissionType.Modifiers[0].InitialTint = color; mTrailEmitter.RegularEmissionType.Modifiers[0].FinalTint = color; mTrailEmitter.RenderScale = 1f; } Rectangle proj = Space3D.Project(mPos.X, mPos.Y, mPos.Z, mSpace3DSize.X, mSpace3DSize.Y, -1f); mTrailEmitter.Position3D = new Vector3(proj.X, proj.Y, -mPos.Z / killDepth); Sparx.AddEmitter(mTrailEmitter); Sparx.AddEmitter(mHeadEmitter); if (speed > 0) mIsGoingAway = true; else mIsGoingAway = false; } /// /// Scroll the torpedoes /// public override void Update() { base.Update(); // Update the photon's position if (mIsGoingAway && mPos.Z > mKillDepth || !mIsGoingAway && mPos.Z < mKillDepth) mAlive = false; // Adjust the Particles Rectangle proj = Space3D.Project(mPos.X, mPos.Y, mPos.Z, mSpace3DSize.X, mSpace3DSize.Y, -1f); float zDepth = mPos.Z / mSpawnDepth; if (mIsGoingAway) zDepth = mPos.Z / mKillDepth; float scale = 1 - zDepth; mTrailEmitter.Position3D = new Vector3(proj.X, proj.Y, MathHelper.Clamp(zDepth, 0f, 1f)); mTrailEmitter.SpawnRate = (Math.Max(zDepth, 0f)) * .2f; mHeadEmitter.RenderScale = scale; if (mLevel == 1) mHeadEmitter.Transform = Matrix.CreateScale(scale * .20f) * Matrix.CreateTranslation(proj.X, proj.Y, MathHelper.Clamp(1 - scale, 0f, 1f)); else mHeadEmitter.Transform = Matrix.CreateScale(scale) * Matrix.CreateTranslation(proj.X, proj.Y, MathHelper.Clamp(1 - scale, 0f, 1f)); if (mIsGoingAway) { mTrailEmitter.RegularEmissionType.Modifiers[0].InitialOpacity = scale; mTrailEmitter.RegularEmissionType.Modifiers[0].FinalOpacity = scale; mHeadEmitter.RegularEmissionType.Modifiers[0].InitialOpacity = scale; } // Kill the particle effect if the torpedo dies if (!mAlive) { mTrailEmitter.Alive = false; mHeadEmitter.Alive = false; } } } }