Esempio n. 1
0
        public void Init()
        {
            CharacterPrefab.LoadAll();
            MissionPrefab.Init();
            TraitorMissionPrefab.Init();
            MapEntityPrefab.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            ScriptedEventSet.LoadPrefabs();
            Order.Init();
            EventManagerSettings.Init();

            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            SkillSettings.Load(GetFilesOfType(ContentType.SkillSettings));
            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            CorpsePrefab.LoadAll(GetFilesOfType(ContentType.Corpses));
            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));
            ItemAssemblyPrefab.LoadAll();
            LevelObjectPrefab.LoadAll();

            GameModePreset.Init();
            LocationType.Init();

            SubmarineInfo.RefreshSavedSubs();

            Screen.SelectNull();

            NetLobbyScreen = new NetLobbyScreen();

            CheckContentPackage();
        }
Esempio n. 2
0
        public void Init()
        {
            MissionPrefab.Init();
            MapEntityPrefab.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            ScriptedEventSet.LoadPrefabs();

            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            ItemAssemblyPrefab.LoadAll();
            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));
            ItemAssemblyPrefab.LoadAll();
            LevelObjectPrefab.LoadAll();

            GameModePreset.Init();
            LocationType.Init();

            Submarine.RefreshSavedSubs();

            Screen.SelectNull();

            NetLobbyScreen = new NetLobbyScreen();

            CheckContentPackage();
        }
        private void PlaceObject(LevelObjectPrefab prefab, SpawnPosition spawnPosition, Level level)
        {
            float rotation = 0.0f;

            if (prefab.AlignWithSurface && spawnPosition.Normal.LengthSquared() > 0.001f && spawnPosition != null)
            {
                rotation = MathUtils.VectorToAngle(new Vector2(spawnPosition.Normal.Y, spawnPosition.Normal.X));
            }
            rotation += Rand.Range(prefab.RandomRotationRad.X, prefab.RandomRotationRad.Y, Rand.RandSync.Server);

            Vector2 position = Vector2.Zero;
            Vector2 edgeDir  = Vector2.UnitX;

            if (spawnPosition == null)
            {
                position = new Vector2(
                    Rand.Range(0.0f, level.Size.X, Rand.RandSync.Server),
                    Rand.Range(0.0f, level.Size.Y, Rand.RandSync.Server));
            }
            else
            {
                edgeDir  = (spawnPosition.GraphEdge.Point1 - spawnPosition.GraphEdge.Point2) / spawnPosition.Length;
                position = spawnPosition.GraphEdge.Point2 + edgeDir * Rand.Range(prefab.MinSurfaceWidth / 2.0f, spawnPosition.Length - prefab.MinSurfaceWidth / 2.0f, Rand.RandSync.Server);
            }

            if (!MathUtils.NearlyEqual(prefab.RandomOffset.X, 0.0f) || !MathUtils.NearlyEqual(prefab.RandomOffset.Y, 0.0f))
            {
                Vector2 offsetDir = spawnPosition.Normal.LengthSquared() > 0.001f ? spawnPosition.Normal : Rand.Vector(1.0f, Rand.RandSync.Server);
                position += offsetDir * Rand.Range(prefab.RandomOffset.X, prefab.RandomOffset.Y, Rand.RandSync.Server);
            }

            var newObject = new LevelObject(prefab,
                                            new Vector3(position, Rand.Range(prefab.DepthRange.X, prefab.DepthRange.Y, Rand.RandSync.Server)), Rand.Range(prefab.MinSize, prefab.MaxSize, Rand.RandSync.Server), rotation);

            AddObject(newObject, level);

            foreach (LevelObjectPrefab.ChildObject child in prefab.ChildObjects)
            {
                int childCount = Rand.Range(child.MinCount, child.MaxCount, Rand.RandSync.Server);
                for (int j = 0; j < childCount; j++)
                {
                    var matchingPrefabs = LevelObjectPrefab.List.Where(p => child.AllowedNames.Contains(p.Name));
                    int prefabCount     = matchingPrefabs.Count();
                    var childPrefab     = prefabCount == 0 ? null : matchingPrefabs.ElementAt(Rand.Range(0, prefabCount, Rand.RandSync.Server));
                    if (childPrefab == null)
                    {
                        continue;
                    }

                    Vector2 childPos = position + edgeDir * Rand.Range(-0.5f, 0.5f, Rand.RandSync.Server) * prefab.MinSurfaceWidth;

                    var childObject = new LevelObject(childPrefab,
                                                      new Vector3(childPos, Rand.Range(childPrefab.DepthRange.X, childPrefab.DepthRange.Y, Rand.RandSync.Server)),
                                                      Rand.Range(childPrefab.MinSize, childPrefab.MaxSize, Rand.RandSync.Server),
                                                      rotation + Rand.Range(childPrefab.RandomRotationRad.X, childPrefab.RandomRotationRad.Y, Rand.RandSync.Server));

                    AddObject(childObject, level);
                }
            }
        }
            public float GetSpawnProbability(LevelObjectPrefab prefab)
            {
                if (prefab.ClusteringAmount <= 0.0f)
                {
                    return(Length);
                }
                float noise = (noiseVal + PerlinNoise.GetPerlin(prefab.ClusteringGroup, prefab.ClusteringGroup * 0.3f)) % 1.0f;

                return(Length * (float)Math.Pow(noise, prefab.ClusteringAmount));
            }
        private void LoadElements(XElement element, int parentTriggerIndex)
        {
            foreach (XElement subElement in element.Elements())
            {
                switch (subElement.Name.ToString().ToLowerInvariant())
                {
                case "sprite":
                    Sprites.Add(new Sprite(subElement, lazyLoad: true));
                    break;

                case "specularsprite":
                    SpecularSprites.Add(new Sprite(subElement, lazyLoad: true));
                    break;

                case "deformablesprite":
                    DeformableSprite = new DeformableSprite(subElement, lazyLoad: true);
                    break;

                case "overridecommonness":
                    string levelType = subElement.GetAttributeString("leveltype", "");
                    if (!OverrideCommonness.ContainsKey(levelType))
                    {
                        OverrideCommonness.Add(levelType, subElement.GetAttributeFloat("commonness", 1.0f));
                    }
                    break;

                case "leveltrigger":
                case "trigger":
                    OverrideProperties.Add(null);
                    LevelTriggerElements.Add(subElement);
                    LoadElements(subElement, LevelTriggerElements.Count - 1);
                    break;

                case "childobject":
                    ChildObjects.Add(new ChildObject(subElement));
                    break;

                case "overrideproperties":
                    var propertyOverride = new LevelObjectPrefab(subElement);
                    OverrideProperties[OverrideProperties.Count - 1] = propertyOverride;
                    if (!propertyOverride.Sprites.Any() && propertyOverride.DeformableSprite == null)
                    {
                        propertyOverride.Sprites          = Sprites;
                        propertyOverride.DeformableSprite = DeformableSprite;
                    }
                    break;

                case "body":
                case "physicsbody":
                    PhysicsBodyElement      = subElement;
                    PhysicsBodyTriggerIndex = parentTriggerIndex;
                    break;
                }
            }
        }
Esempio n. 6
0
        public LevelObject(LevelObjectPrefab prefab, Vector3 position, float scale, float rotation = 0.0f)
        {
            ActivePrefab = Prefab = prefab;
            Position     = position;
            Scale        = scale;
            Rotation     = rotation;

            spriteIndex = ActivePrefab.Sprites.Any() ? Rand.Int(ActivePrefab.Sprites.Count, Rand.RandSync.Server) : -1;

            if (Sprite != null && prefab.SpriteSpecificPhysicsBodyElements.ContainsKey(Sprite))
            {
                PhysicsBody = new PhysicsBody(prefab.SpriteSpecificPhysicsBodyElements[Sprite], ConvertUnits.ToSimUnits(new Vector2(position.X, position.Y)), Scale);
            }
            else if (prefab.PhysicsBodyElement != null)
            {
                PhysicsBody = new PhysicsBody(prefab.PhysicsBodyElement, ConvertUnits.ToSimUnits(new Vector2(position.X, position.Y)), Scale);
            }

            if (PhysicsBody != null)
            {
                PhysicsBody.SetTransformIgnoreContacts(PhysicsBody.SimPosition, -Rotation);
                PhysicsBody.BodyType            = BodyType.Static;
                PhysicsBody.CollisionCategories = Physics.CollisionLevel;
                PhysicsBody.CollidesWith        = Physics.CollisionWall | Physics.CollisionCharacter;
            }

            foreach (XElement triggerElement in prefab.LevelTriggerElements)
            {
                Triggers ??= new List <LevelTrigger>();
                Vector2 triggerPosition = triggerElement.GetAttributeVector2("position", Vector2.Zero) * scale;

                if (rotation != 0.0f)
                {
                    var ca = (float)Math.Cos(rotation);
                    var sa = (float)Math.Sin(rotation);

                    triggerPosition = new Vector2(
                        ca * triggerPosition.X + sa * triggerPosition.Y,
                        -sa * triggerPosition.X + ca * triggerPosition.Y);
                }

                var newTrigger         = new LevelTrigger(triggerElement, new Vector2(position.X, position.Y) + triggerPosition, -rotation, scale, prefab.Name);
                int parentTriggerIndex = prefab.LevelTriggerElements.IndexOf(triggerElement.Parent);
                if (parentTriggerIndex > -1)
                {
                    newTrigger.ParentTrigger = Triggers[parentTriggerIndex];
                }
                Triggers.Add(newTrigger);
            }

            NeedsUpdate = NeedsNetworkSyncing || (Triggers != null && Triggers.Any()) || Prefab.PhysicsBodyTriggerIndex > -1;

            InitProjSpecific();
        }
            public float GetSpawnProbability(LevelObjectPrefab prefab)
            {
                if (prefab.ClusteringAmount <= 0.0f)
                {
                    return(Length);
                }

                float noise = (float)(
                    PerlinNoise.CalculatePerlin(GraphEdge.Point1.X / 10000.0f, GraphEdge.Point1.Y / 10000.0f, prefab.ClusteringGroup) +
                    PerlinNoise.CalculatePerlin(GraphEdge.Point1.X / 20000.0f, GraphEdge.Point1.Y / 20000.0f, prefab.ClusteringGroup));

                return(Length * (float)Math.Pow(noise, prefab.ClusteringAmount));
            }
Esempio n. 8
0
        public LevelObject(LevelObjectPrefab prefab, Vector3 position, float scale, float rotation = 0.0f)
        {
            Triggers = new List <LevelTrigger>();

            ActivePrefab = Prefab = prefab;
            Position     = position;
            Scale        = scale;
            Rotation     = rotation;

            spriteIndex = ActivePrefab.Sprites.Any() ? Rand.Int(ActivePrefab.Sprites.Count, Rand.RandSync.Server) : -1;

            if (prefab.PhysicsBodyElement != null)
            {
                PhysicsBody = new PhysicsBody(prefab.PhysicsBodyElement, ConvertUnits.ToSimUnits(new Vector2(position.X, position.Y)), Scale);
            }

            foreach (XElement triggerElement in prefab.LevelTriggerElements)
            {
                Vector2 triggerPosition = triggerElement.GetAttributeVector2("position", Vector2.Zero) * scale;

                if (rotation != 0.0f)
                {
                    var ca = (float)Math.Cos(rotation);
                    var sa = (float)Math.Sin(rotation);

                    triggerPosition = new Vector2(
                        ca * triggerPosition.X + sa * triggerPosition.Y,
                        -sa * triggerPosition.X + ca * triggerPosition.Y);
                }

                var newTrigger         = new LevelTrigger(triggerElement, new Vector2(position.X, position.Y) + triggerPosition, -rotation, scale, prefab.Name);
                int parentTriggerIndex = prefab.LevelTriggerElements.IndexOf(triggerElement.Parent);
                if (parentTriggerIndex > -1)
                {
                    newTrigger.ParentTrigger = Triggers[parentTriggerIndex];
                }
                Triggers.Add(newTrigger);
            }

            InitProjSpecific();
        }
Esempio n. 9
0
        public void Init()
        {
            NPCSet.LoadSets();
            FactionPrefab.LoadFactions();
            CharacterPrefab.LoadAll();
            MissionPrefab.Init();
            TraitorMissionPrefab.Init();
            MapEntityPrefab.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            CaveGenerationParams.LoadPresets();
            OutpostGenerationParams.LoadPresets();
            EventSet.LoadPrefabs();
            Order.Init();
            EventManagerSettings.Init();
            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            SkillSettings.Load(GetFilesOfType(ContentType.SkillSettings));
            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            UpgradePrefab.LoadAll(GetFilesOfType(ContentType.UpgradeModules));
            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            CorpsePrefab.LoadAll(GetFilesOfType(ContentType.Corpses));
            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));
            ItemAssemblyPrefab.LoadAll();
            LevelObjectPrefab.LoadAll();
            BallastFloraPrefab.LoadAll(GetFilesOfType(ContentType.MapCreature));
            TalentPrefab.LoadAll(GetFilesOfType(ContentType.Talents));
            TalentTree.LoadAll(GetFilesOfType(ContentType.TalentTrees));

            GameModePreset.Init();
            DecalManager = new DecalManager();
            LocationType.Init();

            SubmarineInfo.RefreshSavedSubs();

            Screen.SelectNull();

            NetLobbyScreen = new NetLobbyScreen();

            CheckContentPackage();
        }
