Nerd wannabe

lazy weblog

Archive for the ‘gtkaml’ Category

XAML vs MXML (part 1)

with 2 comments

Lately I have accepted a job involving WPF (Windows Presentation Foundation) and all the .net 3.5 nastiness.

I have a little previous exposure on Flex (MXML) and that only kick-started me to write a(nother) markup language for Gtk+.

It is only now that I came to reckon what XAML is about. And thought you might want to know how it stacks agains Flex, too.

Before going to code and charts, let me tell you that Microsoft’s offer is far more spreaded that Adobe’s:

Abobe Flex was just the flash plugin for “stage”-oriented advertising and online games, which later got widgets (the Flex SDK) then strong-typeness (ActionScript 3), and now tries to conquer the desktop world with Adobe AIR, which is a standalone runtime that gives access to local files.
The flash player is now a full-blown virtual machine, with a garbage collected, strong-typed language, with access to all the graphic features flash already has and since version 10, access to 3D features.

Microsoft has a very long history of dominating the desktop (Win32 hacks were common-knowledge for 15+ years), then switched to a “bytecode”-like technology which was running against the same Win32 platform widgets (.NET Windows.Forms).
Much more later they introduced this XAML markup (plus a widget toolkit refactoring – WPF) and implemented something for Firefox, something less for MacOS, helped some more the Novell Linux guys implementing even less on Linux (Moonlight)… and are generally heading towards RIA.
So now Microsoft offers full-blown desktop applications only for Windows, XBAP (WPF browser applications) for Firefox and IE but only on Windows, Silverlight applications on Windows and MacOS, and Moonlight on Linux (see above).
What is interesting is that if you compare the Silverlight 2 browser plugin vs a WPF application shows that the former cannot do networking using binary protocols, and cannot do accelerated 3D, both of which Flash/Flex do. So there should be no ‘browser plugin is limited’ mindset, but there is.

That is, the history of desktop-to-web transition is reversed for the two players (MS and Adobe).

(The good part from this race is that the old .res/.rc are ditched now, the macros from MFC are less and less used, and spaghetti code generated by Visual Studio.NET xxxx interface designers is now history (I am looking at you, Java!). Long live Application Markup!

Markup Comparison

So basically this is a comparison of the ‘markups‘ named used in Silverlight and WPF (XAML) and the one used in Flex and AIR (MXML), but also of a couple of other features of the platforms.

But how is this markup made? is it something like HTML DOM + JS? something like Mozilla’s XUL? Something like OpenLaszlo?

No. This is where MXML and XAML are alike: they are unlike any of the above.

What they do have in common is:

  • tags are (usually) classes
  • attributes are properties (fields with automatic getter and setter method call)
  • the root tag of the XML is the base class you’re inheriting
  • all other tags are instances that are added up to the parent container
  • both use xml namespaces in a similar way (although the URL schemes are different), to specify that the name of a class belongs to another AS3 package or C# namespace(s)

For example, this is the minimum source code for an application in Flex:
App.mxml

<mx:Application
  xmlns:mx="http://www.macromedia.com/2003/mxml"
  name="App"/>

And in WPF:
App.xaml

<Application
  x:Class="MyNamespace.App"
  xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
  xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" />

One of the first differences is that XAML seems to need 2 xml prefixes: one for the Application and other tags, and a special one for meta-attributes specific to xaml. That, is ‘x:Class‘, is not an attribute of the Application class, but a meta-attribute valid only on the first tag.
The class name includes the namespace definition.

Flex, apparently, simply uses name, an existing attribute which is present on all UI components, to give the class name. But if you’re not stopping at generating classes with Flex Builder but code your own by hand, you’ll notice that in fact the file name is the name of the class, and the ‘name’ attribute is just run-time information (i.e. exactly the value of the ‘name’ property). Even more, the whole subdirectories path represents the package in which the class resides.

Including actual code

So far so good, you can define your application or another object like this. But how does one include ActionScript code (for MXML) or .NET code (for XAML) to.. actually accomplish something?

In MXML’s case, there is a ‘special’ tag in the mx namespace: <mx:Script> which accepts either direct text content (usually written as a CDATA section) or you can use <mx:Script source=… to specify a file from where the code should be included at compile time. Notice that Script is not actually an object that is added to the UI of the application, but a specially-handled tag.

<mx:Application
  xmlns:mx="http://www.macromedia.com/2003/mxml"
  name="App">
  <mx:Script>
    <!&#91;CDATA&#91;
      //code here
    &#93;&#93;>
  </mx:Script>
</mx:Application>

In XAML, the preffered way is code behind. You have your App.xaml file automatically associated with App.xaml.cs if the following apply: the .cs file (or .vb) defines the same class in the same namespace, the class in the .cs file is ‘partial’, and both are included in the files to be compiled list of Visual Studio. That is, automagically:)

