In another month, it will be four years since I started this project! I cannot tell you how much it pains me to write that sentence....
It all started well enough, but within the first year, I had already gotten mired in the details of 3D graphics, multiple platforms, etc. Then my health started acting up, with months at a stretch of not being able to sleep more than four hours a night. The project turned into a "guilt object", which I couldn't give up on, but was sick of working on. By the second year, I was only working on it in spurts, and had lost any concept of where I was going.
I was also determined not to do just another Minecraft-style block world. Partly because I'm not thrilled by the way it looks, but mostly because I just wanted to be more original. Needless to say, I did not come up with a better concept. I have found this whole effort to be humbling.
For the last year, I've been in email conversations with another indie game developer, also working on a block world. Like me, he's a detail oriented person, and he's spent the entire time I've known him tuning his rendering algorithm and not building anything like a game.
Recently he sent me this video showing someone who is obviously going for a game first, and not sweating the rendering details or working down at the OpenGL level (he's using Unity.) I'm jealous.
I challenged my indie friend to write up a design for his game. I would do the same and we'd see if we could find common ground and work together. That hasn't happened yet, but here is the design document I sent to him.
I can't promise that any of this will happen, but I am working on the code again. I will put up a demo as soon as there is something to show. Feel free to comment on the design.
Start with something usable and add features to make a more complete world. Stop obsessing over internals! Each topic below is another enhancement to the game.
The player is on a small planetoid (radius perhaps 5 km, with approximately 300 sq km surface area). In the sky, other planetoids and a sun are visible. The planetoid is spinning, with probably a short day. The landscape is exaggerated, with high snow-capped peaks, melting to many streams and valleys. Biomes vary with altitude, from barren peaks to rolling fields to lush jungle at the base of the mountains. There are some large lakes.
There's no clean tiling of a sphere with squares, so I will use the six-sided "inflated cube" style of mapping, which leads to 12 seams which are a minor problem, and 8 corners which will be very distorted. These can be hidden under water or some other non-editable feature.
In the first demo, basic lighting with no shadows. Distant blocks are replaced with a procedural heightmap landscape. The player can walk around and explore.
We could do an exact rendering of a curved surface by distorting the cubes in the shader. However that's going to be a problem when rendering with quads for performance. A better solution might be to adjust whole 32 by 32 by 32 chunks to the correct angle and leave the internal cubes orthogonal. At a radius of 5 kilometers, the height of a flat base will be 0.025 meters (about 1 inch) off from the ideal. This will probably not be visible. If it is, we can cut the maximum quad size down.
In other words, instead of rendering a pie wedge with curved surfaces, each chunk is a trapezoidal prism.
Next is to add a database for the world and a UI for adding and deleting blocks. The McrView program will allow players to export structures from their existing Minecraft worlds. These can be imported into the game.
I don't really want people cutting and pasting huge buildings. They will undoubtedly stamp them out over the entire landscape. I'm not sure what to do to prevent this. One version of the game, back many parts ago, had the idea of minions that you could recruit to build for you. I was thinking they would also mine to supply materials, and would farm to support themselves.
This is all a lot more than I want to take on at this point (if ever) in the game. I suppose the simplest way to control cut and paste is to require you to mine enough blocks to make the structure you are importing. It would be tedious to make you find all the right materials, but perhaps just the right number of blocks would do.
In the first version, I'll let players cut and paste and see what happens.
Use the SeaOfMemes Part 71 techniques to summarize distant landscape.
We have large regions of 1024 by 1024 by 1024 cubes. At maximum distance, these are summarized as single blocks with textured sides. The top level is divided into 512 by 512 by 512 summaries, etc, down to the leaf 32 by 32 by 32 chunks. At different distances, we use different summary levels.
The big problem with this approach is the sheer amount of data to be managed. A region has one billion cubes. We don't want to fully populate the tree of summaries. Instead, we procedurally generate all the unmodified levels in the tree. Only the modified portions of the landscape and their parent summaries are stored.
When a leaf chunk (size 32) is modified, the parent summaries up to the top have to be regenerated. Since a change is only a single cube, we would compare the new summary to the old as we generate it, and when there is no change, stop generating parent summaries.
Another issue is the initial state of the database. We will immediately need summary levels out to the horizon. Generating these from procedural data takes time. We can let a heightmap landscape stand in until we have a summary block landscape.
To keep the world database from becoming huge over time, we could have modified chunks "age" back to the procedurally-generated defaults, when the area is not owned by a player. This would keep the database proportional to the number of players, not steadily increasing in size over time as players modify the world.
Reuse the cube code to build avatars from small cubes. There's a skeleton which holds chunks. Allow the avatar code to position the skeleton as the player walks, turns his head, etc.
There should be a UI for editing your avatar. Cubes can be any solid color, but there is an internal limit of 16K different cube types. Since any one can be set to an arbitrary RGB, this should be enough.
The GUI will need some more work to support an editor this complex.
The player should be able to start a floating object by doing an operation on a cube. Then the floating object is added to just as a building would be added to. Or the UI could support conversion of a set of blocks from landscape to object.
Simple floating objects would be things like furniture. Power sources should allow construction of vehicles, esp. flying vehicles like balloons.
Transparency in floating objects is a problem, since they can intersect landscape or other objects at an angle. The sort-cubes-by-distance approach will not work. We could either restrict transparency in objects, or just punt it.
Another issue is how the floating object aligns with the landscape. Interference checking becomes more of a nuisance. You don't want your balloon or car stuck because it's rubbing against a single cube in the landscape.
Does the floating object snap to the grid when it lands? If we're also using objects as furniture, it shouldn't.
Are there limits on the number of objects in a region? People will build angled houses out of multiple objects if there are no restrictions.
Do objects have their own summaries for use at a distance?
Add proper lighting with shadows. This would also be the time to add clouds and weather. I'm still not sure about the right way to do this in real time.
Atmosphere and Sunsets
There should be haze in the distance. Unlike my older demos, the atmosphere needs to be spherical. There should also be realistic sunrise and sunset. I think there are algorithms out there which simulate rays through air and handle both of these problems.
I want to add multiplayer relatively early in the development process so that players can give me feedback. Eventually, I want to do peer to peer servers, to avoid setting up large numbers of servers. For this step, a conventional client/server setup will do.
The server offers:
I want user identities to be generated with a cryptographic key stored on the player's computer (he can copy it to multiple machines.) In this version, it's only used for login authentication.
There should be a kind of "boundary stone" that is bound to the player. The player marks out his territory with this stone. As he advances in the game, he can buy more boundary stone and enlarge his territory. No other players can build above or below this stone.
Ordinary unclaimed landscape can still be modified by any player.
Objects are also owned by a player. Must each have some boundary stone in it? What are the restrictions on the size of an object? We want to support flying castles.
In a peer to peer system such as I would like to build, there's no central authority to ban offensive players. To handle this, I would support an "ignore" command. Unlike the normal MMO ignore, this doesn't just stop text messages from the offender. Instead, the ignored player and any structures he has built will disappear from your view of the world, and you and your structures will disappear from his view of the world. You can ignore an offensive structure as well (which will include the player who built it).
One worry is that this "gives goals to trolls" -- he can try to get himself ignored by more people by being an even bigger pest. Still, I think the ignore function may work. First, there's a very strong social sanction -- say something offensive and people disappear all around you. There are fewer people to play with, and the world starts to get less interesting. Even if the troll is trying to see how much of the world he can erase, his behavior affects fewer and fewer people.
The ignore is powerful enough that players won't do it casually. And once they do ignore someone, there's nothing the troll can do to bother them again.
Commerce would include the ability to buy and sell blocks, give money to people, and an auction house. My worry is price inflation/deflation in an unsupervised world.
I'm not sure how well this has been handled in other games. I think WoW prices varied constantly as they increased the level limits. Higher level quests had greater rewards, which pumped too much money into the economy, driving up prices. EVE has had a different result, but they still actively manage the economy. In an unsupervised peer to peer world, that's not going to be possible.
To keep prices stable, there has to be a base activity ("farming") that's of use to the entire economy and which increases as user population increases. In my game world, it will probably be mining, although I suppose people could require food and water as well.
Items also need to wear out or be consumed, otherwise the world will fill with goods and have price inflation.
I'm not sure how well a real world barter economy would work, so I'm not sure what can be implemented here.
Crafting and Skills
In Minecraft, the player learns which materials to combine to make new items. There's no skill involved, just the patience needed to collect all the materials. In WoW, you need to level up and acquire skills before you can make objects.
I'd like a WoW-style skill tree where you practice and specialize in manufacture of objects. This seems necessary for any real commerce, and gives people a reason to cooperate.
Is there a limit on the number of skills a player can have? WoW used to restrict people to two, but I think they may have changed this.
If skills are restricted, can a player have multiple characters? Banning trolls would be easier if there were a single character per player, and all of your skills and belongings were tied to that character, giving him a high value.
Peer To Peer Data
The game could be distributed as clients plus a server product for people who want to support their own groups. However, I'd like to have a really large MMO community. I just can't afford to run more than one or two servers without charging for the game. Even if I did charge, I don't want to run a huge cluster of machines.
I expect most of the traffic will be requests for landscape chunks. If this function can be handled peer to peer, then a single central server can probably handle all the rest of the game functions for a population in the thousands.
I'm thinking that each client maintains as much of the database as it has seen, and must have a copy of all the player's own data. The central server can query for changes, and make itself the authoritative copy of the world.
When a request comes in for data, the central server could also defer it to another client which it knows has that data. Then the player would connect to that peer and do the transfer. If it maintained that connection, the client code could query peers ahead of the central server, to offload traffic.
Non-landscape messages, like movement and chat, exchange of money or mail, would still be handled centrally.
Once the user population gets big enough to outgrow a single asteroid, more territory can be added. These could be asteroids, space stations, hollow colony worlds, or planets.
If we have multiple asteroids, do they move? On a single world, we can send player x,y,z. When the player is in space, what part of an asteroid he's above depends on the exact time. So there can't be a global exact position without synchronized time.
To make the world truly extensible, it needs a scripting language. My dream version of this would use LLVM to generate object code, and the entire system would be rewritten in the scripting language. Then the GUI, the "applications" like the auction house or chat, can be replaced by user mods.
Very little of the client would be fixed. In the extreme case, the protocols for managing connections, the object database and the graphics engine would be hardcoded.
This brings up all sorts of issues relating to security however, so I'd probably have to start with a much more modest scripting environment.
Dual Contour Landscape
Although the cube landscape is practical and many people love it, I still think it looks kind of nasty, especially at a distance. I've always wanted to have a modifiable polygon landscape with cube-based buildings on it. Buildings and other objects could be at any orientation.
It should be possible to implement something using dual contouring that looks acceptable and is still modifiable. I don't want to bog down the project by doing it early in development however.
Full Peer To Peer
If everything in the shared world is owned, and the owners have the definitive copy on their computer, then the full peer to peer implementation is mostly concerned with finding the owner and propagating copies of objects to everyone who wants them.
A second problem is when an object changes owners -- money changing hands for instance. The old version has to be authoritatively destroyed, and the new version created. I think creation is just the first problem again -- propagating knowledge of the object. Destruction should just be propagating the knowledge of an old object's demise.
I'm assuming that the world starts client/server until it builds up a large base of users. There will be enough users that a peer can always be found. The switch to peer to peer distribution of world data enlarges the world again, and lets us debug the exchange algorithms. Finally, the central server is downgraded to just being another peer (or rendezvous point for new users), and the network is self-sustaining.
I have no idea if this style of system is really possible. I would be satisfied with a few thousand users per server, but a really open ended system would be even better.
blog comments powered by Disqus