Search in sources :

Example 1 with BlockEntity

use of net.glowstone.block.entity.BlockEntity in project Glowstone by GlowstoneMC.

the class GlowChunk method toMessage.

/**
     * Creates a new {@link ChunkDataMessage} which can be sent to a client to stream
     * parts of this chunk to them.
     *
     * @param skylight Whether to include skylight data.
     * @param entireChunk Whether to send all chunk sections.
     * @return The {@link ChunkDataMessage}.
     */
public ChunkDataMessage toMessage(boolean skylight, boolean entireChunk) {
    load();
    int sectionBitmask = 0;
    // filter sectionBitmask based on actual chunk contents
    if (sections != null) {
        int maxBitmask = (1 << sections.length) - 1;
        if (entireChunk) {
            sectionBitmask = maxBitmask;
        } else {
            sectionBitmask &= maxBitmask;
        }
        for (int i = 0; i < sections.length; ++i) {
            if (sections[i] == null || sections[i].isEmpty()) {
                // remove empty sections from bitmask
                sectionBitmask &= ~(1 << i);
            }
        }
    }
    ByteBuf buf = Unpooled.buffer();
    if (sections != null) {
        // get the list of sections
        for (int i = 0; i < sections.length; ++i) {
            if ((sectionBitmask & 1 << i) == 0) {
                continue;
            }
            sections[i].writeToBuf(buf, skylight);
        }
    }
    // biomes
    if (entireChunk && biomes != null) {
        buf.writeBytes(biomes);
    }
    ArrayList<CompoundTag> blockEntities = new ArrayList<>();
    for (BlockEntity blockEntity : getRawBlockEntities()) {
        CompoundTag tag = new CompoundTag();
        blockEntity.saveNbt(tag);
        blockEntities.add(tag);
    }
    return new ChunkDataMessage(x, z, entireChunk, sectionBitmask, buf, blockEntities.toArray(new CompoundTag[blockEntities.size()]));
}
Also used : ChunkDataMessage(net.glowstone.net.message.play.game.ChunkDataMessage) ByteBuf(io.netty.buffer.ByteBuf) CompoundTag(net.glowstone.util.nbt.CompoundTag) BlockEntity(net.glowstone.block.entity.BlockEntity)

Example 2 with BlockEntity

use of net.glowstone.block.entity.BlockEntity in project Glowstone by GlowstoneMC.

the class BlockPlacementHandler method revert.

static void revert(GlowPlayer player, GlowBlock target) {
    player.sendBlockChange(target.getLocation(), target.getType(), target.getData());
    BlockEntity entity = target.getBlockEntity();
    if (entity != null) {
        entity.update(player);
    }
}
Also used : BlockEntity(net.glowstone.block.entity.BlockEntity)

Example 3 with BlockEntity

use of net.glowstone.block.entity.BlockEntity in project Glowstone by GlowstoneMC.

the class AnvilChunkIoService method read.

