Is i magen
Efficient scrolling in X11
Lately, I've been trying to make scrolling as efficient as possible. On the surface, it is a simple problem, the algorithm is like this:
So, if you scroll a surface of size 100x100 20 steps to the right and 20 steps down the rectangles become:
xscroll = 20 yscroll = 20 top = (0, 0, 100, 20) left = (0, 0, 20, 100) bottom = (0, 120, 100, -20) right = (120, 0, -20, 100)
bottom and right whose area is negative becomes discarded and you are left with two rectangles totalling 4000 pixels (100 * 20 + 100 * 20) to redraw which is not so bad.
The problem is that this algorithm is freakishly hard to realize on X11 without theComposite extension. X11 doesn't store your surface, so how are you going to redraw it? You could store it yourself, in a GdkPixbuf for example. However, that would mean that the data is stored client side and you'll run into slowdowns when transferring it to the X11 server.
... Client-server is great for some things, but definitely not for computer graphics.
GdkPixbufs are drawn with gdk_draw_pixbuf() which should (or could) be a fast operation because it uses XShmPutImage(), but it is not. GdkPixbuf has a different format from the one that X11 want's so you run into a slowdown caused by the format mismatch.
Next attempt, use a GdkPixmap as the cache. surface.draw(surface, xscroll, yscroll) becomes one fast call to gdk_draw_drawable(). But it still isn't fast enough because pixmaps aren't easy to work with. There is no gdk_pixbuf_scale() equivalent for drawables so we still have to use a pixbuf to store the result of the scale operation. That pixbuf then has to be blitted to our pixmap cache which is then blitted, for real, to the XWindow we are drawing on. In effect, we are using triple buffering and redraws becomes to slow.
Third attempt, use the actual drawable we are drawing on as the cache. It would work except that it totally breaks down when the window is minimized, then your cache is gone.
GtkImageView uses a combination of the first and third method. It special cases scrolling operations and uses the third method to redraw them. By setting exposures to true, it detects when occluded areas becomes visible and then redraws them using the first method. That is far from ideal but is more or less the best thing you can do without composite.
Halfway through GUADEC
Britain as a country is very similar to Sweden, it almost feels like being home except that the language is different. It's funny how many and varied warning signs they have. There are warnings everywhere, for example "Caution! This door may close at any time!" But the warnings at the zebra crossings that tells you to look left or right are very useful. It is completely weird seeing the traffic going in the wrong direction all the time.
The food is cheap but quite bad. Chips are served with about every meal. Best food eaten so far was from a stand at the coach station that sold "Mediterranean Rolls" they tasted really great. Oh, and you don't have to pay tips! That's very much a plus. At least I don't think so, the waitresses and cashiers didn't seem pissed off when we didn't.
The best talk so far was the lightning talk with Michael Meeks and Federico Mena-Quintero. If a memory access is the distance from your nose to your brain, then a disk seek is all the way to the Middle East. Fun stuff. Havoc Pennington and Bryan Clark held their keynote about, unsurprisingly, the Online Desktop. They definitely have the right ideas, but I'm not attracted by their purple "mugshot" client.
Some developer from Beagle held a talk about metadata in which he said that Tracker was unfocused. It will be "interesting" to hear Jamie McCrackens retort in tomorrows talk. :-P Hurray for Open Source Soap Opera.
Alex Gravelys keynote was boring. If you have only one hour, plan for 30 minutes. It seemed like he would have needed at least three hours to communicate everything he wanted to say.
Some poor Eastern European developer got his lightning talk ruined by computer problems. It was fun, but sad that people where laughing seemingly at him. I'll definitely try out his git GUI front end anyway.
Carl Worth and Behdad Esfahbod held a very interesting talk about how the Cairo community has evolved. They are both very good speakers and the topic was interesting. I wanted to ask them how Cairo could be slower than the older xft toolkit. I mean, when you write new code, you usually try to make it faster than the old code you are replacing right? Unfortunately, I didn't have the guts.
Before that, there was a talk about building a modern multi-user desktop. The main thing I took home from that talk was that ConsoleKit, PolicyKit and HAL are boring.
Ari Jaaksi held a keynote about Nokia's involvement in open source. I don't like it so much I think. It's not like I can flash the firmware of their N800 and compile my own OS to run on it, is there? Besides, the device (which has been on sale for several months) had stability problems. Yes I'm biased because I work for a competing company. But retailing a product that is that easy to crash is just bad.
I only saw the end of the libgnomedb talk with Murray Cumming. It was quite interesting. But I don't understand why he didn't understand what I meant when I asked him which libraries libgnomedb was related to. Not many ideas are new in the DB field, even if implementations can contain innovations.
And the disaster of the week has been that my laptop broke. :( I thought I handled it very carefully, but there seems to be some seriously problem with the harddisk. Maybe it couldn't handle the British electricity current or something.
GUADEC it is!
No GUADEC for me
Quote of the Week!
Management and IT there might well be clueless but I am new there and don't want to say that yet.That is the smartest thing I have read all week. :)
Why I will never use Epiphany
Grabbing URL:s with style
urlgrabber is a fairly nice Python package for grabbing URL:s. The documentation is kind of sparse, but reading the source is easy enough.
Here is a simple example:
from urlgrabber.grabber import URLGrabber from urlgrabber.progress import TextMeter grabber = URLGrabber(progress_obj = TextMeter()) grabber.urlgrab('http://www.python.org/ftp/python/2.5.1/Python-2.5.1.tar.bz2')
Snåla SAS
Ibland skickar jag in insändare till tidningar. De blir aldrig publicerade, men det är kul att försöka. Den här handlade om SAS strejken.
Alla som har flugit vet hur stressande det kan vara att sitta på ett kvalmigt fullpackat försenat charterplan. Det är inget mot att ha det som sin ständiga arbetsplats. Kabinpersonalen förtjänar pauser och lunchpauser och att SAS nekar dem detta är dåligt. SAS gick med över en miljard i vinst förra året så de har råd att ge sina anställda drägliga anställningsvillkor. Att de har ratat kabinpersonalens bud är inget annat än ren och skär snålhet.
Tools for GtkImageView
I have decided that I want to extend the GtkImageView widget to make it extensible. Right now, it handles showing images that you can zoom in on and drag around. It will be extended so that you can do the following things:
- Drag a selection on the widget. Very similar to how gThumbs Image->Crop dialog works.
- Various kinds of drawing operations.
I thought about implementing this as "tools":
+------------+
| | 1 1 +-------------+
|GtkImageView| ------> |GtkIImageTool|
| | +-------------+
+------------+ |_____________________
/ |
+-------------------+ +--------------------+
|GtkImageToolDragger| |GtkImageToolSelector|
+-------------------+ +--------------------+
In this diagram, GtkImageView has a reference to a GtkIImageTool which is an interface that abstracts out certain behaviour of GtkImageView. GtkImageToolDragger and GtkImageToolSelector are two concrete implementations of the GtkIImageTool interface. When GtkImageView references a GtkImageToolDragger, it behaves like normal. You have a hand cursor and can drag the image. When GtkImageView references a GtkImageToolSelector, it instead displays a selection cursor and you can make a rectangular selection on the image.
Using this arrangement, it is now possible to dynamically alter the behaviour of GtkImageView.
It should be possible to achieve this, but the interface that GtkIImageTool will specify, might become to fat.
Tired of DocBook
Spent some time trying to find out how to write definition lists in DocBook. DocBook is the markup language used by gtk-doc and consequently the tool I am using for writing documentation for GtkImageView.
... And I am very, VERY sick of it. It turns out it was fairly simple (heh), all you have to do to create a list of directories and paragraphs is this:
The result is almost exactly what you could have accomplised using this HTML:
And of course, even less markup is needed if you use reStructuredText.
My search for a decent documentation writing system continues.
It is official!
It is official! GtkImageView is now released!
Here is the whole release announcement reprinted in full, just for fun:
I'm pleased to finally announce GtkImageView 1.0.0:
Description
GtkImageView is a simple image viewer widget for GTK. Similar to the image viewer panes in gThumb or Eye of Gnome. It makes writing image viewing and editing applications easy. Among its features are:
- Mouse and keyboard zooming.
- Scrolling and dragging.
- Adjustable interpolation.
- Fullscreen mode.
Download
Check it out from Subversion:
svn co http://publicsvn.bjourne.webfactional.com/gtkimageview
Or download the latest release tarball:
http://trac.bjourne.webfactional.com/attachment/wiki/WikiStart/gtkimageview-1.0.0.tar.gz
API documentation can be found by browsing to the ./docs/reference/html/index.html file.
Project website: http://trac.bjourne.webfactiona.com
Examples
Here is the canonical example for using the widget:
#include <gtkimageview/gtkimagescrollwin.h>
#include <gtkimageview/gtkimageview.h>
...
GtkWidget *view = gtk_image_view_new ();
GtkWidget *scroll = gtk_image_scroll_win_new (GTK_IMAGE_VIEW (view));
/* Where "box" is a GtkBox already part of your layout. */
gtk_box_pack_start (GTK_BOX (box), scroll, TRUE, TRUE, 0);
GdkPixbuf *pixbuf = gdk_pixbuf_new_from_file ("someimage.png", NULL);
gtk_image_view_set_pixbuf (GTK_IMAGE_VIEW (view), pixbuf);
Future
- Python bindings.
- Perl bindings.
- Gtk# bindings.
gtk-doc problems
My first reaction was that gtk-doc really sucks. For example, it requires you to write docstrings like this:
You have to repeat my_function_name in the comment even though it should be extremely simple for the documentation generator to find out the name of the function the docstring is documenting.
There is apparently no way to group multiple source code definitions to one docstring. You can't write something like this and expect it to work:
And despite writing docstrings using the weird format that gtk-doc imposes, you will still have to write separate API documentation using SGML. Yay! For each c-file gtk-doc documents, it generates a file called /tmpl/someclass.sgml which contains place holders for each symbol. Here is an except of one such file:
Because gtk-doc likes to write to this file, you will have a hard time keeping it version controlled and you will have to periodically merge it with the real source code. gtk-doc therefore negates the main advantage of using a documentation generator tool which is to keep the documentation close to the source code.
I am sorry for all the complaining. gtk-doc is a decent tool and using it is better than writing all documentation is Latex, for example. But gtk-doc is not the only API documentation tool available. There is doxygen, JavaDoc, Epydoc and a whole host of other documentation generators. gtk-doc just manages to be worse then all of them.