Esempio n. 10
0
        private IEnumerable <object> Load(bool isSeparateThread)
        {
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE", Color.Lime);
            }

            while (TitleScreen.WaitForLanguageSelection)
            {
                yield return(CoroutineStatus.Running);
            }

            SoundManager = new Sounds.SoundManager();
            SoundManager.SetCategoryGainMultiplier("default", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("ui", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("waterambience", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("music", Config.MusicVolume, 0);
            SoundManager.SetCategoryGainMultiplier("voip", Math.Min(Config.VoiceChatVolume, 1.0f), 0);

            if (Config.EnableSplashScreen && !ConsoleArguments.Contains("-skipintro"))
            {
                var   pendingSplashScreens = TitleScreen.PendingSplashScreens;
                float baseVolume           = MathHelper.Clamp(Config.SoundVolume * 2.0f, 0.0f, 1.0f);
                pendingSplashScreens?.Enqueue(new LoadingScreen.PendingSplashScreen("Content/SplashScreens/Splash_UTG.webm", baseVolume * 0.5f));
                pendingSplashScreens?.Enqueue(new LoadingScreen.PendingSplashScreen("Content/SplashScreens/Splash_FF.webm", baseVolume));
                pendingSplashScreens?.Enqueue(new LoadingScreen.PendingSplashScreen("Content/SplashScreens/Splash_Daedalic.webm", baseVolume * 0.1f));
            }

            //if not loading in a separate thread, wait for the splash screens to finish before continuing the loading
            //otherwise the videos will look extremely choppy
            if (!isSeparateThread)
            {
                while (TitleScreen.PlayingSplashScreen || TitleScreen.PendingSplashScreens.Count > 0)
                {
                    yield return(CoroutineStatus.Running);
                }
            }

            GUI.Init(Window, Config.AllEnabledPackages, GraphicsDevice);
            DebugConsole.Init();

            if (Config.AutoUpdateWorkshopItems)
            {
                Config.WaitingForAutoUpdate = true;
                TaskPool.Add("AutoUpdateWorkshopItemsAsync",
                             SteamManager.AutoUpdateWorkshopItemsAsync(), (task) =>
                {
                    bool result = ((Task <bool>)task).Result;

                    Config.WaitingForAutoUpdate = false;
                });

                while (Config.WaitingForAutoUpdate)
                {
                    yield return(CoroutineStatus.Running);
                }
            }

#if DEBUG
            if (Config.ModBreakerMode)
            {
                Config.SelectCorePackage(ContentPackage.CorePackages.GetRandom());
                foreach (var regularPackage in ContentPackage.RegularPackages)
                {
                    if (Rand.Range(0.0, 1.0) <= 0.5)
                    {
                        Config.EnableRegularPackage(regularPackage);
                    }
                    else
                    {
                        Config.DisableRegularPackage(regularPackage);
                    }
                }
                ContentPackage.SortContentPackages(p =>
                {
                    return(Rand.Int(int.MaxValue));
                });
            }
#endif

            if (Config.AllEnabledPackages.None())
            {
                DebugConsole.Log("No content packages selected");
            }
            else
            {
                DebugConsole.Log("Selected content packages: " + string.Join(", ", Config.AllEnabledPackages.Select(cp => cp.Name)));
            }

#if DEBUG
            GameSettings.ShowUserStatisticsPrompt = false;
            GameSettings.SendUserStatistics       = false;
#endif

            InitUserStats();

            yield return(CoroutineStatus.Running);

            Debug.WriteLine("sounds");

            int i = 0;
            foreach (object crObj in SoundPlayer.Init())
            {
                CoroutineStatus status = (CoroutineStatus)crObj;
                if (status == CoroutineStatus.Success)
                {
                    break;
                }

                i++;
                TitleScreen.LoadState = SoundPlayer.SoundCount == 0 ?
                                        1.0f :
                                        Math.Min(40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 40.0f);

                yield return(CoroutineStatus.Running);
            }

            TitleScreen.LoadState = 40.0f;
            yield return(CoroutineStatus.Running);

            LightManager = new Lights.LightManager(base.GraphicsDevice, Content);

            TitleScreen.LoadState = 41.0f;
            yield return(CoroutineStatus.Running);

            GUI.LoadContent();
            TitleScreen.LoadState = 42.0f;

            yield return(CoroutineStatus.Running);

            TaskPool.Add("InitRelayNetworkAccess", SteamManager.InitRelayNetworkAccess(), (t) => { });

            FactionPrefab.LoadFactions();
            NPCSet.LoadSets();
            CharacterPrefab.LoadAll();
            MissionPrefab.Init();
            TraitorMissionPrefab.Init();
            MapEntityPrefab.Init();
            Tutorials.Tutorial.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            CaveGenerationParams.LoadPresets();
            OutpostGenerationParams.LoadPresets();
            WreckAIConfig.LoadAll();
            EventSet.LoadPrefabs();
            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            SkillSettings.Load(GetFilesOfType(ContentType.SkillSettings));
            Order.Init();
            EventManagerSettings.Init();
            BallastFloraPrefab.LoadAll(GetFilesOfType(ContentType.MapCreature));
            HintManager.Init();
            TitleScreen.LoadState = 50.0f;
            yield return(CoroutineStatus.Running);

            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            TitleScreen.LoadState = 55.0f;
            yield return(CoroutineStatus.Running);

            UpgradePrefab.LoadAll(GetFilesOfType(ContentType.UpgradeModules));
            TitleScreen.LoadState = 56.0f;
            yield return(CoroutineStatus.Running);

            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            CorpsePrefab.LoadAll(GetFilesOfType(ContentType.Corpses));

            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));

            ItemAssemblyPrefab.LoadAll();
            TitleScreen.LoadState = 60.0f;
            yield return(CoroutineStatus.Running);

            GameModePreset.Init();

            SaveUtil.DeleteDownloadedSubs();
            SubmarineInfo.RefreshSavedSubs();

            TitleScreen.LoadState = 65.0f;
            yield return(CoroutineStatus.Running);

            GameScreen = new GameScreen(GraphicsDeviceManager.GraphicsDevice, Content);

            TitleScreen.LoadState = 68.0f;
            yield return(CoroutineStatus.Running);

            MainMenuScreen   = new MainMenuScreen(this);
            ServerListScreen = new ServerListScreen();

            TitleScreen.LoadState = 70.0f;
            yield return(CoroutineStatus.Running);

#if USE_STEAM
            SteamWorkshopScreen = new SteamWorkshopScreen();
            if (SteamManager.IsInitialized)
            {
                Steamworks.SteamFriends.OnGameRichPresenceJoinRequested += OnInvitedToGame;
                Steamworks.SteamFriends.OnGameLobbyJoinRequested        += OnLobbyJoinRequested;
            }
#endif

            SubEditorScreen = new SubEditorScreen();

            TitleScreen.LoadState = 75.0f;
            yield return(CoroutineStatus.Running);

            ParticleEditorScreen = new ParticleEditorScreen();

            TitleScreen.LoadState = 80.0f;
            yield return(CoroutineStatus.Running);

            LevelEditorScreen     = new LevelEditorScreen();
            SpriteEditorScreen    = new SpriteEditorScreen();
            EventEditorScreen     = new EventEditorScreen();
            CharacterEditorScreen = new CharacterEditor.CharacterEditorScreen();
            CampaignEndScreen     = new CampaignEndScreen();

            yield return(CoroutineStatus.Running);

            TitleScreen.LoadState = 85.0f;
            ParticleManager       = new ParticleManager(GameScreen.Cam);
            ParticleManager.LoadPrefabs();
            TitleScreen.LoadState = 88.0f;
            LevelObjectPrefab.LoadAll();

            TitleScreen.LoadState = 90.0f;
            yield return(CoroutineStatus.Running);

            DecalManager = new DecalManager();
            LocationType.Init();
            MainMenuScreen.Select();

            foreach (string steamError in SteamManager.InitializationErrors)
            {
                new GUIMessageBox(TextManager.Get("Error"), TextManager.Get(steamError));
            }

            TitleScreen.LoadState = 100.0f;
            hasLoaded             = true;
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE FINISHED", Color.Lime);
            }
            yield return(CoroutineStatus.Success);
        }
Esempio n. 11
0
        private IEnumerable <object> Load()
        {
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE", Color.Lime);
            }

            SoundManager = new Sounds.SoundManager();
            SoundManager.SetCategoryGainMultiplier("default", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("ui", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("waterambience", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("music", Config.MusicVolume);

            GUI.Init(Window, Config.SelectedContentPackages, GraphicsDevice);
            DebugConsole.Init();

            SteamManager.Initialize();

            if (SelectedPackages.Count == 0)
            {
                DebugConsole.Log("No content packages selected");
            }
            else
            {
                DebugConsole.Log("Selected content packages: " + string.Join(", ", SelectedPackages.Select(cp => cp.Name)));
            }

            InitUserStats();

            yield return(CoroutineStatus.Running);

            LightManager = new Lights.LightManager(base.GraphicsDevice, Content);

            WaterRenderer.Instance = new WaterRenderer(base.GraphicsDevice, Content);
            TitleScreen.LoadState  = 1.0f;
            yield return(CoroutineStatus.Running);

            GUI.LoadContent();
            TitleScreen.LoadState = 2.0f;
            yield return(CoroutineStatus.Running);

            MissionPrefab.Init();
            MapEntityPrefab.Init();
            Tutorials.Tutorial.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            ScriptedEventSet.LoadPrefabs();
            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            TitleScreen.LoadState = 10.0f;
            yield return(CoroutineStatus.Running);

            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            TitleScreen.LoadState = 15.0f;
            yield return(CoroutineStatus.Running);

            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            TitleScreen.LoadState = 30.0f;
            yield return(CoroutineStatus.Running);

            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            // Add any missing jobs from the prefab into Config.JobNamePreferences.
            foreach (JobPrefab job in JobPrefab.List)
            {
                if (!Config.JobPreferences.Contains(job.Identifier))
                {
                    Config.JobPreferences.Add(job.Identifier);
                }
            }

            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));

            ItemAssemblyPrefab.LoadAll();
            TitleScreen.LoadState = 35.0f;
            yield return(CoroutineStatus.Running);

            Debug.WriteLine("sounds");
            CoroutineManager.StartCoroutine(SoundPlayer.Init());

            int i = 0;

            while (!SoundPlayer.Initialized)
            {
                i++;
                TitleScreen.LoadState = SoundPlayer.SoundCount == 0 ?
                                        30.0f :
                                        Math.Min(30.0f + 40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 70.0f);
                yield return(CoroutineStatus.Running);
            }

            TitleScreen.LoadState = 70.0f;
            yield return(CoroutineStatus.Running);

            GameModePreset.Init();

            Submarine.RefreshSavedSubs();
            TitleScreen.LoadState = 80.0f;
            yield return(CoroutineStatus.Running);

            GameScreen            = new GameScreen(GraphicsDeviceManager.GraphicsDevice, Content);
            TitleScreen.LoadState = 90.0f;
            yield return(CoroutineStatus.Running);

            MainMenuScreen   = new MainMenuScreen(this);
            LobbyScreen      = new LobbyScreen();
            ServerListScreen = new ServerListScreen();

            if (SteamManager.USE_STEAM)
            {
                SteamWorkshopScreen = new SteamWorkshopScreen();
            }

            SubEditorScreen       = new SubEditorScreen();
            ParticleEditorScreen  = new ParticleEditorScreen();
            LevelEditorScreen     = new LevelEditorScreen();
            SpriteEditorScreen    = new SpriteEditorScreen();
            CharacterEditorScreen = new CharacterEditorScreen();

            yield return(CoroutineStatus.Running);

            ParticleManager = new ParticleManager(GameScreen.Cam);
            ParticleManager.LoadPrefabs();
            LevelObjectPrefab.LoadAll();
            DecalManager = new DecalManager();
            yield return(CoroutineStatus.Running);

            LocationType.Init();
            MainMenuScreen.Select();

            TitleScreen.LoadState = 100.0f;
            hasLoaded             = true;
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE FINISHED", Color.Lime);
            }
            yield return(CoroutineStatus.Success);
        }
