Esempio n. 1
0
        public List <WorldPlaceDataDetails> GetWorldPlaceDataDetails()
        {
            List <WorldPlaceDataDetails> resultList = new List <WorldPlaceDataDetails>();
            WorldPlaceData placeData;

            for (int y = 0; y < this.MapHeight; y++)
            {
                for (int x = 0; x < this.MapWidth; x++)
                {
                    placeData = _worldPlaces[x, y];
                    if (placeData == null)
                    {
                        continue;
                    }

                    WorldPlaceDataDetails result = new WorldPlaceDataDetails()
                    {
                        WorldPosX = placeData.WorldPosX,
                        WorldPosY = placeData.WorldPosY,
                        WmId      = placeData.WmId,
                        PlaceType = (int)placeData.Type,
                        PlaceName = placeData.PlaceName
                    };

                    resultList.Add(result);
                }
            }

            return(resultList);
        }
        public WorldDetailsCmdBuilder(bool isListConfirmation, WorldPlaceDataDetails details = null)
        {
            if (!isListConfirmation && details == null)
            {
                throw new Exception("WorldDetailsCmdBuilder - detail object cannot be NULL for no list confirmation!");
            }

            _details            = details;
            _isListConfirmation = isListConfirmation;
        }
Esempio n. 3
0
        public void AddOrUpdateWorldPlaceDetails(WorldPlaceDataDetails details)
        {
            bool found = false;

            lock (_dataLock)
            {
                for (int i = 0; i < _worldPlaceDetailsList.Count; i++)
                {
                    if (_worldPlaceDetailsList[i].WmId == details.WmId)
                    {
                        _worldPlaceDetailsList[i] = details;
                        found = true;
                        break;
                    }
                }

                if (!found)
                {
                    _worldPlaceDetailsList.Add(details);
                }
            }
        }
        public bool Execute()
        {
            bool executed = false;

            try
            {
                if (_cmdElements.Length < 2)
                {
                    throw new Exception("wrong count of elements");
                }

                if (_cmdElements[1].Equals("position", GlobalData.InputDataStringComparison))
                {
                    string jsonTxt = _rawText.Substring($"{_keyWord} position".Length);
                    WorldPlaceDataDetails details = JsonConvert.DeserializeObject <WorldPlaceDataDetails>(jsonTxt);
                    _gameStateDetails.AddOrUpdateWorldPlaceDetails(details);
                }
                else
                if (_cmdElements[1].Equals("endlist", GlobalData.InputDataStringComparison))
                {
                    _gameStateDetails.WorldPlaceDetailsListConfirmed = true;
                }
                else
                {
                    throw new Exception($"wrong second keyword [{_cmdElements[1]}]");
                }

                executed = true;
            }
            catch (Exception exception)
            {
                _chat.UpdateLog($"Cannot execute world place details command: {exception.Message}");
            }

            return(executed);
        }
Esempio n. 5
0
 public SandWmSectionBuilder(WorldPlaceDataDetails details, Camera camera)
 {
     _details = details;
     _camera  = camera;
 }
