Esempio n. 1
0
    // Update is called once per frame
    void FixedUpdate()
    {
        //Raycast out to see if there is a car in front
        RaycastHit hit;
        //figure out the current view angle
        Vector3 lookDirection = Quaternion.Euler(new Vector3(0, startAngle_ + curAngle_ - (lookAngle_ * 0.5f))) * transform.forward;

        if (error_ && error_.GetDistracted())
        {
            sweep_ = false;
        }

        if (sweep_)
        {
            curAngle_ += lookStepAmount_;
            if (curAngle_ > lookAngle_)
            {
                curAngle_ = 0;
            }
        }

        Ray ray = new Ray(transform.position + transform.forward, (transform.forward + lookDirection.normalized).normalized);

        float lookAhead = Mathf.Clamp(body_.velocity.magnitude, 1, lookAheadMultiplier_);

        Debug.DrawLine(transform.position, transform.position + (transform.forward + lookDirection.normalized).normalized * visionDistance_ * lookAhead, Color.blue);

        objectAhead_ = Physics.Raycast(ray, out hit, visionDistance_ * lookAhead);
        if (objectAhead_ && hit.collider.tag == "TrafficLight")
        {
            objectAhead_ = false;
        }

        bool  stopping           = car_.GetState() == CarState.CS_PARKING || car_.GetState() == CarState.CS_DEPARKING;
        float stoppingMultiplier = stopping ? car_.GetFineMovementMutliplier() : 1.0f;

        //check that the ray hit something
        if (hit.collider && (hit.collider.tag == "Car" || hit.collider.tag == "Player"))
        {
            //check if there's a car coming towards them at speed
            if (hit.rigidbody && hit.rigidbody.velocity.magnitude > car_.GetMaxSpeed() * 0.25f)
            {
                if (IsFacing(hit.collider.gameObject))
                {
                    if (purpose_.enabled)
                    {
                        purpose_.TestImpatience();//SoundHorn();
                    }
                }
            }

            if (hit.distance < stoppingDistance_ * stoppingMultiplier && hit.distance > stoppingDistance_ * stoppingMultiplier * 0.5f)
            {
                car_.SetState(CarState.CS_STOPPING);
                //check if the car has just collided with another
                if (car_.FollowingTarget())
                {
                    //check if this car is moving faster than the other car
                    if (body_.velocity.magnitude > hit.collider.GetComponent <Rigidbody>().velocity.magnitude)
                    {
                        car_.Brake(hit.distance / stoppingDistance_);
                    }
                    if (IsFacing(hit.collider.gameObject))
                    {
                        car_.Avoid(hit.collider.gameObject);
                    }
                }
                else
                {
                    car_.Accelerate(-0.5f);
                }
            }
            else if (hit.distance < stoppingDistance_ * stoppingMultiplier * 0.5f)
            {
                //stop following targets for the next frame
                car_.Wait(Time.deltaTime);
                car_.Brake();
            }
            else
            {
                car_.SetState(CarState.CS_MOVING);
                car_.Accelerate(0);
            }
        }
        else
        {
            sweep_ = true;
        }
        if (hit.collider && hit.collider.tag == "TrafficLight")
        {
            //make sure the traffic light is facing the car
            if (IsFacing(hit.collider.gameObject))
            {
                if (hit.collider.gameObject.GetComponent <TrafficLight>().GetSignal() == Signals.S_STOP && hit.distance < stoppingDistance_)
                {
                    car_.Wait(Time.deltaTime);
                    car_.Brake(hit.distance / stoppingDistance_);
                    car_.SetState(CarState.CS_STOPPING);
                }
                if (hit.collider.gameObject.GetComponent <TrafficLight>().GetSignal() == Signals.S_GO)
                {
                    car_.SetState(CarState.CS_MOVING);
                }
            }
        }
        //check if sweeping should be stopped
        if (hit.collider && ((hit.collider.tag == "Car" || hit.collider.tag == "Player") || (hit.collider.tag == "TrafficLight" && IsFacing(hit.collider.gameObject))))
        {
            sweep_ = false;
        }
        else
        {
            sweep_ = true;
            car_.SetState(CarState.CS_MOVING);
        }

        if (!objectAhead_)
        {
            if (prevObjectAhead_)
            {
                if (error_ && error_.enabled)
                {
                    car_.Wait(error_.GetReactionTime());
                }
            }
        }
        prevObjectAhead_ = objectAhead_;
    }