Esempio n. 12
0
            public GUIMessageBox Create()
            {
                var box = new GUIMessageBox(TextManager.Get("leveleditor.createlevelobj"), string.Empty,
                                            new string[] { TextManager.Get("cancel"), TextManager.Get("done") }, new Vector2(0.5f, 0.8f));

                box.Content.ChildAnchor     = Anchor.TopCenter;
                box.Content.AbsoluteSpacing = 20;
                int elementSize = 30;
                var listBox     = new GUIListBox(new RectTransform(new Vector2(1, 0.9f), box.Content.RectTransform));

                new GUITextBlock(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform),
                                 TextManager.Get("leveleditor.levelobjname"))
                {
                    CanBeFocused = false
                };
                var nameBox = new GUITextBox(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform));

                new GUITextBlock(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform),
                                 TextManager.Get("leveleditor.levelobjtexturepath"))
                {
                    CanBeFocused = false
                };
                var texturePathBox = new GUITextBox(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform));

                foreach (LevelObjectPrefab prefab in LevelObjectPrefab.List)
                {
                    if (prefab.Sprites.FirstOrDefault() == null)
                    {
                        continue;
                    }
                    texturePathBox.Text = Path.GetDirectoryName(prefab.Sprites.FirstOrDefault().FilePath);
                    break;
                }

                newPrefab = new LevelObjectPrefab(null);

                new SerializableEntityEditor(listBox.Content.RectTransform, newPrefab, false, false);

                box.Buttons[0].OnClicked += (b, d) =>
                {
                    box.Close();
                    return(true);
                };
                // Next
                box.Buttons[1].OnClicked += (b, d) =>
                {
                    if (string.IsNullOrEmpty(nameBox.Text))
                    {
                        nameBox.Flash(GUI.Style.Red);
                        GUI.AddMessage(TextManager.Get("leveleditor.levelobjnameempty"), GUI.Style.Red);
                        return(false);
                    }

                    if (LevelObjectPrefab.List.Any(obj => obj.Name.ToLower() == nameBox.Text.ToLower()))
                    {
                        nameBox.Flash(GUI.Style.Red);
                        GUI.AddMessage(TextManager.Get("leveleditor.levelobjnametaken"), GUI.Style.Red);
                        return(false);
                    }

                    if (!File.Exists(texturePathBox.Text))
                    {
                        texturePathBox.Flash(GUI.Style.Red);
                        GUI.AddMessage(TextManager.Get("leveleditor.levelobjtexturenotfound"), GUI.Style.Red);
                        return(false);
                    }

                    newPrefab.Name = nameBox.Text;

                    XmlWriterSettings settings = new XmlWriterSettings {
                        Indent = true
                    };
                    foreach (ContentFile configFile in GameMain.Instance.GetFilesOfType(ContentType.LevelObjectPrefabs))
                    {
                        XDocument doc = XMLExtensions.TryLoadXml(configFile.Path);
                        if (doc == null)
                        {
                            continue;
                        }
                        var newElement = new XElement(newPrefab.Name);
                        newPrefab.Save(newElement);
                        newElement.Add(new XElement("Sprite",
                                                    new XAttribute("texture", texturePathBox.Text),
                                                    new XAttribute("sourcerect", "0,0,100,100"),
                                                    new XAttribute("origin", "0.5,0.5")));

                        doc.Root.Add(newElement);
                        using (var writer = XmlWriter.Create(configFile.Path, settings))
                        {
                            doc.WriteTo(writer);
                            writer.Flush();
                        }
                        // Recreate the prefab so that the sprite loads correctly: TODO: consider a better way to do this
                        newPrefab = new LevelObjectPrefab(newElement);
                        break;
                    }

                    LevelObjectPrefab.List.Add(newPrefab);
                    GameMain.LevelEditorScreen.UpdateLevelObjectsList();

                    box.Close();
                    return(true);
                };
                return(box);
            }
Esempio n. 13
0
        private IEnumerable <object> Load(bool isSeparateThread)
        {
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE", Color.Lime);
            }

            while (TitleScreen.WaitForLanguageSelection)
            {
                yield return(CoroutineStatus.Running);
            }

            SoundManager = new Sounds.SoundManager();
            SoundManager.SetCategoryGainMultiplier("default", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("ui", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("waterambience", Config.SoundVolume, 0);
            SoundManager.SetCategoryGainMultiplier("music", Config.MusicVolume, 0);
            SoundManager.SetCategoryGainMultiplier("voip", Config.VoiceChatVolume * 20.0f, 0);

            if (ConsoleArguments.Contains("-skipintro"))
            {
                Config.EnableSplashScreen = false;
            }

            if (Config.EnableSplashScreen)
            {
                var pendingSplashScreens = TitleScreen.PendingSplashScreens;
                pendingSplashScreens?.Enqueue(new Pair <string, Point>("Content/Splash_UTG.mp4", new Point(1280, 720)));
                pendingSplashScreens?.Enqueue(new Pair <string, Point>("Content/Splash_FF.mp4", new Point(1280, 720)));
                pendingSplashScreens?.Enqueue(new Pair <string, Point>("Content/Splash_Daedalic.mp4", new Point(1920, 1080)));
            }

            //if not loading in a separate thread, wait for the splash screens to finish before continuing the loading
            //otherwise the videos will look extremely choppy
            if (!isSeparateThread)
            {
                while (TitleScreen.PlayingSplashScreen || TitleScreen.PendingSplashScreens.Count > 0)
                {
                    yield return(CoroutineStatus.Running);
                }
            }

            GUI.Init(Window, Config.SelectedContentPackages, GraphicsDevice);
            DebugConsole.Init();

            if (Config.AutoUpdateWorkshopItems)
            {
                if (SteamManager.AutoUpdateWorkshopItems())
                {
                    ContentPackage.LoadAll();
                    Config.ReloadContentPackages();
                }
            }

            if (SelectedPackages.Count == 0)
            {
                DebugConsole.Log("No content packages selected");
            }
            else
            {
                DebugConsole.Log("Selected content packages: " + string.Join(", ", SelectedPackages.Select(cp => cp.Name)));
            }

#if DEBUG
            GameSettings.ShowUserStatisticsPrompt = false;
            GameSettings.SendUserStatistics       = false;
#endif

            InitUserStats();

            yield return(CoroutineStatus.Running);

            Debug.WriteLine("sounds");

            int i = 0;
            foreach (object crObj in SoundPlayer.Init())
            {
                CoroutineStatus status = (CoroutineStatus)crObj;
                if (status == CoroutineStatus.Success)
                {
                    break;
                }

                i++;
                TitleScreen.LoadState = SoundPlayer.SoundCount == 0 ?
                                        1.0f :
                                        Math.Min(40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 40.0f);

                yield return(CoroutineStatus.Running);
            }

            TitleScreen.LoadState = 40.0f;
            yield return(CoroutineStatus.Running);

            LightManager = new Lights.LightManager(base.GraphicsDevice, Content);

            TitleScreen.LoadState = 41.0f;
            yield return(CoroutineStatus.Running);

            GUI.LoadContent();
            TitleScreen.LoadState = 42.0f;

            yield return(CoroutineStatus.Running);

            MissionPrefab.Init();
            MapEntityPrefab.Init();
            Tutorials.Tutorial.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            ScriptedEventSet.LoadPrefabs();
            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            TitleScreen.LoadState = 50.0f;
            yield return(CoroutineStatus.Running);

            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            TitleScreen.LoadState = 53.0f;
            yield return(CoroutineStatus.Running);

            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            TitleScreen.LoadState = 55.0f;
            yield return(CoroutineStatus.Running);

            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            // Add any missing jobs from the prefab into Config.JobNamePreferences.
            foreach (JobPrefab job in JobPrefab.List)
            {
                if (!Config.JobPreferences.Contains(job.Identifier))
                {
                    Config.JobPreferences.Add(job.Identifier);
                }
            }

            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));

            ItemAssemblyPrefab.LoadAll();
            TitleScreen.LoadState = 60.0f;
            yield return(CoroutineStatus.Running);

            GameModePreset.Init();

            Submarine.RefreshSavedSubs();

            TitleScreen.LoadState = 65.0f;
            yield return(CoroutineStatus.Running);

            GameScreen = new GameScreen(GraphicsDeviceManager.GraphicsDevice, Content);

            TitleScreen.LoadState = 68.0f;
            yield return(CoroutineStatus.Running);

            MainMenuScreen   = new MainMenuScreen(this);
            LobbyScreen      = new LobbyScreen();
            ServerListScreen = new ServerListScreen();

            TitleScreen.LoadState = 70.0f;
            yield return(CoroutineStatus.Running);

            if (SteamManager.USE_STEAM)
            {
                SteamWorkshopScreen = new SteamWorkshopScreen();
                if (SteamManager.IsInitialized)
                {
                    SteamManager.Instance.Friends.OnInvitedToGame    += OnInvitedToGame;
                    SteamManager.Instance.Lobby.OnLobbyJoinRequested += OnLobbyJoinRequested;
                }
            }
            SubEditorScreen = new SubEditorScreen();

            TitleScreen.LoadState = 75.0f;
            yield return(CoroutineStatus.Running);

            ParticleEditorScreen = new ParticleEditorScreen();

            TitleScreen.LoadState = 80.0f;
            yield return(CoroutineStatus.Running);

            LevelEditorScreen     = new LevelEditorScreen();
            SpriteEditorScreen    = new SpriteEditorScreen();
            CharacterEditorScreen = new CharacterEditorScreen();

            yield return(CoroutineStatus.Running);

            TitleScreen.LoadState = 85.0f;
            ParticleManager       = new ParticleManager(GameScreen.Cam);
            ParticleManager.LoadPrefabs();
            TitleScreen.LoadState = 88.0f;
            LevelObjectPrefab.LoadAll();

            TitleScreen.LoadState = 90.0f;
            yield return(CoroutineStatus.Running);

            DecalManager = new DecalManager();
            LocationType.Init();
            MainMenuScreen.Select();

            CheckContentPackage();

            foreach (string steamError in SteamManager.InitializationErrors)
            {
                new GUIMessageBox(TextManager.Get("Error"), TextManager.Get(steamError));
            }

            TitleScreen.LoadState = 100.0f;
            hasLoaded             = true;
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE FINISHED", Color.Lime);
            }
            yield return(CoroutineStatus.Success);
        }
