Allegro.cc - Online Community

Allegro.cc Forums » The Depot » Official algui thread.

This thread is locked; no one can reply to it. rss feed Print
Official algui thread.
axilmar
Member #1,204
April 2001

I'll post updates of my gui library in this thread.

Project page: https://github.com/axilmar/algui

I have added a skinning API, as well as a test skin example.

Comments/suggestions are welcomed.

Elias
Member #358
May 2000

Are there screenshots? Or videos like the ones Matthew made of his gui lib?

--
"Either help out or stop whining" - Evert

SiegeLord
Member #7,827
October 2006
avatar

Comments about the build system:

  • Handmade Makefiles were never okay, especially those that hard-code the source files in them

  • Makefile wants Allegro 5.1, there's no good reason for Allegro 5.1 to be necessary for this library

  • stricmp wasn't found on my Ubuntu

Comments about the GUI:

  • Why a separate event hierarchy? The whole point of having an Allegro GUI is that it doesn't add layers of interface bloat, in my opinion

  • This is especially evident with the timer thing... why can't you use your game timer for the GUI as well; why does the GUI need a timer of its own?

Comments about the example:

  • Get a real game loop, please

  • It doesn't draw anything except the messages for me

"For in much wisdom is much grief: and he that increases knowledge increases sorrow."-Ecclesiastes 1:18
[SiegeLord's Abode][Codes]:[DAllegro5]:[RustAllegro]

axilmar
Member #1,204
April 2001

Elias said:

Are there screenshots? Or videos like the ones Matthew made of his gui lib?

There are no widgets yet. I have just completed most of the major API mechanisms. You can check out the API to see if you like it, and then browse the file _main.c to see how it works.

SiegeLord said:

Comments about the build system:

The makefile was kindly donated by Bamcaig. Thank you Bamcaig. I am using Visual Studio on Windows, and I don't indent to spent any time with makefiles any time soon. I suggest you grab an IDE and just put the files to it, or, if you wish, make up the appropriate makefile and I will include it the project.

Quote:

stricmp wasn't found on my Ubuntu

Isn't stricmp a POSIX function in header string.h? why is it absent in your system?

Quote:

Why a separate event hierarchy? The whole point of having an Allegro GUI is that it doesn't add layers of interface bloat, in my opinion

What do you mean? widgets receive messages, not events. Messages have different data than Allegro events, and there are more messages than events.

For example, when you receive a mouse message, you get the mouse coordinates both relative to widget and to the screen, something Allegro doesn't offer.

Another example: when you receive drag and drop messages, you get the data source widget.

Another example: Allegro mouse moves are translated to mouse enter/move/leave events for widgets.

Quote:

This is especially evident with the timer thing... why can't you use your game timer for the GUI as well; why does the GUI need a timer of its own?

Because widgets may have embedded animations in them.

For example, a text widget will have a blinking cursor.

Another example: A list widget will scroll as long as the user holds the mouse button down outside of the widget.

Widgets will use the timer API to automatically manage timer events without the user having to do anything.

Quote:

Get a real game loop, please

You don't have to do anything special for the gui. You just pass the allegro events to it.

Quote:

It doesn't draw anything except the messages for me

Nothing is drawn most probably because the skin is not found.

What's your working directory? you have to set it to where the makefile directory is. The skin is to be found in the folder test/test-skin.

EDIT:

I replaced stricmp with strcmp. Unfortunately, stricmp is not a POSIX function.

SiegeLord
Member #7,827
October 2006
avatar

axilmar said:

Nothing is drawn most probably because the skin is not found.

The skin returned is not NULL, and I checked that all the bitmaps load fine too. It turns out I have to minimize and maximize the window to see the widgets.

Quote:

You don't have to do anything special for the gui. You just pass the allegro events to it.

How do you get the GUI to draw? As in, what function would I call to cause a full redraw of the whole GUI?

"For in much wisdom is much grief: and he that increases knowledge increases sorrow."-Ecclesiastes 1:18
[SiegeLord's Abode][Codes]:[DAllegro5]:[RustAllegro]

Evert
Member #794
November 2000
avatar

axilmar said:

Isn't stricmp a POSIX function in header string.h? why is it absent in your system?

It's not POSIX. strcasecmp might be though. Either way, there is something to be said for using Allegro's UTF-8 string routines for something like this.

Quote:

What do you mean? widgets receive messages, not events. Messages have different data than Allegro events, and there are more messages than events.

I don't know exactly what you're doing (haven't looked at the code), but the way I would make a GUI interact with Allegro's event system is to have it available as an event source, as well as providing a function that lets me pass Allegro events to the GUI handling function from the main loop. Is that what you do?

axilmar
Member #1,204
April 2001

SiegeLord said:

The skin returned is not NULL, and I checked that all the bitmaps load fine too. It turns out I have to minimize and maximize the window to see the widgets.

Perhaps there is no initial expose event under X-Windows. I added a call to draw the gui for the first time.

Quote:

How do you get the GUI to draw? As in, what function would I call to cause a full redraw of the whole GUI?

It's the function algui_draw_widget(widget).

Evert said:

there is something to be said for using Allegro's UTF-8 string routines for something like this

I was using it on skin filenames, and I didn't consider it necessary to handle unicode. I will change it in the future if there is request for it.

Quote:

Is that what you do?

Yes. The function algui_dispatch_event(widget, allegro_event) is used to dispatch the Allegro event to widgets.

I am not using the Allegro event queue for the gui though; it's not necessary. The above function dispatches the events to widgets as needed.

Matthew Leverton
Supreme Loser
January 1999
avatar

Regarding events, I assume Evert is suggesting this:

ALLEGRO_EVENT_SOURCE *algui_get_event_source()
{
  return event_source;
}

(That's from my gui.)

So then the user can just look for ALGUI_BUTTON_CLICK events within an ALLEGRO_EVENT_QUEUE, etc.

I haven't looked at the source, so maybe you already are doing that.

I don't use the Allegro event system exclusively for internal calls either.

axilmar
Member #1,204
April 2001

I haven't looked at the source, so maybe you already are doing that.

No, I don't do that. Events are delivered straight to widgets via messages. They cannot be intercepted at the event loop. There is no need to do that.

Matthew Leverton
Supreme Loser
January 1999
avatar

axilmar said:

There is no need to do that.

Users may disagree. ;)

I set up a dual mode, one where internal messages are sent directly via callback messages (such that the widget can ignore or cancel the event) and a secondary userland version using the Allegro events.

That is, the internal non-Allegro "events" are things that are meant to affect the behavior or implementation of the widget. The external "something happened" event use Allegro events.

axilmar
Member #1,204
April 2001

Users may disagree.

I don't see any use case for that. Perhaps you have one?

Matthew Leverton
Supreme Loser
January 1999
avatar

axilmar said:

I don't see any use case for that. Perhaps you have one?

Strictly speaking, as long as there's some way to know that button Foo was clicked, Allegro events are not required. I added support simply because Allegro is my only target for the GUI and it seemed like the most natural way to do it.

So to me, the use case is simply "User processes events via the native Allegro event system", which is hardly helpful as an argument because it's circular.

Evert
Member #794
November 2000
avatar

I added support simply because Allegro is my only target for the GUI and it seemed like the most natural way to do it.

So to me, the use case is simply "User processes events via the native Allegro event system", which is hardly helpful as an argument because it's circular.

This.
I process all input from a loop that listens to events. I would expect any GUI I use to fit into that design.
Whether you agree and follow that is your own business, but it is what I personally would expect and want.

Trezker
Member #1,739
December 2001
avatar

Hmm, in my gui I feed the gui with allegro events but I have made my own event system for events from the widgets. Perhaps I should add to my todo list to make it possible to get gui events into an allegro queue.

I'll need to think about this some day when I'm not so tired.

AMCerasoli
Member #11,955
May 2010
avatar

axilmar said:

I didn't consider it necessary to handle unicode

That means that if I want to put "Niño" as a name of my window I'm not going to be able?

You library seems really good, but no supporting UTF-8 is an error... there is people around the world using Allegro, apart from the USA most of the from the EU.

The UTF-8 API of Allegro is nice but I think the harder part wasn't developed... Exist al_ustr_append to append a simple charter or a string of charter to the end of another string. But should also exist something like al_ustr_erase to erase the last charter from the string.

This because UTF-8 uses 1 to 4 bytes to save info... so depending of the letter you want to erase you are gonna have to delete 1,2,3 or 4 bytes... so you have to do comparisons and blablabla... Someone correct me if I'm wrong because that is what I'm doing. :P

Of course this might take you a while, so you can leave it to the end... :)

Evert
Member #794
November 2000
avatar

You library seems really good, but no supporting UTF-8 is an error... there is people around the world using Allegro, apart from the USA most of the from the EU.

I suspect he's actually aware of that. ;)
In fact, I'd have thought that UTF-8 would have been a no-brainer...

Matthew Leverton
Supreme Loser
January 1999
avatar

To erase the last character:

al_ustr_remove_chr(str, al_ustr_offset(str, -1));

There's not much the library has to do to support UTF-8. As long as the text drawing functions call the UTF-8 functions you basically get it for free.

I chose to store all strings as ALLEGRO_USTR, but that's not really a requirement.

AMCerasoli
Member #11,955
May 2010
avatar

I knew there was an easier way...

axilmar
Member #1,204
April 2001

Evert said:

I process all input from a loop that listens to events. I would expect any GUI I use to fit into that design.

My library does exactly that: it reads events from an Allegro event queue and then dispatches them to widgets. Widget messages are not placed in the queue though, they are executed directly from the dispatch function. But the event loop is still there.

Do you have any use case for widget messages (not events) to be placed in a queue?

That means that if I want to put "Niño" as a name of my window I'm not going to be able?

Yes. The window name (actually, window id) is not for display purposes. It's for programming purposes only, i.e. skinning, debugging etc, and I think that sticking to English makes sense: it's the simplest solution that works. It only requires static C strings. Putting UTF-8 there will make it necessary to do memory management on those ids, which is unnecessary.

Quote:

but no supporting UTF-8 is an error...

All the widgets will have UTF-8 text. Actually, they will have an ALLEGRO_USTR, just like Matthew's lib.

Edgar Reynaldo
Member #8,592
May 2007
avatar

axilmar said:

Do you have any use case for widget messages (not events) to be placed in a queue?

Not in the way that everyone else is thinking of, I think. ???

I would however like to see the widgets queue messages for the user, such as a button widget queueing a button_pressed message, a slider queueing a value_changed message, and so on...

This way the user can trivially connect one widget's actions to another. Like opening or closing a window widget from a button press, or changing a color from a slider value change, so on...

If you don't do that, then the user is forced to poll every widget for it's state on every update to see what has changed just so they can make their gui interactive.

Peter Wang
Member #23
April 2000

axilmar said:

Putting UTF-8 there will make it necessary to do memory management on those ids, which is unnecessary.

Well, that's misleading. Static strings can contain UTF-8 encoded text.

It's just there are some troubles with MSVC in East Asian locales, the gory details of which were elucidated earlier on this forum.

Evert
Member #794
November 2000
avatar

I would however like to see the widgets queue messages for the user, such as a button widget queueing a button_pressed message, a slider queueing a value_changed message, and so on...

This way the user can trivially connect one widget's actions to another. Like opening or closing a window widget from a button press, or changing a color from a slider value change, so on...

If you don't do that, then the user is forced to poll every widget for it's state on every update to see what has changed just so they can make their gui interactive.

That is what I meant.

AMCerasoli
Member #11,955
May 2010
avatar

I want to try it.

What I need to install it on Windows?

GTK+ and what else?

I'm getting this:

$ make
gcc -shared -Wl,-soname,libalgui.so -o lib/libalgui.so.1 obj/algui_list.o obj/al
gui_rect.o obj/algui_tree.o obj/algui_widget.o `pkg-config --libs allegro-5.1 al
legro_font-5.1 allegro_image-5.1 allegro_primitives-5.1 allegro_ttf-5.1`
Package allegro-5.1 was not found in the pkg-config search path.
Perhaps you should add the directory containing `allegro-5.1.pc'
to the PKG_CONFIG_PATH environment variable
No package 'allegro-5.1' found
Package allegro_font-5.1 was not found in the pkg-config search path.
Perhaps you should add the directory containing `allegro_font-5.1.pc'
to the PKG_CONFIG_PATH environment variable
No package 'allegro_font-5.1' found
Package allegro_image-5.1 was not found in the pkg-config search path.
Perhaps you should add the directory containing `allegro_image-5.1.pc'
to the PKG_CONFIG_PATH environment variable
No package 'allegro_image-5.1' found
Package allegro_primitives-5.1 was not found in the pkg-config search path.
Perhaps you should add the directory containing `allegro_primitives-5.1.pc'
to the PKG_CONFIG_PATH environment variable
No package 'allegro_primitives-5.1' found
Package allegro_ttf-5.1 was not found in the pkg-config search path.
Perhaps you should add the directory containing `allegro_ttf-5.1.pc'
to the PKG_CONFIG_PATH environment variable
No package 'allegro_ttf-5.1' found
obj/algui_widget.o: In function `draw':
c:\axilmal/src/algui_widget.c:186: undefined reference to `al_set_clipping_recta
ngle'
obj/algui_widget.o: In function `destroy':
c:\axilmal/src/algui_widget.c:207: undefined reference to `al_free_with_context'

obj/algui_widget.o: In function `destroy_timer':
c:\axilmal/src/algui_widget.c:362: undefined reference to `al_destroy_timer'
c:\axilmal/src/algui_widget.c:364: undefined reference to `al_free_with_context'

obj/algui_widget.o: In function `algui_draw_widget_rect':
c:\axilmal/src/algui_widget.c:1611: undefined reference to `al_get_clipping_rect
angle'
c:\axilmal/src/algui_widget.c:1617: undefined reference to `al_set_clipping_rect
angle'
obj/algui_widget.o: In function `algui_create_widget_timer':
c:\axilmal/src/algui_widget.c:2063: undefined reference to `al_create_timer'
c:\axilmal/src/algui_widget.c:2065: undefined reference to `al_malloc_with_conte
xt'
c:\axilmal/src/algui_widget.c:2069: undefined reference to `al_get_timer_event_s
ource'
c:\axilmal/src/algui_widget.c:2069: undefined reference to `al_register_event_so
urce'
c:\axilmal/src/algui_widget.c:2070: undefined reference to `al_start_timer'
collect2: ld returned 1 exit status
make: *** [lib/libalgui.so.1] Error 1

I'm using MSYS

axilmar
Member #1,204
April 2001

I would however like to see the widgets queue messages for the user, such as a button widget queueing a button_pressed message, a slider queueing a value_changed message, and so on...

This way the user can trivially connect one widget's actions to another. Like opening or closing a window widget from a button press, or changing a color from a slider value change, so on...

If you don't do that, then the user is forced to poll every widget for it's state on every update to see what has changed just so they can make their gui interactive.

It's not as trivial as you mention. You have to manage notification ids per widget: for every new command or option you put in the program, you have to allocate a new notification id. And this has to be done manually by the programmer. This is something that I have experience on due to using MFC, and let me tell you that it is very difficult and time consuming.

Furthermore, I am not a fan of big switch statements. They are counter productive. It's simply bad code to have switch functions with many hundreds of lines of code.

I am fan of callbacks (signals and slots actually).

In my library, users will be able to write callbacks which connect the appropriate widget actions to anything they want, including other widget actions, of course.

Well, that's misleading. Static strings can contain UTF-8 encoded text.

It's just there are some troubles with MSVC in East Asian locales, the gory details of which were elucidated earlier on this forum.

Ok, I didn't know that static strings can contain UTF-8 encoded text.

I am using ASCII strings for widget ids. Does anyone think that ASCII strings are not enough for such a job? for me, handling ASCII strings for widget ids has the following advantages:

  • no need to do memory management. With statically allocated C strings, each widget can have a pointer to a statically allocated string.


  • no need for extra string documentation regarding ids (who frees the memory, if strings need to be copied etc).


  • less memory footprint. If widget ids are allocated on the heap, then even if widget ids are the same for each widget class, the same strings will be allocated over and over.


  • some compilers are able to merge the same strings that are in different translation units.


  • vastly simpler programming regarding the parsing of skin text data. In the current code, parsing of simple ASCII text is very fast. Computations of string pointers are done by simply adding the number of characters to a pointer. This is not possible with UTF-8 strings. This also results to increased parsing speed.

In my opinion, I think that ASCII text for skin files is the right choice.

I'm getting this:

Your Allegro library installation is not the appropriate one?

AMCerasoli
Member #11,955
May 2010
avatar

hmm.. I supposed it.. but why are you using Allegro 5.1? 5.0 has just been released.

And I don't understand why when Allegro 5.0 wasn't ready, there was already a 5.1 version...

There is big advantages when using Allegro 5.1 instead of 5.0?



Go to: