• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.
  • entries
    432
  • comments
    1166
  • views
    759298

Lua, YAML, Goblinson Crusoe

Sign in to follow this  
Followers 0
JTippetts

1917 views

I love Lua, that shouldn't be a surprise to anybody who reads this blog. I am possessed of a chaotic, ad-hoc personality, so the ad-hoc nature of Lua coding suits me just fine. I love the fluidity and flow of working with a dynamically typed language, and the ability that it gives me to rapidly prototype and iterate on various data structures, code flow schemes and game designs without having to constantly recompile. Lua is awesome for quickly prototyping a game to see how it is going to work.

However, even with LuaJIT, profiling Goblinson Crusoe shows a distressing amount of time being spent in the various book-keeping tasks of Lua: garbage collection, memory allocation, etc... It's not unmanageable at the moment, given the relatively low number of objects in play at any given time, but I can foresee a time when it might be a problem. A bigger game, perhaps, with more stuff going on.

The main areas I really benefit from Lua are message passing (the backbone of object-to-object communication in GC), data structuring (iterating on the structure of a component), and data description and streaming (save/load, entity construction, etc...).

1) Message Passing - The backbone of communication in GC. Messages are constructed as ad-hoc Lua tables populated with relevant data, then sent through the central object handler via a sendMessageTo(receiver_id, message) call. It's like handing a note to someone; the sender doesn't really need to know what the receiver does with the message, or even if the receiver handles it at all. However, the data of the message can't really be nailed down with any kind of concrete type. For example, a ApplyRawDamage message would contain the amount of damage to apply to a unit, as well as the type (fire, electricity, etc...). Whereas an UpdateLogic message doesn't need any data at all; just the fact of sending it to an object causes it to do a Think() cycle followed by an action cycle.

2) Data Structuring - Especially during development of the combat system of GC, I went through many different iterations of many of the components in GC. I continue to iterate on a lot of things, though most of the main structures are nailed down now. Being able to skip the compilation step was a great time saver.

3) Data Description - An object in GC can be loaded simply by loading a save Lua file that consists of a table of tables. The top-level table describes the overall structure of the object, or which components make it up. The sub-tables describe each component. So a tree might be loaded from a table similar to this:

return{ {component="StaticSprite", sprite="Tree15", scale=1}, {component="HarvestableResource", type="Aspen Planks", quantity=Random(2,4)}}

It is easy enough to just call dofile() with the data filename to obtain a parsed and compiled Lua table with the data, then create an empty object and iterate the component list, constructing components as specified in the file and adding them to the object.


Recently, I've been exploring ways of duplicating this system in C++, hedging my bets against the day when I might find Lua to be inadequate. (I'm still not sure that day will come, to be honest; Lua, especially with LuaJIT, is pretty awesome.)

One of the biggest hangups for me has been the message passing. In my earlier days, I would often implement this type of system using the dreaded void *. Which, of course, really isn't the best idea. void * is the Wild West of variant data types, a Wild West where striking gold or getting shot by an Indian are both of equal probability. My efforts along these lines as a novice were thankfully short-lived, once I realized the sheer potential for bugs this provided. In the ten or so years since, I have never used a void *. I've been cured of it, you could say.

I've implemented roll-your-own variant classes using templates, unions, and all sorts of other schemes. I've even used a string-encoding scheme, where all data was encoded into a stringstream, something I saw once here on the forums. Perhaps the safest and cleanest was using a map of boost::any keyed on a string.

Unfortunately, rolling your own variant/any class also requires rolling your own file parser and streaming code, something which I have little patience for. I went through a phase during my early development where I was interested in parsing and writing languages and all that, but it wore off within a matter of months. I just don't really have any enthusiasm for writing any more parsing code, especially when I'm doing it to replace Lua but am not convinced I really need to, and certainly can't do it as efficiently as Lua.

My latest experiment, however, has been with YAML. Specifically, the yaml-cpp library. The cool thing about using YAML (or even JSON, though I don't like JSON syntax; seeing a readable data file full of " " quoted strings just hurts my eyes) is that the file read/parse/write code is already written. The yaml-cpp Node class provides an easy interface for constructing ad-hoc tables as well, allowing me to directly set or read key/value pairs. In all my efforts, using yaml-cpp has come the closest to feeling like Lua, as far as the data description and message passing. yaml-cpp drops in and replaces all of my configuration, data loading and message passing with relative ease.

It has gone well enough, in fact, that I have considered making the leap back to pure C++ even though I haven't hit the theoretical object limit in GC-Lua yet. I do see that limit coming (maybe not in this game, but surely in the next). I could write a tool to convert the Lua data tables for objects over to a YAML format (for many of them, such a fix would be almost as simple as converting = to : and stripping the return keyword from the top of the file) easily enough. And since the prototypes for most of the key components are nailed down now, then I don't benefit quite so much from Lua's lack of re-compilation requirements. I could port most of my components straight across and be done.

Preliminary profiling indicates a noticeable improvement over GC-Lua, but it's still a bit too early to tell. But just skipping the garbage collection cycle has made quite a bit of difference. To be fair, though, I could probably do a large pass of minor refactoring to reduce or eliminate a lot of waste in GC-Lua, where temporaries are created and collected unnecessarily, especially in inner loops and whatnot. Still, as I ease back into GC after one of my many hiatuses (hiatii?) it is something for me to think about.

0
Sign in to follow this  
Followers 0


1 Comment


I kind of been doing this with C++ and XML files lately, putting a bunch of stuff to control objects in a xml file and loading them after the interface is done in C++, neat isn't it.... Think that is what you are kind of doing....

0

Share this comment


Link to comment

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now