@Override
public boolean read(GlowChunk chunk) throws IOException {
    int x = chunk.getX();
    int z = chunk.getZ();
    RegionFile region = cache.getRegionFile(x, z);
    int regionX = x & REGION_SIZE - 1;
    int regionZ = z & REGION_SIZE - 1;
    if (!region.hasChunk(regionX, regionZ)) {
        return false;
    }
    DataInputStream in = region.getChunkDataInputStream(regionX, regionZ);
    CompoundTag levelTag;
    try (NbtInputStream nbt = new NbtInputStream(in, false)) {
        CompoundTag root = nbt.readCompound();
        // NON-NLS
        levelTag = root.getCompound("Level");
    }
    // read the vertical sections
    // NON-NLS
    List<CompoundTag> sectionList = levelTag.getCompoundList("Sections");
    ChunkSection[] sections = new ChunkSection[GlowChunk.SEC_COUNT];
    for (CompoundTag sectionTag : sectionList) {
        // NON-NLS
        int y = sectionTag.getByte("Y");
        if (y < 0 || y > GlowChunk.SEC_COUNT) {
            ConsoleMessages.Warn.Chunk.SECTION_OOB.log(y, chunk);
            continue;
        }
        if (sections[y] != null) {
            ConsoleMessages.Warn.Chunk.SECTION_DUP.log(y, chunk);
            continue;
        }
        sections[y] = ChunkSection.fromNbt(sectionTag);
    }
    // initialize the chunk
    chunk.initializeSections(sections);
    // NON-NLS
    chunk.setPopulated(levelTag.getBoolean("TerrainPopulated", false));
    levelTag.readLong("InhabitedTime", chunk::setInhabitedTime);
    // read biomes
    // NON-NLS
    levelTag.readByteArray("Biomes", chunk::setBiomes);
    // read height map
    if (!levelTag.readIntArray("HeightMap", chunk::setHeightMap)) {
        // NON-NLS
        chunk.automaticHeightMap();
    }
    // read slime chunk
    // NON-NLS
    levelTag.readByte("isSlimeChunk", chunk::setIsSlimeChunk);
    // read entities
    levelTag.iterateCompoundList("Entities", entityTag -> {
        // NON-NLS
        try {
            // note that creating the entity is sufficient to add it to the world
            EntityStorage.loadEntity(chunk.getWorld(), entityTag);
        } catch (UnknownEntityTypeException e) {
            ConsoleMessages.Warn.Entity.UNKNOWN.log(chunk, e.getIdOrTag());
        } catch (Exception e) {
            ConsoleMessages.Warn.Entity.LOAD_FAILED.log(e, chunk);
        }
    });
    // read block entities
    // NON-NLS
    List<CompoundTag> storedBlockEntities = levelTag.getCompoundList("TileEntities");
    BlockEntity blockEntity;
    for (CompoundTag blockEntityTag : storedBlockEntities) {
        // NON-NLS
        int tx = blockEntityTag.getInt("x");
        // NON-NLS
        int ty = blockEntityTag.getInt("y");
        // NON-NLS
        int tz = blockEntityTag.getInt("z");
        blockEntity = chunk.createEntity(tx & 0xf, ty, tz & 0xf, chunk.getType(tx & 0xf, tz & 0xf, ty));
        if (blockEntity != null) {
            try {
                blockEntity.loadNbt(blockEntityTag);
            } catch (Exception ex) {
                // NON-NLS
                String id = blockEntityTag.tryGetString("id").orElse("<missing>");
                ConsoleMessages.Error.BlockEntity.LOAD_FAILED.log(ex, blockEntity.getBlock(), id);
            }
        } else {
            String id = // NON-NLS
            blockEntityTag.tryGetString("id").orElse("<missing>");
            ConsoleMessages.Warn.BlockEntity.UNKNOWN.log(chunk.getWorld().getName(), tx, ty, tz, id);
        }
    }
    levelTag.iterateCompoundList("TileTicks", tileTick -> {
        // NON-NLS
        // NON-NLS
        int tileX = tileTick.getInt("x");
        // NON-NLS
        int tileY = tileTick.getInt("y");
        // NON-NLS
        int tileZ = tileTick.getInt("z");
        // NON-NLS
        String id = tileTick.getString("i");
        Material material = ItemIds.getBlock(id);
        if (material == null) {
            ConsoleMessages.Warn.Chunk.UNKNOWN_BLOCK_TO_TICK.log(id);
            return;
        }
        GlowBlock block = chunk.getBlock(tileX, tileY, tileZ);
        if (material != block.getType()) {
            return;
        }
        // TODO tick delay: tileTick.getInt("t");
        // TODO ordering: tileTick.getInt("p");
        BlockType type = ItemTable.instance().getBlock(material);
        if (type == null) {
            return;
        }
        block.getWorld().requestPulse(block);
    });
    return true;
}
Also used : UnknownEntityTypeException(net.glowstone.io.entity.UnknownEntityTypeException) Material(org.bukkit.Material) DataInputStream(java.io.DataInputStream) NbtInputStream(net.glowstone.util.nbt.NbtInputStream) UnknownEntityTypeException(net.glowstone.io.entity.UnknownEntityTypeException) IOException(java.io.IOException) GlowBlock(net.glowstone.block.GlowBlock) BlockType(net.glowstone.block.blocktype.BlockType) ChunkSection(net.glowstone.chunk.ChunkSection) CompoundTag(net.glowstone.util.nbt.CompoundTag) BlockEntity(net.glowstone.block.entity.BlockEntity)

