示例#1
0
 private static void Reload(Dictionary <long, Chunk> modifiedChunks)
 {
     if (!(Options.ContainsKey("noreload") || Options.ContainsKey("nr")))
     {
         BCChunks.ReloadForClients(modifiedChunks);
     }
 }
示例#2
0
        private static void FillBlocks(Vector3i p3, Vector3i size, BlockValue bv, string search, Dictionary <long, Chunk> modifiedChunks)
        {
            const int clrIdx = 0;

            if (Block.list[bv.type] == null)
            {
                SendOutput("Unable to find block by id or name");

                return;
            }

            SetBlocks(clrIdx, p3, size, bv, search == "*");

            if (Options.ContainsKey("delmulti"))
            {
                SendOutput($@"Removed multidim blocks @ {p3} to {p3 + size}");
            }
            else
            {
                SendOutput($@"Inserting block '{Block.list[bv.type].GetBlockName()}' @ {p3} to {p3 + size}");
                SendOutput("Use bc-wblock /undo to revert the changes");
            }

            //RELOAD CHUNKS
            BCChunks.ReloadForClients(modifiedChunks);
        }
示例#3
0
        private void DoReload()
        {
            if (Params.Count != 5 && Params.Count != 3)
            {
                SendOutput("Incorrect params count for reload");
                SendOutput(GetHelp());

                return;
            }

            int cx;
            int cy;
            int cz;
            int cw;

            if (Params.Count == 3)
            {
                if (!int.TryParse(Params[1], out cx) || !int.TryParse(Params[2], out cy))
                {
                    SendOutput("Unable to parse chunk co-ords from params");
                    SendOutput(GetHelp());

                    return;
                }
                cz = cx;
                cw = cy;
            }
            else
            {
                if (!int.TryParse(Params[1], out cx) || !int.TryParse(Params[2], out cy) ||
                    !int.TryParse(Params[3], out cz) || !int.TryParse(Params[4], out cw))
                {
                    SendOutput("Unable to parse chunk co-ords from params");
                    SendOutput(GetHelp());

                    return;
                }
            }

            var x1 = Math.Min(cx, cz);
            var x2 = Math.Max(cx, cz);
            var z1 = Math.Min(cy, cw);
            var z2 = Math.Max(cy, cw);

            var chunks = new Dictionary <long, Chunk>();

            for (var x = x1; x <= x2; x++)
            {
                for (var z = z1; z <= z2; z++)
                {
                    var chunkKey = WorldChunkCache.MakeChunkKey(x, z);
                    chunks[chunkKey] = null;
                }
            }
            var count = BCChunks.ReloadForClients(chunks);

            SendOutput($"Chunks reloaded for {count} clients in area: {x1},{z1} to {x2},{z2}");
        }
示例#4
0
        public static void InsertPrefab(Prefab prefab, int x, int y, int z, Vector3i pos)
        {
            var world = GameManager.Instance.World;

            if (world == null)
            {
                return;
            }

            if (prefab == null)
            {
                SendOutput("No Prefab loaded.");

                return;
            }

            //GET AFFECTED CHUNKS
            var modifiedChunks = new Dictionary <long, Chunk>();

            for (var cx = -1; cx <= prefab.size.x + 16; cx = cx + 16)
            {
                for (var cz = -1; cz <= prefab.size.z + 16; cz = cz + 16)
                {
                    var chunk = world.GetChunkFromWorldPos(x + cx, y, z + cz) as Chunk;
                    if (chunk == null)
                    {
                        // todo: generate and observe chunks required
                        SendOutput("Unable to load chunk for prefab @ " + (x + cx) + "," + (z + cz));
                    }
                    else
                    {
                        if (modifiedChunks.ContainsKey(chunk.Key))
                        {
                            continue;
                        }

                        modifiedChunks.Add(chunk.Key, chunk);
                    }
                }
            }

            //INSERT PREFAB
            //todo: set owner

            CopyIntoLocal(prefab, world, pos);
            //prefab.CopyIntoLocal(world.ChunkCache, pos, true, true);

            //RELOAD CHUNKS
            BCChunks.ReloadForClients(modifiedChunks);
        }
