Source

Feeling a little better, today: temperature steadily under 37°C, little to no headaches.

I’ve hacked the last bits of the Add Source dialog of Dictionary, and committed away a bunch of other fixes, including one for a crasher spotted by Paolo Borelli, a bunch of UI fixes by Dennis Cranston and corrections for my bad english by Clytie Siddall. Thanks to all of them: with their help, the next release of Dictionary will suck a lot less.

The Add Source dialog makes me feel a little proud:

gnome-dictionary-source-add-1

Here you can see the dialog when you click the “Add” button; you can set the description of the source and its transport. Choosing a transport will automagically show the preferences bound to that transport:

gnome-dictionary-source-add-2

Obviously, since libgdict supports only the Dictionary Protocol transport, you have only one choice, but expect other transports to be available from the next release of GNOME. The “Advanced Settings” pane will expose the Database and Strategy settings:

gnome-dictionary-source-add-3

Those two combo boxes should automagically query the dictionary source using the GdictContext bound to the transport the user has chosen; unfortunately, they don’t – yet. I hope to get around this issue before the code freeze, but I really don’t know if I’m going to make it in time.

If you want to have a look at how it all works, I’ve prepared a little screencast (courtesy of Istanbul).

[]
[]
[]

Health

As usual, I’ve got a flu at the end of the year.

This really sucks, because due to the slight fever and the cold, I had to cut back hacking time; the re-write of the source dialog in Dictionary has begun but I don’t know if I can finish it up before the next release.

Other things I‘m was working on: new features for the Gnome2::GConf module; fleshing out the GTK2-Perl tutorial; writing the Dictionary manual; updates to the RecentManager/RecentChooser code.

Inkscape

On a IRC conversation, I was told that the Dictionary icon sucked. Thus, after having a look at the Tango Project and their beatiful icons, I fired up Inkscape and worked on another version of the icon:

Dictionary

It still sucks, but now it sucks in 3D!

I’ll file a bug report to remove the old “gdict” icon from the theme, and ask the GNOME artists to do a new version, with more than one size.

Gnome2::GConf 1.021

The “An Address Indicates Where It Is” release.

New release of the Perl bindings for GConf, in time for the incoming GNOME 2.13.4 release.

This version sports a bindings for the Gnome2::GConf::Engine::get_for_addresses method of the Gnome2::GConf::Engine class; this method allows the creation of a Gnome2::GConf::Engine for a list of addresses. Many thanks to Laurent Simonneau for letting me know that the method was missing.

The get_for_addresses method was added in the GConf 2.7 cycle, and if you compile Gnome2::GConf against a newer GConf version, you’ll get it. You should be extra careful with it, and check for its usage, since I can’t test it (as well as all the Engine-related methods) using the automated testing platform we use for all the Perl bindings. But, hey: that’s what beta releases are for, aren’t they?

You can find the tarball of this release on the gtk2-perl project page at SourceForge, and hopefully you’ll find it on CPAN too.

[]
[]
[]
[]

Maybe this Christmas

Only a few minutes into Christmas, and a few hours before the traditional lunch and dinner of this day.

In the last four days I feel like I’ve already eaten more than I usually eat in a month. On Tuesday, me and Marta celebrated her birthday with some friends; on the 22nd – the real date of her birthday – just the two of us went to a japanese restaurant here in Milan, to celebrate by ourselves; on the 23rd we went with my family to a restaurant to celebrate both Marta’s and my father’s birthday. Today, we went to lunch with Marta’s parents. Tomorrow (well, today) we are going to have lunch with Marta’s relatives and dinner with my relatives.

This is our first Christmas together (last year, I had to go around all night with the band, playing christmas carrols from 10pm to 6am), and we are celebrating in our own way: she is finishing the translation of her under-grad thesis in order to send it around and get a PhD abroad and I’m finally committing the last features of the GNOME Dictionary. We’s so two geeks.

Now, Dictionary allows the creation (and the removal) of dictionary sources using a nifty UI (it already worked by dropping the dictionary source .desktop file inside $HOME/.gnome2/gnome-dictionary, but with a UI this becomes a little easier for everyone). The dialog still has rough edges, and I think that the code stands out as a little too messy – especially against the overall cleanliness that I tried to keep in the project. I’ll remove it as soon as I can, and will use a proper class for that dialog; for the time being, I tried on making the magic happen as fast as I could, since we are approaching release time.

The next gnome-utils release is due at January, 2nd; I’ll try and get everything in shape before that day, in order to let people use the new Dictionary application and begin filing bugs. I won’t be around when the next GNOME unstable release will happen; instead, I’ll be in Berlin since January, 3rd till January, 10th, for a week of well due holidays.

[]
[]
[]
[]

Fun with Cairo-perl

cairo-perl clock

Just a little fun with the Cairo Perl bindings. The code is courtesy of the gtkmm tutorial, and can be found here.

Update: since the original website went down, here’s the inlined version of the script:

package Egg::ClockFace;

use warnings;
use strict;

use Glib qw/TRUE FALSE/;
use Gtk2;
use Cairo;
use Math::Trig;

use Glib::Object::Subclass
	Gtk2::DrawingArea::,
	signals => {
		expose_event => \&expose,
	};

sub min { return ($_[0] < $_[1] ? $_[0] : $_[1]); }

