public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Angular = 0; Vector3 desired_vector = State.Target - trans.position; float distance = desired_vector.magnitude; float targetSpeed; Vector3 targetVelocity; if(distance < TARGET_RADIUS){ this.State.LinearVelocity = Vector3.zero; ai.Linear = Vector3.zero; return ai; } if(distance > SLOW_RADIUS) targetSpeed = State.MaxLinearVelocity.magnitude; else targetSpeed = State.MaxLinearVelocity.magnitude * (distance / SLOW_RADIUS); targetVelocity = desired_vector.normalized * targetSpeed; ai.Linear = (targetVelocity - State.LinearVelocity) / TIME_TO_TARGET; if(ai.Linear.magnitude > this.State.MaxLinearAcceleration) ai.Linear = ai.Linear.normalized * this.State.MaxLinearAcceleration; return ai; }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Linear = (trans.position - State.Target).normalized * State.MaxLinearAcceleration; ai.Angular = 0; return ai; }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; //UPDATE TARGET Vector3 center = Vector3.zero; for (int i = 0; i < Targets.Length; i++) { Transform t = Targets[i]; center += t.position; } center /= (float)Targets.Length; // Debug.Log(center); average.position = center; return(ai); }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; foreach (Transform t in Targets) { Vector3 direction = (trans.position - t.position).normalized; float distance = direction.magnitude; if (distance < THRESHOLD) { float strength = DECAY * distance * distance; if (State.MaxLinearAcceleration < strength) { strength = State.MaxLinearAcceleration; } ai.Linear += strength * direction; } } //Debug.DrawLine(trans.position, trans.position + 5*ai.Linear, Color.yellow); return(ai); }
private AIDynamic RunBehaviours() { AIDynamic movement = new AIDynamic(); AIDynamic avoidDyn = new AIDynamic(); //Iterate through behaviours foreach (AIBehaviour b in behaviours) { AIDynamic dyn = b.GetDynamics(); movement.Angular += dyn.Angular * b.Weight; movement.Linear += dyn.Linear * b.Weight; if (b.BehaviourType == AIBehaviourType.ObjectAvoid || b.BehaviourType == AIBehaviourType.CollisionAvoid) { avoidDyn.Linear += dyn.Linear * b.Weight * 5f; } } if (avoidDyn.Linear.magnitude > 0) { movement.Linear = avoidDyn.Linear; } return(movement); }
private void PositionUpdate(AIDynamic motion) { //Set linear velocity to max if (state.LinearVelocity.magnitude > state.MaxLinearVelocity.magnitude) { state.LinearVelocity = state.LinearVelocity.normalized * state.MaxLinearVelocity.magnitude; } //Set angular velocity to max if (Mathf.Abs(state.AngularVelocity) > Mathf.Abs(state.MaxAngularVelocity)) { state.AngularVelocity = (state.AngularVelocity / Mathf.Abs(state.AngularVelocity)) * state.MaxAngularVelocity; } //Update position and linear velocity this.transform.position += state.LinearVelocity * Time.deltaTime; state.LinearVelocity += motion.Linear * Time.deltaTime; //Update orientation and angular velocity Vector3 rotation = this.transform.rotation.eulerAngles; rotation.y += state.AngularVelocity * Time.deltaTime; this.transform.rotation = Quaternion.Euler(rotation); state.AngularVelocity += motion.Angular * Time.deltaTime; }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; float shortestTime = float.PositiveInfinity; Transform firstTarget = null; float firstMinSeparation = 0; float firstDistance = 0; Vector3 firstRelativePos = Vector3.zero; Vector3 firstRelativeVel = Vector3.zero; foreach(Transform t in Targets){ Vector3 relativePos = trans.position - t.position; Vector3 relativeVel = t.gameObject.GetComponent<TrooperAI>().GetVelocity() - State.LinearVelocity; float relativeSpeed = relativeVel.magnitude; float timeToCollision = Vector3.Dot (relativePos, relativeVel) / (relativeSpeed * relativeSpeed); float distance = relativePos.magnitude; if(distance > THRESHOLD || t.gameObject.GetComponent<TrooperAI>().GetVelocity().magnitude < .1f) continue; float minSeparation = distance - relativeSpeed*shortestTime; if(minSeparation > 2*RADIUS) continue; if((timeToCollision > 0) && timeToCollision < shortestTime){ shortestTime = timeToCollision; firstTarget = t; firstMinSeparation = minSeparation; firstDistance = distance; firstRelativePos = relativePos; firstRelativeVel = relativeVel; } } if(firstTarget != null) Debug.DrawLine (trans.position, firstTarget.position, Color.red); if(!firstTarget) return ai; Vector3 finalRelativePos; if(firstMinSeparation <= 0 || firstDistance < 2*RADIUS) finalRelativePos = trans.position - firstTarget.position; else finalRelativePos = firstRelativePos + firstRelativeVel * shortestTime; ai.Linear = finalRelativePos.normalized * State.MaxLinearAcceleration; Debug.DrawLine (this.trans.position, this.trans.position + ai.Linear*4, Color.cyan); return ai; }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Linear = (State.Target - trans.position).normalized * State.MaxLinearAcceleration; ai.Angular = 0; return(ai); }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); /* For now, simply lerp this out */ Vector3 rotation = trans.rotation.eulerAngles; if (State.LinearVelocity.magnitude > 1f) { rotation.y = GetDirectionFromVector2D(State.LinearVelocity); trans.rotation = Quaternion.Lerp(trans.rotation, Quaternion.Euler(rotation), Time.deltaTime * 5); } /*float rotation = 0; * float targetRotation; * * rotation = GetDirectionFromVector2D (State.LinearVelocity) - trans.rotation.eulerAngles.y; * * while(rotation > 180) * rotation -= 360; * while(rotation < -180) * rotation += 360; * * float angleMag = Mathf.Abs (rotation); * * AIDynamic ai = new AIDynamic(); * ai.Angular = 0; * ai.Linear = Vector3.zero; * * if(angleMag < TARGET_RADIUS){ * State.AngularVelocity = 0; * return ai; * } * * if(angleMag > SLOW_RADIUS) * targetRotation = 6f; * else * targetRotation = 6f * angleMag / SLOW_RADIUS; * * targetRotation *= (rotation / angleMag); * * ai.Angular = trans.rotation.eulerAngles.y - targetRotation; * ai.Angular /= TIME_TO_TARGET; * * float a = Mathf.Abs (ai.Angular); * * if(a > 2f){ * ai.Angular /= a; * ai.Angular *= 2f; * }*/ return(ai); }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); /* For now, simply lerp this out */ Vector3 rotation = trans.rotation.eulerAngles; if(State.LinearVelocity.magnitude > 1f){ rotation.y = GetDirectionFromVector2D(State.LinearVelocity); trans.rotation = Quaternion.Lerp(trans.rotation, Quaternion.Euler(rotation), Time.deltaTime*5); } /*float rotation = 0; float targetRotation; rotation = GetDirectionFromVector2D (State.LinearVelocity) - trans.rotation.eulerAngles.y; while(rotation > 180) rotation -= 360; while(rotation < -180) rotation += 360; float angleMag = Mathf.Abs (rotation); AIDynamic ai = new AIDynamic(); ai.Angular = 0; ai.Linear = Vector3.zero; if(angleMag < TARGET_RADIUS){ State.AngularVelocity = 0; return ai; } if(angleMag > SLOW_RADIUS) targetRotation = 6f; else targetRotation = 6f * angleMag / SLOW_RADIUS; targetRotation *= (rotation / angleMag); ai.Angular = trans.rotation.eulerAngles.y - targetRotation; ai.Angular /= TIME_TO_TARGET; float a = Mathf.Abs (ai.Angular); if(a > 2f){ ai.Angular /= a; ai.Angular *= 2f; }*/ return ai; }
// Update is called once per frame void Update () { //RUN BEHAVIOURS AIDynamic movement = new AIDynamic(); movement = RunBehaviours(); //UPDATE POSITION PositionUpdate (movement); //ANIMATION animator.SetFloat ("velocity", state.LinearVelocity.magnitude); if(state.LinearVelocity.magnitude > 0.1f) animator.speed = state.LinearVelocity.magnitude / state.MaxLinearVelocity.magnitude; else animator.speed = 1; //TOROIDAL PositionWrap(); }
public override AIDynamic GetDynamics(){ if(Time.frameCount%UPDATE_DELAY == 0){ float r = Random.Range (0f, 1f) - Random.Range (0f, 1f); Vector3 wanderCircle = trans.position + trans.forward * WANDER_CIRCLE_DISTANCE; State.Target = Quaternion.AngleAxis(WANDER_FREEDOM*r, Vector3.up)*(State.LinearVelocity.normalized)*WANDER_CIRCLE_RADIUS + wanderCircle; /* Draw vectors Debug.DrawLine(trans.position, wanderCircle, Color.yellow, 4); Debug.DrawLine (trans.position, State.Target, Color.blue, 4); Debug.DrawLine(State.Target, wanderCircle, Color.red, 4);*/ } AIDynamic ai = new AIDynamic(); ai.Angular = 0; ai.Linear = (State.Target - trans.position).normalized * State.MaxLinearAcceleration; return ai; }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; //UPDATE TARGET Vector3 center = Vector3.zero; for(int i = 0; i < Targets.Length; i++){ Transform t = Targets[i]; center += t.position; } center /= Targets.Length; average.position = center; return ai; }
public override AIDynamic GetDynamics() { if (Time.frameCount % UPDATE_DELAY == 0) { float r = Random.Range(0f, 1f) - Random.Range(0f, 1f); Vector3 wanderCircle = trans.position + trans.forward * WANDER_CIRCLE_DISTANCE; State.Target = Quaternion.AngleAxis(WANDER_FREEDOM * r, Vector3.up) * (State.LinearVelocity.normalized) * WANDER_CIRCLE_RADIUS + wanderCircle; /* Draw vectors * Debug.DrawLine(trans.position, wanderCircle, Color.yellow, 4); * Debug.DrawLine (trans.position, State.Target, Color.blue, 4); * Debug.DrawLine(State.Target, wanderCircle, Color.red, 4);*/ } AIDynamic ai = new AIDynamic(); ai.Angular = 0; ai.Linear = (State.Target - trans.position).normalized * State.MaxLinearAcceleration; return(ai); }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Angular = 0; Vector3 desired_vector = State.Target - trans.position; float distance = desired_vector.magnitude; float targetSpeed; Vector3 targetVelocity; if (distance < TARGET_RADIUS) { this.State.LinearVelocity = Vector3.zero; ai.Linear = Vector3.zero; return(ai); } if (distance > SLOW_RADIUS) { targetSpeed = State.MaxLinearVelocity.magnitude; } else { targetSpeed = State.MaxLinearVelocity.magnitude * (distance / SLOW_RADIUS); } targetVelocity = desired_vector.normalized * targetSpeed; ai.Linear = (targetVelocity - State.LinearVelocity) / TIME_TO_TARGET; if (ai.Linear.magnitude > this.State.MaxLinearAcceleration) { ai.Linear = ai.Linear.normalized * this.State.MaxLinearAcceleration; } return(ai); }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; foreach(Transform t in Targets){ Vector3 direction = (trans.position - t.position).normalized; float distance = direction.magnitude; if(distance < THRESHOLD){ float strength = DECAY * distance * distance; if(State.MaxLinearAcceleration < strength) strength = State.MaxLinearAcceleration; ai.Linear += strength * direction; } } //Debug.DrawLine(trans.position, trans.position + 5*ai.Linear, Color.yellow); return ai; }
// Update is called once per frame void Update() { //RUN BEHAVIOURS AIDynamic movement = new AIDynamic(); movement = RunBehaviours(); //UPDATE POSITION PositionUpdate(movement); //ANIMATION animator.SetFloat("velocity", state.LinearVelocity.magnitude); if (state.LinearVelocity.magnitude > 0.1f) { animator.speed = state.LinearVelocity.magnitude / state.MaxLinearVelocity.magnitude; } else { animator.speed = 1; } //TOROIDAL PositionWrap(); }
private AIDynamic RunBehaviours(){ AIDynamic movement = new AIDynamic(); AIDynamic avoidDyn = new AIDynamic(); //Iterate through behaviours foreach(AIBehaviour b in behaviours){ AIDynamic dyn = b.GetDynamics(); movement.Angular += dyn.Angular * b.Weight; movement.Linear += dyn.Linear * b.Weight; if(b.BehaviourType == AIBehaviourType.ObjectAvoid || b.BehaviourType == AIBehaviourType.CollisionAvoid) avoidDyn.Linear += dyn.Linear * b.Weight * 5f; } if(avoidDyn.Linear.magnitude > 0){ movement.Linear = avoidDyn.Linear; } return movement; }
public override AIDynamic GetDynamics(){ AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; if(State.LinearVelocity.magnitude < 0.3f) return ai; bool hit1 = false; bool hit2 = false; bool hit3 = false; Vector3 ray = State.LinearVelocity.normalized; Vector3 ray_left = Quaternion.AngleAxis(-20, Vector3.up) * ray; Vector3 ray_right = Quaternion.AngleAxis(20, Vector3.up) * ray; RaycastHit ray_info1; //left RaycastHit ray_info2 ; //middle RaycastHit ray_info3; //right RaycastHit min_hit = new RaycastHit(); min_hit.distance = RAYLENGTH + 1f; if(Physics.Raycast(new Ray(trans.position, ray_left), out ray_info1, WHISKER)){ min_hit = ray_info1; hit1 = true; } if(Physics.Raycast(new Ray(trans.position, ray), out ray_info2, RAYLENGTH) && ray_info2.distance < min_hit.distance){ min_hit = ray_info2; hit2 = true; } if(Physics.Raycast(new Ray(trans.position, ray_right), out ray_info3, WHISKER) && ray_info3.distance < min_hit.distance){ min_hit = ray_info3; hit3 = true; } Debug.DrawLine (trans.position, trans.position + ray_left * WHISKER, Color.blue); Debug.DrawLine (trans.position, trans.position + ray * RAYLENGTH, Color.cyan); Debug.DrawLine (trans.position, trans.position + ray_right * WHISKER, Color.blue); if(hit2 && !(hit1 || hit3)){ Vector3 perm_target = State.Target; State.Target = trans.position + ray_right * 4f; ai = seeker.GetDynamics(); State.Target = perm_target; return ai; } else if(hit1 || hit2 || hit3){ Vector3 perm_target = State.Target; Vector3 normal = min_hit.normal * MARGIN; State.Target = min_hit.point + normal; ai = seeker.GetDynamics(); State.Target = perm_target; return ai; } else return ai; }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; if (State.LinearVelocity.magnitude < 0.3f) { return(ai); } bool hit1 = false; bool hit2 = false; bool hit3 = false; Vector3 ray = State.LinearVelocity.normalized; Vector3 ray_left = Quaternion.AngleAxis(-20, Vector3.up) * ray; Vector3 ray_right = Quaternion.AngleAxis(20, Vector3.up) * ray; RaycastHit ray_info1; //left RaycastHit ray_info2; //middle RaycastHit ray_info3; //right RaycastHit min_hit = new RaycastHit(); min_hit.distance = RAYLENGTH + 1f; if (Physics.Raycast(new Ray(trans.position, ray_left), out ray_info1, WHISKER)) { min_hit = ray_info1; hit1 = true; } if (Physics.Raycast(new Ray(trans.position, ray), out ray_info2, RAYLENGTH) && ray_info2.distance < min_hit.distance) { min_hit = ray_info2; hit2 = true; } if (Physics.Raycast(new Ray(trans.position, ray_right), out ray_info3, WHISKER) && ray_info3.distance < min_hit.distance) { min_hit = ray_info3; hit3 = true; } Debug.DrawLine(trans.position, trans.position + ray_left * WHISKER, Color.blue); Debug.DrawLine(trans.position, trans.position + ray * RAYLENGTH, Color.cyan); Debug.DrawLine(trans.position, trans.position + ray_right * WHISKER, Color.blue); if (hit2 && !(hit1 || hit3)) { Vector3 perm_target = State.Target; State.Target = trans.position + ray_right * 4f; ai = seeker.GetDynamics(); State.Target = perm_target; return(ai); } else if (hit1 || hit2 || hit3) { Vector3 perm_target = State.Target; Vector3 normal = min_hit.normal * MARGIN; State.Target = min_hit.point + normal; ai = seeker.GetDynamics(); State.Target = perm_target; return(ai); } else { return(ai); } }
public override AIDynamic GetDynamics() { AIDynamic ai = new AIDynamic(); ai.Linear = Vector3.zero; ai.Angular = 0; float shortestTime = float.PositiveInfinity; Transform firstTarget = null; float firstMinSeparation = 0; float firstDistance = 0; Vector3 firstRelativePos = Vector3.zero; Vector3 firstRelativeVel = Vector3.zero; foreach (Transform t in Targets) { Vector3 relativePos = trans.position - t.position; Vector3 relativeVel = t.gameObject.GetComponent <TrooperAI>().GetVelocity() - State.LinearVelocity; float relativeSpeed = relativeVel.magnitude; float timeToCollision = Vector3.Dot(relativePos, relativeVel) / (relativeSpeed * relativeSpeed); float distance = relativePos.magnitude; if (distance > THRESHOLD || t.gameObject.GetComponent <TrooperAI>().GetVelocity().magnitude < .1f) { continue; } float minSeparation = distance - relativeSpeed * shortestTime; if (minSeparation > 2 * RADIUS) { continue; } if ((timeToCollision > 0) && timeToCollision < shortestTime) { shortestTime = timeToCollision; firstTarget = t; firstMinSeparation = minSeparation; firstDistance = distance; firstRelativePos = relativePos; firstRelativeVel = relativeVel; } } if (firstTarget != null) { Debug.DrawLine(trans.position, firstTarget.position, Color.red); } if (!firstTarget) { return(ai); } Vector3 finalRelativePos; if (firstMinSeparation <= 0 || firstDistance < 2 * RADIUS) { finalRelativePos = trans.position - firstTarget.position; } else { finalRelativePos = firstRelativePos + firstRelativeVel * shortestTime; } ai.Linear = finalRelativePos.normalized * State.MaxLinearAcceleration; Debug.DrawLine(this.trans.position, this.trans.position + ai.Linear * 4, Color.cyan); return(ai); }
private void PositionUpdate(AIDynamic motion){ //Set linear velocity to max if(state.LinearVelocity.magnitude > state.MaxLinearVelocity.magnitude) state.LinearVelocity = state.LinearVelocity.normalized * state.MaxLinearVelocity.magnitude; //Set angular velocity to max if(Mathf.Abs (state.AngularVelocity) > Mathf.Abs (state.MaxAngularVelocity)) state.AngularVelocity = (state.AngularVelocity / Mathf.Abs (state.AngularVelocity)) * state.MaxAngularVelocity; //Update position and linear velocity this.transform.position += state.LinearVelocity * Time.deltaTime; state.LinearVelocity += motion.Linear * Time.deltaTime; //Update orientation and angular velocity Vector3 rotation = this.transform.rotation.eulerAngles; rotation.y += state.AngularVelocity * Time.deltaTime; this.transform.rotation = Quaternion.Euler (rotation); state.AngularVelocity += motion.Angular * Time.deltaTime; }