Esempio n. 14
0
        private void CreateLevelObjectEditor(LevelObjectPrefab levelObjectPrefab)
        {
            editorContainer.ClearChildren();

            var editor = new SerializableEntityEditor(editorContainer.Content.RectTransform, levelObjectPrefab, false, true, elementHeight: 20, titleFont: GUI.LargeFont);

            if (selectedParams != null)
            {
                var commonnessContainer = new GUILayoutGroup(new RectTransform(new Point(editor.Rect.Width, 70))
                {
                    IsFixedSize = true
                },
                                                             isHorizontal: false, childAnchor: Anchor.TopCenter)
                {
                    AbsoluteSpacing = 5,
                    Stretch         = true
                };
                new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.4f), commonnessContainer.RectTransform),
                                 TextManager.GetWithVariable("leveleditor.levelobjcommonness", "[leveltype]", selectedParams.Name), textAlignment: Alignment.Center);
                new GUINumberInput(new RectTransform(new Vector2(0.5f, 0.4f), commonnessContainer.RectTransform), GUINumberInput.NumberType.Float)
                {
                    MinValueFloat  = 0,
                    MaxValueFloat  = 100,
                    FloatValue     = levelObjectPrefab.GetCommonness(selectedParams.Name),
                    OnValueChanged = (numberInput) =>
                    {
                        levelObjectPrefab.OverrideCommonness[selectedParams.Name] = numberInput.FloatValue;
                    }
                };
                new GUIFrame(new RectTransform(new Vector2(1.0f, 0.2f), commonnessContainer.RectTransform), style: null);
                editor.AddCustomContent(commonnessContainer, 1);
            }

            Sprite sprite = levelObjectPrefab.Sprites.FirstOrDefault() ?? levelObjectPrefab.DeformableSprite?.Sprite;

            if (sprite != null)
            {
                editor.AddCustomContent(new GUIButton(new RectTransform(new Point(editor.Rect.Width / 2, (int)(25 * GUI.Scale)))
                {
                    IsFixedSize = true
                },
                                                      TextManager.Get("leveleditor.editsprite"))
                {
                    OnClicked = (btn, userdata) =>
                    {
                        editingSprite = sprite;
                        GameMain.SpriteEditorScreen.SelectSprite(editingSprite);
                        return(true);
                    }
                }, 1);
            }

            if (levelObjectPrefab.DeformableSprite != null)
            {
                var deformEditor = levelObjectPrefab.DeformableSprite.CreateEditor(editor, levelObjectPrefab.SpriteDeformations, levelObjectPrefab.Name);
                deformEditor.GetChild <GUIDropDown>().OnSelected += (selected, userdata) =>
                {
                    CreateLevelObjectEditor(selectedLevelObject);
                    return(true);
                };
                editor.AddCustomContent(deformEditor, editor.ContentCount);
            }
            //child object editing
            new GUITextBlock(new RectTransform(new Point(editor.Rect.Width, 40), editorContainer.Content.RectTransform),
                             TextManager.Get("leveleditor.childobjects"), font: GUI.SubHeadingFont, textAlignment: Alignment.BottomCenter);
            foreach (LevelObjectPrefab.ChildObject childObj in levelObjectPrefab.ChildObjects)
            {
                var childObjFrame = new GUIFrame(new RectTransform(new Point(editor.Rect.Width, 30)));
                var paddedFrame   = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.9f), childObjFrame.RectTransform, Anchor.Center), isHorizontal: true)
                {
                    Stretch         = true,
                    RelativeSpacing = 0.05f
                };
                var selectedChildObj = childObj;
                var dropdown         = new GUIDropDown(new RectTransform(new Vector2(0.5f, 1.0f), paddedFrame.RectTransform), elementCount: 10, selectMultiple: true);
                foreach (LevelObjectPrefab objPrefab in LevelObjectPrefab.List)
                {
                    dropdown.AddItem(objPrefab.Name, objPrefab);
                    if (childObj.AllowedNames.Contains(objPrefab.Name))
                    {
                        dropdown.SelectItem(objPrefab);
                    }
                }
                dropdown.OnSelected = (selected, obj) =>
                {
                    childObj.AllowedNames = dropdown.SelectedDataMultiple.Select(d => ((LevelObjectPrefab)d).Name).ToList();
                    return(true);
                };
                new GUINumberInput(new RectTransform(new Vector2(0.2f, 1.0f), paddedFrame.RectTransform), GUINumberInput.NumberType.Int)
                {
                    MinValueInt    = 0,
                    MaxValueInt    = 10,
                    OnValueChanged = (numberInput) =>
                    {
                        selectedChildObj.MinCount = numberInput.IntValue;
                        selectedChildObj.MaxCount = Math.Max(selectedChildObj.MaxCount, selectedChildObj.MinCount);
                    }
                }.IntValue = childObj.MinCount;
                new GUINumberInput(new RectTransform(new Vector2(0.2f, 1.0f), paddedFrame.RectTransform), GUINumberInput.NumberType.Int)
                {
                    MinValueInt    = 0,
                    MaxValueInt    = 10,
                    OnValueChanged = (numberInput) =>
                    {
                        selectedChildObj.MaxCount = numberInput.IntValue;
                        selectedChildObj.MinCount = Math.Min(selectedChildObj.MaxCount, selectedChildObj.MinCount);
                    }
                }.IntValue = childObj.MaxCount;

                new GUIButton(new RectTransform(new Vector2(0.1f, 1.0f), paddedFrame.RectTransform, scaleBasis: ScaleBasis.BothHeight), style: "GUICancelButton")
                {
                    OnClicked = (btn, userdata) =>
                    {
                        selectedLevelObject.ChildObjects.Remove(selectedChildObj);
                        CreateLevelObjectEditor(selectedLevelObject);
                        return(true);
                    }
                };

                childObjFrame.RectTransform.Parent = editorContainer.Content.RectTransform;
            }

            var buttonContainer = new GUIFrame(new RectTransform(new Vector2(1.0f, 0.01f), editorContainer.Content.RectTransform), style: null);

            new GUIButton(new RectTransform(new Point(editor.Rect.Width / 2, 20), buttonContainer.RectTransform, Anchor.Center),
                          TextManager.Get("leveleditor.addchildobject"))
            {
                OnClicked = (btn, userdata) =>
                {
                    selectedLevelObject.ChildObjects.Add(new LevelObjectPrefab.ChildObject());
                    CreateLevelObjectEditor(selectedLevelObject);
                    return(true);
                }
            };
            buttonContainer.RectTransform.MinSize = buttonContainer.RectTransform.Children.First().MinSize;

            //light editing
            new GUITextBlock(new RectTransform(new Point(editor.Rect.Width, 40), editorContainer.Content.RectTransform),
                             TextManager.Get("leveleditor.lightsources"), textAlignment: Alignment.BottomCenter, font: GUI.SubHeadingFont);
            foreach (LightSourceParams lightSourceParams in selectedLevelObject.LightSourceParams)
            {
                new SerializableEntityEditor(editorContainer.Content.RectTransform, lightSourceParams, inGame: false, showName: true);
            }
            buttonContainer = new GUIFrame(new RectTransform(new Vector2(1.0f, 0.01f), editorContainer.Content.RectTransform), style: null);
            new GUIButton(new RectTransform(new Point(editor.Rect.Width / 2, 20), buttonContainer.RectTransform, Anchor.Center),
                          TextManager.Get("leveleditor.addlightsource"))
            {
                OnClicked = (btn, userdata) =>
                {
                    selectedLevelObject.LightSourceTriggerIndex.Add(-1);
                    selectedLevelObject.LightSourceParams.Add(new LightSourceParams(100.0f, Color.White));
                    CreateLevelObjectEditor(selectedLevelObject);
                    return(true);
                }
            };
            buttonContainer.RectTransform.MinSize = buttonContainer.RectTransform.Children.First().MinSize;
        }
Esempio n. 15
0
        public LevelEditorScreen()
        {
            cam = new Camera()
            {
                MinZoom = 0.01f,
                MaxZoom = 1.0f
            };

            leftPanel = new GUIFrame(new RectTransform(new Vector2(0.125f, 0.8f), Frame.RectTransform)
            {
                MinSize = new Point(150, 0)
            });
            var paddedLeftPanel = new GUILayoutGroup(new RectTransform(new Vector2(0.9f, 0.95f), leftPanel.RectTransform, Anchor.CenterLeft)
            {
                RelativeOffset = new Vector2(0.02f, 0.0f)
            })
            {
                Stretch         = true,
                RelativeSpacing = 0.01f
            };

            paramsList             = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.3f), paddedLeftPanel.RectTransform));
            paramsList.OnSelected += (GUIComponent component, object obj) =>
            {
                selectedParams = obj as LevelGenerationParams;
                editorContainer.ClearChildren();
                SortLevelObjectsList(selectedParams);
                new SerializableEntityEditor(editorContainer.Content.RectTransform, selectedParams, false, true, elementHeight: 20);
                return(true);
            };

            ruinParamsList             = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.2f), paddedLeftPanel.RectTransform));
            ruinParamsList.OnSelected += (GUIComponent component, object obj) =>
            {
                var ruinGenerationParams = obj as RuinGenerationParams;
                editorContainer.ClearChildren();
                new SerializableEntityEditor(editorContainer.Content.RectTransform, ruinGenerationParams, false, true, elementHeight: 20);
                return(true);
            };

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                          TextManager.Get("leveleditor.createlevelobj"))
            {
                OnClicked = (btn, obj) =>
                {
                    Wizard.Instance.Create();
                    return(true);
                }
            };

            lightingEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.025f), paddedLeftPanel.RectTransform),
                                             TextManager.Get("leveleditor.lightingenabled"));

            cursorLightEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.025f), paddedLeftPanel.RectTransform),
                                                TextManager.Get("leveleditor.cursorlightenabled"));

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                          TextManager.Get("leveleditor.reloadtextures"))
            {
                OnClicked = (btn, obj) =>
                {
                    Level.Loaded?.ReloadTextures();
                    return(true);
                }
            };

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                          TextManager.Get("editor.saveall"))
            {
                OnClicked = (btn, obj) =>
                {
                    SerializeAll();
                    return(true);
                }
            };

            rightPanel = new GUIFrame(new RectTransform(new Vector2(0.25f, 1.0f), Frame.RectTransform, Anchor.TopRight)
            {
                MinSize = new Point(450, 0)
            });
            var paddedRightPanel = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), rightPanel.RectTransform, Anchor.Center)
            {
                RelativeOffset = new Vector2(0.02f, 0.0f)
            })
            {
                Stretch         = true,
                RelativeSpacing = 0.01f
            };

            editorContainer = new GUIListBox(new RectTransform(new Vector2(1.0f, 1.0f), paddedRightPanel.RectTransform));

            var seedContainer = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), paddedRightPanel.RectTransform), isHorizontal: true);

            new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), seedContainer.RectTransform), TextManager.Get("leveleditor.levelseed"));
            seedBox = new GUITextBox(new RectTransform(new Vector2(0.5f, 1.0f), seedContainer.RectTransform), ToolBox.RandomSeed(8));

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedRightPanel.RectTransform),
                          TextManager.Get("leveleditor.generate"))
            {
                OnClicked = (btn, obj) =>
                {
                    Submarine.Unload();
                    GameMain.LightManager.ClearLights();
                    Level.CreateRandom(seedBox.Text, generationParams: selectedParams).Generate(mirror: false);
                    GameMain.LightManager.AddLight(pointerLightSource);
                    cam.Position = new Vector2(Level.Loaded.Size.X / 2, Level.Loaded.Size.Y / 2);
                    foreach (GUITextBlock param in paramsList.Content.Children)
                    {
                        param.TextColor = param.UserData == selectedParams ? GUI.Style.Green : param.Style.TextColor;
                    }
                    seedBox.Deselect();
                    return(true);
                }
            };

            bottomPanel = new GUIFrame(new RectTransform(new Vector2(0.75f, 0.22f), Frame.RectTransform, Anchor.BottomLeft)
            {
                MaxSize = new Point(GameMain.GraphicsWidth - rightPanel.Rect.Width, 1000)
            }, style: "GUIFrameBottom");

            levelObjectList = new GUIListBox(new RectTransform(new Vector2(0.99f, 0.85f), bottomPanel.RectTransform, Anchor.Center))
            {
                UseGridLayout = true
            };
            levelObjectList.OnSelected += (GUIComponent component, object obj) =>
            {
                selectedLevelObject = obj as LevelObjectPrefab;
                CreateLevelObjectEditor(selectedLevelObject);
                return(true);
            };

            spriteEditDoneButton = new GUIButton(new RectTransform(new Point(200, 30), anchor: Anchor.BottomRight)
            {
                AbsoluteOffset = new Point(20, 20)
            },
                                                 TextManager.Get("leveleditor.spriteeditdone"))
            {
                OnClicked = (btn, userdata) =>
                {
                    editingSprite = null;
                    return(true);
                }
            };

            topPanel = new GUIFrame(new RectTransform(new Point(400, 100), GUI.Canvas)
            {
                RelativeOffset = new Vector2(leftPanel.RectTransform.RelativeSize.X * 2, 0.0f)
            }, style: "GUIFrameTop");
        }
Esempio n. 16
0
            public GUIMessageBox Create()
            {
                var box = new GUIMessageBox(TextManager.Get("LevelEditorCreateLevelObj"), string.Empty, 
                    new string[] { TextManager.Get("Cancel"), TextManager.Get("Done") }, GameMain.GraphicsWidth / 2, (int)(GameMain.GraphicsHeight * 0.8f));

                box.Content.ChildAnchor = Anchor.TopCenter;
                box.Content.AbsoluteSpacing = 20;
                int elementSize = 30;
                var listBox = new GUIListBox(new RectTransform(new Vector2(1, 0.9f), box.Content.RectTransform));

                new GUITextBlock(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform), 
                    TextManager.Get("LevelEditorLevelObjName")) { CanBeFocused = false };
                var nameBox = new GUITextBox(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform));

                new GUITextBlock(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform), 
                    TextManager.Get("LevelEditorLevelObjTexturePath")) { CanBeFocused = false };
                var texturePathBox = new GUITextBox(new RectTransform(new Point(listBox.Content.Rect.Width, elementSize), listBox.Content.RectTransform));
                foreach (LevelObjectPrefab prefab in LevelObjectPrefab.List)
                {
                    if (prefab.Sprite == null) continue;
                    texturePathBox.Text = Path.GetDirectoryName(prefab.Sprite.FilePath);
                    break;
                }

                newPrefab = new LevelObjectPrefab(null);

                new SerializableEntityEditor(listBox.Content.RectTransform, newPrefab, false, false);
                
                box.Buttons[0].OnClicked += (b, d) =>
                {
                    box.Close();
                    return true;
                };
                // Next
                box.Buttons[1].OnClicked += (b, d) =>
                {
                    if (string.IsNullOrEmpty(nameBox.Text))
                    {
                        nameBox.Flash(Color.Red);
                        GUI.AddMessage(TextManager.Get("LevelEditorLevelObjNameEmpty"), Color.Red);
                        return false;
                    }
                    
                    if (LevelObjectPrefab.List.Any(obj => obj.Name.ToLower() == nameBox.Text.ToLower()))
                    {
                        nameBox.Flash(Color.Red);
                        GUI.AddMessage(TextManager.Get("LevelEditorLevelObjNameTaken"), Color.Red);
                        return false;
                    }

                    if (!File.Exists(texturePathBox.Text))
                    {
                        texturePathBox.Flash(Color.Red);
                        GUI.AddMessage(TextManager.Get("LevelEditorLevelObjTextureNotFound"), Color.Red);
                        return false;
                    }

                    newPrefab.Name = nameBox.Text;
                    
                    XmlWriterSettings settings = new XmlWriterSettings { Indent = true };
                    foreach (string configFile in GameMain.Instance.GetFilesOfType(ContentType.LevelObjectPrefabs))
                    {
                        XDocument doc = XMLExtensions.TryLoadXml(configFile);
                        if (doc?.Root == null) continue;
                        var newElement = new XElement(newPrefab.Name);
                        newPrefab.Save(newElement);
                        newElement.Add(new XElement("Sprite", 
                            new XAttribute("texture", texturePathBox.Text), 
                            new XAttribute("sourcerect", "0,0,100,100"),
                            new XAttribute("origin", "0.5,0.5")));

                        doc.Root.Add(newElement);
                        using (var writer = XmlWriter.Create(configFile, settings))
                        {
                            doc.WriteTo(writer);
                            writer.Flush();
                        }
                        break;
                    }

                    LevelObjectPrefab.List.Add(newPrefab);
                    GameMain.LevelEditorScreen.UpdateLevelObjectsList();

                    box.Close();
                    return true;
                };
                return box;
            }