Example 4 with BlockEntity

use of net.glowstone.block.entity.BlockEntity in project Glowstone by GlowstoneMC.

the class BlockDispenser method trigger.

/**
 * Dispense an item from the given block if it's a dispenser.
 *
 * @param block the dispenser block
 */
public void trigger(GlowBlock block) {
    BlockEntity te = block.getBlockEntity();
    if (!(te instanceof DispenserEntity)) {
        return;
    }
    DispenserEntity teDispenser = (DispenserEntity) te;
    GlowDispenser dispenser = (GlowDispenser) teDispenser.getState();
    dispenser.dispense();
}
Also used : DispenserEntity(net.glowstone.block.entity.DispenserEntity) GlowDispenser(net.glowstone.block.entity.state.GlowDispenser) BlockEntity(net.glowstone.block.entity.BlockEntity)

Example 5 with BlockEntity

use of net.glowstone.block.entity.BlockEntity in project Glowstone by GlowstoneMC.

the class CloneCommand method execute.

@Override
public boolean execute(CommandSender sender, String label, String[] args, CommandMessages messages) {
    if (!testPermission(sender, messages.getPermissionMessage())) {
        return true;
    }
    if (args.length < 9) {
        sendUsageMessage(sender, messages);
        return false;
    }
    final ResourceBundle bundle = messages.getResourceBundle();
    if (!CommandUtils.isPhysical(sender)) {
        messages.getGeneric(GenericMessage.NOT_PHYSICAL).send(sender);
        return false;
    }
    GlowWorld world = CommandUtils.getWorld(sender);
    Location parsedFrom1 = CommandUtils.getLocation(sender, args[0], args[1], args[2]);
    Location parsedFrom2 = CommandUtils.getLocation(sender, args[3], args[4], args[5]);
    Location to = CommandUtils.getLocation(sender, args[6], args[7], args[8]);
    MaskMode maskMode = args.length >= 10 ? MaskMode.fromCommandName(args[9]) : MaskMode.REPLACE;
    CloneMode cloneMode = args.length >= 11 ? CloneMode.fromCommandName(args[10]) : CloneMode.NORMAL;
    // TODO: Investigate what happens when maskMode or cloneMode are invalid (thus, null).
    if (maskMode == null || cloneMode == null) {
        sendUsageMessage(sender, messages);
        return false;
    }
    BlockFilter blockFilter;
    switch(maskMode) {
        case REPLACE:
            blockFilter = new ReplaceBlockFilter();
            break;
        case MASKED:
            blockFilter = new MaskedBlockFilter();
            break;
        case FILTERED:
            if (args.length >= 12) {
                Material blockType = ItemIds.getItem(args[11]);
                if (args.length >= 13) {
                    Byte data;
                    try {
                        data = Byte.parseByte(args[12]);
                    } catch (NumberFormatException ignored) {
                        data = null;
                    }
                    if (data == null || 0 > data || data > 15) {
                        new LocalizedStringImpl("clone.bad-blockdata", bundle).sendInColor(ChatColor.RED, sender);
                        return false;
                    } else {
                        blockFilter = new FilteredWithDataBlockFilter(blockType, data);
                    }
                } else {
                    blockFilter = new FilteredBlockFilter(blockType);
                }
            } else {
                new LocalizedStringImpl("clone.usage.filtered", bundle).sendInColor(ChatColor.RED, sender);
                return false;
            }
            break;
        default:
            sendUsageMessage(sender, messages);
            return false;
    }
    RectangularRegion fromRegion = new RectangularRegion(parsedFrom1, parsedFrom2);
    RectangularRegion toRegion = fromRegion.moveTo(to);
    Location lowCorner = fromRegion.getLowCorner();
    Location highCorner = fromRegion.getHighCorner();
    boolean overlaps = between(lowCorner.getBlockX(), highCorner.getBlockX(), to.getBlockX()) || between(lowCorner.getBlockY(), highCorner.getBlockY(), to.getBlockY()) || between(lowCorner.getBlockZ(), highCorner.getBlockZ(), to.getBlockZ());
    if (overlaps && !cloneMode.isAllowedToOverlap()) {
        sendUsageMessage(sender, messages);
        return false;
    }
    int blocksCloned = 0;
    IterationDirection directionX = to.getBlockX() < lowCorner.getBlockX() ? IterationDirection.FORWARDS : IterationDirection.BACKWARDS;
    IterationDirection directionY = to.getBlockY() < lowCorner.getBlockY() ? IterationDirection.FORWARDS : IterationDirection.BACKWARDS;
    IterationDirection directionZ = to.getBlockZ() < lowCorner.getBlockZ() ? IterationDirection.FORWARDS : IterationDirection.BACKWARDS;
    Iterator<Location> fromIterator = fromRegion.blockLocations(directionX, directionY, directionZ).iterator();
    Iterator<Location> toIterator = toRegion.blockLocations(directionX, directionY, directionZ).iterator();
    while (fromIterator.hasNext() && toIterator.hasNext()) {
        Location fromLocation = fromIterator.next();
        Location toLocation = toIterator.next();
        GlowBlock fromBlock = world.getBlockAt(fromLocation);
        if (blockFilter.shouldClone(fromBlock)) {
            GlowBlock toBlock = world.getBlockAt(toLocation);
            toBlock.setType(fromBlock.getType());
            toBlock.setBlockData(fromBlock.getBlockData());
            BlockEntity fromEntity = fromBlock.getBlockEntity();
            if (fromEntity != null) {
                BlockEntity toEntity = toBlock.getChunk().createEntity(toBlock.getX(), toBlock.getY(), toBlock.getZ(), toBlock.getType());
                if (toEntity != null) {
                    CompoundTag entityTag = new CompoundTag();
                    fromEntity.saveNbt(entityTag);
                    toEntity.loadNbt(entityTag);
                }
            }
            if (cloneMode == CloneMode.MOVE) {
                fromBlock.setType(Material.AIR, false);
            }
            blocksCloned++;
        }
    }
    switch(blocksCloned) {
        case 0:
            new LocalizedStringImpl("clone.done.zero", bundle).sendInColor(ChatColor.RED, sender);
            break;
        case 1:
            new LocalizedStringImpl("clone.done.singular", bundle).send(sender);
            break;
        default:
            new LocalizedStringImpl("clone.done", bundle).send(sender, blocksCloned);
    }
    return true;
}
Also used : IterationDirection(net.glowstone.util.RectangularRegion.IterationDirection) Material(org.bukkit.Material) RectangularRegion(net.glowstone.util.RectangularRegion) GlowBlock(net.glowstone.block.GlowBlock) LocalizedStringImpl(net.glowstone.i18n.LocalizedStringImpl) GlowWorld(net.glowstone.GlowWorld) ResourceBundle(java.util.ResourceBundle) CompoundTag(net.glowstone.util.nbt.CompoundTag) Location(org.bukkit.Location) BlockEntity(net.glowstone.block.entity.BlockEntity)

Aggregations

BlockEntity (net.glowstone.block.entity.BlockEntity)11 CompoundTag (net.glowstone.util.nbt.CompoundTag)5 GlowBlock (net.glowstone.block.GlowBlock)4 BlockType (net.glowstone.block.blocktype.BlockType)4 Material (org.bukkit.Material)3 ByteBuf (io.netty.buffer.ByteBuf)2 IOException (java.io.IOException)2 ChunkSection (net.glowstone.chunk.ChunkSection)2 GlowChunk (net.glowstone.chunk.GlowChunk)2 UnknownEntityTypeException (net.glowstone.io.entity.UnknownEntityTypeException)2 ChunkDataMessage (net.glowstone.net.message.play.game.ChunkDataMessage)2 Location (org.bukkit.Location)2 DataInputStream (java.io.DataInputStream)1 ArrayList (java.util.ArrayList)1 HashSet (java.util.HashSet)1 ResourceBundle (java.util.ResourceBundle)1 ThreadLocalRandom (java.util.concurrent.ThreadLocalRandom)1 GlowWorld (net.glowstone.GlowWorld)1 DispenserEntity (net.glowstone.block.entity.DispenserEntity)1 GlowDispenser (net.glowstone.block.entity.state.GlowDispenser)1