Esempio n. 1
0
        public override bool Update(GameTime CurrTime)
        {
            Vector2 vNewPos;
            int     nCtr, nBestTargetID = -1;
            float   nBestTargetDist = 0, nCurrDist;
            List <PhysicalObject> aTargetList = cObjMgr[cnTargetGroupID];
            bool bRetVal = true;

            base.Update(CurrTime);

            if (ctCreated == -1)               //Just created, mark the time
            {
                ctCreated = CurrTime.TotalGameTime.TotalMilliseconds;
            }

            switch (ceProjType)
            {
            case eProjectileType_t.Tracking:
                //Find a target to track
                for (nCtr = 0; nCtr < aTargetList.Count; nCtr++)
                {
                    nCurrDist = MGMath.SquaredDistanceBetweenPoints(CenterPoint, aTargetList[nCtr].CenterPoint);

                    if (nBestTargetID == -1)                       //No target picked
                    {
                        nBestTargetID   = nCtr;
                        nBestTargetDist = nCurrDist;
                    }
                    else if (nCurrDist < nBestTargetDist)
                    {
                        nBestTargetID   = nCtr;
                        nBestTargetDist = nCurrDist;
                    }
                }

                if (nBestTargetID != -1)                   //Found a valid target, steer toward it
                {
                    nCurrDist = AITools.SteerTowardTarget(CenterPoint, aTargetList[nBestTargetID].CenterPoint, ObjectRotation, cnMaxTurn);

                    //Set the new movement direction, but don't change the speed
                    SetMovement(nCurrDist, cnMaxSpeed);
                }

                if (CurrTime.TotalGameTime.TotalMilliseconds - ctCreated > ctTimeToLive)
                {
                    //Lived its full life, time to pop
                    bRetVal = false;
                }

                break;

            case eProjectileType_t.Straight:
            default:
                //No logic, just flies straight
                if (cGraphDev.Viewport.Width < CenterPoint.X + Width)                   //remove it when off screen
                {
                    bRetVal = false;
                }

                if (cGraphDev.Viewport.Height < CenterPoint.Y + Height)                  //remove it when off screen
                {
                    bRetVal = false;
                }

                if (CenterPoint.X < -1 * Width)
                {
                    bRetVal = false;
                }

                if (CenterPoint.Y < -1 * Height)
                {
                    bRetVal = false;
                }

                break;
            }

            //Look for collisions with all possible targets
            foreach (PhysicalObject CurrObj in aTargetList)
            {
                if (CurrObj.TestCollision(this) == true)
                {
                    //Hit a target! (tell it that it was hit)
                    CurrObj.ReportCollision(CurrTime, this);
                    bRetVal = false;
                    break;
                }
            }

            //Apply the current speed
            vNewPos     = CenterPoint;
            vNewPos.X  += Speed.X;
            vNewPos.Y  += Speed.Y;
            CenterPoint = vNewPos;

            if ((ParticleHandler != null) && (bRetVal == false))
            {
                //Missile is expiring, throw some particles
                for (nCtr = 0; nCtr < 10; nCtr++)
                {
                    ParticleHandler.AddParticle(new DustParticle(CenterPoint, Rand, cGraphDev, cImgAtlas, "spaceEffects_008.png"));
                }
            }

            //Return True to keep this alive, false to have it removed
            return(bRetVal);
        }
