By now we’ve kind of become accustomed to seeing RIFT patch notes like “Performance has been improved slightly” without seeing a further explanation. Sure, any improvements to the game are welcome, but it’s also sometimes nice to at least see the simplified explanation regarding what performance improvements were made and how they should improve our gameplay exactly. ZorbaTHut, RIFT’s resident addon expert, had one such explanation post for us last Friday, where he outlined the performance improvements coming to RIFT in 2.2 and talked a bit about what issues the team plans on looking at next.
The short version is that we might be seeing about a 10% framerate boost in 2.2 with more on the way potentially. This is great news for players who experience major slowdowns during large group activities like Conquest and Storm Legion’s zone events. Keep reading to see ZorbaTHut’s full post.
Originally posted by ZorbaTHut (Source)
Greetings, fellow Telarans!
Most of the time I work on RIFT’s Addon system, but lately I’ve been co-opted for some performance improvements. We want your stay in the world of Telara to be as smooth and beautiful as possible, and making the client fast is an important part of that.
In 2.2 we’ve got a few fixes that might boost your framerate by around 10%, and I thought I’d give a quick explanation on the major things we improved and what our next steps are. Be warned: this might get a bit technical!
First, I’m sure you’re all aware of the cloak physics simulation code that is now in the game. Every frame we update a “collision skeleton” for the cloak to bump into. This is a simplified model of the player character – it looks kind of like a balloon animal – that’s easy to do physics calculations with, so the cloak doesn’t move through your body and legs. Before the launch of 2.0 we updated our collision skeleton in a simple manner that worked fine for a simple model, especially given that the cloak simulation itself was rather slow.
Since then, our artists have improved the collision model quite a bit, we’ve added support for dynamic mount collisions, and we’ve multithreaded the cloak simulation so it can take advantage of recent high-end processors. This all means that the collision skeleton update was turning into a major speed bottleneck. We solved this through caching a lot of the internal data and updating it only when necessary, as well as moving more of the skeleton update system into the multithreaded section. This took some work to get right, considering that we had to deal with polymorphs and mounts and the like, but this alone gave us around a 3% improvement in busy environments like cities and raids.
The second issue was in the addon system. Our addon system tracks a lot of data internally so it can hand our addon authors compact and detailed messages. Without this work, writing an addon would be many times more difficult than it is today. Unfortunately, it turned out the addon system was doing a good deal of redundant and unnecessary work with abilities, often processing a lot of data and then throwing it away after it was discovered to be un-needed. Many of these checks have been moved earlier in the process, so that instead of throwing away the data, we just never generate it in the first place. (The fastest code is, of course, code that never runs ) We’re also in the middle of a major rework of the addon framework event system – you won’t see any performance gains from this right now, but once the old system can be removed, there are further improvements we can make to addon performance.
Finally, we found a small stable of small performance losses in the ability button code. I know, I know, “it’s an ability button, how complicated can it be? You just check to see if it’s on cooldown!” RIFT’s abilities are actually really complicated!
Some abilities require specific item types to be equipped (Druid’s Fervent Strike, for example). Some abilities require that the player or target has a buff (Necromancer’s Desecrate), some need to keep track of a past event (Bladedancer’s Reprisal). Some even share cooldowns with other abilities (Paladin’s Shield Throw and Void Knight’s Spark). Many of these checks had performance problems, and while none of them individually were huge, together they added up fast, especially given how many abilities a RIFT player usually juggles.
For a specific example: Years ago, Rift was a much simpler game, with a small number of roles available and a maximum of two dozen ability buttons on the screen at once. Every frame, for each ability on your bar, it would have to unpack a small data structure and figure out whether it represented a Role ability or not. With a small number of buttons and a small number of roles, this wasn’t a problem . . . but now that you can fit over 130 ability buttons on the screen at once, and each button has six roles to check, it became an issue Easy to fix in many ways, via a more efficient search method and a little caching – we just needed to realize it was a problem. That’s one of the things optimization is all about – making sure that the code best represents the game as it is today, not as it was two years ago.
Keep in mind that these fixes are all CPU improvements. They’ll be most noticeable to people with slow CPUs and fast graphics cards, ideally running at low detail settings. If you have a fast CPU and a slow graphics card, the gains might be smaller.
So, what’s coming up next?
First, realize that these are all possibilities, not guarantees. Performance improvements are uncertain at best!
The work I’ve been doing up until now has been idle optimization, with a character standing in the middle of town or an empty field, or, at most, standing in the middle of a flock of a hundred test bots. Obviously there’s a lot of benefit in catching universal performance issues without combat muddying up the data. Equally obviously, if there are performance problems in combat, idle optimization won’t find them My next step is to take this on to live servers, running performance tools while standing shoulder-to-shoulder with you fighting zone event bosses.
Next, there are several hotspots in our rendering pipeline that don’t seem justified. We seem to be using too much CPU to render models; we seem to be using too much CPU to calculate shadowing; we seem to be using too much CPU, ironically, on one of our performance optimization passes. It’s possible that these will be dead-end leads, but they’re worth looking into. Again, I want to reiterate that there’s no way to know if these will work – if I knew, I’d already have fixed them – but they’re all possibilities.
Finally, those of you with modern multi-core computers may have noticed RIFT does most of its work in a single thread. Modern computers are capable of calculating many things simultaneously, but RIFT, by and large, does all its calculations in a straight-line order, not taking advantage of multiple cores or processors. I think there are opportunities to split RIFT’s work into several threads and really exercise modern gaming computers. The programmers reading this are cringing in sympathy right now, as adding support for multiple cores is often a nightmare, but it’s worth trying for the framerate boost that might be achievable.
With luck, you’ll see a few of these issues fixed in 2.3. I hope you’ve enjoyed this look behind the curtain of RIFT development!