Better animation control through scripting

Edit: I uploaded a video on YouTube that shows these features in action. The video can be found at the bottom of the post

Among the features I implemented in the past two weeks this is probably the most promising one: the ability to control animations through Lua scripts. Simply put, now it is posible to load an animated scene and attach it a Lua script that controls the animation loop by specifying which animation to play.

Animation Components

Any node in the scene may have one or more components attached to it. A component can be anything from a single value to complex artificial intelligence behaviors. In this case, I’m going to focus on the Animation Components family.  Since an animation can be defined in multiple ways, it seems logical to have several animation components. For example, the VertexAnimationComponent class is used to perform vertex morphing (i.e. the animation used in MD2 models). SpriteAnimationComponent is a new class created with the purpose of handling sprite animations through the update of texture coordinates. Although not yet completed, the SkeletalAnimationComponent class will be used when dealing with skeletal animation. The following is a simplified UML diagram of the animation-related components:

A simplified class diagram for animation-related components

A single animation interface

For the sake of simplicity, we’re going to focus only on the two operations that are present in the diagram: setCurrentAnimation() and update()

setCurrentAnimation() is used to indicate the key frames that we want to display in the animation. For example, setCurrentAnimation(0, 10, -1) will reproduce an animation from key frame 0 to key frame 10 in an infinite loop (the last argument indicates how may loops we want, with -1 indicating infinite).

As it name suggests, update() is used to perform the animation step and varies depending on the animation type. If we’re performing a morphing animation, the update() function will modify the vertex positions to the interpolated value between the current frame and the next one. On the other hand, a sprite animation will change the texture coordinates based on the texture atlas containing all of the animation frames.

A texture atlas containing all of the animation frames for the character

These two methods are key to handle animations regardless of the actual animation implementations:

Node *aNode = getSomeNode();
AnimationComponent *animationComponent = 
   static_cast(aNode->getComponentWithName(AnimationComponent::NAME));
if (animationComponent) {
   animationComponent->setCurrentAnimation(0, 10, -1);
}

Scripting

In Lua, the above code is translated as follows:

function playJumpAnimation()
   animationComponent = owner:getComponent("Animation")
   animationComponent:setCurrentAnimation(0, 10, -1)
end

Whenever the character jumps it will perform the animation indicated by the script. And since this script can be changed in real-time, we do any adjustment as necessary on the fly. This is particularly useful for artists, as they can modify the animation execution as they play the game.

Demo

I just uploaded this video to YouTube showing these features in action using the Sandbox

Conclusion

This is my first attempt for consolidating animation control. I still need to implement some sort of speed mechanism that can be used to vary the time between frames (some animations may be required to be played at lower/higher frame rates). I tried this out in the Sandbox with both MD2 models and sprites and it works like a charm. In most cases I was able to switch between one and the other without having to modify the Lua script at all.

See you next time

New Sandbox features

I have some many things to write about that it was hard to decide where to start. A lot of new features were added in the past couple of weeks, including scene streaming (the possibility to save/load an entire scene either to a file or to a memory buffer), new reusable components, an improved XML factory and even an entire new interface for the Sandbox.

Contrary to common sense, I will start from the very end. That is, the new user interface for the Sandbox which I just finished a couple of hours ago. If you recall from my previous post, the interface for the Sandbox was, well, a bit ugly to say the least:

Web developers are familiar with the jQuery library. This library provides a set of useful Javascript tools to create state-of-the-art web interfaces. And there’s also jQuery UI (which you can learn more about it here). jQuery UI is built on top of jQuery and comes with an entire collection of ready-to-use widgets and themes. Thanks to jQuery, the Sandbox interface now looks a lot better:

In addition to the new interface I also added several new functionalities. Tacking advantage of the new streaming features, I can now save and load any scene created within the Sandbox. I added new/load/save project modal dialogs to handle this:

The script editor is now making use of the Lua mode for editing, which allows for syntax highlighting. I’m still not sure about the dark theme and the font size is a bit small, but I’ll worry about that later:

An asset loader was also added, listing all available assets. Assets are specified using the Crimild XML schema as defined by the XML Factory. This allows the possibility of creating new assets on the fly without having to restart the Sandbox:

I’m still working on node selection and manipulation. I want to achieve a mechanism that allows the user to select, move, rotate and scale any object in the scene (whether it’s representing geometry, a trigger, a camera or any other type of object) using simple controls. Mainly because we’re all using laptops here with touch pads and I want the the object manipulation to feel as natural as possible.  I’ll probably make a video about this once it’s done.

That’s it for this week. Next week I’ll give a brief introduction to scene streaming support, including some design considerations and usage instructions

Achieving rich UIs with HTML and Awesomium

There are a lot of different ways to create user interface for games. Which one to use will depend mostly the information that we need to display and the interaction requirements. So let’s take a look first at some screenshots taken from different games:

The first thing to notice is the amount of information the UI includes. In the first screens, the UI displays various indicators, pop-up messages for objectives or notifications, and maybe a map. In these cases, the interface is simple enough that can be coded in whatever programming language it’s being used in the rest of the game without too many complexities. Keep in mind that I’m not saying that they are easy to program though.

In contrast, the rest of the images show interfaces with not only more information, but also different kind of interaction as well. There are several panels with text and images, collapsible skill trees, windows that can be moved, sized or even restyled according to the player preferences.

As the interface complexity rises, we need simpler ways to create and modify them probably without having to recompile the entire game in the process. For example, World of Warcraft uses Lua to define user interfaces.

Why HTML

In the last then years there has been a lot of process towards rich user interfaces in web applications. Just take a look at the Sandbox Demo in the Ext Project Website to understand what I’m trying to say here.

By building our interfaces on top of HTML and JavaScript we not only can achieve impressive results, but also it will speed up the development process. Most of the interface requirements can be coded and tested without even starting the game. And if CSS is used as well, the entire look & feel can be changed on the fly.

What is Awesomium?

Awesomium is a windowless Web-Browser framework that renders web pages into a memory buffer that can be later used as a texture for a 3D object. Being a branch of Google Chromium project, it supports HTML 5, CSS, Javascript and even Flash.

Awesomium is really simple to use. The framework loads a URL (or file URL) and a listener object is used to respond to the different events like new requests, mouse and keyboard events, JavaScript callbacks, etc. Look at Awesomium Basic Concepts Guide for a more in depth explanation.

If you’re still skeptical about what can be achieved with HTML interfaces and this framework, just take a look at the video below:

How is Awesomium used in Crimild?

I’m using the Awesomium Framework as part of the Sandbox Project, but I’m planning on extracting the integration classes into its own library so it can be used in other projects as well.

On one side, a listener object reacts to interface events, like creating new objects when the corresponding button is pressed or starting and pausing the simulation. In addition, I’ve included a basic script editor tool using the CodeMirror2 HTML source code editor.

Script Editor

Editing Lua scripts in real-time

Another advantage of HTML interfaces is that we can include these kind of widgets with very low effort. The interface is rendered into an Image object that is later used a texture for a rectangle geometry that is displayed on top of the 3D world.

There is a downside on this approach, though. I’ve noticed some performance loss each time the UI is refreshed. It is by no means a showstopper as the Sandbox still runs at a very high FPS rate, but it is something to keep in mind when designing the UI for our games.

Stay tuned to know more about the Crimild/Awesomium integration in the future.