public partial class App : Application
{
//code here
}

XAML’s x: prefix also includes an <x:Code> tag (notice that it’s in the XAML-specific namespace) but its use is highly discouraged by Microsoft.

--

This post was only a warm-up (for you, for me) to give the general impression of how the two technologies are similar a bit of their differences.

The part 2 will continue to explore all the features of these two Application Markups.

Written by vlad

December 6, 2008 at 11:21 pm

Posted in gtkaml

Pointless update

with 5 comments

So.. I needed to re-cap a never-learned science, the computer one.

You see, when I joined a computer science university, I had no “official” CS background (math high-school, yadda-yadda).
I did had a computer at home in highschool – which allowed me to poke around with some ‘exotic’ VGA poking.. but never got into backtracking or other stuff my friends from CS highschool got.

Then, just when the 3rd year in university got to those subjects, I was _so_ employed I haven’t had the time to.. you know.. think before the exams.

So I bought some books now, that I am old enough to afford myself shopping from amazon (heh):
– the algorithm design manual – which I favoured over ‘CLR’ because everybody said CLR was ‘sooo basic’. Now I have to struggle with my english skills because the ADM is explained in plain english rather than scientific way
– the dragon book – yeah..
– learn to tango with D – the only D book available today (I love reading paper, you know..)
– erlang – the only book to – influenced by my reddit fellows

Soo.. I am planning re-writing gtkaml, the markup for UI that I ripped from my XAML/MXML/XUL experience.

But is it worth it?

I want to:
– stop using libxml2, switch to GMarkup, to minimize dependencies. But GMarkup doesn’t even discern CDATA from regular text (I need that for code in a gtkaml class)
– cleanly separate parsing from semantic analisys (lexing is XML).
– generate native Vala AST instead of text (I currently feed a generated source to the Vala parser)

Again.. why would I do it? It’s my first open-source attempt, I tried to announce it on vala list, I had as little as.. one user, then a couple of _month_ later tried to announce it on gnome-announce.

It seems like nobody’s getting where I’m going or doesn’t want to. Since I have this (mainly MXML) background, I concieved gtkaml as a shortcut for _me_ to learn the _Gtk_ UI widgets and their properties. I used it a couple of times to prototype UI for something that would have been to boring to write in C or in Vala.

I got at maximum 100 downloads per release, starring on gnomefiles and freshmeat. It lowers – the latest version, posted on gnome-announce, had less downloads.
Is it because, not having a well organized parser/code generator, every hacker scares away (from the error messages for example)??

I also get compared with glade/GtkBuilder that often that I explained in a previous post the differences. But still nobody cared.

Can somebody point me their open-source experience? is this normal? (i.e. to have an unique itch and scratch it?)

Written by vlad

August 21, 2008 at 8:00 pm

Posted in gtkaml, ideas, morons

what gtkaml is not

with 2 comments

Updated nov. 2010

I noticed that the first reaction when people hear about gtkaml is “But GtkBuilder/glade already does this!” or “How is gtkaml better than glade?” or something along these lines.

Let me put this straight: there is no resemblance between gtkaml and glade (other than using markup). None. They are not mutually exclusive, and do not do the same thing.

You can tell this by looking at them!

what they are

First, libglade is a library (and GtkBuilder comes bundled with Gtk+). You link against it and it parses your UI markup at runtime.. Glade is also a visual editor for that markup.

On the other side, gtkaml is a preprocessor. Your markup becomes code, Vala code, which and eventually becomes static C code.

language bindings

glade and GtkBuilder can be used from many different programming languages.

gtkaml is only available for Vala. However, libraries created with Vala can be used from any language.

run-time vs compile-time

GtkBuilder and glade make it possible to change the UI markup without compiling. This is because they call Gtk+ functions from libgtk, functions determined at runtime.

gtkaml only knows what you meant when compiling – it uses Vala’s AST to do this. You have to recompile to change the UI, therefore.

syntax

GtkBuilder and glade have their own markup which is verbose and usually must be written by means of an interactive tool (glade).
Every new Gtk property or class must have Glade/GtkBuilder support for it to work.

gtkaml simply maps tag names to classes and tag attributes to properties/fields/signals.

signals

Because of the run-time capabilities, GtkBuilder and glade require you to export your signal handlers from your own executable, like an .so/.dll does, or to write GtkBuilderConnectFunc’s for them.

gtkaml simply uses Vala’s signal .connect() which translates into g_signal_connect () function calls.

widget referencing

GtkBuilder requires calling gtk_builder_get_object (“by name”) to get a reference to a widget. Similarly, glade has lookup_widget (“by name”).

