Zylann / godot_voxel

Voxel module for Godot Engine
MIT License
2.66k stars 250 forks source link

How do i rotate voxel #158

Closed KylaCpper closed 4 years ago

KylaCpper commented 4 years ago

I am making a game similar to minecraft I encountered a problem How to rotate textured blocks Like the logs in minecraft, they can be placed in different rotations with different angles

Zylann commented 4 years ago

At the moment, they don't. Also, not all kinds of blocks in Minecraft can rotate, and no block actually rotates by the 24 possible angles. Some have only a few rotated variants, some can flip (doors), have different states (crops, stairs), have multiple parts (doors, beds), or change color (redstone). To be able to place variants, you have to register one item for each. Basically, what you register in VoxelLibrary isn't going to be 1:1 with the types from your game, you'll have to handle the mapping between the raw voxel type ID and your game-specific ID. I had an idea how to do this and been wanting to create a more advanced demo showing it but didnt get the time to do it yet.

Another way is to allocate more data in the terrain to make room for rotation/flip and modify the meshing process such that it handles them, but I'm not sure yet if it's worth it, because it would occupy more memory that would be wasted for non-rotating voxels, slow down meshing and complexify the logic that occludes invisible faces.

Since doing this will go well over 256 IDs, 16-bit voxels would be required (currently supported), and that could be a starting point to implement packed data. Instead of solely storing voxel types, voxels could be structured like this:

tttttttt  ttdddddd

With t being the type (up to 1024), and d being 6 bits of extra data. Depending on the type, that data could represent various kinds of rotation:

Although it's hard to keep things general purpose. Possibilities explode quickly, and that's only rotation. The module would have to implement every configuration one by one (not saying it's not a possibility in the future tho). Unlike Gridmap, this module bakes as much data as possible for speed and memory efficiency so that it can handle very large volumes, so for now, baking oriented voxel types is the way.

KylaCpper commented 4 years ago

At the moment, they don't. Also, not all kinds of blocks in Minecraft can rotate, and no block actually rotates by the 24 possible angles. Some have only a few rotated variants, some can flip (doors), have different states (crops, stairs), have multiple parts (doors, beds), or change color (redstone). To be able to place variants, you have to register one item for each. Basically, what you register in VoxelLibrary isn't going to be 1:1 with the types from your game, you'll have to handle the mapping between the raw voxel type ID and your game-specific ID. I had an idea how to do this and been wanting to create a more advanced demo showing it but didnt get the time to do it yet.

Another way is to allocate more data in the terrain to make room for rotation/flip and modify the meshing process such that it handles them, but I'm not sure yet if it's worth it, because it would occupy more memory that would be wasted for non-rotating voxels, slow down meshing and complexify the logic that occludes invisible faces.

Since doing this will go well over 256 IDs, 16-bit voxels would be required, and that could be a starting point to implement packed data. Instead of solely storing voxel types, voxels could be structured like this:

tttttttt  ttdddddd

With t being the type (up to 1024), and d being 6 bits of extra data. Depending on the type, that data could represent various kinds of rotation:

  • Fixed: data isn't used for rotation
  • Axial: 2 bits used for 3 possible orientations (along X, Y or Z), ex: logs
  • Y: 2 bits used for 4 possible orientations along the Y axis, ex: lecterns, torches
  • Directed: 3 bits used for 6 orientations, ex: coral
  • Full: 5 bits used for all possible 24 orientations with 90 degree angles, but there is only 1 bit left for extra data. Minecraft doesnt have any of these.
  • And other...

Although it's hard to keep things general purpose. Possibilities explode quickly, and that's only rotation. The module would have to implement every configuration one by one. Unlike Gridmap, this module bakes as much data as possible for speed and memory efficiency so that it can handle very large volumes, so for now, baking oriented voxel types is the way.

thanks I get it After all, most blocks are not rotating blocks