Esempio n. 17
0
        public void PlaceObjects(Level level, int amount)
        {
            objectGrid = new List <LevelObject> [
                level.Size.X / GridSize,
                (level.Size.Y - level.BottomPos) / GridSize];

            List <SpawnPosition> availableSpawnPositions = new List <SpawnPosition>();
            var levelCells = level.GetAllCells();

            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(levelCells, LevelObjectPrefab.SpawnPosType.Wall));
            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(level.SeaFloor.Cells, LevelObjectPrefab.SpawnPosType.SeaFloor));

            foreach (Structure structure in Structure.WallList)
            {
                if (!structure.HasBody || structure.HiddenInGame)
                {
                    continue;
                }
                if (level.Ruins.Any(r => r.Submarine == structure.Submarine))
                {
                    if (structure.IsHorizontal)
                    {
                        bool topHull    = Hull.FindHull(structure.WorldPosition + Vector2.UnitY * 64) != null;
                        bool bottomHull = Hull.FindHull(structure.WorldPosition - Vector2.UnitY * 64) != null;
                        if (topHull && bottomHull)
                        {
                            continue;
                        }

                        availableSpawnPositions.Add(new SpawnPosition(
                                                        new GraphEdge(new Vector2(structure.WorldRect.X, structure.WorldPosition.Y), new Vector2(structure.WorldRect.Right, structure.WorldPosition.Y)),
                                                        bottomHull ? Vector2.UnitY : -Vector2.UnitY,
                                                        LevelObjectPrefab.SpawnPosType.RuinWall,
                                                        bottomHull ? Alignment.Bottom : Alignment.Top));
                    }
                    else
                    {
                        bool rightHull = Hull.FindHull(structure.WorldPosition + Vector2.UnitX * 64) != null;
                        bool leftHull  = Hull.FindHull(structure.WorldPosition - Vector2.UnitX * 64) != null;
                        if (rightHull && leftHull)
                        {
                            continue;
                        }

                        availableSpawnPositions.Add(new SpawnPosition(
                                                        new GraphEdge(new Vector2(structure.WorldPosition.X, structure.WorldRect.Y), new Vector2(structure.WorldPosition.X, structure.WorldRect.Y - structure.WorldRect.Height)),
                                                        leftHull ? Vector2.UnitX : -Vector2.UnitX,
                                                        LevelObjectPrefab.SpawnPosType.RuinWall,
                                                        leftHull ? Alignment.Left : Alignment.Right));
                    }
                }
            }

            foreach (var posOfInterest in level.PositionsOfInterest)
            {
                if (posOfInterest.PositionType != Level.PositionType.MainPath && posOfInterest.PositionType != Level.PositionType.SidePath)
                {
                    continue;
                }

                availableSpawnPositions.Add(new SpawnPosition(
                                                new GraphEdge(posOfInterest.Position.ToVector2(), posOfInterest.Position.ToVector2() + Vector2.UnitX),
                                                Vector2.UnitY,
                                                LevelObjectPrefab.SpawnPosType.MainPath,
                                                Alignment.Top));
            }

            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.StartPosition - Vector2.UnitX, level.StartPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelStart, Alignment.Top));
            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.EndPosition - Vector2.UnitX, level.EndPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelEnd, Alignment.Top));

            var availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List);

            objects           = new List <LevelObject>();
            updateableObjects = new List <LevelObject>();

            Dictionary <LevelObjectPrefab, List <SpawnPosition> > suitableSpawnPositions = new Dictionary <LevelObjectPrefab, List <SpawnPosition> >();
            Dictionary <LevelObjectPrefab, List <float> >         spawnPositionWeights   = new Dictionary <LevelObjectPrefab, List <float> >();

            for (int i = 0; i < amount; i++)
            {
                //get a random prefab and find a place to spawn it
                LevelObjectPrefab prefab = GetRandomPrefab(level.GenerationParams, availablePrefabs);
                if (prefab == null)
                {
                    continue;
                }
                if (!suitableSpawnPositions.ContainsKey(prefab))
                {
                    float minDistance = level.Size.X * 0.2f;

                    suitableSpawnPositions.Add(prefab,
                                               availableSpawnPositions.Where(sp =>
                                                                             sp.SpawnPosTypes.Any(type => prefab.SpawnPos.HasFlag(type)) &&
                                                                             sp.Length >= prefab.MinSurfaceWidth &&
                                                                             (prefab.AllowAtStart || !level.IsCloseToStart(sp.GraphEdge.Center, minDistance)) &&
                                                                             (prefab.AllowAtEnd || !level.IsCloseToEnd(sp.GraphEdge.Center, minDistance)) &&
                                                                             (sp.Alignment == Alignment.Any || prefab.Alignment.HasFlag(sp.Alignment))).ToList());

                    spawnPositionWeights.Add(prefab,
                                             suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                }

                SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                {
                    continue;
                }
                PlaceObject(prefab, spawnPosition, level);
                if (prefab.MaxCount < amount)
                {
                    if (objects.Count(o => o.Prefab == prefab) >= prefab.MaxCount)
                    {
                        availablePrefabs.Remove(prefab);
                    }
                }
            }

            foreach (Level.Cave cave in level.Caves)
            {
                availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List.FindAll(p => p.SpawnPos.HasFlag(LevelObjectPrefab.SpawnPosType.CaveWall)));
                availableSpawnPositions.Clear();
                suitableSpawnPositions.Clear();
                spawnPositionWeights.Clear();

                var caveCells = cave.Tunnels.SelectMany(t => t.Cells);
                List <VoronoiCell> caveWallCells = new List <VoronoiCell>();
                foreach (var edge in caveCells.SelectMany(c => c.Edges))
                {
                    if (!edge.NextToCave)
                    {
                        continue;
                    }
                    if (edge.Cell1?.CellType == CellType.Solid)
                    {
                        caveWallCells.Add(edge.Cell1);
                    }
                    if (edge.Cell2?.CellType == CellType.Solid)
                    {
                        caveWallCells.Add(edge.Cell2);
                    }
                }
                availableSpawnPositions.AddRange(GetAvailableSpawnPositions(caveWallCells.Distinct(), LevelObjectPrefab.SpawnPosType.CaveWall));

                for (int i = 0; i < cave.CaveGenerationParams.LevelObjectAmount; i++)
                {
                    //get a random prefab and find a place to spawn it
                    LevelObjectPrefab prefab = GetRandomPrefab(cave.CaveGenerationParams, availablePrefabs, requireCaveSpecificOverride: true);
                    if (prefab == null)
                    {
                        continue;
                    }
                    if (!suitableSpawnPositions.ContainsKey(prefab))
                    {
                        suitableSpawnPositions.Add(prefab,
                                                   availableSpawnPositions.Where(sp =>
                                                                                 sp.Length >= prefab.MinSurfaceWidth &&
                                                                                 (sp.Alignment == Alignment.Any || prefab.Alignment.HasFlag(sp.Alignment))).ToList());
                        spawnPositionWeights.Add(prefab,
                                                 suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                    }
                    SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                    if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                    {
                        continue;
                    }
                    PlaceObject(prefab, spawnPosition, level, cave);
                    if (prefab.MaxCount < amount)
                    {
                        if (objects.Count(o => o.Prefab == prefab && o.ParentCave == cave) >= prefab.MaxCount)
                        {
                            availablePrefabs.Remove(prefab);
                        }
                    }
                }
            }
        }