Esempio n. 2
0
        public override bool Update(GameTime CurrTime)
        {
            int     nCtr, nBestTargetID = -1, nBestAvoidID = -1;
            float   nBestTargetDist = 0, nBestAvoidDist = 0, nCurrDist, nAvoidDir, nTargetDir;
            Vector2 vNewPos;
            List <PhysicalObject> aTargetList = cObjMgr[cnTargetGroupID];
            List <PhysicalObject> aAvoidList  = cObjMgr[cnAvoidGroupID];

            base.Update(CurrTime);

            if (cnHealth <= 0)
            {
                //This enemy is dead :(
                //Should fire off some explosion particles

                return(false);
            }

            cTarget = null;
            cAvoid  = null;

            //Find a target to track
            for (nCtr = 0; nCtr < aTargetList.Count; nCtr++)
            {
                nCurrDist = MGMath.SquaredDistanceBetweenPoints(CenterPoint, aTargetList[nCtr].CenterPoint);

                if (nBestTargetID == -1)                   //No target picked
                {
                    nBestTargetID   = nCtr;
                    nBestTargetDist = nCurrDist;
                    cTarget         = aTargetList[nCtr];
                }
                else if (nCurrDist < nBestTargetDist)
                {
                    nBestTargetID   = nCtr;
                    nBestTargetDist = nCurrDist;
                    cTarget         = aTargetList[nCtr];
                }
            }

            for (nCtr = 0; nCtr < aAvoidList.Count; nCtr += 1)
            {
                nCurrDist = MGMath.SquaredDistanceBetweenPoints(CenterPoint, aAvoidList[nCtr].CenterPoint);

                if (nBestAvoidID == -1)                   //No target picked
                {
                    nBestAvoidID   = nCtr;
                    nBestAvoidDist = nCurrDist;
                    cAvoid         = aAvoidList[nCtr];
                }
                else if (nCurrDist < nBestAvoidDist)
                {
                    nBestAvoidID   = nCtr;
                    nBestAvoidDist = nCurrDist;
                    cAvoid         = aAvoidList[nCtr];
                }
            }

            if (nBestAvoidDist > cnMaxStrafeDist * cnMaxStrafeDist)
            {
                //Thing to avoid is too far away to worry about
                nBestAvoidID = -1;
                cAvoid       = null;
            }

            if (nBestTargetID != -1)               //Found a valid target, attack it
            {
                if (nBestTargetDist > (cnMaxStrafeDist * cnMaxStrafeDist))
                {
                    if (cnLastMove != 1)
                    {
                        cDevConsole?.AddText("Move closer");
                    }
                    cnLastMove = 1;
                    //Too far away to strafe, move closer
                    nTargetDir = AITools.SteerTowardTarget(CenterPoint, aTargetList[nBestTargetID].CenterPoint, ObjectRotation, cnMaxTurn);
                }
                else if (nBestTargetDist < cnMinStrafeDist * cnMinStrafeDist)
                {
                    if (cnLastMove != 2)
                    {
                        cDevConsole?.AddText("Back away");
                    }
                    cnLastMove = 2;
                    //Too close, steer away from target
                    nTargetDir = AITools.SteerAwayFromTarget(CenterPoint, aTargetList[nBestTargetID].CenterPoint, ObjectRotation, cnMaxTurn);
                }
                else                      //Close enough, strafe around the target
                {
                    if (cnLastMove != 3)
                    {
                        cDevConsole?.AddText("Strafe");
                    }
                    cnLastMove = 3;
                    nTargetDir = AITools.SteerToCircleTarget(CenterPoint, aTargetList[nBestTargetID].CenterPoint, ObjectRotation, cnMaxTurn, cbStrafeCW);
                }
            }
            else
            {
                nTargetDir = 0;
            }

            if (nBestAvoidID != -1)
            {
                nAvoidDir = AITools.SteerAwayFromTarget(CenterPoint, aAvoidList[nBestAvoidID].CenterPoint, ObjectRotation, cnMaxTurn);
            }
            else
            {
                nAvoidDir = 0;
            }

            if (cnTargetGroupID != -1)
            {
                if ((nBestAvoidID != -1) && (nBestAvoidDist < nBestTargetDist))
                {
                    //Thing to avoid is closer than the target, it gets priority
                    nCurrDist = (0.75f * nAvoidDir) + (0.25f * nTargetDir);
                }
                else
                {
                    //Target is closer, go for the kill
                    nCurrDist = nTargetDir;
                }
            }
            else
            {
                //No target so just avoid?
                nCurrDist = nAvoidDir;
            }

            //Set the new movement direction, but don't change the speed
            SetMovement(nCurrDist, cnMaxSpeed);

            //Apply current speed
            vNewPos    = CenterPoint;
            vNewPos.X += cvCurrSpeed.X;
            vNewPos.Y += cvCurrSpeed.Y;

            CenterPoint = vNewPos;

            if (ctHitFlashUntil > CurrTime.TotalGameTime.TotalMilliseconds)
            {
                //Flash red when being hit
                this.TintColor = Color.Red;
            }
            else
            {
                //Normal condition is white, for no tint
                this.TintColor = cclrNormalColor;
            }

            //Return True to keep this alive, false to have it removed
            return(true);
        }
