Error getting keysets and creating array

Discussion in 'Spigot Plugin Development' started by 42Jamie42, May 17, 2017.

  1. Hey guys, so I need your help. I'm making a chat plugin but my system doesn't work.

    This is the error:
    Code (Text):
    java.lang.NullPointerException
            at me.jamie42.java.delayedchat.DelayTimer$1.run(DelayTimer.java:17) ~[?:?]
            at org.bukkit.craftbukkit.v1_11_R1.scheduler.CraftTask.run(CraftTask.java:71) ~[spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at org.bukkit.craftbukkit.v1_11_R1.scheduler.CraftScheduler.mainThreadHeartbeat(CraftScheduler.java:353) [spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at net.minecraft.server.v1_11_R1.MinecraftServer.D(MinecraftServer.java:730) [spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at net.minecraft.server.v1_11_R1.DedicatedServer.D(DedicatedServer.java:399) [spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at net.minecraft.server.v1_11_R1.MinecraftServer.C(MinecraftServer.java:675) [spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at net.minecraft.server.v1_11_R1.MinecraftServer.run(MinecraftServer.java:574) [spigot-1.11.2.jar:git-Spigot-7d78b81-775f1e1]
            at java.lang.Thread.run(Unknown Source) [?:1.8.0_111]

    This is DelayTimer.java:17
    Code (Text):
    Player[] InnerMapKeyArray = (Player[]) InnerMap.keySet().toArray();
    And these are all files.
    DelayTimer.java
    Code (Text):
    package me.jamie42.java.delayedchat;

    import java.util.HashMap;

    import org.bukkit.Bukkit;
    import org.bukkit.entity.Player;

    public class DelayTimer {
        public static HashMap<Player, HashMap<Player, Integer>> Delayed = new HashMap<>();
     
        public static void startDelayTimer() {
            Bukkit.getServer().getScheduler().scheduleSyncRepeatingTask(Main.getMain(), new Runnable(){
                @Override
                public void run() {
                    for(int i = 0; i < Delayed.size(); i++){
                        HashMap<Player, Integer> InnerMap = Delayed.get(i);
                        Player[] InnerMapKeyArray = (Player[]) InnerMap.keySet().toArray();
                        Player p = InnerMapKeyArray[0];
                        int delay = InnerMap.get(p);
                     
                        if(delay == 0){
                            Delayed.remove(i);
                        }else if(delay > 0){
                            HashMap<Player, Integer> InnerHMap = new HashMap<>();
                            InnerHMap.put(p, delay - 1);
                            Delayed.replace(p, InnerHMap);
                        }
                    }
                }
            }, 0L, 1L);
        }
     
    }
     
    ChatListener.java
    Code (Text):
    package me.jamie42.java.delayedchat.listener;

    import java.util.HashMap;

    import org.bukkit.Bukkit;
    import org.bukkit.entity.Player;
    import org.bukkit.event.Event;
    import org.bukkit.event.EventException;
    import org.bukkit.event.Listener;
    import org.bukkit.event.player.AsyncPlayerChatEvent;
    import org.bukkit.plugin.EventExecutor;

    import me.jamie42.java.delayedchat.DelayTimer;
    import me.jamie42.java.delayedchat.Main;
    import net.md_5.bungee.api.ChatColor;

    public class ChatListener implements Listener {
     
        public static EventExecutor ChatListenerEE = new EventExecutor() {
            @Override
            public void execute(Listener listener, Event e) throws EventException {
             
                if(e instanceof AsyncPlayerChatEvent){
                    Bukkit.broadcastMessage("!");
                    Player p = ((AsyncPlayerChatEvent) e).getPlayer();
                 
                    if(DelayTimer.Delayed.containsKey(p)){
                        int remainDelay = DelayTimer.Delayed.get(p).get(p);
                     
                        p.sendMessage(ChatColor.translateAlternateColorCodes('&', Main.getSettings().getConfig().getString("Locale.chatDenied").replace("%delay%", Integer.toString(remainDelay))));
                        ((AsyncPlayerChatEvent) e).setCancelled(true);
                    }else{
                        int delay = 0;
                        boolean delaySet = false;
                        for(String key : Main.getSettings().getConfig().getConfigurationSection("Permissions").getKeys(false)){
                         
                            p.sendMessage(key +"\n"+Main.getSettings().getConfig().getConfigurationSection("Permissions").getKeys(false).size() );
                         
                            int itemValue = Main.getSettings().getConfig().getInt("Permissions." + key);
                            if(p.hasPermission(key.replaceAll("%DOT%", "."))){
                                if(delaySet){
                                    if(Main.getSettings().getConfig().getString("DelayPriority").equalsIgnoreCase("Lowest") && itemValue < delay){
                                        delay = itemValue;
                                    }else if(Main.getSettings().getConfig().getString("DelayPriority").equalsIgnoreCase("Highest") && itemValue > delay){
                                        delay = itemValue;
                                    }
                                }else{
                                    delay = itemValue;
                                }
                            }
                        }
                     
                        if(p.hasPermission("delayedchat.nodelay")){
                            delay = 0;
                        }
                     
                        if(delay > 0){
                            HashMap<Player, Integer> InnerMap = new HashMap<>();
                            InnerMap.put(p, delay * 20);
                            DelayTimer.Delayed.put(p, InnerMap);
                        }
                    }
                }
            }
        };
    }

    Thanks for any help, i really don't know my problem, tried so much things. But can't figure it out.
     
  2. Basically you request an int value from a hashmap.

    You can't, unless you use the Player as request

    Your Issue is here:

    Code (Text):

        public static HashMap<Player, HashMap<Player, Integer>> Delayed = new HashMap<>();
     for(int i = 0; i < Delayed.size(); i++){
                        HashMap<Player, Integer> InnerMap = Delayed.get(i);
    }
     
    Basically your HashMap (Delayed) contains a Player as Key and not an Integer.class.
    Use a loop that goes through the Delayed.keySet() automatically and grabs the hashmap ( Value ) out.

    get(Integer.class) is only available for Lists / Set's.

    Also Change "HashMap" to Map.
     
  3. I don't see the point in having a HashMap within a HashMap if your storing Player twice. Make the HashMap<Player, Integer> instead. As for the NPE just print everything out until you find it.
     
  4. Thanks, that was what i needed, now i can fix it. I hope :)
     
  5. Still don't see the point in that extra HashMap if your always going to get index 0 of the second hashmap
     
  6. It's cause I want to have a hashmap for player + delay. I'm going to change the first player definition to integer and then i need it do.