Esempio n. 18
0
        public LevelEditorScreen()
        {
            cam = new Camera()
            {
                MinZoom = 0.01f,
                MaxZoom = 1.0f
            };

            leftPanel = new GUIFrame(new RectTransform(new Vector2(0.125f, 0.8f), Frame.RectTransform)
            {
                MinSize = new Point(150, 0)
            });
            var paddedLeftPanel = new GUILayoutGroup(new RectTransform(new Vector2(0.9f, 0.95f), leftPanel.RectTransform, Anchor.CenterLeft)
            {
                RelativeOffset = new Vector2(0.02f, 0.0f)
            })
            {
                Stretch         = true,
                RelativeSpacing = 0.01f
            };

            paramsList             = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.3f), paddedLeftPanel.RectTransform));
            paramsList.OnSelected += (GUIComponent component, object obj) =>
            {
                selectedParams = obj as LevelGenerationParams;
                editorContainer.ClearChildren();
                SortLevelObjectsList(selectedParams);
                new SerializableEntityEditor(editorContainer.Content.RectTransform, selectedParams, false, true, elementHeight: 20);
                return(true);
            };

            var ruinTitle = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.0f), paddedLeftPanel.RectTransform), TextManager.Get("leveleditor.ruinparams"), font: GUI.SubHeadingFont);

            ruinParamsList             = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.1f), paddedLeftPanel.RectTransform));
            ruinParamsList.OnSelected += (GUIComponent component, object obj) =>
            {
                var ruinGenerationParams = obj as RuinGenerationParams;
                editorContainer.ClearChildren();
                new SerializableEntityEditor(editorContainer.Content.RectTransform, ruinGenerationParams, false, true, elementHeight: 20);
                return(true);
            };

            var outpostTitle = new GUITextBlock(new RectTransform(new Vector2(1.0f, 0.0f), paddedLeftPanel.RectTransform), TextManager.Get("leveleditor.outpostparams"), font: GUI.SubHeadingFont);

            GUITextBlock.AutoScaleAndNormalize(ruinTitle, outpostTitle);

            outpostParamsList             = new GUIListBox(new RectTransform(new Vector2(1.0f, 0.2f), paddedLeftPanel.RectTransform));
            outpostParamsList.OnSelected += (GUIComponent component, object obj) =>
            {
                var outpostGenerationParams = obj as OutpostGenerationParams;
                editorContainer.ClearChildren();
                var outpostParamsEditor = new SerializableEntityEditor(editorContainer.Content.RectTransform, outpostGenerationParams, false, true, elementHeight: 20);

                // location type -------------------------

                var locationTypeGroup = new GUILayoutGroup(new RectTransform(new Point(editorContainer.Content.Rect.Width, 20)), isHorizontal: true, childAnchor: Anchor.CenterLeft)
                {
                    Stretch = true
                };

                new GUITextBlock(new RectTransform(new Vector2(0.5f, 1f), locationTypeGroup.RectTransform), TextManager.Get("outpostmoduleallowedlocationtypes"), textAlignment: Alignment.CenterLeft);
                HashSet <string> availableLocationTypes = new HashSet <string> {
                    "any"
                };
                foreach (LocationType locationType in LocationType.List)
                {
                    availableLocationTypes.Add(locationType.Identifier);
                }

                var locationTypeDropDown = new GUIDropDown(new RectTransform(new Vector2(0.5f, 1f), locationTypeGroup.RectTransform),
                                                           text: string.Join(", ", outpostGenerationParams.AllowedLocationTypes.Select(lt => TextManager.Capitalize(lt)) ?? "any".ToEnumerable()), selectMultiple: true);
                foreach (string locationType in availableLocationTypes)
                {
                    locationTypeDropDown.AddItem(TextManager.Capitalize(locationType), locationType);
                    if (outpostGenerationParams.AllowedLocationTypes.Contains(locationType))
                    {
                        locationTypeDropDown.SelectItem(locationType);
                    }
                }
                if (!outpostGenerationParams.AllowedLocationTypes.Any())
                {
                    locationTypeDropDown.SelectItem("any");
                }

                locationTypeDropDown.OnSelected += (_, __) =>
                {
                    outpostGenerationParams.SetAllowedLocationTypes(locationTypeDropDown.SelectedDataMultiple.Cast <string>());
                    locationTypeDropDown.Text = ToolBox.LimitString(locationTypeDropDown.Text, locationTypeDropDown.Font, locationTypeDropDown.Rect.Width);
                    return(true);
                };
                locationTypeGroup.RectTransform.MinSize = new Point(locationTypeGroup.Rect.Width, locationTypeGroup.RectTransform.Children.Max(c => c.MinSize.Y));

                outpostParamsEditor.AddCustomContent(locationTypeGroup, 100);

                // module count -------------------------

                var moduleLabel = new GUITextBlock(new RectTransform(new Point(editorContainer.Content.Rect.Width, (int)(70 * GUI.Scale))), TextManager.Get("submarinetype.outpostmodules"), font: GUI.SubHeadingFont);
                outpostParamsEditor.AddCustomContent(moduleLabel, 100);

                foreach (KeyValuePair <string, int> moduleCount in outpostGenerationParams.ModuleCounts)
                {
                    var moduleCountGroup = new GUILayoutGroup(new RectTransform(new Point(editorContainer.Content.Rect.Width, (int)(25 * GUI.Scale))), isHorizontal: true, childAnchor: Anchor.CenterLeft);
                    new GUITextBlock(new RectTransform(new Vector2(0.5f, 1f), moduleCountGroup.RectTransform), TextManager.Capitalize(moduleCount.Key), textAlignment: Alignment.CenterLeft);
                    new GUINumberInput(new RectTransform(new Vector2(0.5f, 1f), moduleCountGroup.RectTransform), GUINumberInput.NumberType.Int)
                    {
                        MinValueInt    = 0,
                        MaxValueInt    = 100,
                        IntValue       = moduleCount.Value,
                        OnValueChanged = (numInput) =>
                        {
                            outpostGenerationParams.SetModuleCount(moduleCount.Key, numInput.IntValue);
                            if (numInput.IntValue == 0)
                            {
                                outpostParamsList.Select(outpostParamsList.SelectedData);
                            }
                        }
                    };
                    moduleCountGroup.RectTransform.MinSize = new Point(moduleCountGroup.Rect.Width, moduleCountGroup.RectTransform.Children.Max(c => c.MinSize.Y));
                    outpostParamsEditor.AddCustomContent(moduleCountGroup, 100);
                }

                // add module count -------------------------

                var addModuleCountGroup = new GUILayoutGroup(new RectTransform(new Point(editorContainer.Content.Rect.Width, (int)(40 * GUI.Scale))), isHorizontal: true, childAnchor: Anchor.Center);

                HashSet <string> availableFlags = new HashSet <string>();
                foreach (string flag in OutpostGenerationParams.Params.SelectMany(p => p.ModuleCounts.Select(m => m.Key)))
                {
                    availableFlags.Add(flag);
                }
                foreach (var sub in SubmarineInfo.SavedSubmarines)
                {
                    if (sub.OutpostModuleInfo == null)
                    {
                        continue;
                    }
                    foreach (string flag in sub.OutpostModuleInfo.ModuleFlags)
                    {
                        availableFlags.Add(flag);
                    }
                }

                var moduleTypeDropDown = new GUIDropDown(new RectTransform(new Vector2(0.8f, 0.8f), addModuleCountGroup.RectTransform),
                                                         text: TextManager.Get("leveleditor.addmoduletype"));
                foreach (string flag in availableFlags)
                {
                    if (outpostGenerationParams.ModuleCounts.Any(mc => mc.Key.Equals(flag, StringComparison.OrdinalIgnoreCase)))
                    {
                        continue;
                    }
                    moduleTypeDropDown.AddItem(TextManager.Capitalize(flag), flag);
                }
                moduleTypeDropDown.OnSelected += (_, userdata) =>
                {
                    outpostGenerationParams.SetModuleCount(userdata as string, 1);
                    outpostParamsList.Select(outpostParamsList.SelectedData);
                    return(true);
                };
                addModuleCountGroup.RectTransform.MinSize = new Point(addModuleCountGroup.Rect.Width, addModuleCountGroup.RectTransform.Children.Max(c => c.MinSize.Y));
                outpostParamsEditor.AddCustomContent(addModuleCountGroup, 100);

                return(true);
            };

            var createLevelObjButton = new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                                                     TextManager.Get("leveleditor.createlevelobj"))
            {
                OnClicked = (btn, obj) =>
                {
                    Wizard.Instance.Create();
                    return(true);
                }
            };

            GUITextBlock.AutoScaleAndNormalize(createLevelObjButton.TextBlock);

            lightingEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.025f), paddedLeftPanel.RectTransform),
                                             TextManager.Get("leveleditor.lightingenabled"));

            cursorLightEnabled = new GUITickBox(new RectTransform(new Vector2(1.0f, 0.025f), paddedLeftPanel.RectTransform),
                                                TextManager.Get("leveleditor.cursorlightenabled"));

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                          TextManager.Get("leveleditor.reloadtextures"))
            {
                OnClicked = (btn, obj) =>
                {
                    Level.Loaded?.ReloadTextures();
                    return(true);
                }
            };

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedLeftPanel.RectTransform),
                          TextManager.Get("editor.saveall"))
            {
                OnClicked = (btn, obj) =>
                {
                    SerializeAll();
                    return(true);
                }
            };

            rightPanel = new GUIFrame(new RectTransform(new Vector2(0.25f, 1.0f), Frame.RectTransform, Anchor.TopRight)
            {
                MinSize = new Point(450, 0)
            });
            var paddedRightPanel = new GUILayoutGroup(new RectTransform(new Vector2(0.95f, 0.95f), rightPanel.RectTransform, Anchor.Center)
            {
                RelativeOffset = new Vector2(0.02f, 0.0f)
            })
            {
                Stretch         = true,
                RelativeSpacing = 0.01f
            };

            editorContainer = new GUIListBox(new RectTransform(new Vector2(1.0f, 1.0f), paddedRightPanel.RectTransform));

            var seedContainer = new GUILayoutGroup(new RectTransform(new Vector2(1.0f, 0.05f), paddedRightPanel.RectTransform), isHorizontal: true);

            new GUITextBlock(new RectTransform(new Vector2(0.5f, 1.0f), seedContainer.RectTransform), TextManager.Get("leveleditor.levelseed"));
            seedBox = new GUITextBox(new RectTransform(new Vector2(0.5f, 1.0f), seedContainer.RectTransform), ToolBox.RandomSeed(8));

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedRightPanel.RectTransform),
                          TextManager.Get("leveleditor.generate"))
            {
                OnClicked = (btn, obj) =>
                {
                    Submarine.Unload();
                    GameMain.LightManager.ClearLights();
                    LevelData levelData = LevelData.CreateRandom(seedBox.Text, generationParams: selectedParams);
                    levelData.ForceOutpostGenerationParams = outpostParamsList.SelectedData as OutpostGenerationParams;
                    Level.Generate(levelData, mirror: false);
                    GameMain.LightManager.AddLight(pointerLightSource);
                    cam.Position = new Vector2(Level.Loaded.Size.X / 2, Level.Loaded.Size.Y / 2);
                    foreach (GUITextBlock param in paramsList.Content.Children)
                    {
                        param.TextColor = param.UserData == selectedParams ? GUI.Style.Green : param.Style.TextColor;
                    }
                    seedBox.Deselect();
                    return(true);
                }
            };

            new GUIButton(new RectTransform(new Vector2(1.0f, 0.05f), paddedRightPanel.RectTransform),
                          TextManager.Get("leveleditor.test"))
            {
                OnClicked = (btn, obj) =>
                {
                    if (Level.Loaded?.LevelData == null)
                    {
                        return(false);
                    }

                    GameMain.GameScreen.Select();

                    var currEntities = Entity.GetEntities().ToList();
                    if (Submarine.MainSub != null)
                    {
                        var toRemove = Entity.GetEntities().Where(e => e.Submarine == Submarine.MainSub).ToList();
                        foreach (Entity ent in toRemove)
                        {
                            ent.Remove();
                        }
                        Submarine.MainSub.Remove();
                    }

                    //TODO: hacky workaround to check for wrecks and outposts, refactor SubmarineInfo and ContentType at some point
                    var nonPlayerFiles = ContentPackage.GetFilesOfType(GameMain.Config.AllEnabledPackages, ContentType.Wreck).ToList();
                    nonPlayerFiles.AddRange(ContentPackage.GetFilesOfType(GameMain.Config.AllEnabledPackages, ContentType.Outpost));
                    nonPlayerFiles.AddRange(ContentPackage.GetFilesOfType(GameMain.Config.AllEnabledPackages, ContentType.OutpostModule));
                    SubmarineInfo subInfo = SubmarineInfo.SavedSubmarines.FirstOrDefault(s => s.Name.Equals(GameMain.Config.QuickStartSubmarineName, StringComparison.InvariantCultureIgnoreCase));
                    subInfo ??= SubmarineInfo.SavedSubmarines.GetRandom(s =>
                                                                        s.IsPlayer && !s.HasTag(SubmarineTag.Shuttle) &&
                                                                        !nonPlayerFiles.Any(f => f.Path.CleanUpPath().Equals(s.FilePath.CleanUpPath(), StringComparison.InvariantCultureIgnoreCase)));
                    GameSession gameSession = new GameSession(subInfo, "", GameModePreset.TestMode, null);
                    gameSession.StartRound(Level.Loaded.LevelData);
                    (gameSession.GameMode as TestGameMode).OnRoundEnd = () =>
                    {
                        GameMain.LevelEditorScreen.Select();
                        Submarine.MainSub.Remove();

                        var toRemove = Entity.GetEntities().Where(e => !currEntities.Contains(e)).ToList();
                        foreach (Entity ent in toRemove)
                        {
                            ent.Remove();
                        }

                        Submarine.MainSub = null;
                    };

                    GameMain.GameSession = gameSession;

                    return(true);
                }
            };

            bottomPanel = new GUIFrame(new RectTransform(new Vector2(0.75f, 0.22f), Frame.RectTransform, Anchor.BottomLeft)
            {
                MaxSize = new Point(GameMain.GraphicsWidth - rightPanel.Rect.Width, 1000)
            }, style: "GUIFrameBottom");

            levelObjectList = new GUIListBox(new RectTransform(new Vector2(0.99f, 0.85f), bottomPanel.RectTransform, Anchor.Center))
            {
                UseGridLayout = true
            };
            levelObjectList.OnSelected += (GUIComponent component, object obj) =>
            {
                selectedLevelObject = obj as LevelObjectPrefab;
                CreateLevelObjectEditor(selectedLevelObject);
                return(true);
            };

            spriteEditDoneButton = new GUIButton(new RectTransform(new Point(200, 30), anchor: Anchor.BottomRight)
            {
                AbsoluteOffset = new Point(20, 20)
            },
                                                 TextManager.Get("leveleditor.spriteeditdone"))
            {
                OnClicked = (btn, userdata) =>
                {
                    editingSprite = null;
                    return(true);
                }
            };

            topPanel = new GUIFrame(new RectTransform(new Point(400, 100), GUI.Canvas)
            {
                RelativeOffset = new Vector2(leftPanel.RectTransform.RelativeSize.X * 2, 0.0f)
            }, style: "GUIFrameTop");
        }
        public void PlaceObjects(Level level, int amount)
        {
            objectGrid = new List <LevelObject> [
                level.Size.X / GridSize,
                (level.Size.Y - level.BottomPos) / GridSize];

            List <SpawnPosition> availableSpawnPositions = new List <SpawnPosition>();
            var levelCells = level.GetAllCells();

            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(levelCells, LevelObjectPrefab.SpawnPosType.Wall));
            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(level.SeaFloor.Cells, LevelObjectPrefab.SpawnPosType.SeaFloor));

            foreach (RuinGeneration.Ruin ruin in level.Ruins)
            {
                foreach (var ruinShape in ruin.RuinShapes)
                {
                    foreach (var wall in ruinShape.Walls)
                    {
                        availableSpawnPositions.Add(new SpawnPosition(
                                                        new GraphEdge(wall.A, wall.B),
                                                        (wall.A + wall.B) / 2.0f - ruinShape.Center,
                                                        LevelObjectPrefab.SpawnPosType.RuinWall,
                                                        ruinShape.GetLineAlignment(wall)));
                    }
                }
            }

            foreach (var posOfInterest in level.PositionsOfInterest)
            {
                if (posOfInterest.PositionType != Level.PositionType.MainPath)
                {
                    continue;
                }

                availableSpawnPositions.Add(new SpawnPosition(
                                                new GraphEdge(posOfInterest.Position.ToVector2(), posOfInterest.Position.ToVector2() + Vector2.UnitX),
                                                Vector2.UnitY,
                                                LevelObjectPrefab.SpawnPosType.MainPath,
                                                Alignment.Top));
            }

            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.StartPosition - Vector2.UnitX, level.StartPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelStart, Alignment.Top));
            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.EndPosition - Vector2.UnitX, level.EndPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelEnd, Alignment.Top));

            var availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List);

            objects = new List <LevelObject>();

            Dictionary <LevelObjectPrefab, List <SpawnPosition> > suitableSpawnPositions = new Dictionary <LevelObjectPrefab, List <SpawnPosition> >();
            Dictionary <LevelObjectPrefab, List <float> >         spawnPositionWeights   = new Dictionary <LevelObjectPrefab, List <float> >();

            for (int i = 0; i < amount; i++)
            {
                //get a random prefab and find a place to spawn it
                LevelObjectPrefab prefab = GetRandomPrefab(level.GenerationParams.Identifier, availablePrefabs);
                if (prefab == null)
                {
                    continue;
                }
                if (!suitableSpawnPositions.ContainsKey(prefab))
                {
                    suitableSpawnPositions.Add(prefab, availableSpawnPositions.Where(sp =>
                                                                                     prefab.SpawnPos.HasFlag(sp.SpawnPosType) && (sp.Length >= prefab.MinSurfaceWidth && prefab.Alignment.HasFlag(sp.Alignment) || sp.SpawnPosType == LevelObjectPrefab.SpawnPosType.LevelEnd || sp.SpawnPosType == LevelObjectPrefab.SpawnPosType.LevelStart)).ToList());
                    spawnPositionWeights.Add(prefab,
                                             suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                }

                SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                {
                    continue;
                }

                float rotation = 0.0f;
                if (prefab.AlignWithSurface && spawnPosition != null)
                {
                    rotation = MathUtils.VectorToAngle(new Vector2(spawnPosition.Normal.Y, spawnPosition.Normal.X));
                }
                rotation += Rand.Range(prefab.RandomRotationRad.X, prefab.RandomRotationRad.Y, Rand.RandSync.Server);

                Vector2 position = Vector2.Zero;
                Vector2 edgeDir  = Vector2.UnitX;
                if (spawnPosition == null)
                {
                    position = new Vector2(
                        Rand.Range(0.0f, level.Size.X, Rand.RandSync.Server),
                        Rand.Range(0.0f, level.Size.Y, Rand.RandSync.Server));
                }
                else
                {
                    edgeDir  = (spawnPosition.GraphEdge.Point1 - spawnPosition.GraphEdge.Point2) / spawnPosition.Length;
                    position = spawnPosition.GraphEdge.Point2 + edgeDir * Rand.Range(prefab.MinSurfaceWidth / 2.0f, spawnPosition.Length - prefab.MinSurfaceWidth / 2.0f, Rand.RandSync.Server);
                }

                var newObject = new LevelObject(prefab,
                                                new Vector3(position, Rand.Range(prefab.DepthRange.X, prefab.DepthRange.Y, Rand.RandSync.Server)), Rand.Range(prefab.MinSize, prefab.MaxSize, Rand.RandSync.Server), rotation);
                AddObject(newObject, level);
                if (prefab.MaxCount < amount)
                {
                    if (objects.Count(o => o.Prefab == prefab) >= prefab.MaxCount)
                    {
                        availablePrefabs.Remove(prefab);
                    }
                }

                foreach (LevelObjectPrefab.ChildObject child in prefab.ChildObjects)
                {
                    int childCount = Rand.Range(child.MinCount, child.MaxCount, Rand.RandSync.Server);
                    for (int j = 0; j < childCount; j++)
                    {
                        var matchingPrefabs = LevelObjectPrefab.List.Where(p => child.AllowedNames.Contains(p.Name));
                        int prefabCount     = matchingPrefabs.Count();
                        var childPrefab     = prefabCount == 0 ? null : matchingPrefabs.ElementAt(Rand.Range(0, prefabCount, Rand.RandSync.Server));
                        if (childPrefab == null)
                        {
                            continue;
                        }

                        Vector2 childPos = position + edgeDir * Rand.Range(-0.5f, 0.5f, Rand.RandSync.Server) * prefab.MinSurfaceWidth;

                        var childObject = new LevelObject(childPrefab,
                                                          new Vector3(childPos, Rand.Range(childPrefab.DepthRange.X, childPrefab.DepthRange.Y, Rand.RandSync.Server)),
                                                          Rand.Range(childPrefab.MinSize, childPrefab.MaxSize, Rand.RandSync.Server),
                                                          rotation + Rand.Range(childPrefab.RandomRotationRad.X, childPrefab.RandomRotationRad.Y, Rand.RandSync.Server));

                        AddObject(childObject, level);
                    }
                }
            }
        }
        public void PlaceObjects(Level level, int amount)
        {
            objectGrid = new List <LevelObject> [
                level.Size.X / GridSize,
                (level.Size.Y - level.BottomPos) / GridSize];

            List <SpawnPosition> availableSpawnPositions = new List <SpawnPosition>();
            var levelCells = level.GetAllCells();

            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(levelCells, LevelObjectPrefab.SpawnPosType.Wall));
            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(level.SeaFloor.Cells, LevelObjectPrefab.SpawnPosType.SeaFloor));

            foreach (RuinGeneration.Ruin ruin in level.Ruins)
            {
                foreach (var ruinShape in ruin.RuinShapes)
                {
                    foreach (var wall in ruinShape.Walls)
                    {
                        availableSpawnPositions.Add(new SpawnPosition(
                                                        new GraphEdge(wall.A, wall.B),
                                                        (wall.A + wall.B) / 2.0f - ruinShape.Center,
                                                        LevelObjectPrefab.SpawnPosType.RuinWall,
                                                        ruinShape.GetLineAlignment(wall)));
                    }
                }
            }

            foreach (var posOfInterest in level.PositionsOfInterest)
            {
                if (posOfInterest.PositionType != Level.PositionType.MainPath && posOfInterest.PositionType != Level.PositionType.SidePath)
                {
                    continue;
                }

                availableSpawnPositions.Add(new SpawnPosition(
                                                new GraphEdge(posOfInterest.Position.ToVector2(), posOfInterest.Position.ToVector2() + Vector2.UnitX),
                                                Vector2.UnitY,
                                                LevelObjectPrefab.SpawnPosType.MainPath,
                                                Alignment.Top));
            }

            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.StartPosition - Vector2.UnitX, level.StartPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelStart, Alignment.Top));
            availableSpawnPositions.Add(new SpawnPosition(
                                            new GraphEdge(level.EndPosition - Vector2.UnitX, level.EndPosition + Vector2.UnitX),
                                            -Vector2.UnitY, LevelObjectPrefab.SpawnPosType.LevelEnd, Alignment.Top));

            var availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List);

            objects           = new List <LevelObject>();
            updateableObjects = new List <LevelObject>();

            Dictionary <LevelObjectPrefab, List <SpawnPosition> > suitableSpawnPositions = new Dictionary <LevelObjectPrefab, List <SpawnPosition> >();
            Dictionary <LevelObjectPrefab, List <float> >         spawnPositionWeights   = new Dictionary <LevelObjectPrefab, List <float> >();

            for (int i = 0; i < amount; i++)
            {
                //get a random prefab and find a place to spawn it
                LevelObjectPrefab prefab = GetRandomPrefab(level.GenerationParams, availablePrefabs);
                if (prefab == null)
                {
                    continue;
                }
                if (!suitableSpawnPositions.ContainsKey(prefab))
                {
                    suitableSpawnPositions.Add(prefab,
                                               availableSpawnPositions.Where(sp =>
                                                                             sp.SpawnPosTypes.Any(type => prefab.SpawnPos.HasFlag(type)) &&
                                                                             sp.Length >= prefab.MinSurfaceWidth &&
                                                                             (sp.Alignment == Alignment.Any || prefab.Alignment.HasFlag(sp.Alignment))).ToList());
                    spawnPositionWeights.Add(prefab,
                                             suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                }

                SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                {
                    continue;
                }
                PlaceObject(prefab, spawnPosition, level);
                if (prefab.MaxCount < amount)
                {
                    if (objects.Count(o => o.Prefab == prefab) >= prefab.MaxCount)
                    {
                        availablePrefabs.Remove(prefab);
                    }
                }
            }

            foreach (Level.Cave cave in level.Caves)
            {
                availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List.FindAll(p => p.SpawnPos.HasFlag(LevelObjectPrefab.SpawnPosType.CaveWall)));
                availableSpawnPositions.Clear();
                suitableSpawnPositions.Clear();
                spawnPositionWeights.Clear();

                var caveCells = cave.Tunnels.SelectMany(t => t.Cells);
                List <VoronoiCell> caveWallCells = new List <VoronoiCell>();
                foreach (var edge in caveCells.SelectMany(c => c.Edges))
                {
                    if (!edge.NextToCave)
                    {
                        continue;
                    }
                    if (edge.Cell1?.CellType == CellType.Solid)
                    {
                        caveWallCells.Add(edge.Cell1);
                    }
                    if (edge.Cell2?.CellType == CellType.Solid)
                    {
                        caveWallCells.Add(edge.Cell2);
                    }
                }
                availableSpawnPositions.AddRange(GetAvailableSpawnPositions(caveWallCells.Distinct(), LevelObjectPrefab.SpawnPosType.CaveWall));

                for (int i = 0; i < cave.CaveGenerationParams.LevelObjectAmount; i++)
                {
                    //get a random prefab and find a place to spawn it
                    LevelObjectPrefab prefab = GetRandomPrefab(cave.CaveGenerationParams, availablePrefabs);
                    if (prefab == null)
                    {
                        continue;
                    }
                    if (!suitableSpawnPositions.ContainsKey(prefab))
                    {
                        suitableSpawnPositions.Add(prefab,
                                                   availableSpawnPositions.Where(sp =>
                                                                                 sp.Length >= prefab.MinSurfaceWidth &&
                                                                                 (sp.Alignment == Alignment.Any || prefab.Alignment.HasFlag(sp.Alignment))).ToList());
                        spawnPositionWeights.Add(prefab,
                                                 suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                    }
                    SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                    if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                    {
                        continue;
                    }
                    PlaceObject(prefab, spawnPosition, level);
                    if (prefab.MaxCount < amount)
                    {
                        if (objects.Count(o => o.Prefab == prefab) >= prefab.MaxCount)
                        {
                            availablePrefabs.Remove(prefab);
                        }
                    }
                }
            }
        }
        private SpawnPosition FindObjectPosition(List <SpawnPosition> availableSpawnPositions, Level level, LevelObjectPrefab prefab)
        {
            if (prefab.SpawnPos == LevelObjectPrefab.SpawnPosType.None)
            {
                return(null);
            }

            var suitableSpawnPositions = availableSpawnPositions.Where(sp =>
                                                                       prefab.SpawnPos.HasFlag(sp.SpawnPosType) && sp.Length >= prefab.MinSurfaceWidth && prefab.Alignment.HasFlag(sp.Alignment)).ToList();

            return(ToolBox.SelectWeightedRandom(suitableSpawnPositions, suitableSpawnPositions.Select(sp => sp.GetSpawnProbability(prefab)).ToList(), Rand.RandSync.Server));
        }
