Пример #1
0
        /// <summary>
        /// Function to select a target for the tank.
        /// It requires at least 2 buildings from a neighbourhood to be eligible.
        /// </summary>
        /// <returns></returns>
        private IVisualizedObject SelectTarget()
        {
            List <NeighbourhoodModel> randomNeighbourhoodQuery = CityManager.Instance.GameModel.Neighbourhoods
                                                                 .Where(neighbourhoodModel =>
                                                                        neighbourhoodModel.VisualizedObjects.Count(visualizedObject =>
                                                                                                                   visualizedObject is VisualizedBuildingModel) >= _minimumBuildings).ToList();

            if (TeamManager.Instance.SelectedTeam != null)
            {
                randomNeighbourhoodQuery =
                    randomNeighbourhoodQuery.Where(x => x.Team == TeamManager.Instance.SelectedTeam).ToList();
            }

            // No target found. Tank is probably going in standby mode now.
            if (randomNeighbourhoodQuery.Count == 0)
            {
                _foundTargets = false;
                return(null);
            }

            // Pick a random neighbourhood from the list
            NeighbourhoodModel randomNeighbourhoodModel =
                randomNeighbourhoodQuery.PickRandom();

            // We found a target and it's a building. Return the target.
            IVisualizedObject obj = randomNeighbourhoodModel.VisualizedObjects
                                    .First(visualizedObject =>
                                           visualizedObject.GameObject != null && visualizedObject is VisualizedBuildingModel);

            _foundTargets = true;
            return(obj);
        }
Пример #2
0
        /// <summary>
        /// Function to add a new visualized object to the game.
        /// </summary>
        /// <param name="neighbourhoodName"></param>
        /// <param name="newVisualizedObject"></param>
        private void AddBuilding(string neighbourhoodName, IVisualizedObject newVisualizedObject)
        {
            // We only care about buildings in this manager
            if (!(newVisualizedObject is IVisualizedBuilding))
            {
                return;
            }

            NeighbourhoodModel neighbourhood =
                GameModel.Neighbourhoods.SingleOrDefault(x => x.Name == neighbourhoodName);

            if (neighbourhood == null)
            {
                Debug.LogWarning($"Adding object went wrong! Neighbourhood {neighbourhoodName} does not exists!");
                return;
            }

            // Check if there are buildings with the same identifier.
            List <IVisualizedBuilding> existingVisualizedObjects = neighbourhood.VisualizedObjects
                                                                   .OfType <IVisualizedBuilding>().Where(x =>
                                                                                                         x.Identifier == newVisualizedObject.Identifier)
                                                                   .ToList();

            // Destroy every building that has the same identifier.
            foreach (IVisualizedBuilding visualizedObject in existingVisualizedObjects)
            {
                GridManager.Instance.DestroyBuilding(visualizedObject);
                neighbourhood.VisualizedObjects.Remove(visualizedObject);
            }

            // TODO: We actually need to check if there are destroyed grass tiles, but haven't found a solution for it yet.
            neighbourhood.VisualizedObjects.Add(newVisualizedObject);
            GridManager.Instance.DestroyBlock(neighbourhood, false);
            GridManager.Instance.SpawnNeighbourhood(neighbourhood);
        }
        /// <summary>
        /// Function to highlight a neighbourhood when clicked.
        /// </summary>
        /// <param name="clickedObject"></param>
        /// <param name="showInfoPanel"></param>
        public void HighlightNeighbourhood(GameObject clickedObject, bool showInfoPanel = true)
        {
            if (showInfoPanel)
            {
                string neighbourhoodName = clickedObject.name.Replace("neighbourhood-", "");
                string infoText          = $"Neighbourhood: {neighbourhoodName}";
                try
                {
                    if (clickedObject.CompareTag("Building"))
                    {
                        NeighbourhoodModel neighboorhoud =
                            CityManager.Instance.GameModel.Neighbourhoods.SingleOrDefault(
                                (x => x.Name == neighbourhoodName));
                        if (neighboorhoud != null)
                        {
                            IVisualizedObject visualizedObject =
                                neighboorhoud.VisualizedObjects.SingleOrDefault(x => x.GameObject == clickedObject);
                            _selectedObject = visualizedObject;
                            string days = neighboorhoud.Age == 1 ? "day" : "days";
                            infoText =
                                $"Neighbourhood: {neighbourhoodName}\r\nAge: {neighboorhoud.Age} {days}";
                            VisualLayerModel selectedLayer = LayerManager.Instance.SelectedLayer;
                            if (visualizedObject is IVisualizedBuilding visualizedBuilding)
                            {
                                DestroyButton.SetActive(true);
                                OpenButton.SetActive(true);
                                if (selectedLayer != null)
                                {
                                    // Only enable destroy button for buildings
                                    infoText =
                                        $"Neighbourhood: {neighbourhoodName}\r\n{selectedLayer.Name.Replace("Layer", "")}: {visualizedBuilding.LayerValues[selectedLayer.Name]} / {neighboorhoud.LayerValues.Single(x => x.LayerType == selectedLayer.Name).MaxValue} ";
                                }
                            }
                        }
                    }
                }
                catch (Exception e)
                {
                    Debug.LogError($"[OnObjectClickManager] {e.Message}");
                }
                finally
                {
                    InfoPanel.GetComponentInChildren <TMP_Text>().text = infoText;
                    InfoPanel.gameObject.SetActive(true);
                }
            }

            Renderer[] renderComponents = clickedObject.GetComponentsInChildren <Renderer>();
            foreach (Renderer renderComponent in renderComponents)
            {
                _clickedObjects.Add(renderComponent, renderComponent.material.color);
                renderComponent.material.color = Color.green;
            }
        }