Esempio n. 6
0
        private async void HandleCharactersMovementAsync()
        {
            if (_movementHandlingInProgress)
            {
                _logger.UpdateLog("Character movement handling already started!");
                return;
            }

            _movementHandlingInProgress = true;
            _logger.UpdateLog("Game state handler - character movement handling started!");

            try
            {
                List <CharacterMovementDetails> movementDetailsListTemp = new List <CharacterMovementDetails>();
                CharacterData                  characterData;
                List <GeoDataElement>          geoDataList           = new List <GeoDataElement>();
                CharacterPositionUpdateDetails positionDetailsToSend = null;
                int count = 0;

                int  wmId;
                int  parentObjectId;
                bool isOnWorldMap;

                GeoDataValidationDetails geoDataValidationDetails = null;
                bool            geoMovementValid        = false;
                Point3 <double> lastValidMovementPoint  = new Point3 <double>(0, 0, 0);
                bool            exitPointFound          = false;
                Point3 <double> exitPosition            = null;
                double          lastTParamValue         = 0;
                int             timeArrivalMsIncomplete = 0;
                bool            worldMovingValid        = false;

                do
                {
                    #region Main list item removal
                    //MAIN LIST ITEM REMOVAL
                    lock (_movementDetailsLock)
                    {
                        count = _movementDetailsList.Count;

                        if (count > 0)
                        {
                            movementDetailsListTemp = _movementDetailsList.Clone();
                            foreach (CharacterMovementDetails item in _movementDetailsList)
                            {
                                item.Dispose();
                            }

                            _movementDetailsList.Clear();
                        }
                    }

                    #endregion

                    #region Interval handling
                    //INTERVAL HANDLING
                    if (count == 0)
                    {
                        await Task.Factory.StartNew(() => Thread.Sleep(GameStateHandler._movementHandlingTickMs));

                        continue;
                    }

                    #endregion

                    #region Movement details handling
                    //MOV. DETAILS HANDLING
                    foreach (CharacterMovementDetails movementDetails in movementDetailsListTemp)
                    {
                        if (geoDataList.Count > 0)
                        {
                            geoDataList.Clear();
                        }

                        if (movementDetails.CharId < 0)
                        {
                            _logger.UpdateLog("Movement details handling warning - character's ID less than 0!");
                            continue;
                        }

                        //characterData = await _characterInfo.GetCharacterByNameTaskStart(movementDetails.CharName);
                        characterData = await _characterInfo.GetCharacterByIdTaskStart(movementDetails.CharId);

                        if (characterData == null)
                        {
                            _logger.UpdateLog($"Movement details handling warning - character's ID [{movementDetails.CharId}] not found!");
                            continue;
                        }

                        wmId           = characterData.WmId;
                        parentObjectId = characterData.ParentObjectId;
                        isOnWorldMap   = characterData.IsOnWorldMap;

                        switch (movementDetails.Type)
                        {
                        case CharacterMovementDetails.MovementType.SwitchMovementType:
                        {
                            #region Local enter/exit point veryfication
                            //LOCAL ENTER/EXIT POINT VERYFICATION
                            exitPointFound = false;

                            if (characterData.IsOnWorldMap)
                            {
                                using (BoxedData geoBoxedData = await _geoDataInfo.GetLocalGeoDataOfExitElementsTaskStart(wmId, parentObjectId))
                                {
                                    geoDataList = (List <GeoDataElement>)geoBoxedData.Data;
                                    if (!String.IsNullOrEmpty(geoBoxedData.Msg))
                                    {
                                        _logger.UpdateLog(geoBoxedData.Msg);
                                    }
                                }

                                exitPosition = GeoDataValidator.GetRandomExitPosition(geoDataList);

                                if (exitPosition != null)
                                {
                                    exitPointFound = true;

                                    //PLACING CHARACTER ON ENTRY POINT
                                    characterData.MoveCharacterLocal
                                    (
                                        exitPosition.Copy(),
                                        exitPosition.Copy(),
                                        0
                                    );
                                }
                            }

                            #endregion

                            #region State change section
                            //STATE CHANGE SECTION

                            if (!exitPointFound && characterData.IsOnWorldMap)
                            {
                                _logger.UpdateLog($"Cannot find location exit point for character's ID [{movementDetails.CharId}] wm_id [{wmId}] parent object ID [{parentObjectId}]");
                                SendMessageToPlayer(movementDetails.CharId, "Error: cannot find entry point!");
                            }
                            else
                            {
                                characterData.IsOnWorldMap = !isOnWorldMap;
                                _logger.UpdateLog($"Movement type switched for character's ID [{movementDetails.CharId}] to {(characterData.IsOnWorldMap ? "world" : "local")} state");

                                positionDetailsToSend = new CharacterPositionUpdateDetails()
                                {
                                    MovementType       = (characterData.IsOnWorldMap ? "switchmap" : "switchlocal"),
                                    CharId             = movementDetails.CharId,
                                    OldLocationLocal   = characterData.CurrentLoc.Copy(),
                                    NewLocationLocal   = characterData.CurrentLoc.Copy(),
                                    TimeArrivalMsLocal = 0,
                                    OldLocationWorld   = characterData.CurrentWorldLoc.Copy(),
                                    NewLocationWorld   = characterData.CurrentWorldLoc.Copy()
                                };

                                if (characterData.IsOnWorldMap)
                                {
                                    SendMovementDetailsToCurrentPlayerAsync(positionDetailsToSend, movementDetails.CharId);
                                }

                                SendMovementDetailsToPlayersInLocationAsync(positionDetailsToSend, wmId, false, parentObjectId);
                            }

                            #endregion
                        }
                        break;

                        case CharacterMovementDetails.MovementType.Local:
                        {
                            #region Local movement handling
                            //LOCAL MOVEMENT HANDLING
                            if (isOnWorldMap)
                            {
                                _logger.UpdateLog($"Movement details handling warning - local movement cancelled for character's ID [{movementDetails.CharId}], reason: world map state");
                            }
                            else
                            {
                                #region Geo data validation
                                //GEO DATA VALIDATION
                                using
                                (
                                    BoxedData geoBoxedData = await _geoDataInfo.GetLocalGeoDataTaskStart
                                                             (
                                        wmId,
                                        parentObjectId,
                                        PointConverter.Point3DoubleToInt(movementDetails.OldLocationLocal),
                                        PointConverter.Point3DoubleToInt(movementDetails.NewLocationLocal)
                                                             )
                                )
                                {
                                    geoDataList = (List <GeoDataElement>)geoBoxedData.Data;
                                    if (!String.IsNullOrEmpty(geoBoxedData.Msg))
                                    {
                                        _logger.UpdateLog(geoBoxedData.Msg);
                                    }
                                }

                                using (BoxedData geoValidationBoxedData = await GeoDataValidator.ValidateMovementTaskStart(geoDataList, movementDetails))
                                {
                                    geoDataValidationDetails = (GeoDataValidationDetails)geoValidationBoxedData.Data;
                                    if (!String.IsNullOrEmpty(geoValidationBoxedData.Msg))
                                    {
                                        _logger.UpdateLog(geoValidationBoxedData.Msg);
                                    }

                                    geoMovementValid       = geoDataValidationDetails.Valid;
                                    lastValidMovementPoint = geoDataValidationDetails.LastValidMovementPoint;
                                    lastTParamValue        = geoDataValidationDetails.LastTParamValue;

                                    geoDataValidationDetails.Dispose();
                                    geoDataValidationDetails = null;
                                }
                                #endregion

                                //_logger.UpdateLog($"GEO VALID [{geoMovementValid}]");
                                //geoMovementValid = true; //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

                                //CHARACTER MOVING
                                if (geoMovementValid)
                                {
                                    characterData.MoveCharacterLocal
                                    (
                                        movementDetails.OldLocationLocal.Copy(),
                                        movementDetails.NewLocationLocal.Copy(),
                                        movementDetails.TimeArrivalMsLocal
                                    );

                                    positionDetailsToSend = new CharacterPositionUpdateDetails()
                                    {
                                        MovementType       = "movelocal",
                                        CharId             = movementDetails.CharId,
                                        OldLocationLocal   = movementDetails.OldLocationLocal.Copy(),
                                        NewLocationLocal   = movementDetails.NewLocationLocal.Copy(),
                                        TimeArrivalMsLocal = movementDetails.TimeArrivalMsLocal,
                                        OldLocationWorld   = new Point2 <int>(0, 0),
                                        NewLocationWorld   = new Point2 <int>(0, 0)
                                    };

                                    SendMovementDetailsToPlayersInLocationAsync(positionDetailsToSend, wmId, isOnWorldMap, parentObjectId);
                                }
                                else
                                {
                                    timeArrivalMsIncomplete = Convert.ToInt32(Convert.ToDouble(movementDetails.TimeArrivalMsLocal) * lastTParamValue);

                                    characterData.MoveCharacterLocal
                                    (
                                        movementDetails.OldLocationLocal.Copy(),
                                        lastValidMovementPoint.Copy(),
                                        timeArrivalMsIncomplete
                                    );

                                    positionDetailsToSend = new CharacterPositionUpdateDetails()
                                    {
                                        MovementType       = "movelocal",
                                        CharId             = movementDetails.CharId,
                                        OldLocationLocal   = movementDetails.OldLocationLocal.Copy(),
                                        NewLocationLocal   = lastValidMovementPoint.Copy(),
                                        TimeArrivalMsLocal = timeArrivalMsIncomplete,
                                        OldLocationWorld   = new Point2 <int>(0, 0),
                                        NewLocationWorld   = new Point2 <int>(0, 0)
                                    };

                                    SendMovementDetailsToPlayersInLocationAsync(positionDetailsToSend, wmId, isOnWorldMap, parentObjectId);
                                }
                            }

                            #endregion
                        }
                        break;

                        case CharacterMovementDetails.MovementType.World:
                        {
                            #region World map movement handling
                            //WORLD MAP MOVEMENT HANDLING
                            if (!isOnWorldMap)
                            {
                                _logger.UpdateLog($"Movement details handling warning - world map movement cancelled for character's ID [{movementDetails.CharId}], reason: local movement state");
                            }
                            else
                            {
                                Point2 <int> oldLocWorld = movementDetails.OldLocationWorld.Copy();
                                Point2 <int> newLocWorld = movementDetails.NewLocationWorld.Copy();

                                //WORLD MOVEMENT VALIDATION
                                worldMovingValid = true;

                                int distanceX = Math.Abs(oldLocWorld.X - newLocWorld.X);
                                int distanceY = Math.Abs(oldLocWorld.Y - newLocWorld.Y);

                                if
                                (
                                    oldLocWorld.X != characterData.CurrentWorldLoc.X || oldLocWorld.Y != characterData.CurrentWorldLoc.Y ||
                                    distanceX > 2 || distanceY > 2
                                )
                                {
                                    worldMovingValid = false;
                                    //_logger.UpdateLog($"Movement details handling warning - world map movement cancelled for character's ID [{movementDetails.CharId}]");
                                }

                                //CHARACTER MOVING
                                if (worldMovingValid)
                                {
                                    WorldPlaceDataDetails worldPlaceDetails = _geoDataInfo.GetWorldPlaceDataDetails(newLocWorld.X, newLocWorld.Y);
                                    int newWmId = (worldPlaceDetails != null ? worldPlaceDetails.WmId : -1);

                                    characterData.MoveCharacterWorld(newLocWorld);

                                    positionDetailsToSend = new CharacterPositionUpdateDetails()
                                    {
                                        MovementType       = "moveworld",
                                        CharId             = movementDetails.CharId,
                                        OldLocationLocal   = new Point3 <double>(0, 0, 0),
                                        NewLocationLocal   = new Point3 <double>(0, 0, 0),
                                        TimeArrivalMsLocal = 0,
                                        OldLocationWorld   = oldLocWorld,
                                        NewLocationWorld   = newLocWorld
                                    };

                                    SendMovementDetailsToPlayersInLocationAsync(positionDetailsToSend, wmId, isOnWorldMap, parentObjectId);
                                    ChangeWmIdAsync(characterData, newWmId);
                                }
                                else
                                {
                                    SendMessageToPlayer(movementDetails.CharId, "You're moving too far");
                                }
                            }

                            #endregion
                        }
                        break;

                        default:
                            throw new Exception($"unknown movement type [{movementDetails.Type.ToString()}]!");
                        }
                    }

                    #endregion

                    #region Temp. list disposal
                    //TEMP. LIST DISPOSAL
                    foreach (CharacterMovementDetails item in movementDetailsListTemp)
                    {
                        item.Dispose();
                    }

                    movementDetailsListTemp.Clear();

                    #endregion
                }while (_movementHandlingInProgress);
            }
            catch (Exception exception)
            {
                _logger.UpdateLog($"Character movement handling error: {exception.Message}");
            }
            finally
            {
                _movementHandlingInProgress = false;
                _logger.UpdateLog("Game state handler - character movement handling stopped!");
            }
        }
    private void ReloadScene()
    {
        try
        {
            DestroyCurrentWorldMapSectionObjects();
            SetPlayerPosition(_gameStateDetails.Position.x, _gameStateDetails.Position.y);

            int mapWidth  = _gameStateDetails.MapWidth;
            int mapHeight = _gameStateDetails.MapHeight;
            List <WorldPlaceDataDetails> worldPlaceDetailsList = _gameStateDetails.GetWorldPlaceDataDetails();

            _worldMapSectionObjects = new GameObject[mapWidth, mapHeight];
            GameObject createdMapSection = null;

            int worldPosX;
            int worldPosY;

            foreach (WorldPlaceDataDetails details in worldPlaceDetailsList)
            {
                //BUILDING SECTIONS BASED ON SERVER INSTANCES
                worldPosX = details.WorldPosX;
                worldPosY = details.WorldPosY;

                if (worldPosX >= mapWidth || worldPosY >= mapHeight)
                {
                    _chat.UpdateLog($"World map - ReloadScene() - WARNING - position over the constraints! Pos [{worldPosX}, {worldPosY}] constr [{mapWidth} - 1, {mapHeight} - 1]");
                    continue;
                }

                switch ((PlaceType)details.PlaceType)
                {
                case PlaceType.Urban:
                    createdMapSection = WorldMapSectionCreator.CreateWorldMapSection(new UrbanWmSectionBuilder(details, _camera), this);
                    break;

                case PlaceType.Sand:
                    createdMapSection = WorldMapSectionCreator.CreateWorldMapSection(new SandWmSectionBuilder(details, _camera), this);
                    break;

                default:     //forest
                    createdMapSection = WorldMapSectionCreator.CreateWorldMapSection(new ForestWmSectionBuilder(details, _camera), this);
                    break;
                }

                _worldMapSectionObjects[worldPosX, worldPosY] = createdMapSection;
            }

            WorldPlaceDataDetails dummyDetails;
            Transform             sectionTransform;

            for (int x = 0; x < mapWidth; x++)
            {
                for (int y = 0; y < mapHeight; y++)
                {
                    //EMPTY SECTIONS FILLING
                    if (_worldMapSectionObjects[x, y] == null)
                    {
                        dummyDetails = new WorldPlaceDataDetails()
                        {
                            WorldPosX = x,
                            WorldPosY = y,
                            WmId      = -1,
                            PlaceType = (int)PlaceType.Forest,
                            PlaceName = ""
                        };

                        createdMapSection             = WorldMapSectionCreator.CreateWorldMapSection(new ForestWmSectionBuilder(dummyDetails, _camera), this);
                        _worldMapSectionObjects[x, y] = createdMapSection;
                    }

                    //POSITIONING
                    sectionTransform          = _worldMapSectionObjects[x, y].GetComponent <Transform>();
                    sectionTransform.position = new Vector3
                                                (
                        x * _distanceBetweenSections,
                        sectionTransform.position.y,
                        y * _distanceBetweenSections
                                                );
                }
            }

            HideLoadingScreen();
        }
        catch (Exception exception)
        {
            MainGameHandler.ShowMessageBox($"Failed to reload world map scene: {exception.Message}");
        }
    }