Esempio n. 22
0
        private IEnumerable <object> Load()
        {
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE", Color.Lime);
            }

            SoundManager = new Sounds.SoundManager();
            SoundManager.SetCategoryGainMultiplier("default", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("ui", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("waterambience", Config.SoundVolume);
            SoundManager.SetCategoryGainMultiplier("music", Config.MusicVolume);
            SoundManager.SetCategoryGainMultiplier("voip", Config.VoiceChatVolume);
            if (Config.EnableSplashScreen)
            {
                try
                {
                    (TitleScreen as LoadingScreen).SplashScreen = new Video(base.GraphicsDevice, SoundManager, "Content/splashscreen.mp4", 1280, 720);
                }
                catch (Exception e)
                {
                    Config.EnableSplashScreen = false;
                    DebugConsole.ThrowError("Playing the splash screen failed.", e);
                }
            }

            GUI.Init(Window, Config.SelectedContentPackages, GraphicsDevice);
            DebugConsole.Init();

            SteamManager.Initialize();
            if (Config.AutoUpdateWorkshopItems)
            {
                if (SteamManager.AutoUpdateWorkshopItems())
                {
                    ContentPackage.LoadAll(ContentPackage.Folder);
                    Config.ReloadContentPackages();
                }
            }

            if (SelectedPackages.Count == 0)
            {
                DebugConsole.Log("No content packages selected");
            }
            else
            {
                DebugConsole.Log("Selected content packages: " + string.Join(", ", SelectedPackages.Select(cp => cp.Name)));
            }

#if DEBUG
            GameSettings.ShowUserStatisticsPrompt = false;
            GameSettings.SendUserStatistics       = false;
#endif

            InitUserStats();

            yield return(CoroutineStatus.Running);


            LightManager = new Lights.LightManager(base.GraphicsDevice, Content);

            WaterRenderer.Instance = new WaterRenderer(base.GraphicsDevice, Content);
            TitleScreen.LoadState  = 1.0f;
            yield return(CoroutineStatus.Running);

            GUI.LoadContent();
            TitleScreen.LoadState = 2.0f;

            yield return(CoroutineStatus.Running);

            MissionPrefab.Init();
            MapEntityPrefab.Init();
            Tutorials.Tutorial.Init();
            MapGenerationParams.Init();
            LevelGenerationParams.LoadPresets();
            ScriptedEventSet.LoadPrefabs();
            AfflictionPrefab.LoadAll(GetFilesOfType(ContentType.Afflictions));
            TitleScreen.LoadState = 10.0f;
            yield return(CoroutineStatus.Running);

            StructurePrefab.LoadAll(GetFilesOfType(ContentType.Structure));
            TitleScreen.LoadState = 15.0f;
            yield return(CoroutineStatus.Running);

            ItemPrefab.LoadAll(GetFilesOfType(ContentType.Item));
            TitleScreen.LoadState = 25.0f;
            yield return(CoroutineStatus.Running);

            JobPrefab.LoadAll(GetFilesOfType(ContentType.Jobs));
            // Add any missing jobs from the prefab into Config.JobNamePreferences.
            foreach (JobPrefab job in JobPrefab.List)
            {
                if (!Config.JobPreferences.Contains(job.Identifier))
                {
                    Config.JobPreferences.Add(job.Identifier);
                }
            }

            NPCConversation.LoadAll(GetFilesOfType(ContentType.NPCConversations));

            ItemAssemblyPrefab.LoadAll();
            TitleScreen.LoadState = 30.0f;
            yield return(CoroutineStatus.Running);

            Debug.WriteLine("sounds");

            int i = 0;
            foreach (object crObj in SoundPlayer.Init())
            {
                CoroutineStatus status = (CoroutineStatus)crObj;
                if (status == CoroutineStatus.Success)
                {
                    break;
                }

                i++;
                TitleScreen.LoadState = SoundPlayer.SoundCount == 0 ?
                                        30.0f :
                                        Math.Min(30.0f + 40.0f * i / Math.Max(SoundPlayer.SoundCount, 1), 70.0f);

                yield return(CoroutineStatus.Running);
            }

            TitleScreen.LoadState = 70.0f;
            yield return(CoroutineStatus.Running);

            GameModePreset.Init();

            Submarine.RefreshSavedSubs();

            TitleScreen.LoadState = 80.0f;

            yield return(CoroutineStatus.Running);

            GameScreen = new GameScreen(GraphicsDeviceManager.GraphicsDevice, Content);

            TitleScreen.LoadState = 90.0f;

            yield return(CoroutineStatus.Running);

            MainMenuScreen   = new MainMenuScreen(this);
            LobbyScreen      = new LobbyScreen();
            ServerListScreen = new ServerListScreen();

            if (SteamManager.USE_STEAM)
            {
                SteamWorkshopScreen = new SteamWorkshopScreen();
            }

            SubEditorScreen       = new SubEditorScreen();
            ParticleEditorScreen  = new ParticleEditorScreen();
            LevelEditorScreen     = new LevelEditorScreen();
            SpriteEditorScreen    = new SpriteEditorScreen();
            CharacterEditorScreen = new CharacterEditorScreen();

            yield return(CoroutineStatus.Running);

            TitleScreen.LoadState = 95.0f;
            ParticleManager       = new ParticleManager(GameScreen.Cam);
            ParticleManager.LoadPrefabs();
            TitleScreen.LoadState = 97.0f;
            LevelObjectPrefab.LoadAll();
            DecalManager          = new DecalManager();
            TitleScreen.LoadState = 99.0f;
            yield return(CoroutineStatus.Running);

            LocationType.Init();
            MainMenuScreen.Select();

            CheckContentPackage();

            TitleScreen.LoadState = 100.0f;
            hasLoaded             = true;
            if (GameSettings.VerboseLogging)
            {
                DebugConsole.NewMessage("LOADING COROUTINE FINISHED", Color.Lime);
            }
            yield return(CoroutineStatus.Success);
        }
        public void PlaceObjects(Level level, int amount)
        {
            objectGrid = new List <LevelObject> [
                level.Size.X / GridSize,
                (level.Size.Y - level.BottomPos) / GridSize];

            List <SpawnPosition> availableSpawnPositions = new List <SpawnPosition>();
            var levelCells = level.GetAllCells();

            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(levelCells, LevelObjectPrefab.SpawnPosType.Wall));
            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(level.SeaFloor.Cells, LevelObjectPrefab.SpawnPosType.SeaFloor));

            foreach (RuinGeneration.Ruin ruin in level.Ruins)
            {
                foreach (var ruinShape in ruin.RuinShapes)
                {
                    foreach (var wall in ruinShape.Walls)
                    {
                        availableSpawnPositions.Add(new SpawnPosition(
                                                        new GraphEdge(wall.A, wall.B),
                                                        (wall.A + wall.B) / 2.0f - ruinShape.Center,
                                                        LevelObjectPrefab.SpawnPosType.RuinWall,
                                                        ruinShape.GetLineAlignment(wall)));
                    }
                }
            }

            foreach (var posOfInterest in level.PositionsOfInterest)
            {
                if (posOfInterest.PositionType != Level.PositionType.MainPath)
                {
                    continue;
                }

                availableSpawnPositions.Add(new SpawnPosition(
                                                new GraphEdge(posOfInterest.Position.ToVector2(), posOfInterest.Position.ToVector2() + Vector2.UnitX),
                                                Vector2.UnitY,
                                                LevelObjectPrefab.SpawnPosType.MainPath,
                                                Alignment.Top));
            }

            objects = new List <LevelObject>();
            for (int i = 0; i < amount; i++)
            {
                //get a random prefab and find a place to spawn it
                LevelObjectPrefab prefab = GetRandomPrefab(level.GenerationParams.Name);

                SpawnPosition spawnPosition = FindObjectPosition(availableSpawnPositions, level, prefab);

                if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                {
                    continue;
                }

                float rotation = 0.0f;
                if (prefab.AlignWithSurface && spawnPosition != null)
                {
                    rotation = MathUtils.VectorToAngle(new Vector2(spawnPosition.Normal.Y, spawnPosition.Normal.X));
                }
                rotation += Rand.Range(prefab.RandomRotationRad.X, prefab.RandomRotationRad.Y, Rand.RandSync.Server);

                Vector2 position = Vector2.Zero;
                Vector2 edgeDir  = Vector2.UnitX;
                if (spawnPosition == null)
                {
                    position = new Vector2(
                        Rand.Range(0.0f, level.Size.X, Rand.RandSync.Server),
                        Rand.Range(0.0f, level.Size.Y, Rand.RandSync.Server));
                }
                else
                {
                    edgeDir  = (spawnPosition.GraphEdge.Point1 - spawnPosition.GraphEdge.Point2) / spawnPosition.Length;
                    position = spawnPosition.GraphEdge.Point2 + edgeDir * Rand.Range(prefab.MinSurfaceWidth / 2.0f, spawnPosition.Length - prefab.MinSurfaceWidth / 2.0f, Rand.RandSync.Server);
                }

                var newObject = new LevelObject(prefab,
                                                new Vector3(position, Rand.Range(prefab.DepthRange.X, prefab.DepthRange.Y, Rand.RandSync.Server)), Rand.Range(prefab.MinSize, prefab.MaxSize, Rand.RandSync.Server), rotation);
                AddObject(newObject, level);

                foreach (LevelObjectPrefab.ChildObject child in prefab.ChildObjects)
                {
                    int childCount = Rand.Range(child.MinCount, child.MaxCount, Rand.RandSync.Server);
                    for (int j = 0; j < childCount; j++)
                    {
                        var matchingPrefabs = LevelObjectPrefab.List.Where(p => child.AllowedNames.Contains(p.Name));
                        int prefabCount     = matchingPrefabs.Count();
                        var childPrefab     = prefabCount == 0 ? null : matchingPrefabs.ElementAt(Rand.Range(0, prefabCount, Rand.RandSync.Server));
                        if (childPrefab == null)
                        {
                            continue;
                        }

                        Vector2 childPos = position + edgeDir * Rand.Range(-0.5f, 0.5f, Rand.RandSync.Server) * prefab.MinSurfaceWidth;

                        var childObject = new LevelObject(childPrefab,
                                                          new Vector3(childPos, Rand.Range(childPrefab.DepthRange.X, childPrefab.DepthRange.Y, Rand.RandSync.Server)),
                                                          Rand.Range(childPrefab.MinSize, childPrefab.MaxSize, Rand.RandSync.Server),
                                                          rotation + Rand.Range(childPrefab.RandomRotationRad.X, childPrefab.RandomRotationRad.Y, Rand.RandSync.Server));

                        AddObject(childObject, level);
                    }
                }
            }
        }
