Need some assistance with animation again… When I run the drawing
code in a separate thread, it’s slow as heck. I think it may be
because the drawing thread isn’t getting enough time from the thread
scheduler.
I was able to reproduce the problem in my little sample program simply
by increasing the number of lines it draws per update. I’m lucky to
get one frame every three seconds with this. If I “thread.join” or
“thread.priority += 1” the speed greatly increases, but then the GUI
becomes unresponsive. (Similar problems with threads have been
discussed previously on the wxRuby mailing list.)
require ‘rubygems’
require ‘wx’
class MyApp < Wx::App
def on_init
#Animate every 33 milliseconds.
t = Wx::Timer.new(self, 55)
evt_timer(55) { Thread.pass }
t.start(33)
#Containing frame.
frame = Wx::Frame.new(nil, :size => [300, 300])
frame.show
#Offscreen drawing buffer.
buffer = Wx::Bitmap.new(300, 300)
#Displays drawing.
window = Wx::Window.new(frame, :size => [300, 300])
#Animate.
thread = Thread.new do
300.times do |i|
#Clear screen.
buffer.draw do |surface|
surface.pen = Wx::Pen.new(Wx::Colour.new(0, 0, 0), 0)
surface.brush = Wx::BLACK_BRUSH
surface.draw_rectangle(0, 0, 300, 300)
end
#Draw lines.
30.times do |j|
x = i + j
buffer.draw do |surface|
surface.pen = Wx::Pen.new(
Wx::Colour.new(128, 255, 128),
3
)
surface.pen.cap = Wx::CAP_ROUND
surface.draw_line(x, 0, x+100, 100)
end
end
#Update screen.
update_window(window, buffer)
end
end
end
def update_window(window, buffer)
window.paint do |dc|
#Copy the buffer to the viewable window.
dc.draw_bitmap(buffer, 0, 0, false)
end
end
end
app = MyApp.new
app.main_loop
I ran it through ruby-prof… Am I right in thinking these results
mean the drawing thread is getting a fraction of the time that the
main loop is?
Thread ID: 59174940
Total: 0.01
%self total self wait child calls name
1250.00 30.45 0.13 2.02 28.31 11 Integer#times-1
160.00 2.86 0.02 2.84 0.00 3391
Wxruby2::Colour#initialize
160.00 0.02 0.02 0.00 0.00 3378
Wxruby2::DC#draw_line
0.00 0.05 0.00 0.05 0.00 11
Wxruby2::Window#paint
…
Thread ID: 42518340
Total: 32.594
%self total self wait child calls name
96.59 31.72 31.48 0.00 0.24 1
Wxruby2::App#main_loop
2.01 0.77 0.66 0.00 0.11 42
Kernel#gem_original_require-1
0.19 0.06 0.06 0.00 0.00 28 Class::Dir#[]
…
My actual program (a game) is going to be doing even more drawing
operations than this, so I need to boost the speed wherever I can.
Any advice would be most appreciated!
-Jay McGavren
http://jay.mcgavren.com/zyps