Posted June 7, 20232 yr I know that with this you can save a data in nbt data of a player player.getPersistentData().putInt("value", 0); Is there any way to save this data in nbt data world instead of nbt data player? Edited June 7, 20232 yr by BaRiBoD
June 7, 20232 yr 3 hours ago, BaRiBoD said: Is there any way to save this data in nbt data world instead of nbt data player? Use a capability on the level or SavedData depending on what you're trying to do.
June 7, 20232 yr Author 32 minutes ago, ChampionAsh5357 said: Use a capability on the level or SavedData depending on what you're trying to do. I'm sorry, but if possible, please write the code on how to save and how to get it
June 7, 20232 yr https://forge.gemwire.uk/wiki/Saved_Data if it makes sense to split data for each dimensions then attach to dimensions separately. if it makes no sense, attach everything to overworld.
June 8, 20232 yr Author 9 hours ago, MFMods said: https://forge.gemwire.uk/wiki/Saved_Data if it makes sense to split data for each dimensions then attach to dimensions separately. if it makes no sense, attach everything to overworld. I'm sorry, but if possible, please write the code on how to save and how to get it
June 9, 20232 yr ok. you have "your" storage. where you keep data. let's say this is it: public class OurMap { private HashMap<String, Integer> internal; // getter, setter, etc. } now a Saved data class. before 1.18, it had save and load methods. as of 1.18 load is done in constructor. i don't like it but it is how it is. again, you do not tell the game to save anything. save will happen when it happens. public class OurWorldSavedData extends SavedData { private final OurMap map = new OurMap(100); public OurWorldSavedData() { } public OurWorldSavedData(CompoundTag root) // load method is now this { if (root.contains(Constants.MODID)) { ListTag list = root.getList(Constants.MODID, 10); CompoundTag current; for (Tag nbt : list) { current = (CompoundTag) nbt; this.map.init(current.getString("key"), current.getInt("val")); } } } @Override public CompoundTag save(CompoundTag root) { ListTag list = new ListTag(); foreach (String k, int v) in map do something like this( { CompoundTag c = new CompoundTag(); c.putString("key", k); c.putInt("val", v); list.add(c); } ); root.put(Constants.MODID, list); return root; } public OurMap getMap() { return this.map; } } last part may sound cringy but there are many ways to do this and i can't list them all (and this isn't how i prefer to do it). maybe you'll have the class just expose the internal structure and have the rest of the mod write to it. or you'll provide getters and setters in SavedData. or keep them separate. doesn't matter much. important part - hooking it to work: this is my FoodManager class. don't worry about the logic. also implementation isn't elegant (i have separate map and saved data) but focus on the last part - i attach a single instance of saved data to overworld: public class FoodDataManager { private static OurMap foodMap = null; private static OurWorldSavedData data = null; private static final Logger LOGGER = LogManager.getLogger(); public static int increase(Player player, ItemStack item) { if (!(player.level instanceof ServerLevel)) { return -1; } VerifyInitialized(player.level); int result = foodMap.increase(player, item.getItem()); data.setDirty(); return result; } private static void VerifyInitialized(Level currentWorld) { if (foodMap == null) { data = currentWorld.getServer().overworld().getDataStorage().computeIfAbsent(OurWorldSavedData::new, OurWorldSavedData::new, Constants.MODID); foodMap = data.getMap(); } } }
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.