Пример #4
0
 /// <summary>
 /// Function to set the target of the tank
 /// </summary>
 /// <param name="target">The GameObject of the target should not be null</param>
 public void SetTarget(IVisualizedObject target)
 {
     IsStandby      = false;
     Target         = target;
     _agent.enabled = true;
     if (_agent.isActiveAndEnabled && target.GameObject != null)
     {
         _agent.isStopped = false;
         _agent.SetDestination(target.GameObject.transform.position);
         HasTarget = true;
         ChaosManager.Instance.TankTargetChanged.Invoke(target.GameObject.name.Replace("neighbourhood-", ""));
     }
 }
Пример #5
0
        /// <summary>
        /// Function to search for a neighbourhood.
        /// </summary>
        /// <param name="serviceName"></param>
        public void SearchNeighbourhood(string serviceName)
        {
            NeighbourhoodModel search = CityManager.Instance.GameModel.Neighbourhoods
                                        .FirstOrDefault(x => x.Name.Contains(serviceName));
            IVisualizedObject randomContainer = search?.VisualizedObjects.FirstOrDefault(x => x.GameObject != null);

            if (randomContainer == null || randomContainer.GameObject == null)
            {
                return;
            }
            CameraController.Instance.FocusOnTarget(randomContainer.GameObject.transform.position);
            OnObjectClickManager.Instance.ResetHighlighting();
            OnObjectClickManager.Instance.HighlightNeighbourhood(randomContainer.GameObject);
        }
        // Update is called once per frame
        void Update()
        {
            // Check if left mouse button is pressed and if there has not been clicked on an UI element
            if (!Input.GetMouseButtonDown(0) ||
                UnityEngine.EventSystems.EventSystem.current.IsPointerOverGameObject())
            {
                return;
            }


            // Check if we have a hit on a prefab with the active camera
            bool hit = Physics.Raycast(CameraManager.Instance.ActiveCamera.ScreenPointToRay(Input.mousePosition),
                                       out RaycastHit hitInfo,
                                       _maxDistance,
                                       _defaultLayer);

            // We reset the highlighting
            ResetHighlighting();
            _selectedObject = null;
            if (hit)
            {
                DestroyButton.SetActive(false);
                OpenButton.SetActive(false);
                GameObject targetObject = hitInfo.transform.gameObject;
                // Check if the object we hit has a parent, since buildings, vehicle etc don't have parents but they do have children
                if (hitInfo.transform.parent != null)
                {
                    targetObject = hitInfo.transform.parent.gameObject;
                }

                if ((targetObject.CompareTag("Building") || targetObject.CompareTag("DestroyedBuilding")) &&
                    targetObject.name.StartsWith("neighbourhood-"))
                {
                    HighlightNeighbourhood(targetObject);
                }
                else if (targetObject.CompareTag("Tank") || targetObject.CompareTag("Vehicle"))
                {
                    HighlightVehicle(targetObject);
                }
                else
                {
                    InfoPanel.gameObject.SetActive(false);
                }
            }
            else
            {
                InfoPanel.gameObject.SetActive(false);
            }
        }
        /// <summary>
        /// Function that is executed when a button is pressed.
        /// The player will focus with the camera on the first building of a neighbourhood
        /// </summary>
        /// <param name="neighbourhoodModel"></param>
        private static void OnButtonClick(NeighbourhoodModel neighbourhoodModel)
        {
            IVisualizedObject visualizedBuilding =
                neighbourhoodModel.VisualizedObjects.FirstOrDefault(x =>
                                                                    x is IVisualizedBuilding && x.GameObject != null);

            if (visualizedBuilding == null)
            {
                return;
            }

            CameraController.Instance.FocusOnTarget(visualizedBuilding.GameObject.transform.position);
            OnObjectClickManager.Instance.ResetHighlighting();
            OnObjectClickManager.Instance.HighlightNeighbourhood(visualizedBuilding.GameObject);
        }
