Ruby is *not* at all suitable for game development!

I love ruby. It’s beautiful language, with elegant and expressive syntax – perfect as a scripting language, and great for prototyping new ideas quickly… I use it every chance I get, and truly enjoy coding in it.

But is it suitable for game development?

Unfortunately the answer is a resounding no!

I say this probably being the largest ruby fan on the planet, but the simple answer is if performance is at all important for you, you are going to find ruby completely unsuitable.

It’s not because ruby is “slow”. We all know that it’s slow, it is an interpreted language after all. Ruby 1.9 has made it quite a bit faster, and in most cases the performance is slow, and there is plenty of room for improvement, but it’s not too bad.

The problems with ruby aren’t directly related to performance, but are more architectural…

Several years ago when I first started to tinker with Ruby (1.6.8 era), I felt it needed the following things before it could be ready to use in games:

  • Bytecode interpreter
  • Native threads (not green threads)
  • Incremental garbage collector

With Ruby 1.9 we can now check off the first two, but unfortunately the garbage collector is still stuck in the stone age.

The problem of course is that ruby uses a mark-sweep garbage collector. This is a two pass algorithm that first walks over objects that can be reached from top-level references (the “mark” step), then in the second pass it walks over all objects and removes those that aren’t marked (the “sweep”).

This is of course exceptionally cute and ruby like. Reference counting (as used in python and obj-c) can be a pain in the ass to maintain, because if you mess up inc/dec references, you leak memory or access a dead object. With the mark-sweep nothing is required except a function that tells ruby what objects are referenced by one object, and of course ruby can work this out itself (hint: it’s the member variables…)

The problem with this is that it takes a long time to execute. In my simple game application under normal use I found that ruby garbage collects once every 5 seconds or so, and each time it caused a frame hitch of 35 – 100 milliseconds on my macbook air.

Problem is, at 60FPS we only have 16.67ms per-frame… and the GC just blew the budget. This means we’re going to drop frames on a regular basis, and the game feels awful to play.

So what is the solution?

Right now the only option is to disable the GC entirely, and avoid allocating memory on the fly. Pre-allocate all objects, “GC.collect” immediately after level load then “GC.disable” until the end of the level. Of course you also have to avoid calling methods that allocate ruby objects, this basically rules out using any 3rd party ruby libraries (which are allocate happy), and eventually you end up writing your code basically in a C-like fashion within ruby

After a month of this, you start asking yourself “hey, why exactly am I writing code in ruby again?”. After all, if I wanted to pre-allocate everything and not use garbage collection, I could just use C++, and the performance would be much better, and I wouldn’t have to write all this glue code between Ruby and C++…

So until somebody writes a real garbage collector for ruby, one that either runs asynchronously on another thread, *or* one where I can throttle the GC once per-frame “ok, please garbage collect now, but you have a time limit of 1ms to do everything you need”, I have to conclude that ruby is not suitable for game development and you should not waste your time trying to use it!

If you are set embedding a scripting language in your game, I would say that the main choices at this point would be between LUA and Python. I do prefer the syntax of Ruby over Python considerably, and I’m worried that LUA wont actually add enough on top of C++ to be worth integrating without a lot of customization… but clearly either of these options are good, both having shipped in many commercial games.

For now, I’m sticking with pure C++ for games.

