Re: Performance issues of GDK deprecation in favour of Cairo
hi, On 17.08.2010 12:01, James Morris wrote: Hi, I see that some GDK drawing functions and graphics contexts have been deprecated in favour of using Cairo. Yesterday I spent a few hours *removing* Cairo code from my fledgling GTK application and replacing it with gdk_draw_rectangle, gdk_gc_set_rgb_fg_color, and gdk_gc_set_function. I did this for performance reasons[1] I am wondering if my approach to drawing is wrong however and if a better approach might yield less CPU usage? It begins with a 33ms timeout. The timeout callback calls gtk_widget_queue_draw on the window and the drawing area. Would it be possible to isolate this into a standalone demo. Or could you point us to the actual code? Stefan (Imagine rectangles appearing each time a note is played in a piece of music and disappearing when that note ends.) In the expose event callback a linked-list of rectangles is maintained. Rectangles are added to the list and removed from the list as notes start and end (The application is an experimental MIDI sequencer/arpeggiator operating in real time). Each and every time the expose event callback is called (every 33ms) the background and the entire list of rectangles is drawn as well as various maintenance functions performed on the list. The documentation of gdk_cairo_create seems to suggest this is the only way of doing it when it says: Note that due to double-buffering, Cairo contexts created in a GTK+ expose event handler cannot be cached and reused between different expose events. Is it possible to do this any other way? Cheers, James. [1]My machine is a 64bit 3.0ghz dual core desktop. Using GDK for drawing, the CPU usage is at worst 5% on both cores. Using Cairo on the other hand, the CPU usage can reach as much as 20% on both cores. The project is here:http://github.com/jwm-art-net/BoxySeq Cairo routines is here: http://github.com/jwm-art-net/BoxySeq/tree/97f6d674a2a182a143ef82b03bde11689fedcf18 GDK routines is here: http://github.com/jwm-art-net/BoxySeq/tree/29f412b41b2371ec136aa86da50d858f5892bfa0 ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list
Re: Performance issues of GDK deprecation in favour of Cairo
On 18 August 2010 15:57, Stefan Kost enso...@hora-obscura.de wrote: hi, On 17.08.2010 12:01, James Morris wrote: Hi, I see that some GDK drawing functions and graphics contexts have been deprecated in favour of using Cairo. Yesterday I spent a few hours *removing* Cairo code from my fledgling GTK application and replacing it with gdk_draw_rectangle, gdk_gc_set_rgb_fg_color, and gdk_gc_set_function. I did this for performance reasons[1] I am wondering if my approach to drawing is wrong however and if a better approach might yield less CPU usage? It begins with a 33ms timeout. The timeout callback calls gtk_widget_queue_draw on the window and the drawing area. Would it be possible to isolate this into a standalone demo. Or could you point us to the actual code? Hi Stefan, The actual code is here: http://github.com/jwm-art-net/BoxySeq/blob/97f6d674a2a182a143ef82b03bde11689fedcf18/gui_grid.c I'm probably not going to work on it for a while. Probably going to make the back-end into a library first and then investigate the possibility of using FLTK. Cheers, James. Stefan (Imagine rectangles appearing each time a note is played in a piece of music and disappearing when that note ends.) In the expose event callback a linked-list of rectangles is maintained. Rectangles are added to the list and removed from the list as notes start and end (The application is an experimental MIDI sequencer/arpeggiator operating in real time). Each and every time the expose event callback is called (every 33ms) the background and the entire list of rectangles is drawn as well as various maintenance functions performed on the list. The documentation of gdk_cairo_create seems to suggest this is the only way of doing it when it says: Note that due to double-buffering, Cairo contexts created in a GTK+ expose event handler cannot be cached and reused between different expose events. Is it possible to do this any other way? Cheers, James. [1]My machine is a 64bit 3.0ghz dual core desktop. Using GDK for drawing, the CPU usage is at worst 5% on both cores. Using Cairo on the other hand, the CPU usage can reach as much as 20% on both cores. The project is here: http://github.com/jwm-art-net/BoxySeq Cairo routines is here: http://github.com/jwm-art-net/BoxySeq/tree/97f6d674a2a182a143ef82b03bde11689fedcf18 GDK routines is here: http://github.com/jwm-art-net/BoxySeq/tree/29f412b41b2371ec136aa86da50d858f5892bfa0 ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list
Re: Performance issues of GDK deprecation in favour of Cairo
On Tue, 17 Aug 2010 10:01:43 +0100 James Morris ja...@jwm-art.net wrote: I see that some GDK drawing functions and graphics contexts have been deprecated in favour of using Cairo. Yesterday I spent a few hours *removing* Cairo code from my fledgling GTK application and replacing it with gdk_draw_rectangle, gdk_gc_set_rgb_fg_color, and gdk_gc_set_function. I did this for performance reasons[1] I am wondering if my approach to drawing is wrong however and if a better approach might yield less CPU usage? It begins with a 33ms timeout. The timeout callback calls gtk_widget_queue_draw on the window and the drawing area. (Imagine rectangles appearing each time a note is played in a piece of music and disappearing when that note ends.) In the expose event callback a linked-list of rectangles is maintained. Rectangles are added to the list and removed from the list as notes start and end (The application is an experimental MIDI sequencer/arpeggiator operating in real time). Each and every time the expose event callback is called (every 33ms) the background and the entire list of rectangles is drawn as well as various maintenance functions performed on the list. The documentation of gdk_cairo_create seems to suggest this is the only way of doing it when it says: Note that due to double-buffering, Cairo contexts created in a GTK+ expose event handler cannot be cached and reused between different expose events. Is it possible to do this any other way? Cheers, James. Can you avoid redrawing the entire list of rectangles on each expose event? When drawing in an expose event callback, you would normally clip to the rectangle representing the dirty area (the area enclosed by event-area.x, event-area.y, event-area.width, event-area.height). You could then only call gdk_window_invalidate_rect() or gdk_window_invalidate_region() on the particular parts of the particular GdkWindow object(s) which need redrawing. In your particular case, unless the notes move, you could just invalidate only the areas representing the notes which have just begun or ended. Depending on your program logic you may be able to dispense with the timeout entirely: your active code which handles note changes could call gdk_window_invalidate_* on a selective basis as necessary. Chris ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list
Re: Performance issues of GDK deprecation in favour of Cairo
On Tue, 17 Aug 2010 12:26:04 +0100 James Morris ja...@jwm-art.net wrote: On 17 August 2010 11:23, Chris Vine ch...@cvine.freeserve.co.uk wrote: Can you avoid redrawing the entire list of rectangles on each expose event? Yes this is what I'm hoping. Though I've been a bit mixed up with how Cairo and GTK work together. When drawing in an expose event callback, you would normally clip to the rectangle representing the dirty area (the area enclosed by event-area.x, event-area.y, event-area.width, event-area.height). You could then only call gdk_window_invalidate_rect() or gdk_window_invalidate_region() on the particular parts of the particular GdkWindow object(s) which need redrawing. Right. I think I'm starting to see where I went wrong. Though say it is a real expose event (ie not due to the timeout) which has erased some rectangles. Do I need to redraw the dirty area with calls to cairo, that is, I will still need to maintain a list of rectangles that currently exist? Yes. You can just clip (mask) the area to be drawn to with something like: cairo_rectangle (cr, event-area.x, event-area.y, event-area.width, event-area.height); cairo_clip (cr); After that you can draw to the cairo surface as normal but areas outside the clipped area will be masked out and ignored. I imagine it would still be more efficient even so to ignore note rectangles which you know have not been changed if you can (that would I imagine depend on how complex they are) but I don't think there is any easy means of determining, in the callback, what has generated the expose event. In other words, I don't think you can assume that any particular expose event is not one generated artificially rather than one called up by the window manager. So you may need to examine the co-ordinates of any one note rectangle with those of the dirty area of the event if you wanted to make the implementation more efficient still. What about drawing via cairo to a pixbuf and using that for the (real) expose events? You can convert pixels in pixbuf format to cairo image format, but I don't see why that would be advantageous in your case. They use different formats (RGB/RGBA, alpha not pre-multipled, for pixbuf, and BGR/BGRA, with pre-multiplied alpha, for image surfaces). You would also need to allow for endianness in converting, because image surfaces are in 32-bit native endian format. Draw to the surface directly, if you can, because it saves conversion, and futzing around with endianness. That is why gdk provides you with a cairo context, incorporating a destination surface, for any GdkDrawable. I am not an expert on cairo drawing functions. Others in the list probably know considerably more. I just know what I need to know for the things I write. Chris ___ gtk-app-devel-list mailing list gtk-app-devel-list@gnome.org http://mail.gnome.org/mailman/listinfo/gtk-app-devel-list