Пример #8
0
 /// <summary>
 /// Check if the tank still has a target. Otherwise pick a new target.
 /// It won't check for a new target is the tank is in stand-by.
 /// </summary>
 void LateUpdate()
 {
     // We need to pick a new target for the tank here
     if (_tankNavigator != null && _tankNavigator.Target == null && !_tankNavigator.IsStandby)
     {
         IVisualizedObject target = SelectTarget();
         if (target == null || !_foundTargets)
         {
             _tankNavigator.SetStandby(true);
         }
         else
         {
             _tankNavigator.SetTarget(target);
         }
     }
 }
Пример #9
0
        /// <summary>
        /// Function to kill a object through the API.
        /// </summary>
        /// <returns></returns>
        public IEnumerator KillVisualizedObject(IVisualizedObject building, bool force = false)
        {
            using (UnityWebRequest webRequest =
                       UnityWebRequest.Delete($"{_gameEndpoint}?identifier={building.Identifier}&force={force}"))
            {
                // Request and wait for the desired page.
                webRequest.timeout = 10;
                yield return(webRequest.SendWebRequest());

                if (webRequest.isNetworkError || webRequest.isHttpError)
                {
                    Debug.LogError($"Webrequest failed! Error: {webRequest.error}");
                }

                yield return(null);
            }

            yield return(null);
        }
Пример #10
0
        private static NeighbourhoodModel ParseNeighbourhoodModel(JSONNode jsonNode)
        {
            NeighbourhoodModel neighbourhood = new NeighbourhoodModel();

            neighbourhood.Name = jsonNode["name"];
            neighbourhood.Age  = jsonNode["daysOld"];
            neighbourhood.Team = jsonNode["team"];

            List <LayerValueModel> visualLayers = jsonNode["layerValues"].Children.Select(visualLayer =>
                                                                                          new LayerValueModel
            {
                MinValue  = visualLayer["minValue"],
                LayerType = visualLayer["layerType"],
                MaxValue  = visualLayer["maxValue"]
            }).ToList();

            neighbourhood.LayerValues = visualLayers;

            // Loop through all visualized objects (buildings, traffic for later, etc)
            foreach (JSONNode visualizedObjectJson in jsonNode["visualizedObjects"].Children)
            {
                Dictionary <string, double> layerValues = new Dictionary <string, double>();
                foreach (KeyValuePair <string, JSONNode> layerValue in visualizedObjectJson["layerValues"])
                {
                    layerValues.Add(layerValue.Key, layerValue.Value);
                }

                IVisualizedObject visualizedObject =
                    VisualizedObjectFactory.Build(
                        visualizedObjectJson["type"],
                        visualizedObjectJson["size"],
                        layerValues, visualizedObjectJson["identifier"]);


                neighbourhood.VisualizedObjects.Add(visualizedObject);
            }

            return(neighbourhood);
        }
Пример #11
0
        /// <summary>
        /// Function to process vehicle queue. Every vehicle has a navigator <see cref="VehicleNavigator"/>.
        /// The path has already been set in the <see cref="SpawnVehicle(VisualizedVehicleModel)"/> function
        /// We call the <see cref="VehicleNavigator.StartPathFinding"/> function.
        /// This function will enable all the renderers, making the object visible and the vehicle starts to navigate
        /// As soon as a vehicle reached their destination it will drive back to the start position of the vehicle
        /// </summary>
        /// <returns></returns>
        private IEnumerator ProcessQueue()
        {
            while (true)
            {
                while (_vehicleQueue.Count > 0)
                {
                    // Grab the vehicle from the queue
                    Vehicle v = _vehicleQueue.Dequeue();
                    // Check if in the main time the neighbourhood is not de-spawned together with the vehicle
                    if (v.VehicleGameObject != null && v.NeighbourhoodModel != null)
                    {
                        // Start the path finding of the vehicle
                        v.VehicleGameObject.GetComponent <VehicleNavigator>().StartPathFinding();
                        // Fire the event that we spawned a vehicle
                        VehicleSpawned?.Invoke(v);

                        // Check if the vehicle is already in the list of the neighbourhood
                        IVisualizedObject vehicle = v.NeighbourhoodModel.VisualizedObjects.SingleOrDefault(x =>
                                                                                                           x is VisualizedVehicleModel && x.Identifier == v.VehicleModel.Identifier);
                        // If vehicle is not in the list of visualized objects of a neighbourhood, add it
                        if (vehicle == null)
                        {
                            v.VehicleModel.GameObject = v.VehicleGameObject;
                            v.NeighbourhoodModel.VisualizedObjects.Add(v.VehicleModel);
                        }
                        else
                        {
                            vehicle.GameObject = v.VehicleGameObject;
                        }
                    }

                    yield return(new WaitForSeconds(0.3f));
                }

                yield return(new WaitForSeconds(0.1f));
            }
        }