2006-04-05
Ruby/SDL の 2D 描画速度実験
Ruby/SDL や Miyako のサイトを見ると速度が遅いとある。実際どんなものなのか実験してみた。
PCのスペックは次の通り。詳しくないがゲームの実行にはいまいちな環境だと思う。
- Windows XP SP2
- Pentium(R) 4 CPU 2.80GHz
- NVIDIA GeForce4 MX 4000
- 使用した RubyとRuby/SDL は Win32's binary(ver 1.0.0) and ruby 1.8.4 interpreter package
SDL.blitSurface でのイメージ描画
256x256 のスクリーンに対して 16x16 のイメージを秒間 60 フレームで何個表示できるかという実験。結論から言うと手元のマシンでおよそ5000個。下記ののスクリプトの実行時間が、
- 1.031 秒 …… スクリーンを 256x256 , イメージを 16x16
であった。
同じような処理を某ゲーム機(プレ○ステー○ョン)で行うと 1/60 秒で 2000 強スプライトが表示可能であったと記憶しているから、 Ruby/SDL のこの性能なら基礎的な 2D 描画能力は実用に十分な速度と言える。
スクリーンのサイズとイメージのサイズを変えると以下の通り。
- 1.328 秒 …… スクリーンを 512x512 , イメージを 16x16
- 1.532 秒 …… スクリーンを 256x256 , イメージを 32x32
- 1.844 秒 …… スクリーンを 512x512 , イメージを 32x32
require 'sdl' SCREEN_W = 256 SCREEN_H = 256 SDL.init( SDL::INIT_VIDEO ) screen = SDL.setVideoMode( SCREEN_W, SCREEN_H, 16, SDL::SWSURFACE ) image = SDL::Surface.load( 'icon16.bmp' ) image.setColorKey( SDL::SRCCOLORKEY, image.getPixel(0,0) ) cx, cy = image.w / 2, image.h / 2 image = image.displayFormat t = Time.now 60.times do while event = SDL::Event2.poll case event when SDL::Event2::Quit, SDL::Event2::KeyDown exit end end screen.fillRect( 0, 0, SCREEN_W, SCREEN_H, [ 0, 0, 128 ] ) 5000.times do image_x = rand(SCREEN_W) image_y = rand(SCREEN_H) SDL.blitSurface(image, 0, 0, 0, 0, screen, image_x, image_y) end screen.updateRect( 0, 0, 0, 0 ) end p Time.now - t
※手元の環境では SDL::HWSURFACE に変えても速度差はでなかった。
SDL.transform_blit は 10 倍以上遅い
transform_blit を使ってイメージを回転させて表示。
5000.times do image_x = rand(SCREEN_W) image_y = rand(SCREEN_H) angle = rand(360) SDL.transform_blit(image, screen, angle, 1, 1, cx, cy, image_x, image_y, 0) end
実行にかかった時間は 14.844 秒。
Ruby はどれくらい遅いのか
ループ部分から SDL の処理を取り除いて速度を計測。ループ部分を次のようにした。
60.times do 5000.times do image_x = rand(SCREEN_W) image_y = rand(SCREEN_H) end end
結果は 0.484 秒。これは驚くほど遅い。さらに次のようにすると、
60.times do 5000.times do image_x = rand(SCREEN_W) - cx image_y = rand(SCREEN_H) - cy end end
0.625 秒という結果に。 5000 個ぶんの座標計算とはいえこんなにかかるのか。ふうむ。
結論としては速度に注意を払いながら作らないと確かにすぐに非現実的な速度になってしまいそうだ。まあそれはコンシュマーゲーム機でも同じなんだけど。