/// <summary> /// Adds the thePrimitive to this set. /// </summary> /// <param name="thePrimitive">The primitive to be added.</param> public void AddToSet(XNACS1Primitive thePrimitive) { if (!m_DrawSet.Contains(thePrimitive)) { m_DrawSet.Add(thePrimitive); } }
public Texture2D FindTexture(XNACS1Primitive primitive) { Texture2D tex = null; if (null != primitive.Texture) { tex = m_TexTable.FindTexture(primitive.Texture); if (tex == null) { m_TexTable.LoadTexture(primitive.Texture); tex = m_TexTable.FindTexture(primitive.Texture); } } if (tex == null) { if (primitive.m_Type == XNACS1Primitive.PrimitiveType.PrimitiveCircle) { tex = m_TheCircle; } else { tex = m_TheSquare; } } return(tex); }
public virtual void Update(XNACS1Primitive obj) { XNACS1Base.World.ClampAtWorldBound(this); if(this.Collided(obj)) this.Clip(obj); }
internal void CreateDrawHelper() { // World to NDC transform float height; height = (DrawViewHeight / DrawViewWidth) * RequestedWorldWidth; Vector2 min, max; min = new Vector2(RequestedWorldMin.X, RequestedWorldMin.Y); max = new Vector2((min.X + RequestedWorldWidth), (min.Y + height)); Vector2 size = max - min; Vector2 center = min + (size * 0.5f); m_WorldBound.Center = center; m_WorldBound.Width = size.X; m_WorldBound.Height = size.Y; if (null == m_DrawHelper) { m_DrawHelper = new XNACS1LibDrawHelper(m_GraphicsManager.GraphicsDevice, Content, m_WorldBound, m_FontManager, new Vector2(XNACS1_AppWindowWidth, XNACS1_AppWindowHeight)); XNACS1Primitive.SetDrawHelper(m_DrawHelper); } else { // update the transformation matrices m_DrawHelper.SetTransformationMatrices(m_WorldBound, new Vector2(XNACS1_AppWindowWidth, XNACS1_AppWindowHeight)); } }
public virtual void Clip(XNACS1Primitive obj) { if (obj is XNACS1Circle) this.CollideWithCircle((XNACS1Circle)obj); else if (obj is XNACS1Rectangle) this.CollideWithRectangle((XNACS1Rectangle)obj); }
protected override void Clip(XNACS1Primitive obj) { float distance = (obj.Center - this.Center).Length(); if ((obj is XNACS1Circle) && (distance <= this.radius)) this.Repel((XNACS1Circle)obj); }
/// <summary> /// Ensures that the inputPrimitive is kept within bounds of the world. If inputPrimitive position is outside /// of the world bound, This function will determine the distances to the closes bound and force the inputPrimitive to /// be insde that world bound. /// </summary> /// <param name="inputPrimitive">The primtive to be tested</param> /// <returns>Which of the world bound that the inputPrimitive has moved out of.</returns> public static BoundCollideStatus ClampAtWorldBound(XNACS1Primitive inputPrimitive) { BoundCollideStatus status = CollideWorldBound(inputPrimitive); if (status != BoundCollideStatus.InsideBound) { Vector2 size = (inputPrimitive.MaxBound - inputPrimitive.MinBound) * 0.5f; Vector2 max = new Vector2(WorldMax.X - size.X, WorldMax.Y - size.Y); Vector2 min = new Vector2(WorldMin.X + size.X, WorldMin.Y + size.Y); Vector2 pos = new Vector2(inputPrimitive.Center.X, inputPrimitive.Center.Y); if (pos.X > max.X) { pos.X = max.X; } if (pos.Y > max.Y) { pos.Y = max.Y; } if (pos.X < min.X) { pos.X = min.X; } if (pos.Y < min.Y) { pos.Y = min.Y; } inputPrimitive.Center = pos; } return(status); }
public virtual void Update(XNACS1Primitive obj, Vector2 input_pos) { XNACS1Base.World.ClampAtWorldBound(this); this.Center += input_pos; if (this.Collided(obj)) this.Clip(obj); }
public void RemoveFromSet(XNACS1Primitive p) { if (null != m_DrawSet) { m_DrawSet.Remove(p); m_TravelSet.Remove(p); } }
internal static void Draw(XNACS1Primitive p, XNACS1LibDrawHelper dh) { OBB2D a = new OBB2D(p); dh.DrawLineSegments(a.m_Corner[0], a.m_Corner[1]); dh.DrawLineSegments(a.m_Corner[1], a.m_Corner[2]); dh.DrawLineSegments(a.m_Corner[2], a.m_Corner[3]); dh.DrawLineSegments(a.m_Corner[3], a.m_Corner[0]); }
public override void UpdateAgainst(XNACS1Primitive obj = null) { if (obj != null && obj.IsInAutoDrawSet()) { if (this.Collided(obj)) transportObject( (Money) obj); } }
public virtual void Update(XNACS1Primitive obj = null) { XNACS1Base.World.ClampAtWorldBound(this); if (obj != null && obj.IsInAutoDrawSet()) { if (this.Collided(obj)) this.Clip(obj); } }
/// <summary> /// Returns true if the inputPrimitive is outside of the worldBound. /// </summary> /// <param name="inputPrimitive">the primitive to check</param> /// <returns>True if inputPrimitive is outside the world bound, otherwise returns false.</returns> public static bool OutsideWorldBound(XNACS1Primitive inputPrimitive) { Vector2 min = m_GraphicsAccess.m_WorldBound.MinBound; Vector2 max = m_GraphicsAccess.m_WorldBound.MaxBound; return((inputPrimitive.MinBound.X > max.X) || (inputPrimitive.MaxBound.X < min.X) || (inputPrimitive.MinBound.Y > max.Y) || (inputPrimitive.MaxBound.Y < min.Y)); }
/// <summary> /// Overrides the base Update function to allow extra steps for /// "blowing" a circle object. /// </summary> /// <param name="obj"></param> public override void Update(Vector2 input_pos, XNACS1Primitive obj = null) { XNACS1Base.World.ClampAtWorldBound(this); this.Center += input_pos; if (this.Collided(obj)) this.Clip(obj); if (obj is XNACS1Circle) this.Blow((XNACS1Circle)obj); }
public void TopOfDrawSet(XNACS1Primitive p) { if (null != m_DrawSet) { if (IsInDrawSet(p)) { m_DrawSet.Remove(p); m_DrawSet.Add(p); } } }
public virtual void Update(Vector2 input_pos, XNACS1Primitive obj = null) { XNACS1Base.World.ClampAtWorldBound(this); this.Center += input_pos; if (obj != null && obj.IsInAutoDrawSet()) { if (this.Collided(obj)) this.Clip(obj); } }
internal static bool OBB2DIntersect(XNACS1Primitive a, XNACS1Primitive b, Vector2 pos) { OBB2D aOBB = new OBB2D(a); OBB2D bOBB = new OBB2D(b); bool touched = aOBB.overlaps1Way(bOBB) && bOBB.overlaps1Way(aOBB); if (touched) { pos = a.Center + b.Center; pos /= 2.0f; } return touched; }
/// <summary> /// Overrides the base Update function to allow extra steps for /// "blowing" a circle object. /// </summary> /// <param name="obj"></param> public override void Update(XNACS1Primitive obj = null) { XNACS1Base.World.ClampAtWorldBound(this); if (obj != null && obj.IsInAutoDrawSet()) { if (this.Collided(obj)) this.Clip(obj); if (obj is XNACS1Circle) this.Blow((XNACS1Circle)obj); } }
internal static bool OBB2DIntersect(XNACS1Primitive a, XNACS1Primitive b, out Vector2 pos) { pos = Vector2.Zero; OBB2D aOBB = new OBB2D(a); OBB2D bOBB = new OBB2D(b); bool touched = aOBB.overlaps1Way(bOBB) && bOBB.overlaps1Way(aOBB); if (touched) { pos = a.Center + b.Center; pos /= 2.0f; } return(touched); }
/// <summary> /// Pixel Accurate collision. This function is extremely sensitive to texture resolution. /// Should ALWASY have the low res primitive collide with high res primitive. /// e.g., primA is 60x60 and PrimB is 1000x1000 /// primA.TextureCollided(primB) is O(60x60) /// primB.TextureCollided(primA) is O(1000x1000) /// Use with care!! /// </summary> /// <param name="otherPrimitive">Higher resolution texture map</param> /// <param name="collisionPt">collided position</param> /// <returns></returns> public bool TextureCollided(XNACS1Primitive otherPrimitive, out Vector2 collisionPt) { collisionPt = Vector2.Zero; if ((null == otherPrimitive.Texture) || (null == Texture)) { return(false); // no texture, cannot perform pixel-accurate intersection } if (Collided(otherPrimitive, out collisionPt)) //texutres may be collided { return(sm_DrawHelper.TexturesCollided(this, otherPrimitive, out collisionPt)); } return(false); }
public void AddToSet(XNACS1Primitive p) { if (null != m_DrawSet) { if (!m_DrawSet.Contains(p)) { m_DrawSet.Add(p); } if (p.ShouldTravel || p.UseSpriteSheetAnimation) { if (!m_TravelSet.Contains(p)) { m_TravelSet.Add(p); } } } }
internal void UpdateTravelSet(XNACS1Primitive p) { if (null != m_TravelSet) { if (p.ShouldTravel || p.UseSpriteSheetAnimation) { if (!m_TravelSet.Contains(p)) { m_TravelSet.Add(p); } } else { m_TravelSet.Remove(p); } } }
/// <summary> /// Determines if this primitive collides with the otherPrimitive. If true, pos is the colliding position. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <param name="pos">If two primitives collide, this is the "average" of all the possible colliding positions.</param> /// <returns>True: if the two primitives has collided. Pos is the approximated colliding position. /// False: if the two primitives do not collide, (Pos is undefined in this case). /// </returns> public bool Collided(XNACS1Primitive otherPrimitive, out Vector2 pos) { if ((m_Type == PrimitiveType.PrimitiveCircle) && (otherPrimitive.m_Type == PrimitiveType.PrimitiveCircle)) { return(CircleCircle(m_Center, SizeX * 0.5f, otherPrimitive.Center, otherPrimitive.SizeX * 0.5f, out pos)); } else { if ((m_Rotate == 0.0f) && (otherPrimitive.m_Rotate == 0.0f)) { return(RecRec(MinBound, MaxBound, otherPrimitive.MinBound, otherPrimitive.MaxBound, out pos)); } else { return(OBB2D.OBB2DIntersect(this, otherPrimitive, out pos)); } } }
private double[] m_Origin; // origin[a] = corner[0].dot(axis[a]); #endregion Fields #region Constructors public OBB2D(XNACS1Primitive p) { m_Axis = new Vector2[2]; m_Corner = new Vector2[4]; m_Origin = new double[2]; double angle = p.RotateAngle * Math.PI / 180.0f; Vector2 X = new Vector2((float)Math.Cos(angle), (float)Math.Sin(angle)); Vector2 Y = new Vector2((float)-Math.Sin(angle), (float)Math.Cos(angle)); X *= p.SizeX / 2; Y *= p.SizeY / 2; m_Corner[0] = p.Center - X - Y; m_Corner[1] = p.Center + X - Y; m_Corner[2] = p.Center + X + Y; m_Corner[3] = p.Center - X + Y; computeAxes(); }
public OBB2D(XNACS1Primitive p) { m_Axis = new Vector2[2]; m_Corner = new Vector2[4]; m_Origin = new double[2]; double angle = p.RotateAngle * Math.PI / 180.0f; Vector2 X = new Vector2((float)Math.Cos(angle), (float)Math.Sin(angle)); Vector2 Y = new Vector2((float)-Math.Sin(angle), (float)Math.Cos(angle)); X *= p.SizeX / 2; Y *= p.SizeY / 2; m_Corner[0] = p.Center - X - Y; m_Corner[1] = p.Center + X - Y; m_Corner[2] = p.Center + X + Y; m_Corner[3] = p.Center - X + Y; computeAxes(); }
/// <summary> /// Collide the inputPrimitive with the worldBound and return which of the worldBound (left/right/top/bottom or inside) /// did this primitive intersect with. /// </summary> /// <param name="inputPrimitive">Primitive to be tested</param> /// <returns>The side upon which the primitive has collided with (or if the primitive is inside the world bound).</returns> public static BoundCollideStatus CollideWorldBound(XNACS1Primitive inputPrimitive) { Vector2 min = m_GraphicsAccess.m_WorldBound.MinBound; Vector2 max = m_GraphicsAccess.m_WorldBound.MaxBound; if (inputPrimitive.MinBound.X < min.X) { return(BoundCollideStatus.CollideLeft); } if (inputPrimitive.MaxBound.X > max.X) { return(BoundCollideStatus.CollideRight); } if (inputPrimitive.MinBound.Y < min.Y) { return(BoundCollideStatus.CollideBottom); } if (inputPrimitive.MaxBound.Y > max.Y) { return(BoundCollideStatus.CollideTop); } return(BoundCollideStatus.InsideBound); }
public bool IsInDrawSet(XNACS1Primitive p) { return(m_DrawSet.Contains(p)); }
/// <summary> /// Returns if the center of this primitive is "to the right" (in x) in relation to the center of otherPrimitive /// </summary> /// <param name="otherPrimitive">the other primitive</param> /// <returns>True: if the center's x value of this primitive is larger than the /// x value of the max bound of the otherPrimitive.</returns> public bool RightOf(XNACS1Primitive otherPrimitive) { return (Center.X > otherPrimitive.MaxBound.X); }
/// <summary> /// Adds the thePrimitive to this set. /// </summary> /// <param name="thePrimitive">The primitive to be added.</param> public void AddToSet(XNACS1Primitive thePrimitive) { if (!m_DrawSet.Contains(thePrimitive)) m_DrawSet.Add(thePrimitive); }
private void updateShooting(XNACS1Primitive obj) { if (obj != null) { if (((Money)obj).amIControlled()) { // this object is already being controlled. if (((Money)obj).amIYourOwner(this)) { countdownUntilAction--; this.Size *= 1.01f; //obj.Center += this.NormalDirection * (this.Height / 100.0f); ///*rotate circle based on movement */ //float xDisplacement = (this.Height / 64.0f / ((Money)obj).Radius) * 180f / (float)Math.PI; //((Money)obj).RotateAngle -= xDisplacement; //// is object off the end of the cannon? //Vector2 V = obj.Center - this.Center; //Vector2 N = this.NormalDirection; //Normal vector //float distOnNormal = Vector2.Dot(V, N); if (countdownUntilAction <= 0) { // shoot the coin off the cannon. #region Vector Calculations Vector2 T = this.FrontDirection; Vector2 N = this.NormalDirection; float theta = MathHelper.Clamp(12.5f, 0f, 90f); /*Find a random velocity vector between (-theta, theta)*/ float angle_offset = 0 + XNACS1Base.RandomFloat(-theta, theta); angle_offset = angle_offset * (float)Math.PI / 180; float vT = (float)(Math.Cos(angle_offset)); float vN = Math.Abs((float)(Math.Sin(angle_offset))); Vector2 V_hat = (vT * T) + (vN * N); obj.Velocity = 4f * V_hat; ((Money)obj).GetMoving(); this.beginCooldown(); #endregion } } } } }
/// <summary> /// Updates the Spawner object. Update its coins separately. Odd /// behaviour occurs when coins are updated here. --Tony /// </summary> /// <param name="obj"></param> public override void Update(XNACS1Primitive obj = null) { if (this.state == SpawnState.Idle) return; else { this.SpawnMoney(); } }
/// <summary> /// Remove thePrimitive from this set. Will also remove the primitive from the AutoDrawSet. /// </summary> /// <param name="thePrimitive">The primitive to be removed from this set.</param> public void RemoveFromSet(XNACS1Primitive thePrimitive) { m_DrawSet.Remove(thePrimitive); thePrimitive.RemoveFromAutoDrawSet(); }
/// <summary> /// Determines if this primitive collides with otherPrimitive. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <returns>True: if the two primitives has collided. /// False: if the two primitives do not collide. /// </returns> public bool Collided(XNACS1Primitive otherPrimitive) { Vector2 pos = new Vector2(); return Collided(otherPrimitive, pos); }
/// <summary> /// Returns if the center of this primitive is "to the right" (in x) in relation to the center of otherPrimitive /// </summary> /// <param name="otherPrimitive">the other primitive</param> /// <returns>True: if the center's x value of this primitive is larger than the /// x value of the max bound of the otherPrimitive.</returns> public bool RightOf(XNACS1Primitive otherPrimitive) { return(Center.X > otherPrimitive.MaxBound.X); }
/// <summary> /// Returns if the center of this primitive is "to the left" (in x) in relation to the center of otherPrimtive /// </summary> /// <param name="otherPrimitive">the other primitive</param> /// <returns>True: if the center's x value of this primitive is smaller than the /// x value of the min bound of otherPrimitive</returns> public bool LeftOf(XNACS1Primitive otherPrimitive) { return(Center.X < otherPrimitive.MinBound.X); }
/// <summary> /// Returns if the center of this primitive is "below" (in y) in relation to the center of otherPrimitive. /// </summary> /// <param name="otherPrmitive">the other primitive.</param> /// <returns>True: if the center's y value of this primitive is smaller than the /// y value of the min bound of otherPrimitive, returns /// false otherwise.</returns> public bool Below(XNACS1Primitive otherPrmitive) { return(Center.Y < otherPrmitive.MinBound.Y); }
/// <summary> /// Determines if this primitive collides with otherPrimitive. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <returns>True: if the two primitives has collided. /// False: if the two primitives do not collide. /// </returns> public bool Collided(XNACS1Primitive otherPrimitive) { Vector2 pos = Vector2.Zero; return(Collided(otherPrimitive, out pos)); }
/// <summary> /// Determs if thePrimitive is already in the draw set. /// </summary> /// <param name="thePrimitive">Primitive to be tested</param> /// <returns>True: if thePrmitive is already in the set, else returns False.</returns> public bool IsInDrawSet(XNACS1Primitive thePrimitive) { return(m_DrawSet.Contains(thePrimitive)); }
public void AddToSet(XNACS1Primitive p) { if (null != m_DrawSet) { if (!m_DrawSet.Contains(p)) { m_DrawSet.Add(p); } if (p.ShouldTravel || p.UseSpriteSheetAnimation) if (!m_TravelSet.Contains(p)) m_TravelSet.Add(p); } }
//public bool TextureCollided(XNACS1Primitive otherPrimitive) { // // if (RecRec(MinBound, MaxBound, otherPrimitive.MinBound, otherPrimitive.MaxBound, pos)) { //texutres may be collided // return sm_DrawHelper.TexturesCollided(this, otherPrimitive); // // } // // return false; //} /// <summary> /// Determines if this primitive collides with the otherPrimitive. If true, pos is the colliding position. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <param name="pos">If two primitives collide, this is the "average" of all the possible colliding positions.</param> /// <returns>True: if the two primitives has collided. Pos is the approximated colliding position. /// False: if the two primitives do not collide, (Pos is undefined in this case). /// </returns> public bool Collided(XNACS1Primitive otherPrimitive, Vector2 pos) { if ((m_Type == PrimitiveType.PrimitiveCircle) && (otherPrimitive.m_Type == PrimitiveType.PrimitiveCircle)) { return (CircleCircle(m_Center, SizeX * 0.5f, otherPrimitive.Center, otherPrimitive.SizeX * 0.5f, pos)); } else { if ((m_Rotate == 0.0f) && (otherPrimitive.m_Rotate == 0.0f)) { return (RecRec(MinBound, MaxBound, otherPrimitive.MinBound, otherPrimitive.MaxBound, pos)); } else { return (OBB2D.OBB2DIntersect(this, otherPrimitive, pos)); } } }
private void updateIdle(XNACS1Primitive obj) { if (obj != null) { // is object already being controlled? if (false == ((Money)obj).amIControlled()) { // is object touching the cannon hole? float distanceBetween = Math.Abs(Vector2.Distance(obj.Center, this.cannonHole.Center)); if (distanceBetween < 5f) { // grab and shoot the coin. ((Money)obj).setNewOwner(this); this.beginShooting(); } } } }
/// <summary> /// Returns if the center of this primitive is "below" (in y) in relation to the center of otherPrimitive. /// </summary> /// <param name="otherPrmitive">the other primitive.</param> /// <returns>True: if the center's y value of this primitive is smaller than the /// y value of the min bound of otherPrimitive, returns /// false otherwise.</returns> public bool Below(XNACS1Primitive otherPrmitive) { return (Center.Y < otherPrmitive.MinBound.Y); }
public override void UpdateAgainst(XNACS1Primitive obj = null) { switch(state) { case(CannonStates.idle): this.updateIdle(obj); break; case(CannonStates.shooting): this.updateShooting(obj); break; case( CannonStates.coolingDown): break; }; }
/// <summary> /// Returns if the center of this primitive is "above" (in y) in relation to the center of otherPrimitive. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <returns>True: if the center's y value of this primitive is greater than the /// y value of the max bound of otherPrimitive, returns /// false otherwise.</returns> public bool Above(XNACS1Primitive otherPrimitive) { return (Center.Y > otherPrimitive.MaxBound.Y); }
/// <summary> /// Determs if thePrimitive is already in the draw set. /// </summary> /// <param name="thePrimitive">Primitive to be tested</param> /// <returns>True: if thePrmitive is already in the set, else returns False.</returns> public bool IsInDrawSet(XNACS1Primitive thePrimitive) { return m_DrawSet.Contains(thePrimitive); }
/// <summary> /// Returns if the center of this primitive is "to the left" (in x) in relation to the center of otherPrimtive /// </summary> /// <param name="otherPrimitive">the other primitive</param> /// <returns>True: if the center's x value of this primitive is smaller than the /// x value of the min bound of otherPrimitive</returns> public bool LeftOf(XNACS1Primitive otherPrimitive) { return (Center.X < otherPrimitive.MinBound.X); }
internal bool TexturesCollided(XNACS1Primitive primitive1, XNACS1Primitive primitive2) { Texture2D tex1 = FindTexture(primitive1); Texture2D tex2 = FindTexture(primitive2); Color[] tex1Data = new Color[tex1.Width*tex1.Height]; tex1.GetData<Color>(tex1Data); Color[] tex2Data= new Color[tex2.Width*tex2.Height]; tex1.GetData<Color>(tex2Data); Vector2 wMin = m_WorldMin; Vector2 wMax = m_WorldMax; Vector2 wSize = wMax - wMin; Vector3 deviceSize = new Vector3(m_DeviceSize,1); Vector3 center = new Vector3(); Vector3 scale = new Vector3(); scale.Z = 1; center.Z = 0; //center = Vector3.Transform(center, mW2D); scale.X = primitive1.SizeX/((float) tex1.Width); scale.Y = primitive1.SizeY/((float) tex1.Height); center.X = primitive1.Center.X - primitive1.SizeX / 2f; center.Y = primitive1.Center.Y - primitive1.SizeY / 2f; Matrix m1 = Matrix.CreateScale(scale) * Matrix.CreateRotationZ(primitive2.RotateAngle * (float)Math.PI / 180) * Matrix.CreateTranslation(center) * mW2D ; //center = Vector3.Transform(center, mW2D); scale.X = primitive2.SizeX/((float)tex2.Width); scale.Y = primitive2.SizeY/((float)tex2.Height); center.X = primitive2.Center.X - primitive2.SizeX/2f; center.Y = primitive2.Center.Y - primitive2.SizeY/ 2f; Matrix m2 = Matrix.CreateScale(scale) * Matrix.CreateRotationZ(primitive2.RotateAngle * (float)Math.PI / 180)* Matrix.CreateTranslation(center) * mW2D ; return IntersectPixels(m1,tex1.Width,tex1.Height,tex1Data,m2,tex2.Width,tex2.Height,tex2Data); }
public override void UpdateAgainst(XNACS1Primitive obj = null) { if (obj != null) { if (((Money)obj).amIControlled()) { // this object is already being controlled. if (((Money)obj).amIYourOwner(this)) { obj.Center += this.NormalDirection * (this.Height / 100.0f); /*rotate circle based on movement */ float xDisplacement = (this.Height / 64.0f / ((Money)obj).Radius) * 180f / (float)Math.PI; ((Money)obj).RotateAngle -= xDisplacement; // is object off the end of the mover? Vector2 V = obj.Center - this.Center; Vector2 N = this.NormalDirection; //Normal vector float distOnNormal = Vector2.Dot(V, N); if (distOnNormal > this.Height / 2 + 5) { // shoot the coin off the mover. #region Vector Calculations Vector2 T = this.FrontDirection; N = this.NormalDirection; float theta = MathHelper.Clamp(12.5f, 0f, 90f); /*Find a random velocity vector between (-theta, theta)*/ float angle_offset = 90 + XNACS1Base.RandomFloat(-theta, theta); angle_offset = angle_offset * (float)Math.PI / 180; float vT = (float)(Math.Cos(angle_offset)); float vN = Math.Abs((float)(Math.Sin(angle_offset))); Vector2 V_hat = (vT * T) + (vN * N); obj.Velocity = 2f * V_hat; ((Money)obj).GetMoving(); #endregion } } } else { // is object within the bounds of this mover? Vector2 V = obj.Center - this.Center; Vector2 T = this.FrontDirection; float distOnTangent = Vector2.Dot(V, T); // take a shot at quitting this check early... if (Math.Abs(distOnTangent) < this.Width / 2) { // might be touching... keep checking. Vector2 ptT = this.Center + (distOnTangent * T); //Point on tangent Vector2 N = obj.Center - ptT; //Normal vector N.Normalize(); float distOnNormal = Vector2.Dot(V, N); if (Math.Abs(distOnNormal) < this.Height / 2) { // yes, object is within bounds of mover. // obj.Label = "touching"; ((Money)obj).setNewOwner(this); } } } } }
/// <summary> /// Returns if the center of this primitive is "above" (in y) in relation to the center of otherPrimitive. /// </summary> /// <param name="otherPrimitive">the other primitive.</param> /// <returns>True: if the center's y value of this primitive is greater than the /// y value of the max bound of otherPrimitive, returns /// false otherwise.</returns> public bool Above(XNACS1Primitive otherPrimitive) { return(Center.Y > otherPrimitive.MaxBound.Y); }
internal bool TexturesCollided(XNACS1Primitive primitive1, XNACS1Primitive primitive2, out Vector2 collidePos) { collidePos = Vector2.Zero; Texture2D tex1 = m_TexTable.FindTexture(primitive1.Texture); Texture2D tex2 = m_TexTable.FindTexture(primitive2.Texture); if ((null == tex1) || (null == tex2)) { return(false); } Color[] tex1Color = m_TexTable.FindTextureColor(primitive1.Texture); Color[] tex2Color = m_TexTable.FindTextureColor(primitive2.Texture); bool pixelTouch = false; float r1InRadian = MathHelper.ToRadians(primitive1.RotateAngle); float r2InRadian = MathHelper.ToRadians(primitive2.RotateAngle); Vector2 p1XDir = RotateVectorByAngle(Vector2.UnitX, r1InRadian); Vector2 p1YDir = RotateVectorByAngle(Vector2.UnitY, r1InRadian); Vector2 p2XDir = RotateVectorByAngle(Vector2.UnitX, r2InRadian); Vector2 p2YDir = RotateVectorByAngle(Vector2.UnitY, r2InRadian); int tex1Width = tex1.Width; int tex1Height = tex1.Height; int tex1XOffset = 0; int tex1YOffset = 0; int tex2Width = tex2.Width; int tex2Height = tex2.Height; int tex2XOffset = 0; int tex2YOffset = 0; if (primitive1.UseSpriteSheet) { tex1Width = primitive1.m_SpriteSourceRect.Width; tex1Height = primitive1.m_SpriteSourceRect.Height; tex1XOffset = primitive1.m_SpriteSourceRect.X; tex1YOffset = primitive1.m_SpriteSourceRect.Y; } if (primitive2.UseSpriteSheet) { tex2Width = primitive2.m_SpriteSourceRect.Width; tex2Height = primitive2.m_SpriteSourceRect.Height; tex2XOffset = primitive2.m_SpriteSourceRect.X; tex2YOffset = primitive2.m_SpriteSourceRect.Y; } int i = 0; while ((!pixelTouch) && (i < tex1Width)) { int j = 0; while ((!pixelTouch) && (j < tex1Height)) { collidePos = primitive1.TextureToWorldPos(i, j, tex1Width, tex1Height, p1XDir, p1YDir); Color color1 = tex1Color[tex1XOffset + i + ((j + tex1YOffset) * tex1.Width)]; if (color1.A > 0) { int p2I, p2J; primitive2.CameraPosToTexIndex(collidePos, tex2Width, tex2Height, p2XDir, p2YDir, out p2I, out p2J); if ((p2I >= 0) && (p2I < tex2Width) && (p2J >= 0) && (p2J < tex2Height)) { pixelTouch = (tex2Color[tex2XOffset + p2I + ((p2J + tex2YOffset) * tex2.Width)].A > 0); } } j++; } i++; } return(pixelTouch); }