gtkaml optionally lets you declare widgets as public or private fields, so you can use them directly.

using custom widgets

glade requires specific code to instantiate custom widgets (set_custom_handler ()). GtkBuilder requires the widgets to implement GtkBuildable (which is a Good Thing).

gtkaml only needs them widgets to be compatible with the parent add method (wether is Container.add or something else).

Update: They don’t even have to be widgets, they can be Clutter actors or some business model objects.

creating custom widgets

GtkBuilder or glade do not have support for creating custom widgets.

gtkaml does only this. It creates custom (composite) widgets.

other than Gtk

glade and GtkBuilder are Gtk+ specific.

gtkaml can now accomodate any library that has a Vala vapi file (such as Clutter, Hildon, MX really, any) – you only have to point out in an .implicits file the methods used to add childs to a container.

Conclusion: use GtkBuilder if you need to change the GUI without recompiling. Use gtkaml to write custom composite widgets (with Vala code within) or use a gtkaml with the MVC pattern to separate view from behavior.

Written by vlad

March 25, 2008 at 1:29 pm

Posted in gtkaml

attribute values in gtkaml

leave a comment »

Rule of the thumb: when you don’t enclose your attribute values in {}’s, something magic is going to happen.

That is because gtkaml tries to make your life easier. Let’s take the first example,

Properties

<Window title="my window" type="{WindowType.TOPLEVEL}" ...&#91;/sourcecode&#93;
The difference between using and not using curly braces is obvious: if you use {}, you get to write a valid <b>code</b> expression. Otherwise, gtkaml tries to guess a literal for you: in this case, title being a <b>string </b>property, the value &lt;&lt;my window&gt;&gt; gets translated to &lt;&lt;"my window""&gt;&gt; in Vala.

This would be the equivalent of <b>title='{"my window"}'</b> (you have to use the alternate single-quotes of xml for this).If the  property is <b>bool</b>, you get exactly the "false" or "true" literal, and if the property is an <b>integer</b>, the same.

Actually, whatever the property is that is not a string, you get what you typed - the "magic" happens only for string properties.

Alternate 'spellings' for the code above are possible, along the lines of:

<Window>
   <title>my window</title>
   <type>{WindowType.TOPLEVEL}</type>
</Window>

or if your value contains invalid xml characters:

   <title><!&#91;CDATA&#91;my window >= your window&#93;&#93;></title>

Signals

<Window destroy="{Gtk.main_quit}" />
<Window delete_event="Gtk.main_quit()" />
<Window delete_event="{ widget => { Gtk.main_quit (); }" />

The difference is that the first is an expression of type “function” (an expression that returns a function), while the second is executable code. The generated Vala source is like this:

//with curly braces:
this.destroy += Gtk.main_quit;

//without curly braces
this.delete_event += (target, event) => { Gtk.main_quit(); };

//third way - just like the first
this.delete_event += widget => { Gtk.main_quit (); };

Second, the value without curly braces does the “magic” of creating an anonymous function and to automatically fill the signal parameters for you. This can be helpful if you want to write short executable code in a simple attribute; otherwise you can write a ‘full-blow’ function body in a CDATA section:

<Window>
   <delete_event><!&#91;CDATA&#91;{
widget => {
     Gtk.main_quit ();
}
}&#93;&#93;> </delete_event>
</Window>

Notice, however, that you have to use curly braces two times: one for the method body, the other for gtkaml to know not to do any ‘magic’.As you can see, no matter how you specify the signal, gtkaml adds the last “;”.

Construct

gtkaml 0.2 (svn version as we speak) features two new properties, named gtkaml:construct and preconstruct. This is because gtkaml creates the class construct for you (where it sets up the attributes, adds children to containers etc), but you might need to add yourself code there. You can use gtkaml:preconstruct and gtkaml:preconstruct on all tags:

  • preconstruct is executed just after the object is instantiated, before setting the other properties
  • construct is executed just before the object is added to it’s parent container

As a side effect, the root tag has ‘preconstruct’ executed before all others preconstructs and the ‘construct’ after all other constructs.

These attributes are to be used exactly like a signal: you write code, and you have the “target” parameter (the widget)

In the case of using {}, you can directly assign an existing function that receives a widget or void as parameter, or write a lambda expression in-place.

Example:

<Window 
   class:preconstruct="{view_init}" 
   class:construct="post_init(target)" />

As with the signals above, the first attribute simply sets “view_init” as the method to be called, and the second method actually wraps the call into a lambda function defined like target => { post_init (target); };

There isn’t much to do with the target parameter in this example: you can always use this. instead. But it may be very useful if you want to modify an unnamed widget.

Written by vlad

February 26, 2008 at 12:42 am