sub draw
{
	my $self = shift;
	my $cr = $self->{cr};

	return FALSE unless $cr;

	my $width  = $self->allocation->width;
	my $height = $self->allocation->height;
	
	$cr->scale($width, $height);
	$cr->translate(0.5, 0.5);
	$cr->set_line_width($self->{line_width});
	
	$cr->save;
	$cr->set_source_rgba (0.337, 0.612, 0.117, 0.9);
	$cr->paint;
	$cr->restore;
	$cr->arc (0, 0, $self->{radius}, 0, 2 * Math::Trig::pi);
	$cr->save;
	$cr->set_source_rgba (1.0, 1.0, 1.0, 0.8);
	$cr->fill_preserve;
	$cr->restore;
	$cr->stroke_preserve;
	$cr->clip;

	for (1 .. 12) {
		my $inset = 0.05;

		$cr->save;
		$cr->set_line_cap('round');

		if ($_ % 3 != 0) {
			$inset *= 0.8;
			$cr->set_line_width(0.03);
		}

		$cr->move_to(($self->{radius} - $inset) * cos ($_ * Math::Trig::pi / 6),
		             ($self->{radius} - $inset) * sin ($_ * Math::Trig::pi / 6));
		$cr->line_to($self->{radius} * cos ($_ * Math::Trig::pi / 6),
		             $self->{radius} * sin ($_ * Math::Trig::pi / 6));

		$cr->stroke;
		$cr->restore;
	}

	my @time    = localtime;
	my $hours   = $time[2] * Math::Trig::pi / 6;
	my $minutes = $time[1] * Math::Trig::pi / 30;
	my $seconds = $time[0] * Math::Trig::pi / 30;
	
	$cr->save;
	$cr->set_line_cap('round');
	
	# seconds
	$cr->save;
	$cr->set_line_width($self->{line_width} / 3);
	$cr->set_source_rgba(1.0, 0.0, 0.0, 0.8);
	$cr->move_to(0, 0);
	$cr->line_to(     sin($seconds) * ($self->{radius} * .9),
	             -1 * cos($seconds) * ($self->{radius} * .9));
	$cr->stroke;
	$cr->restore;
	
	# minutes;
	$cr->set_source_rgba(0.7, 0.7, 0.7, 0.8);
	$cr->move_to(0, 0);
	$cr->line_to(     sin($minutes + $seconds / 60) * ($self->{radius} * 0.8),
	             -1 * cos($minutes + $seconds / 60) * ($self->{radius} * 0.8));
	$cr->stroke;
	
	# hours
	$cr->set_source_rgba(0.117, 0.337, 0.612, 0.9);
	$cr->move_to(0, 0);
	$cr->line_to(     sin($hours + $minutes / 12.0) * ($self->{radius} * 0.5),
	             -1 * cos($hours + $minutes / 12.0) * ($self->{radius} * 0.5));
	$cr->stroke;
	
	$cr->restore;
	
	# dot
	$cr->arc(0, 0,  $self->{line_width} / 3.0, 0, 2 * Math::Trig::pi);
	$cr->fill;

	return TRUE;
}

sub expose
{
	my ($self, $event) = @_;

	my $cr = Gtk2::Gdk::Cairo::Context->create($self->window);
	$cr->rectangle ($event->area->x,
			$event->area->y,
			$event->area->width,
			$event->area->height);
	$cr->clip;
	$self->{cr} = $cr;
	
	$self->draw;

	$self->{timeout} = Glib::Timeout->add(1000, sub {
			my $self = shift;
			
			my $alloc = $self->allocation;
			my $rect = Gtk2::Gdk::Rectangle->new(0, 0, $alloc->width, $alloc->height);
			$self->window->invalidate_rect($rect, FALSE);

			return TRUE;
		}, $self) unless $self->{timeout};

	return FALSE;
}

sub INIT_INSTANCE
{
	my $self = shift;

	$self->{line_width} = 0.05;
	$self->{radius}     = 0.42;
}

sub FINALIZE_INSTANCE
{
	my $self = shift;

	Glib::Source->remove($self->{timeout}) if $self->{timeout};
}

1;

package main;

use Gtk2 '-init';

my $window = Gtk2::Window->new('toplevel');
my $clock = Egg::ClockFace->new;

$window->add($clock);
$window->signal_connect(destroy => sub { Gtk2->main_quit; });

$window->show_all;

Gtk2->main;

0;

Sadism, Bestiality and Necrophily

Or “Flogging a Dead Horse for Fun and Profit”

Spatial Nautilus. Again.

Both Ubuntu Dapper and Novell Linux Desktop will ship with browser mode by default for Nautilus – now that browser mode got much love, enough to be usable.

While both Ubuntu and Novell, as GNOME packagers, are entitled to change as much as they wish to the applications’ GConf schemas, I think that upstream GNOME should continue to ship with the spatial Nautilus; changing now would confuse new users just as much as did when we shipped with spatial Nautilus – with the aggravation of swinging back and forth.

GNOME has made a decision of treating each “first class object” as a window itself: documents, folders, people. With the approaching of Topaz this will become even more true. The browser paradigm breaks this.

So, it’s fine if Ubuntu, Novell, Red Hat, and ${WHATEVER_DISTRO} ships with its own version of GNOME – they already rebrand it; but upstream GNOME is another beast entirely.

Icon

I’ve just committed my development trunk of the BookmarkFile and RecentManager objects. The former now supports custom icons for every bookmark inside the file, using the icon element; the latter, finally, supports group names for every recently used item.

I’m writing a small page for documenting how to port an application from the old EggRecent code to the new RecentManager, and also how to use the new RecentChooser widgets.

On a related note, I’ve been contacted by other developers interested about the RecentManager/RecentChooser code; expect more news soon.