1. This site uses cookies. By continuing to use this site, you are agreeing to our use of cookies. Learn More.

Falling Leaves Plugin! [Open Source]

Discussion in 'Plugins/Codes' started by ExtendedHorizons, Dec 6, 2015.

  1. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    Today I was thinking of what to work on, and thought of this! I had an older version, that was pretty much broken. This version works 10x better. If you guys want to use the code, feel free too! Please just give me credit. Also if you want to use the code, put Leaves.spawnLeaves(); in your onEnable :D P.S. Sorry for the spaghetti code. Its an old project. I touched it up a bit, but mainly worked on fixing bugs.

    Code:
    package me.extendedhorizons.kitverse.cosmetics;
    
    import me.extendedhorizons.kitverse.Main;
    import me.extendedhorizons.kitverse.util.BlockUtil;
    import net.minecraft.server.v1_8_R3.*;
    import org.bukkit.*;
    import org.bukkit.Chunk;
    import org.bukkit.Material;
    import org.bukkit.World;
    import org.bukkit.block.Block;
    import org.bukkit.craftbukkit.v1_8_R3.entity.CraftPlayer;
    import org.bukkit.craftbukkit.v1_8_R3.inventory.CraftItemStack;
    import org.bukkit.entity.ArmorStand;
    import org.bukkit.entity.EntityType;
    import org.bukkit.entity.Player;
    import org.bukkit.inventory.ItemStack;
    import org.bukkit.scheduler.BukkitRunnable;
    import org.bukkit.util.Vector;
    
    import java.util.ArrayList;
    import java.util.HashMap;
    import java.util.List;
    import java.util.Random;
    
    @SuppressWarnings("unused")
    public class Leaves {
        static HashMap<ArmorStand, Double> stands = new HashMap<>();
    
        public static void fixExistingleaves() {
            new BukkitRunnable() {
                @Override
                public void run() {
                    for (ArmorStand stand : stands.keySet()) {
                        if (stand.getLocation().getBlock().getType().equals(Material.AIR) || stand.getLocation().getBlock().getType().equals(Material.WATER)) {
                            stand.setGravity(true);
                        }
                        if (stand.getLocation().getY() != stands.get(stand)) {
                            fancyFall(stand);
                        }
                    }
                }
            }.runTaskTimer(Main.getPlugin(), 1, 10);
        }
    
        public static void leaf(Location loc) {
            World w = loc.getWorld();
            ItemStack stack = new ItemStack(Material.LEAVES, 1);
            Location centerLoc = BlockUtil.getCenterLoc(loc);
            ArmorStand block = (ArmorStand) w.spawnEntity(centerLoc, EntityType.ARMOR_STAND);
            block.setSmall(true);
            block.setGravity(true);
            block.setVisible(false);
            if (!block.isOnGround()) {
                fancyFall(block);
            }
            for (Player allPlayers : Bukkit.getServer().getOnlinePlayers()) {
                CraftPlayer allP = (CraftPlayer) allPlayers;
                PacketPlayOutEntityEquipment equip = new PacketPlayOutEntityEquipment(block.getEntityId(), 4, CraftItemStack.asNMSCopy(stack));
                allP.getHandle().playerConnection.sendPacket(equip);
                PlayerConnection connection = allP.getHandle().playerConnection;
            }
        }
        //Main.getPlugin().getLogger().info("Spawned Leaf At: " + centerLoc);
    
        public static void fancyFall(ArmorStand stand) {
            World w = stand.getWorld();
            new BukkitRunnable() {
                public void run() {
                    double spin = (double) Math.round(Math.random() * 6);
                    spin = spin / 100;
                    if (!stand.isOnGround()) {
                        stand.setVelocity(new Vector(0, -0.06, 0));
                        stand.setHeadPose(stand.getHeadPose().add(0, -spin, 0));
    
                    } else {
                        stand.setVelocity(new Vector(0, 0, 0));
                        lower(stand, spin);
                        this.cancel();
                    }
                }
            }.runTaskTimer(Main.getPlugin(), 1, 1);
        }
    
        public static void lower(ArmorStand stand, double spin) {
            Location loc = stand.getLocation();
            new BukkitRunnable() {
                int count = 0;
                @Override
                public void run() {
                    if (count <= 8) {
                        stand.teleport(loc.clone().add(0, -0.05, 0));
                        stand.setHeadPose(stand.getHeadPose().add(0, -spin, 0));
                        count++;
                    } else {
                        Location loc = stand.getLocation().clone().add(0, 1.75, 0);
                        Random random = new Random();
                        int randomInt1 = random.nextInt(1);
                        int randomInt2 = random.nextInt(1);
                        int lifeSpan = random.nextInt(25);
    
                        IBlockData iblockdata = net.minecraft.server.v1_8_R3.Block.getByCombinedId(18);
                        net.minecraft.server.v1_8_R3.Block block1 = iblockdata.getBlock();
    
                        PacketPlayOutWorldParticles packet = new PacketPlayOutWorldParticles(EnumParticle.BLOCK_DUST, false, loc.getBlockX(), loc.getBlockY(), loc.getBlockZ(), randomInt1, 0, randomInt2, 0, 5, net.minecraft.server.v1_8_R3.Block.getCombinedId(iblockdata));
    
                        for (Player players : Bukkit.getOnlinePlayers()) {
                            PlayerConnection playerConnection = ((CraftPlayer)players).getHandle().playerConnection;
                            playerConnection.sendPacket(packet);
                            new BukkitRunnable() {
                                @Override
                                public void run() {
                                    playerConnection.sendPacket(new PacketPlayOutEntityDestroy(stand.getEntityId()));
                                }
                            }.runTaskLater(Main.getPlugin(), 20 * lifeSpan);
                        }
                        stand.setGravity(false);
                        stands.put(stand, stand.getLocation().getY());
                        this.cancel();
                    }
                }
            }.runTaskTimer(Main.getPlugin(), 1, 1);
        }
    
        public static List<Chunk> getSurroundingChunks(Location loc, int radius) {
            List<Chunk> chunks = new ArrayList<>();
            for (int x = (loc.getChunk().getX() - radius); x <= (loc.getChunk().getX() + radius); x++) {
                for (int z = (loc.getChunk().getZ() - radius); z <= (loc.getChunk().getZ() + radius); z++) {
                    chunks.add(loc.getWorld().getChunkAt(x, z));
                }
            }
            return chunks;
        }
    
        public static void spawnLeaves() {
            Random random = new Random();
            World world = Bukkit.getServer().getWorld("world");
            fixExistingleaves();
            new BukkitRunnable() {
                @Override
                public void run() {
                    ArrayList<Block> blocks = new ArrayList<>();
                    blocks.clear();
                    blocks = getPossibleBlocks(world);
                    int playerAmount = Bukkit.getOnlinePlayers().toArray().length * 2;
                    if (blocks != null && blocks.size() > 0) {
                        for (int i = 0; i < playerAmount; i++) {
                            int index = random.nextInt(blocks.size());
                            Block block = blocks.get(index);
                            leaf(block.getLocation());
                        }
                    }
                }
            }.runTaskTimer(Main.getPlugin(), 1, 10 * 20);
        }
    
        public static ArrayList<Block> getPossibleBlocks(World world) {
            ArrayList<Block> blocks = new ArrayList<>();
            blocks.clear();
            for (Player player : Bukkit.getOnlinePlayers()) {
                player.getLocation().getChunk().load();
                for (Chunk chunk : getSurroundingChunks(player.getLocation(), 1)) {
                    int bx = chunk.getX() << 4;
                    int bz = chunk.getZ() << 4;
    
                    for (int xx = bx; xx < bx + 32; xx++) {
                        for (int zz = bz; zz < bz + 32; zz++) {
                            for (int yy = 0; yy < 48; yy++) {
                                Block b = world.getBlockAt(xx, yy, zz);
                                Location loc1 = b.getLocation();
                                if (b.getType().equals(Material.LEAVES) && b.getLocation().clone().add(0, -1, 0).getBlock().getType().equals(Material.AIR) && isLowestLeafBlock(b)) {
                                    if (!blocks.contains(b)) {
                                        blocks.add(b);
                                    }
                                }
                            }
                        }
                    }
                }
            }
            return blocks;
        }
    
        public static boolean isLowestLeafBlock(Block block) {
            Location location = block.getLocation();
            for (int i = block.getLocation().getBlockY(); i > 0; i--) {
                location.add(0, -1, 0);
                if (location.getBlock().getType().equals(Material.LEAVES)) {
                    return false;
                }
            }
            return true;
        }
    }
    Video Showcase (reuploaded for better quality):
     
    Last edited: Dec 7, 2015
    TheAdventurerMM likes this.
  2. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    Reuploaded the video and it should have way better quality now. Sorry if my voice is still really loud xD. I keep on forgetting to tone my mic settings down on OBS.
     
  3. A Christmas Hangar

    A Christmas Hangar Member

    Joined:
    Sep 15, 2015
    Messages:
    2,535
    Likes Received:
    1,480
    Trophy Points:
    113
    Gender:
    Male
    Location:
    Kepler452B
    Home Page:
    Do you code with eclipse?
     
  4. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    IntelliJ Community Version :D
     
  5. DanOF

    DanOF Member

    Joined:
    Aug 20, 2015
    Messages:
    335
    Likes Received:
    230
    Trophy Points:
    43
    Gender:
    Male
    Location:
    New Jersey, USA
    Home Page:
    Awesome! :D
     
    ExtendedHorizons likes this.
  6. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    Ty :)
     
  7. YounB

    YounB Helper Staff Member Helper

    Joined:
    May 13, 2014
    Messages:
    5,912
    Likes Received:
    6,509
    Trophy Points:
    113
    Gender:
    Male
    Occupation:
    ¯\_(ツ)_/¯
    Location:
    London, England
    I understood nothing ;-; but good thing that you're letting people use some coding stuff :)
     
  8. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    xD ty, I appreciate it
     
  9. DavidozNL

    DavidozNL Member

    Joined:
    Dec 11, 2015
    Messages:
    7
    Likes Received:
    1
    Trophy Points:
    3
    Gender:
    Male
    Woah, this code is sweet! Pretty cool!
     
  10. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    Thanks!
     
  11. The Fancy Whale

    The Fancy Whale Member

    Joined:
    Jan 4, 2016
    Messages:
    2
    Likes Received:
    0
    Trophy Points:
    1
    Gender:
    Male
    Occupation:
    Computer Science Major
    Location:
    whale.getLocation();
    These two lines jumped out at me right away:
    Code:
    ArrayList<Block> blocks = new ArrayList<>(); //new ArrayList<Block>();
    blocks.clear();
    Why do you clear an empty ArrayList?
     
  12. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    @The Fancy Whale I was having problems with it at some point. Forgot to remove it later on.
     
  13. Superherolinker

    Superherolinker Member

    Joined:
    Dec 11, 2015
    Messages:
    594
    Likes Received:
    453
    Trophy Points:
    63
    Gender:
    Male
    Occupation:
    Coder
    Location:
    In my lab, brewing a poison potion
    You've got dem skillzz
     
  14. NitroPelle

    NitroPelle Member

    Joined:
    Jun 30, 2015
    Messages:
    1,931
    Likes Received:
    347
    Trophy Points:
    83
    Gender:
    Male
    Occupation:
    YouTube
    Location:
    Amsterdam
    Home Page:
    Wow epic!
     
  15. The Fancy Whale

    The Fancy Whale Member

    Joined:
    Jan 4, 2016
    Messages:
    2
    Likes Received:
    0
    Trophy Points:
    1
    Gender:
    Male
    Occupation:
    Computer Science Major
    Location:
    whale.getLocation();
    Ok just a couple more suggestions:
    1) For the getPossibleBlocks(World world) method, I suggest removing the parameter. You can just use the players' worlds instead of using a parameter, and that would allow the plugin to function in all worlds.
    2) Rather than dropping 1 leaf every 20 seconds, you could run a random check on every leaf to see if it will drop. This will be a little more resource intensive, but it would allow for a variety in the number of leaves to fall.
     
  16. ExtendedHorizons

    ExtendedHorizons Member

    Joined:
    Oct 4, 2014
    Messages:
    206
    Likes Received:
    166
    Trophy Points:
    43
    Gender:
    Male
    Occupation:
    Drawing 24/7
    Location:
    Utah
    Home Page:
    Ty! I will fix/look into those.