Saturday, February 15, 2014

Oculus VR: FPS Integration Challenges

So I just got my shiny new Oculus Rift developer headset the other day. It is difficult to keep my jaw from dropping to the floor while using it - it truly is a sea-change moment as Valve is predicting.

I got started right away on getting support working in my game, which isn't really an FPS but definitely takes place from a first-person perspective and features guns (so it kind of is an FPS I guess, but doesn't focus solely on shooting).

Early on in the development of my game (before I had even considered Rift support), I decided my game would not have crosshairs. I feel that ADS-style aiming is where FPS games are headed, and it's deprecating the need for crosshairs. Hell, DOOM didn't need crosshairs - and if you think about it, DOOM basically took place from an ADS-perspective for the whole game (which is why it didn't need crosshairs).
It also gives gun attachments new meaning. In games like Call of Duty where you have crosshairs while hipfiring, they have to intentionally nerf the usability of the gun while the user isn't aiming down the sights. This has always annoyed me to no end - that if I aim down my sights, my shots magically line up, but the moment I don't hold the gun up to my face, my shots fly wildly around like my character is drunk.
Since there's no crosshair, I don't have to deal with this. The incentive to use ADS is that, well, you can see where your shots are going. It's something that anyone can just pick up and understand. The incentive to use a Holo Sight is that you get a handy crosshair painted onto glass instead of using the weapon's iron sights, the incentive to a laser pointer is that you can see where the gun is pointing from hipfiring, etc. It ends up feeling more realistic and more understandable because we're not just throwing stats at the player - we're showing the player that for instance aiming with a sight is objectively easier than iron sights, and infinitely better than hip firing, without having to explicitly tell them.

And now comes the problem. In your standard 2D monitor mode, the FPS is lined up smack in the middle of the screen.
This is a problem in VR. Want to see the problem first hand? Grab a paper towel tube, and aim down it as if you were firing a gun. You'll immediately notice that it's line up with one eye (probably your right eye, but maybe not if you're left hand dominant), and your other eye is either squinted or closed entirely.
Now try lining up the gun with the bridge of your nose instead. That's basically what lining up the gun smack in the middle looks like in VR, and causes significant eye strain.
It turns out, what you actually want to do in an FPS is pick an eye, and align the gun with that eye. By default this is probably the right eye, but you will also want to give players the option to use their left eye.

It's worth mentioning that this doesn't matter with motion controls such as the Razor - since the user will be doing the aiming rather than letting the game align the gun.

Friday, February 7, 2014

Thoughts on uLink and TNet

During the development of my game, I've been using Tasharen Networking for multiplayer (by the developer of NGUI). But now I'm looking at moving my game over to a much more well-known (and much more expensive) framework, uLink.

Why would I move from a $60 framework to a nearly $800 framework?
Simply put, my project has outgrown TNet.

Actually, it had outgrown TNet the moment I added multiplayer, but I hadn't realized it until I started working on interest management. Area of Interest is something that, it turns out, TNet is fundamentally not designed to handle. Nor are authoritative servers.
TNet is meant to act a bit like a self-hosted Photon Cloud - your clients connect to a server, players create and join "channels" (which are basically rooms), within each channel there is one single host, etc. There's really a lot of similarities to be drawn there. It's designed for the server to act as little more than a middleman for players to connect to each other.
That was a mistake on my part - trying to force TNet to act in a way it was not intended. To be fair it helped me develop my multiplayer logic (which will remain largely intact in the move to uLink) but the creator (Michael Lyashenko) actively discourages using TNet as a dedicated server.
The limitations became glaringly obvious when I tried to add AoI. This required ripping out TNet code and hacking in the concept of player scope. Days later I'm still hacking away with no end in sight (after coming close several times, I'm currently left with a game that doesn't even remotely work). It's taking valuable time away from working on the rest of the game.
So it's time for uLink. Unlike TNet, uLink was designed for this kind of stuff. In fact, MuchDifferent (the company behind uLink) set a Guinness World Record for most concurrent players in an FPS game - a nearly 1,000 player match between team Man and team Machine. uLink is designed for authoritative servers, and optimized for performance. Granted the 1,000 player match also used other technologies besides uLink (likely load-balancing tech like Pikko), but nonetheless uLink still remains my best option.
And that is why I dumped $800 on an indie UnityPark Suite license.

Monday, February 3, 2014

Progress of my game

Figured I'd post a little bit on how far I've come in my personal project. I'm not sure what to call it yet (Alien Skies is the working title but may and probably will change).
After so long researching and playing with open-world type setups in Unity, I've determined that terrain streaming is nigh on impossible in Unity without rewriting the terrain engine itself - everything takes FOREVER to do, from modifying the heightmap, to adding trees, to even culling the terrain (with many terrain tiles with trees on them, performance dropped whenever the camera frustum changed). It's not very optimized, unfortunately, and is one of those things that needs tons of work in future version of Unity.
Therefore I'm sticking with a naive one big terrain approach. Seems almost too naive to work, then again Operation Flashpoint, Arma 1, and Arma 2 all got away with it (terrain streaming is new in Arma 3). DayZ is using the Arma 2 engine, which means the entire world is loaded at once (although pieces of the world are likely disabled to reduce the rendering burden). So I'm sticking with a fairly small world (10km per side), no streaming, with culling masks to disable rendering of distant objects (which are assigned to various layers which affect the distance at which they cull, so small objects are culled sooner than large objects).

After settling on this, I finally got to working on actual gameplay. I set up a Trello page for myself so I could keep track of my progress, and a Git repository on BitBucket so I can check it into remote backup and eventually share it with people.
This being a multiplayer game, I had to evaluate what I would use for networking fairly early on. At first I was dead set on buying uLink. Then, after evaluating the actual features uLink provided I realized that I already owned Tasharen Networking which provides much of the same functionality I'm actually going to be using, with a little extra effort.
I also had to make a little build tool for myself, to make server builds of my game (which I need to do quite frequently). This was easy enough - the tool adds SERVER to the list of scripting defines, ensures that a special ServerStartupScene is the startup scene in the build (this scene automatically loads up the map and starts a TNet server instance), builds a standalone player, and then reverts those changes. I have build tools for both Windows and Linux, so I can just pick Build Windows or Build Linux Server and have a ready-made game server.

Gameplay-wise, I actually spent a lot of time working on the singleplayer prototype before adding multiplayer. I'm nearly to where I was before adding multiplayer now, which includes:
- GUNS! Player can equip guns from their hotbar. They can fire the gun with LMB, and shoot with RMB.
- Loot and inventory. Players can move items between hotbar and inventory, and between loot box and inventory/hotbar. There's also a handy Take All function (which actually means "Take as many as possible")
- Alien( capsule)s. Aliens currently spawn in mobs MMO style, which I'll eventually change to a kind of random dropship encounter (which sounds better? aliens popping in before your eyes, or dropships unloading an alien squad before your eyes?). They have a fairly simple behavior tree, which causes them to wander, or upon seeing the player alert nearby allies and start engaging/pursuing. If there's no line of sight to the player, aliens will pathfind to player, otherwise they randomly strafe back and forth while firing in bursts. They also lead targets (broken in multiplayer, but will be fixed soon enough), which makes their bullets very tough (almost impossible) to dodge at close range.

I've been hearing things about Rust and DayZ being chock full of hackers, so I've been very careful during the addition of multiplayer to keep things server authoritative. Using items is server authoritative (server calls Use method and sends back the results), looting and inventory (dragging and dropping sends message to server, which handles the actual drag-drop and sends the results back), weapons (equip weapon is server authoritative, sending results back to player, as is weapon firing - no entity rewinding so players will have to lead targets, but I think I'm OK with that)
My next task is to work on movement in multiplayer (and I'll make THAT server authoritative too! ain't nobody gonna be noclipping or super jumping).
And then?
I have no idea. More content? Team recruiting?
I'll see when I get there.