0

Ive been trying everything online and have yet to find it. Heres my code. Please tell me what to fix Im so confused.

private void loadProtectionEnchant() {
    
    int protectionID = 0;
    
    try {
        Field id = net.minecraft.server.v1_8_R3.Enchantment.class.getDeclaredField("byId");
        Field protEnchant = Enchantment.class.getDeclaredField("PROTECTION_ENVIRONMENTAL");
        
        id.setAccessible(true);
        protEnchant.setAccessible(true);
        
         Object[] byID = (Object[]) id.get(null);
        byID[protectionID] = null;
        
        Field modifiersField = Field.class.getDeclaredField("modifiers");
        modifiersField.setAccessible(true);
        modifiersField.setInt(id, id.getModifiers() & ~Modifier.FINAL & ~Modifier.PRIVATE);
        id.setAccessible(true);
        System.out.println(byID.toString());
        
        System.out.println(id.toString());
        
        id.set(null, byID);
        protEnchant.set(null, new CustomProtectionEnchantment(protectionID, new MinecraftKey("protection"), 10, 0));
        
    } catch (NoSuchFieldException | SecurityException | IllegalArgumentException | IllegalAccessException e) {
        e.printStackTrace();
    }
    
    System.out.println(Enchantment.PROTECTION_ENVIRONMENTAL.toString());
    
}

and heres my error java.lang.IllegalAccessException: Can not set static final [Lnet.minecraft.server.v1_8_R3.Enchantment; field net.minecraft.server.v1_8_R3.Enchantment.byId to [Lnet.minecraft.server.v1_8_R3.Enchantment;

Please tell me if u know whats wrong TY.

Eddie O
  • 1
  • 1
  • 1
    You almost certainly can't do what you are trying to do. It's likely that the value in a static final is inlined during compilation so can't be changed at runtime. See the caveats on the accepted answer for https://stackoverflow.com/questions/3301635/change-private-static-final-field-using-java-reflection – sprinter Jan 31 '21 at 23:05
  • but when I print it out it says that I removed all the modifiers from the field, hmmm idk im confused. – Eddie O Jan 31 '21 at 23:09
  • 1
    Using reflection to subvert normal access restrictions is never guaranteed to work. Implementations are free to optimise in ways that prevent this irrespective of what you do to the modifiers at runtime. – sprinter Jan 31 '21 at 23:17
  • I just feel like because its a list you should be able to change one of the values in the index. Like is there a way I could do that. – Eddie O Feb 01 '21 at 04:32
  • Have you tried `Array.set(id.get(null), index, newValue)`? I suspect you'll still have the same exception but worth trying. – sprinter Feb 01 '21 at 06:02
  • Im gunna try it but I dont think that does what I want from my understanding – Eddie O Feb 01 '21 at 16:27
  • 1
    There are no read-only arrays in Java. When you did `byID[protectionID] = null;`, you already modified the array. There is no point in setting the field referencing the array to exactly the same reference it already contains. – Holger Feb 01 '21 at 17:16
  • 1
    @sprinter you are thinking too complicated. The OP’s `byID[protectionID] = null;` did the job already and writing back the array reference is entirely pointless. – Holger Feb 01 '21 at 17:19
  • Yeah you were right @Holger Didnt need it at all TY sm – Eddie O Feb 01 '21 at 17:47

0 Answers0