Posted in gtkaml

how gtkaml works

with 5 comments

If you are writing something based on GTK+ / GObject then you should be interested by this:

  • Vala is a very productivity-boosting language based on GObject OOP-ness, which translates to C and therefore can export GObject classes and interfaces from shared libraries.
  • gtkaml is a thin SAX Parser on top of Vala that allows you to write XML user interface descriptions

This is how a minimal Vala class described with gtkaml looks like:

<VBox class:name="MyVBox"
      xmlns="Gtk" xmlns:class="http://gtkaml.org/0.1">
        <Label label="Hi_story"
               expand="false" fill="false" padding="0" />
</VBox>

This code creates a class named MyVBox that extends VBox and contains a Label. The label has the value “History”, it does not expand or fill its box and is not padded.Easy, no?

But GtkLabel doesn’t have expand, fill, or padding properties! I hear you say. Yes, but the pack_start () method has them as parameters.

Which leads us to the first subject:

Container Add Methods

gtkaml uses a file named implicits.ini to determine which containers have which add methods. This is for “implicit” decisions it makes based on your UI layout.

For the example above, it simply finds this:

[Gtk.Container]
adds=add_with_properties
[Gtk.Box]
adds = pack_start;pack_end;pack_start_defaults;pack_end_defaults

This simply lists all the functions that one can use to add widgets to a Box and to a Container. Since VBox is a Box and Box is a Container, gtkaml finds these two entries ‘significant’ and merges them in this order (most specialized first):

pack_start;pack_end;pack_start_defaults;pack_end_defaults;add_with_properties

Then it loops over these methods – in this order – finds the first matching one and ‘picks’ the parameters from the child widget tag: that is, it removes “expand”, “fill” and “padding” from the Label and makes a note to use their value when adding the label in the VBox.

What if I want to use another add method?

Well, in that case simply specify the method’s name as an attribute of the child tag, with the value “true”:

<Label pack_end="true" label="Hi_story"
               expand="false" fill="false" padding="0" />

Creation methods

In this same example we notice that the label contains an underscore: this is intended to show up as a “mnemonic” (an keyboard shortcut) or simply as “History”.

Looking again at the GtkLabel documentation we notice that the only ways to get a mnemonic is to use either gtk_label_set_text_with_mnemonic () or gtk_label_new_with_mnemonic (). But since gtkaml can only help you with public fields, properties and signals, and not with function calls, how does one specify a mnemonic?

The answer is that you can select a “creation method”, and gtk_label_new_with_mnemonic () is not an ordinary function but a creation method. That is, a method that does not require the object as the first parameter but returns a new object.

So simply specify the creation method name as an attribute with a value of “true”: with_mnemonic=”true”.

Wait, but how about the creation method’s parameters? with_mnemonic has one parameter named str..

Well, usually Gtk widgets’ creation methods have their parameters named after the field/property they are initializing. gtkaml recognizes them from the specified attributes.

In this case, though, str is not a field or parameter of GtkLabel. But we know that it actually refers to the label property.

So what gtkaml does is to specify, again, in implicits.ini, the attributes that will go as parameters to the creation method:

[Gtk.Label]
new = label
new.with_mnemonic = label

So the code becomes:

<Label pack_end="true" with_mnemonic="true" label="Hi_story"
               expand="false" fill="false" padding="0" />

That’s it! – more on what gtkaml 0.2 will do for you in a future article.

p.s. as I am writing this, gtkaml was accepted on freshmeat.net! yay!

Written by vlad

February 7, 2008 at 3:06 pm

Posted in gtkaml, trivia

gtkaml 0.1 released!

with 3 comments

Well, actually gtkaml 0.1.0.1…

I had problems with autotools.. my examples installed in the /usr/bin directory – which was uncool.

And the googlecode decided that no release should be deleted – so I bumped the version up and released once again..

Anyway, in case you don’t know, gtkaml is an XML preprocessor that transforms all your container/widget descriptions into Vala. I proposed myself to build this project some time ago.

And now it’s done! Next thing I know, I’ll be that proficient in GTK that I will event start my own Norton-Commander clone in gtkaml + vala!

So here it is, the announce: giocommander will be a NortonCommander clone written in GTK with the new GIO api that’s bundled in GLIB.

The Linux version will be featureful, if you have GVFS installed, and the Windows version will be “O.K”

You know why? Because it’s simpler to develop a software that’s featureful in Linux and crippled in Windows:-P

And if you add enough features, you might end up installing Linux just to get them! (What, you never installed Windows just to get Photoshop or Autocad? Why not the other way?!?)

Ok, jokes aside, let’s get back to the drawing board..

Written by vlad

February 3, 2008 at 8:55 pm

Posted in gtkaml, ideas