Beispiel #1
0
    void StateDesire()
    {
        desireStated = true;

        GameManager.Instance.CheckForFood();

        if (!hasHome)
        {
            currentDesire = HumanDesire.HOUSING;
        }

        switch (currentDesire)
        {
        case HumanDesire.FOOD:      // This unit is hungry or out of food.
            desireClouds[0].SetActive(true);
            break;

        case HumanDesire.HOUSING:       // This unit has no housing or doesn't have enough room to build one.
            desireClouds[1].SetActive(true);
            break;

        case HumanDesire.TO_ASCEND:
            Debug.Log("I am ready to ascend, allmighty one.");
            // set ascension cloud active.
            break;
        }
    }
Beispiel #2
0
    // Update is called once per frame
    public virtual void Update()
    {
        inFront   = humanHips.position + (humanHips.transform.forward * 6f);
        inFront.y = 33f;

        if (isAscended)
        {
            halo.SetActive(true);
        }
        else
        {
            halo.SetActive(false);
        }

        if (!_wasInvoked)
        {
            StartCoroutine(IncreaseFaithOverTime(false));    // Continually gain levels of faith.
        }
        if (!humanAnimator.hasCollapsed && isGrounded)
        {
            AddForce();
        }

        if (readyToAscend)
        {
            currentDesire = HumanDesire.TO_ASCEND;
        }

        if (happiness < 15)
        {
            isDepressed = true;
        }

        if (humanAnimator.hasCollapsed)
        {
            currentState = HumanState.RECOVER;
        }

        if (currentState == HumanState.IDLE) // Human wanders about when idle.
        {
            Idling();
        }

        if (currentState == HumanState.PRAYING)
        {
            Debug.Log("Praying");
            MoveToDestination(2);

            if (!desireStated && atShrine)
            {
                StateDesire();
            }
        }

        #region Neutral AI
        if (!hasFaith)
        {
            ConvertToNeutral();
            // The neutral human prays at a different shrine every night. The first human to please it will convert it to their side.
            if ((Sun.Instance.rotation < 90 && Sun.Instance.rotation >= 0) || (Sun.Instance.rotation > 270 && Sun.Instance.rotation <= 360))
            {
                foreach (GameObject cloud in desireClouds)
                {
                    cloud.SetActive(false);
                }

                if (timesSwitched >= 5)
                {
                    var deathParticles = particles[2];
                    deathParticles.Play();        // Play the death particle.
                    if (deathParticles.IsAlive()) // Wait for the particle system to finish playing;
                    {
                        gameObject.SetActive(false);
                    }
                }

                // During the day the only thing it does is switch the shrine it will pray at during the upcoming night, and idle about.
                currentState = HumanState.IDLE;

                if (!shrineSwitched)
                {
                    if (switchShrine == false)
                    {
                        GameManager.Instance.TeamOneNeutralHumans.Remove(gameObject);
                        GameManager.Instance.TeamTwoNeutralHumans.Add(gameObject);
                        switchShrine = true;
                    }
                    else
                    {
                        GameManager.Instance.TeamTwoNeutralHumans.Remove(gameObject);
                        GameManager.Instance.TeamOneNeutralHumans.Add(gameObject);
                        switchShrine = false;
                    }

                    timesSwitched++;
                    shrineSwitched = true;
                }
            }

            if (Sun.Instance.rotation >= 90 && Sun.Instance.rotation <= 180)
            {
                // Then, at nighttime, the human will pray as normal together with the non-neutral humans, in an attempt to get what it desires.
                currentState   = HumanState.PRAYING;
                shrineSwitched = false;
            }
        }
        #endregion  // Idling doesnt work?

        #region Human AI
        else
        {
            #region State Declaration
            if ((Sun.Instance.rotation < 90 && Sun.Instance.rotation >= 0) || (Sun.Instance.rotation > 270 && Sun.Instance.rotation <= 360) && !isDepressed)
            {
                isDayTime = true;
                if (!statsTweaked)
                {
                    TweakStats();
                }

                else if (!hasHome)
                {
                    currentState = HumanState.BUILDING_HOUSE;
                }

                else if (!isDepressed && hasHome && currentDesire != HumanDesire.FOOD)
                {
                    currentState = HumanState.BUILDING_MONUMENT;
                }

                else
                {
                    currentState = HumanState.IDLE;
                }
            }

            if (Sun.Instance.rotation >= 90 && Sun.Instance.rotation <= 180 && !isDepressed)
            {
                isDayTime    = false;
                currentState = HumanState.PRAYING;
            }
            else if (Sun.Instance.rotation > 180 && Sun.Instance.rotation <= 270 && !isDepressed)
            {
                isDayTime    = false;
                currentState = HumanState.SLEEPING;
            }

            // Depressed states (Human becomes depressed if the happiness value drops below 15).
            if (humanAnimator.hasCollapsed && isDepressed)
            {
                currentState = HumanState.RECOVER;
            }

            else if (Sun.Instance.rotation >= 90 && Sun.Instance.rotation <= 180 && isDepressed)
            {
                currentState = HumanState.PRAYING;
            }

            else if (isDepressed)
            {
                currentState = HumanState.IDLE;
            }

            #endregion

            #region State Machine Day
            if (isDayTime)
            {
                Debug.Log("dayTime");

                switch (currentState)
                {
                case HumanState.RECOVER:
                    // Do nothing untill recovered.
                    break;


                case HumanState.BUILDING_HOUSE:       // The human builds a house. secondsSinceLastBuild value is a debug value, change when ready.
                    int layer = 17;
                    int mask  = 1 << layer;

                    Collider[] trees = Physics.OverlapSphere(humanHips.position, 1.5f, mask);

                    if (!buildingHouse && isGrounded)
                    {
                        var newPos = humanHips.position + (humanHips.transform.forward * 6f);      // Instantiate the collision checker before checking if there is enough space.
                        newPos.y = 36.5f;
                        checkHouse.transform.position = newPos;
                        checkHouse.SetActive(true);

                        if (enoughSpaceToBuild)
                        {
                            buildingHouse = true;
                            newPos.y      = 32.34402f;

                            var humanID = GetComponent <NetworkIdentity>().netId;
                            CmdSpawnHouse(newPos, isServer, humanID);     // Spawn a house through the server

                            checkHouse.SetActive(false);
                        }
                        else
                        {
                            Idling();
                        }
                    }

                    if (gatheredWood < 30 && buildingHouse)
                    {
                        // Chopping
                        if (!hasWood)
                        {
                            MoveToDestination(1);       // Move to the tree first.

                            foreach (Collider tree in trees)
                            {
                                //tree.GetComponentInParent<Tree>().state = Tree.States.CHOPPED;   // Then destroy all nearby trees

                                var obj = tree.GetComponentInParent <Tree>();
                                var ID  = obj.GetComponent <NetworkIdentity>().netId;
                                CmdChopTreeServer(ID);     // Send the networked variables to the server

                                gatheredWood += 10;
                                hasWood       = true;
                            }
                        }
                        else
                        {
                            rotationReference.LookAt(_house.transform.position);
                            var _houseRot = rotationReference.rotation;
                            _houseRot.x = 0f;
                            _houseRot.z = 0f;

                            movementParent.rotation = _houseRot;      // Then, if the player has chopped a tree, move (look at) to the house that he's building

                            if (Vector3.Distance(humanHips.position, _house.transform.position) <= 2f)
                            {
                                hasWood = false;
                                // Advance the building to the next stage
                            }
                        }
                    }
                    else if (gatheredWood >= 30 && buildingHouse)
                    {
                        MoveToDestination(4);

                        if (Vector3.Distance(humanHips.position, _house.transform.position) <= 2f)
                        {
                            var obj = _house.GetComponentInParent <House>();
                            var id  = obj.GetComponent <NetworkIdentity>().netId;
                            obj.CmdSendVarServer(id, true);

                            humanHips.position = _house.GetComponentInParent <House>().doorPosition.position;     // Set human to entrance position

                            // Reset the human's speed
                            for (int i = 0; i < humanAnimator.bones.Length; i++)
                            {
                                humanAnimator.bones[i].GetComponent <Rigidbody>().velocity = Vector3.zero;
                            }

                            // Assign standard data & reset bools
                            _house.layer  = 16;
                            gatheredWood -= 30;
                            buildingHouse = false;
                            hasWood       = false;
                            hasHome       = true;

                            if (currentDesire == HumanDesire.HOUSING)
                            {
                                currentDesire = HumanDesire.NOTHING;
                            }
                        }
                    }
                    break;

                case HumanState.BUILDING_MONUMENT:
                    if (!isDepressed)
                    {
                        MoveToDestination(5);
                    }

                    BuildMonument();
                    break;
                }
            }
            #endregion

            #region "State Machine" Night
            if (!isDayTime)
            {
                if (currentState == HumanState.SLEEPING)
                {
                    Debug.Log("Sleeping");

                    desireStated = false;
                    statsTweaked = false;

                    foreach (GameObject cloud in desireClouds)
                    {
                        cloud.SetActive(false);  // Deactivate all the desire clouds.
                    }
                    if (_house != null)
                    {
                        MoveToDestination(3);
                    }
                    else
                    {
                        Idling();
                    }
                }
            }
            #endregion
        }
        #endregion
    }