示例#5
0
        public static void InsertPrefab(World world, Prefab prefab, Vector3i pos)
        {
            if (prefab == null)
            {
                SendOutput("No Prefab loaded.");

                return;
            }

            //GET AFFECTED CHUNKS
            var modifiedChunks = new Dictionary <long, Chunk>();

            for (var cx = -1; cx <= prefab.size.x + 16; cx = cx + 16)
            {
                for (var cz = -1; cz <= prefab.size.z + 16; cz = cz + 16)
                {
                    if (world.GetChunkFromWorldPos(pos.x + cx, 0, pos.z + cz) is Chunk chunk)
                    {
                        if (modifiedChunks.ContainsKey(chunk.Key))
                        {
                            continue;
                        }

                        modifiedChunks.Add(chunk.Key, chunk);
                    }
                    else
                    {
                        SendOutput($"Unable to load chunk for prefab @ {pos.x + cx},{pos.z + cz}");
                    }
                }
            }

            //INSERT PREFAB
            CopyIntoLocal(world, prefab, pos);

            //RELOAD CHUNKS
            if (!(Options.ContainsKey("noreload") || Options.ContainsKey("nr")))
            {
                BCChunks.ReloadForClients(modifiedChunks);
            }
        }
示例#6
0
        public override void Process()
        {
            if (Params.Count == 0)
            {
                SendOutput(GetHelp());

                return;
            }

            var world = GameManager.Instance.World;

            if (world == null)
            {
                return;
            }

            switch (Params[0])
            {
            //case "region":
            //  {
            //    var chunkCache = world.ChunkCache;
            //    if (!(chunkCache.ChunkProvider is ChunkProviderGenerateWorld chunkProvider))
            //    {
            //      SendOutput("Unable to load chunk provider");

            //      return;
            //    }

            //    var field = typeof(ChunkProviderGenerateWorld).GetField("m_regionFileManager", BindingFlags.NonPublic | BindingFlags.Instance);
            //    var rfm = (RegionFileManager)field?.GetValue(chunkProvider);
            //    if (rfm == null)
            //    {
            //      SendOutput("Region Manager is null");

            //      return;
            //    }

            //    if (!int.TryParse(Params[1], out var cx) || !int.TryParse(Params[2], out var cz))
            //    {
            //      SendOutput("Unable to parse cx or cz as numbers");

            //      return;
            //    }

            //    var chunkKey = WorldChunkCache.MakeChunkKey(cx, cz);
            //    //do stuff
            //    rfm.RemoveChunkSync(chunkKey);

            //    break;
            //  }
            case "chunk":
            {
                //CHUNK - Resets the chunk to the original state it was created in
                if (Params.Count != 3)
                {
                    SendOutput("Incorrect Params");
                    SendOutput(GetHelp());

                    return;
                }

                if (!int.TryParse(Params[1], out var cx) || !int.TryParse(Params[2], out var cz))
                {
                    SendOutput("Unable to parse cx or cz as numbers");

                    return;
                }
                var chunkKey = WorldChunkCache.MakeChunkKey(cx, cz);

                //todo: make unloaded chunk option
                //todo: deferred load
                var chunkCache = world.ChunkCache;
                if (!(chunkCache.ChunkProvider is ChunkProviderGenerateWorld chunkProvider))
                {
                    SendOutput("Unable to load chunk provider");

                    return;
                }
                //todo: deferred load
                var chunkSync = chunkCache.GetChunkSync(chunkKey);
                if (chunkSync == null)
                {
                    SendOutput("Chunk not loaded");

                    return;
                }

                //create reset chunk
                var chunk = MemoryPools.PoolChunks.AllocSync(true);
                if (chunk == null)
                {
                    SendOutput("Couldn't allocate chunk from memory pool");

                    return;
                }

                chunk.X = cx;
                chunk.Z = cz;

                if (!(chunkProvider.GetTerrainGenerator() is TerrainGeneratorWithBiomeResource terrainGenerator))
                {
                    SendOutput("Couldn't load terrain generator");

                    return;
                }

                var random = Utils.RandomFromSeedOnPos(cx, cz, world.Seed);
                terrainGenerator.GenerateTerrain(world, chunk, random);
                chunk.NeedsDecoration       = true;
                chunk.NeedsLightCalculation = true;
                DoPrefabDecorations(world, chunkProvider, chunk, random);
                DeEntityDecoration(world, chunkProvider, chunk, random);
                DoSpawnerDecorations(world, chunkProvider, chunk, random);

                //UPDATE CHUNK
                var syncRoot = chunkCache.GetSyncRoot();
                lock (syncRoot)
                {
                    //remove old chunk
                    if (chunkCache.ContainsChunkSync(chunkKey))
                    {
                        chunkCache.RemoveChunkSync(chunkKey);
                    }

                    if (chunkCache.ContainsChunkSync(chunk.Key))
                    {
                        SendOutput("Reset chunk still exists in chunk cache");

                        return;
                    }

                    if (!chunkCache.AddChunkSync(chunk))
                    {
                        MemoryPools.PoolChunks.FreeSync(chunk);
                        SendOutput("Unable to add new chunk to cache");

                        return;
                    }
                }
                var decorateWithNeigbours = typeof(ChunkProviderGenerateWorld).GetMethod(_decorateFunction, BindingFlags.NonPublic | BindingFlags.Instance);
                if (decorateWithNeigbours == null)
                {
                    SendOutput("Couldn't access method for DecorateWithNeigbours");

                    return;
                }
                decorateWithNeigbours.Invoke(chunkProvider, new object[] { chunk });

                chunk.InProgressRegeneration = false;
                chunk.NeedsCopying           = true;
                chunk.isModified             = true;

                SendOutput($"Chunk reset @ {cx},{cz}");
                Log.Out($"{Config.ModPrefix} Chunk reset @ {cx},{cz}");

                //RELOAD CHUNKS
                if (!(Options.ContainsKey("noreload") || Options.ContainsKey("nr")))
                {
                    BCChunks.ReloadForClients(new Dictionary <long, Chunk> {
                            { chunkKey, chunk }
                        });
                }
                break;
            }

            //case "player":
            //  {
            //    //resets the player by kicking them if online and then backing up player files before deleting
            //    break;
            //  }

            default:
                SendOutput(GetHelp());
                break;
            }
        }