54 thoughts on “Ruby is *not* at all suitable for game development!”

  1. Wow, I’m surprised that Ruby doesn’t have a better GC. I guess in the web world it’s not important (since you tear down at end of page processing).

    Have you looked at other Ruby backends, like .net? (I guess that has its own problems.)

    Have you looked at Tamarin?

  2. I tried with ruby 1.8, then with latest 1.9.1 (YARV bytecode)

    Looked at the available options… MacRuby did not seem mature enough, didn’t really want to switch to JRuby and of course .NET ruby and Mono on the mac… just didnt want to go there!

    At this point my real hope is that google ports ruby along with python to run in their bytecode for chrome (used for javascript interpreting right now) – that would do it!

    cheers

  3. I’d like to see an explanation of why those 3 things are needed for game development. Further, “I don’t really want to switch to JRuby” is not a compelling reason to say Ruby is not suitable for game development because Ruby doesn’t have X even though an implementation of Ruby does have X.

    I’m not saying I’d be trying to build the latest Calls of Duty in any implementation of Ruby. But you’re dismissing it, and contradicting yourself at the same time.

  4. Have you looked at Parrot (http://www.parrot.org/) ? I’m not sure if it is ready for general use yet, but I love the idea and hope it turns out into something fantastic one day. From quickly skimming over some docs, it seems like it only has a working mark-and-sweep gc currently, but apparently they are working on other schemes too.

  5. what can i say tomas, i’m a fan of ruby – so i’d like to be able to use it for game development, even given that its slow, it is still useful given that you can rapidly develop and prototype ideas, then swap out time critical parts for native code

  6. aman, to be honest i’ve had enough tinkering around with the runtime – i’ll wait till something is in the official release before considering it again, thanks for the tips though!

  7. sammy, i don’t really see how i’m contradicting myself here

    #1 is for speed, interpreting a language from AST is just too slow to be seriously considered as a game scripting language, contrast this with python which has compiled to bytecode for a long time, or LUA…

    #2 is because concurrency is becoming a larger issue the days. most computers have multiple cores, if you write single-threaded code or use green threads you don’t get the full performance on the machine. in this case compare ruby’s original threading model (green threads) with say, java threading model – its almost a windows 3.1 vs linux type comparison to be honest

    #3 – well, since garbage collection is mark sweep it is O(n) on the number of active objects. in a large game world this cost becomes unbearable. why not jruby in this case? well the java runtime and bytecode is quite good, and the GC is good… but java is pretty heavyweight and of course, on top of this I write a lot of C++ native code to supplement my pure ruby code, do I really want to be writing code in ruby, then interfacing via JNI to get native code in C++? What a huge pain in the ass! No thanks! – its bad enough accessing native code from ruby with the high data-type conversion cost between ruby and C (this overhead btw. is the *other* reason why i have given up on ruby for my home game engine, i can see no solution for it – short of what macruby is doing to reimplement all ruby types in terms of obj-c types internally)

  8. Pingback: Ennuyer.net » Blog Archive » 2009-01-12 - Today’s Ruby/Rails Reading
  9. Hi, i want to learn gameprogramming and i thought i should start with ruby because it seems easy and smart. I am fluent with bash and have made some fairly large apps in it and have also used multimedia fusion but that’s about it. Will ruby do(i’m thinking ruby and rubygame) to make some simple 2d games? Which dev environment should i use with ruby & rubygame? i am not interested in Vim or Emacs but are using linux(archlinux).

    And if it is so that ruby needs those two items could you not post a feature suggestion to rubys bugtracker(i do not know well enough of what you are talking) :) I am sure we wil get those two if those are the main ones holding ruby off as a viable gamemaking platform :) but right now it seems that we will have to wait because it is not tha many ruby devs…

  10. meh. that was a bit shorter answer than i wanted :P Right now i’m thinking i’m just going to go with ruby just in order to learn some skills i can hopefully implement in whatever language later. going straight to c++ seems a bit too much right now but i’m sure it’ll be a cake after learning some ruby.

    you recommend unity which to me seems you didn’t read my post very well or are trying to “sneak one in”. Because unity doesn’t support linux i guess it’s SDL for me unless you know an other awesome lib.

    what should i use for ruby and c++ dev on linux? :D

    1. hey it’s just that simple i don’t recommend ruby for game development (hint: check the title of the blog post), so i don’t really see what else i can say

      use something else, it’s a waste of time to try to make games in ruby

  11. how about prototyping? I would like to use ruby to see if the game’s idea work, if the answer is YES then port it to C++

    1. possibly useful for prototyping, just make sure you throw all the ruby code out once done – don’t expect you’ll be able to get it running fast by swapping out parts for native code, ruby scales poorly in this respect

  12. Well, for anyone interested, let me recommend a nice little framework for making 2D games in Ruby.

    It’s fast, it’s clean & elegant. And it’s called Gosu.

    Just check the Ruby tutorial:
    http://code.google.com/p/gosu/wiki/RubyTutorial

    Or if C++ is your thing, check this one out:
    http://code.google.com/p/gosu/wiki/CppTutorial

    Gosu has some samples on integrating it with Chipmunk (a cool physics library for 2D games) and RMagick, check them out here:
    http://www.libgosu.org/

    And from the “What’s next?” you can tell it’s pretty much alive and going strong:

    What’s next?

    Current work focuses on bringing Gosu to the iPhone, making it easy to deploy Gosu games with Ruby 1.9 on Windows and OS X, and making it easier to integrate robust custom OpenGL.

    You can check the Chipmunk page here:
    http://wiki.slembcke.net/main/published/Chipmunk

    I think Ruby can be suitable for making small to medium (even large) 2D games. I’m just starting with Gosu, and the tutorial shows how you can get a small functional game with very little effort. And things can only get better. Remember the old Java days? :)

    1. Æ!!

      Just for information:
      Gosu is a native extension to Ruby, and it is written entirely in C++, using some things of SDL (audio I think). :)

      But anyway, I’m playing with Ruby for games and I don’t have any problems with it. :)
      But the situation is: I’m just writing simple 2d games with Gosu and I don’t want to sell this games or whatever, I just want to have fun! In this case, enjoy game development with Ruby.

      Last words: If you want to develop a bit AAA game please use C/C++.


      PotHix

  13. Well, I would need to develop a big enough game to notice them. In small games it’s not noticeable.

    And, eventually it won’t be a problem later. I’m sure Ruby will get a better GC, since a lot of people are criticizing it’s current one. ;)

  14. Well, my experience is that GC’s are always a performance problem, even when they are well written and configurable. My solution has long been to identify what objects are being GCed and handle their memory management myself.

    For example, I recently wrote a library that implements the PostScript path and font model in OpenGL in Java. This resulted in a ton of edges and path elms being generated and overwhelmed the GC in Java. So I simply wrote a pool manager for each object. The result was that it now runs flat out without hitting the GC at all. The only real downside is that you have to explicitly release objects, but that isn’t a real problem. I almost consider that a benefit (I like to know where my memory is coming and going).

  15. Huh, I haven’t run up against the GC in the couple of 2D games I’ve developed. Well, that’s not entirely true. I used Rubygame for a while, which used SDL for image manipulation, and I found out that arbitrary sprite rotation was creating new in-memory copies of my images for each game object on every frame! This was SDL_gfx’s fault, though, I think. My memory usage would spiral up into the hundreds of megabytes and the GC couldn’t keep up.

    Once I switched to OpenGL (glfw or gosu or chingu), I didn’t have that problem anymore. I could hit 30-60fps with near 100 (simple) on-screen objects powered by the Chipmunk physics library. Probably would’ve been even faster if I’d switched from vertex arrays to vertex buffer objects. The Chipmunk Ruby demos don’t seem to have hitching problems, either. I’m going to have to file Ruby game development under “works for me”.

    What sort of game were you trying to develop, and what parts of it were thrashing massive amounts of memory?

  16. Hi.

    I don’t know how fast is classic Ruby implementation. I am using now MacRuby 0.5 with NSOpenGLView subclass and drawing simple sprites with rectangular textures (not power of two). I just started porting one of my old platform 2d games to Ruby to learn about it more. I didn’t noticed any big problem with FPS.
    I load all textures once. Interfacing with C or Objective C is really great. Except for pointer stuff. Pointers are more readable with straight C helper function or some Objective C wrapper class.

  17. Javascript also has a mark/sweep GC and lots of games are being made with it. Firefox has a bit of a problem with intermittent freezes, but it’s very manageable overall.

  18. If you’re not making a twitch game, does this really matter? In, say, a turn-based RPG, even if you have animated graphics while awaiting input or if GC happens while displaying a spell effect or whatever, is a player likely to even notice the game freezing for a mere tenth of a second?

  19. Have you looked at rubinius? It seems they’re doing a ruby VM with JIT and a generational GC. I’d love to be able to use Ruby as a scripting language for games, myself.

    1. I was also just beginning to explore this. I’m planning on creating a novel game engine (so that I have a grasp of how they work internally), and I’m really considering using rubinius as the scripting language. Glenn, do you think that your list of 3 gripes with ruby are solved in rubinius? The latest release includes a concurrent garbage collector. Here’s a link to a blog post about it: http://rubini.us/blog/

  20. I think that you definitely have to use a third party game maker with Ruby elements, but it also depends on which game. Ruby is brilliant for text adventures and text games, but not for actual applications.

  21. i want to learn game programming in ruby as i want small and easy games to develop big i will do in c++ as i like it and presently learning.

  22. I’m pretty excited about Matz’ new project, mruby – it’s a tiny little embeddable ruby, similar to Lua, and it’s being designed with games in mind. I’m really looking forward to a ruby version of Löve 2D – it seems kind of inevitable? If you search on the iPhone app store you can play a little ruby game masuidrive made with MobiRuby (which plugs mruby in to the iOS Cocoa Touch APIs). It’s a fun little game – not particularly graphically intensive, but in these early stages of development it’s pretty cool to think there’s a tiny ruby in there.

    I think there’s also a lot of potential with tools like RubyMotion. RubyMotion’s garbage collection is by automatic reference counting. Last I checked it still struggles a little with cyclic references, but they were working on some solution to deal with those specifically. Maybe a ruby game system could use automatic reference counting to clear away objects as soon as they’re disused, and fall back on a mark and sweep or other kind of garbage collection to clean up cyclic references every now and then like you said in another thread or between levels, or throttled in little steps to not pause the interpreter for more than a millisecond at a time.

    It’s good to see the core ruby team tackling this issue now. I really like making games in ruby. We also have garbage collection problems in web games with javascript, so browser vendors are quite keen to figure out new schemes of garbage collection to fix that, meaning there are some great minds working on this issue now.

    1. Jenna, RubyMotion recently fixed their GC and cyclic reference issues making it “production ready”. You should check out http://joybox.io. Joybox is a RubyMotion wrapper around Cocos2D, a popular iOS game framework. It provides a lot of the basic game programming building blocks while keeping performance high and allowing you to use Ruby syntax.

  23. Pingback: Java Game Development | Matt Wrench
  24. I am working with Ruby (1.9.3) now, making quite complex platformer using Gosu library and I can say this article is bullshit. My game is about as complex as SMB2 (Doki Doki Panic one, not Lost Levels), completed with dynamically allocated particles, and it maintains solid 60fps. Since I’m using also few gems (mysql one for online highscores and updates).

  25. So, after reading article and all of the comments (such a historical chronicle), now, in the end of 2014 can anyone at least give concrete answer – is current Ruby (2.0+) suitable for game development or not?))
    Of course, I don’t mean any of tops as CoDs or Battlefields, rather some sorts of android or iOS apps.

    1. It’s still not. You should consider LUA or Squirrel as better choices, although even these are still quite slow and you have to be careful with them.

    2. In my opinion: YES! There are a few different games (that I know of, including one very successful game) in the Apple App Store thanks to RubyMotion or mruby (two new implementations of Ruby). Along with some new libraries like Joybox (https://github.com/rubymotion/Joybox). You still can’t use Ruby 2 on iPhone, and likely never will. But RubyMotion is a very good choice. There’s still a long way to go in the realm of Ruby game programming. That’s why I created RubyGameDev.com. I want to centralize the discussion and advance Ruby game programming. Check it out and help get involved!

Leave a Reply