BlockState <-> Byte[]

Hello,

How would I go about converting a BlockState into a byte array and back? Is a mapper absolutely necessary to do this? Or even better yet, is there a way I could extract all values of a block to save as strings/ints/primitive variables, and then create a BlockState back from this?

I’ve tried

ByteArrayOutputStream out = new ByteArrayOutputStream();
ObjectOutputStream os = new ObjectOutputStream(out);
os.writeObject(/*BlockState here*/);

however I get an exception on the third line with the message

net.minecraft.block.state.BlockState$StateImplementation

My programmer spider sense, plus a history of developing Sponge plugins during development, tell me this is just due to the BlockState not being fully implemented (plus common sense with the message).

I feel like what I described in the first paragraph could be possible, or there is another way to do what I’m trying to do. Thanks for the help!

What are you wanting the byte array to represent?

Currently, implementation-wise BlockState is effectively a byte value representing a damage value on a block. However this is the old thinking - in the future there will only be one id - one id per Block state. The implementation of the API deals with linking a set of values to a particular block state.

Perhaps use BlockState.getValues() to get a list of values that lead to that state? (you’ll need the block type too, of course)

1 Like

Basically I want to be able to store the information necessary to save the BlockState information, so I can later do world.setBlock(x, y, z, myBlockState). I think I see how it would be possible to get the values of the state and the block type and save them. I would then be confused on how to recreate the BlockState, since I can’t instantiate it from what I recall.

My main problem is that I’m trying to save the BlockState into a database, and I can’t easily just save the object, so I need to break it apart first and then put it back together. I would probably then run into the problem of not being able to save each value of it, since they aren’t simply strings or basic types. Do you have any tips regarding all of this?

You can use ConfigurateTranslator in SpongeAPI to convert a DataView (which most stuff in sponge is) to the Configurate API - which supports outputting JSON, HOCON, or whatever you want.

Then you can convert back to a DataView with that same object. You can then use DataManipulator.from(DataContainer) to check possibly getting a given manipulator (ie value) from that. Do this for all manipulators and you’ll have yourself a list of values you can apply to your given BlockType with BlockStateBuilder!

I know that seems a bit lengthy, but this system could conceivably be used for anything that is a DataSerializable, including entities, blocks, worlds, etc.

1 Like

If you want to store and restore not just BlockStates but also data on TileEntity(ies), you should use a BlockSnapshot as it will not only retain the block state information, but also any other information on the TileEntity.