示例#7
0
        private static void SwapBlocks(Vector3i p3, Vector3i size, BlockValue newbv, string blockname, Dictionary <long, Chunk> modifiedChunks)
        {
            var targetbv = int.TryParse(blockname, out int blockId) ? Block.GetBlockValue(blockId) : Block.GetBlockValue(blockname);

            const int clrIdx  = 0;
            var       counter = 0;

            var block1 = Block.list[targetbv.type];

            if (block1 == null)
            {
                SendOutput("Unable to find target block by id or name");

                return;
            }

            var block2 = Block.list[newbv.type];

            if (block2 == null)
            {
                SendOutput("Unable to find replacement block by id or name");

                return;
            }

            var world = GameManager.Instance.World;

            for (var i = 0; i < size.x; i++)
            {
                for (var j = 0; j < size.y; j++)
                {
                    for (var k = 0; k < size.z; k++)
                    {
                        //todo:
                        sbyte density     = 1;
                        var   textureFull = 0L;

                        if (newbv.Equals(BlockValue.Air))
                        {
                            density = MarchingCubes.DensityAir;
                        }
                        else if (newbv.Block.shape.IsTerrain())
                        {
                            density = MarchingCubes.DensityTerrain;
                        }

                        var p5 = new Vector3i(i + p3.x, j + p3.y, k + p3.z);
                        if (world.GetBlock(p5).Block.GetBlockName() != block1.GetBlockName())
                        {
                            continue;
                        }

                        world.ChunkClusters[clrIdx].SetBlock(p5, true, newbv, false, density, false, false);
                        world.ChunkClusters[clrIdx].SetTextureFull(p5, textureFull);

                        counter++;
                    }
                }
            }

            SendOutput($@"Replaced {counter} '{block1.GetBlockName()}' blocks with '{block2.GetBlockName()}' @ {p3} to {p3 + size}");
            SendOutput("Use bc-wblock /undo to revert the changes");

            //RELOAD CHUNKS
            BCChunks.ReloadForClients(modifiedChunks);
        }
