Plugin Résolu [Besoin d'aide] onClick() qui bug ??? (Plugin Java)

teidova

Bucheron
15 Juin 2014
7
0
11
Bonjour/bonsoir,
Depuis quelques temps déjà, je code des petits plugins simples en JAVA (avec spigot 1.9.4),
mais ayant besoin d'un plugin pour mon hub, je me suis mis en tête de créer le mien.

Voici quelques fonctionnalitées déjà présentes:
  • /hub : téléporte le joueur au spawn
  • /ano <message> : broadcast classique
  • Give d'un item "Menu" à la connection
  • Ouverture d'un menu quand on clic avec l'item (27 slots) qui contient(si le joueur est op) un item "Interface Admin"
  • Ouverture de l'interface Admin
Après avoir codé tout ça, je décide d'ajouter des Items pour changer de gamemode à l'interface Admin, mais lors du clic, il ne se passe rien.

Edit:
En effet, quand j'ouvre le menu en cliquant avec mon item,
tout se passe bien, je clique ensuite sur l'item "Interface Admin",
tout reste normal, l'interface s'ouvre avec les items..
Mais quand je clique sur un item, le menu agit comme un coffre,
et le onClick() ne se déclenche pas

Mon Item Builder:

Code:
public ItemStack getItem(Material material,int nombre, String DisplayName) {
    ItemStack it = new ItemStack(material, nombre);
    ItemMeta Meta = it.getItemMeta();
    Meta.setDisplayName(DisplayName);
    it.setItemMeta(Meta);
    return it;
}

Fonction d'affichage de l'interface admin :

Code:
public void adminInterface(Player player) {
    Inventory admininv = Bukkit.createInventory(null, 9, "§cInterface Admin");
    admininv.setItem(0, getItem(Material.APPLE, 1, "§7Survie"));
    admininv.setItem(1, getItem(Material.BRICK, 1, "§7Créatif"));
    admininv.setItem(2, getItem(Material.WOOD_PICKAXE, 1, "§7Aventure"));
    admininv.setItem(3, getItem(Material.BARRIER, 1, "§7Spectateur"));
  
    player.openInventory(admininv);
    }

Listener "onClick" qui ne se déclenche pas:
Code:
@EventHandler
public void OnClick(InventoryClickEvent event) { //Event qui ne se déclenche que sur le menu
    Inventory inv = event.getInventory();
    Player player = (Player) event.getWhoClicked();
    ItemStack current = event.getCurrentItem();
      
    if(current == null) return;
      
    if(inv.getName().equalsIgnoreCase("§8Menu")) { //clic sur le menu
        player.closeInventory();
        if(current.getItemMeta().getDisplayName().equalsIgnoreCase("§cInterface Admin")) { //qui ouvre l'interface admin
            adminInterface(player);
        }
    }
    player.sendMessage("if effectué"); //Message affiché

    if(inv.getName().equalsIgnoreCase("§cInterface Admin")) { //clic sur l'interface admin
        player.sendMessage("if = true, détection de l'inventaire"); //Message non-affiché
        player.closeInventory();
          
        if(current.getItemMeta().getDisplayName().equalsIgnoreCase("§7Survie")) { //qui met en gm0 le joueur
            player.setGameMode(GameMode.SURVIVAL);
            player.sendMessage("Détection complète, mise en gm0"); //Message non-affiché
        }
    }
}
}

Voilà tout, merci d'avoir pris le temps de regarder mon problème.
Si vous avez des idées n'hésitez pas.

Cordialement,
teidova

PS: je n'ai aucune erreur dans la console, exactement comme un coffre...?
 
Dernière édition:

Luca_008

Architecte en herbe
21 Novembre 2016
150
20
125
22
Salut,

Code:
 if(current == null) return;
Depuis quand on fait cela pour une condition ?

Code:
if(current == null){
    return;
}

Ou alors au pire, c'est moche et pas conseillé, mais tu peux faire comme cela
Code:
if(current == null) { return; }

Mais sans les accolades c'est complètement faux.

Et ensuite pour ton problème, tu devrais plutôt vérifier le nom de l'inventaire avec