Esempio n. 3
0
        public override bool Update(GameTime CurrTime)
        {
            Vector2 MyCenter, TargetCenter, Speed;
            float   Distance;

            MyCenter.X = TopLeft.X + (Width / 2);
            MyCenter.Y = TopLeft.Y + (Height / 2);

            TargetCenter = TargetObject.GetCenterCoordinates();

            Rotation = MGMath.GetAngleFromPoints(MyCenter, TargetCenter, true);

            Distance = MGMath.SquaredDistanceBetweenPoints(MyCenter, TargetCenter);

            if ((Distance >= MaxDistanceFromTarget * MaxDistanceFromTarget) && (cStrafeDirection != 0))               //Too far away get closer
            {
                Speed            = MGMath.CalculateXYMagnitude(Rotation, 3);
                cStrafeDirection = 0;
            }
            else if ((Distance >= (MaxDistanceFromTarget * MaxDistanceFromTarget * 0.8f * 0.8f)) && (cStrafeDirection == 0))                 //If moving forward overshoot a bit
            {
                Speed = MGMath.CalculateXYMagnitude(Rotation, 3);
            }
            else if (Distance <= MinDistanceFromTarget * MinDistanceFromTarget)                 //Too close back away
            {
                Speed            = MGMath.CalculateXYMagnitude(Rotation + 3.14f, 3);
                cStrafeDirection = 0;
            }
            else if ((Distance <= MinDistanceFromTarget * MinDistanceFromTarget * 1.2f * 1.2f) && (cStrafeDirection == 0))                 //If backing away overshoot a bit
            {
                Speed = MGMath.CalculateXYMagnitude(Rotation + 3.14f, 3);
            }
            else                 //Close enough, circle
            {
                if (cStrafeDirection == 0)
                {
                    if (cRand.Next(1, 3) == 1)
                    {
                        cStrafeDirection = -1;
                    }
                    else
                    {
                        cStrafeDirection = 1;
                    }
                }

                Speed = MGMath.CalculateXYMagnitude(Rotation + 1.57f, 2);

                Speed.X *= cStrafeDirection;
                Speed.Y *= cStrafeDirection;
            }

            SpeedX = (SpeedX + Speed.X) / 2;
            SpeedY = (SpeedY + Speed.Y) / 2;

            TopLeft.X += SpeedX;
            TopLeft.Y -= SpeedY;

            if (cLastShot == 0)
            {
                cLastShot = CurrTime.TotalGameTime.TotalMilliseconds + 1500 + cRand.Next(1000);
            }

            if (cLastShot < CurrTime.TotalGameTime.TotalMilliseconds)
            {
                Vector2 BulletOrigin;

                BulletOrigin.Y = TopLeft.Y + (Height / 2);
                BulletOrigin.X = TopLeft.X + (Height / 2);

                Rotation += (float)(cRand.Next(-10, 10) * (Math.PI / 180.0));                 //Randmize the direction so that it's not perfect (+/- 10 degrees)
                BulletManager.AddParticle(BulletTexture, BulletOrigin.Y - 10, BulletOrigin.X - 10, 20, 20, Rotation, 8, new Color(255, 75, 75, 255));

                cLastShot = CurrTime.TotalGameTime.TotalMilliseconds + 1500 + cRand.Next(1000);
            }

            return(true);
        }