示例#8
0
        protected override void Process()
        {
            if (!BCUtils.CheckWorld(out var world))
            {
                return;
            }

            //Resets the chunk to the original state it was created in
            if (Params.Count != 2)
            {
                SendOutput("Incorrect Params");
                SendOutput(GetHelp());

                return;
            }

            if (!int.TryParse(Params[0], out var cx) || !int.TryParse(Params[1], out var cz))
            {
                SendOutput("Unable to parse cx or cz as numbers");

                return;
            }
            var chunkKey = WorldChunkCache.MakeChunkKey(cx, cz);

            //todo: make unloaded chunk option
            //todo: deferred load
            var chunkCache = world.ChunkCache;

            if (!(chunkCache.ChunkProvider is ChunkProviderGenerateWorld chunkProvider))
            {
                SendOutput("Unable to load chunk provider");

                return;
            }
            //todo: deferred load
            var chunkSync = chunkCache.GetChunkSync(chunkKey);

            if (chunkSync == null)
            {
                SendOutput("Chunk not loaded");

                return;
            }

            //create reset chunk
            var chunk = MemoryPools.PoolChunks.AllocSync(true);

            if (chunk == null)
            {
                SendOutput("Couldn't allocate chunk from memory pool");

                return;
            }

            chunk.X = cx;
            chunk.Z = cz;

            if (!(chunkProvider.GetTerrainGenerator() is TerrainGeneratorWithBiomeResource terrainGenerator))
            {
                SendOutput("Couldn't load terrain generator");

                return;
            }

            var random = Utils.RandomFromSeedOnPos(cx, cz, world.Seed);

            terrainGenerator.GenerateTerrain(world, chunk, random);
            chunk.NeedsDecoration       = true;
            chunk.NeedsLightCalculation = true;
            DoPrefabDecorations(world, chunkProvider, chunk, random);
            DoEntityDecoration(world, chunkProvider, chunk, random);
            DoSpawnerDecorations(world, chunkProvider, chunk, random);

            //UPDATE CHUNK
            var syncRoot = chunkCache.GetSyncRoot();

            lock (syncRoot)
            {
                //todo: instead of remove and add, generate the chunk then use regular setblockrpc calls to update chunk blocks
                //remove old chunk
                if (chunkCache.ContainsChunkSync(chunkKey))
                {
                    chunkCache.RemoveChunkSync(chunkKey);
                }

                if (chunkCache.ContainsChunkSync(chunk.Key))
                {
                    SendOutput("Reset chunk still exists in chunk cache");

                    return;
                }

                if (!chunkCache.AddChunkSync(chunk))
                {
                    MemoryPools.PoolChunks.FreeSync(chunk);
                    SendOutput("Unable to add new chunk to cache");

                    return;
                }
            }


            var decorateWithNeigbours = typeof(ChunkProviderGenerateWorld).GetMethod(_decorateFunction, BindingFlags.NonPublic | BindingFlags.Instance);

            if (decorateWithNeigbours == null)
            {
                SendOutput("Couldn't access method for DecorateWithNeigbours");

                return;
            }
            decorateWithNeigbours.Invoke(chunkProvider, new object[] { chunk });

            chunk.InProgressRegeneration = false;
            chunk.NeedsCopying           = true;
            chunk.isModified             = true;

            SendOutput($"Chunk reset @ {cx},{cz}");
            Log.Out($"{Config.ModPrefix} Chunk reset @ {cx},{cz}");

            //RELOAD CHUNKS
            if (!(Options.ContainsKey("noreload") || Options.ContainsKey("nr")))
            {
                BCChunks.ReloadForClients(new Dictionary <long, Chunk> {
                    { chunkKey, chunk }
                });
            }
        }