Code:
if(e.getInventory().getTitle().equalsIgnoreCase("§cInterface admin"){

et non
Code:
if(e.getInventory().getName().equalsIgnoreCase("§cInterface admin"){

Et dernièrement, pour récupérer le nom de l'item, fait plutôt cela;
Code:
if(e.getCurrentItem().hasItemMeta() && e.getCurrentItem().getItemMeta().hasDisplayName() && e.getCurrentItem().getItemMeta().getDisplayName().contains("String")){
    //Ou tu peux remplacer par "contains" par "equals", "equalsIgnoreCase"
}

PS: la prochaine fois envoie aussi tes logs console qui contiennent les erreurs.
 
Dernière édition:

teidova

Bucheron
15 Juin 2014
7
0
11
@Luca_008 je n'ai aucune erreur dans la console,
de plus ce n'est pas la ligne
Code:
if(current == null) return;
qui pose problème.
Ni les ifs, (je ne fais pas ta manière pour les items, ils ont tous un DisplayName)
Cette ligne ne se déclenche pas mais marche très bien pour le menu...
Code:
if(e.getInventory().getName().equalsIgnoreCase("§cInterface admin"){
En effet, je viens de m'apercevoir que le message qui s'affiche,
Code:
player.sendMessage("if effectué"); //Message affiché
s'affiche avec l'interaction avec le menu et non l'interface admin, et cela change tout le problème.

En effet le problème est en réalité le fait que l'event
Code:
public void OnClick(InventoryClickEvent event) {
ne se déclenche pas lors de l'interaction avec l'interface admin.


Ps : Je fais un édit
 
Dernière édition:

Luca_008

Architecte en herbe
21 Novembre 2016
150
20
125
22
s'affiche avec l'interaction avec le menu et non l'interface admin, et cela change tout le problème.
Je pense que c'est un problème de l'item en question alors. Car ça me paraît bizarre qu'un event ne se déclenche dans un inventaire et pas un autre.

Essayes de mettre
Code:
 if(inv.getTitle().equalsIgnoreCase("§cInterface Admin")) {
    Bukkit.broadcastMessage("test");
}
Au tout début de ton event, juste après la ligne "Inventory inv etc..". Ensuite mets le plugin sur ton serveur et essaye de cliquer n'importe ou sur l'inventaire "Admin" et regarde si tu recois le broadcast.

Si tu le reçois c'est que l'event est bien déclenché et donc que la faute est ailleurs, si tu ne le reçois pas effectivement c'est un peu problématique...
EDIT: ps, rajoute un "e.setCancelled(true);" lorsque tu vérifies que l'inventaire cliqué est celui de l'admin ou l'autre. ça évitera deja que ça agisse "comme un coffre"
 

teidova

Bucheron
15 Juin 2014
7
0
11
@Luca_008 j'ai juste rajouté tes deux lignes de test et ça marche ?????!

PS: dsl pour le triple post

en retirant tes lignes unes à une je me suis aperçus que ca venait de e.setCanceled(true)

Code fonctionnel :

Code:
    @EventHandler
    public void OnClick(InventoryClickEvent event) {
        Inventory inv = event.getInventory();
        Player player = (Player) event.getWhoClicked();
        ItemStack current = event.getCurrentItem();
     
        if(current == null) return;
     
        event.setCancelled(true); //ligne ajoutée
     
        System.out.println(inv.getName());
     
        if(inv.getName().equalsIgnoreCase("§8Menu")) { //clic sur le menu
            player.closeInventory();
            if(current.getItemMeta().getDisplayName().equalsIgnoreCase("§cInterface Admin")) { //qui ouvre l'interface admin
                adminInterface(player);
            }
        }
        player.sendMessage("if effectué"); //Message affiché
        //clic
        if(inv.getName().equalsIgnoreCase("§cInterface Admin")) { //clic sur l'interface admin
            player.sendMessage("if = true, détection de l'inventaire"); //Message non-affiché
            player.closeInventory();
         
            if(current.getItemMeta().getDisplayName().equalsIgnoreCase("§7Survie")) { //qui met en gm0 le joueur
                player.setGameMode(GameMode.SURVIVAL);
                player.sendMessage("Détection complète, mise en gm0"); //Message non-affiché
            }
        }
    }
Merci à toi
 
Dernière édition:

Luca_008

Architecte en herbe
21 Novembre 2016
150
20
125
22
Fais attention car si tu mets un "event.cancelled()" sans vérifier le nom des inventaires, à chaque fois que tu cliqueras dans TON propre inventaire ou qu'un joueur cliquera dans un coffre dans la map, l'event sera annulé.

Fais plutôt comme cela;
Code:
 if(inv.getName().equalsIgnoreCase("§8Menu")) { //clic sur le menu
            event.setCancelled(true);
            //player.closeInventory(); Cette ligne est inutile, si tu ouvre un inventaire sur un autre inventaire, le premier sera forcement fermé :)
            if(current.getItemMeta().getDisplayName().equalsIgnoreCase("§cInterface Admin")) { //qui ouvre l'interface admin
                adminInterface(player);
            }
        }