Esempio n. 24
0
        public void PlaceNestObjects(Level level, Level.Cave cave, Vector2 nestPosition, float nestRadius, int objectAmount)
        {
            Rand.SetSyncedSeed(ToolBox.StringToInt(level.Seed));

            var availablePrefabs = new List <LevelObjectPrefab>(LevelObjectPrefab.List.FindAll(p => p.SpawnPos.HasFlag(LevelObjectPrefab.SpawnPosType.NestWall)));
            Dictionary <LevelObjectPrefab, List <SpawnPosition> > suitableSpawnPositions = new Dictionary <LevelObjectPrefab, List <SpawnPosition> >();
            Dictionary <LevelObjectPrefab, List <float> >         spawnPositionWeights   = new Dictionary <LevelObjectPrefab, List <float> >();

            List <SpawnPosition> availableSpawnPositions = new List <SpawnPosition>();
            var caveCells = cave.Tunnels.SelectMany(t => t.Cells);
            List <VoronoiCell> caveWallCells = new List <VoronoiCell>();

            foreach (var edge in caveCells.SelectMany(c => c.Edges))
            {
                if (!edge.NextToCave)
                {
                    continue;
                }
                if (MathUtils.LineSegmentToPointDistanceSquared(edge.Point1.ToPoint(), edge.Point2.ToPoint(), nestPosition.ToPoint()) > nestRadius * nestRadius)
                {
                    continue;
                }
                if (edge.Cell1?.CellType == CellType.Solid)
                {
                    caveWallCells.Add(edge.Cell1);
                }
                if (edge.Cell2?.CellType == CellType.Solid)
                {
                    caveWallCells.Add(edge.Cell2);
                }
            }
            availableSpawnPositions.AddRange(GetAvailableSpawnPositions(caveWallCells.Distinct(), LevelObjectPrefab.SpawnPosType.CaveWall));

            for (int i = 0; i < objectAmount; i++)
            {
                //get a random prefab and find a place to spawn it
                LevelObjectPrefab prefab = GetRandomPrefab(cave.CaveGenerationParams, availablePrefabs, requireCaveSpecificOverride: false);
                if (prefab == null)
                {
                    continue;
                }
                if (!suitableSpawnPositions.ContainsKey(prefab))
                {
                    suitableSpawnPositions.Add(prefab,
                                               availableSpawnPositions.Where(sp =>
                                                                             sp.Length >= prefab.MinSurfaceWidth &&
                                                                             (sp.Alignment == Alignment.Any || prefab.Alignment.HasFlag(sp.Alignment))).ToList());
                    spawnPositionWeights.Add(prefab,
                                             suitableSpawnPositions[prefab].Select(sp => sp.GetSpawnProbability(prefab)).ToList());
                }
                SpawnPosition spawnPosition = ToolBox.SelectWeightedRandom(suitableSpawnPositions[prefab], spawnPositionWeights[prefab], Rand.RandSync.Server);
                if (spawnPosition == null && prefab.SpawnPos != LevelObjectPrefab.SpawnPosType.None)
                {
                    continue;
                }
                PlaceObject(prefab, spawnPosition, level);
                if (objects.Count(o => o.Prefab == prefab) >= prefab.MaxCount)
                {
                    availablePrefabs.Remove(prefab);
                }
            }
        }