In guichan (and hence also in alguichan) there is a concept of frames around a widget. I'm not completely happy with this...

So, what is a frame? Essentially it's something drawn around a widget, which is more or less a rectangular area with content. It serves to give the impression of a 3D-effect, like showing the widget somewhat deeper than the rest of the screen.

There are two problems with this. One is, the frame is outside the widget itself, so it looks strange when widgets are close together. The other is, depending on what you want to see, some widgets should have a frame (like a button or a window), other should not (like a label or a checkbox). Then there are widgets (like listbox) that should have a frame in some places, but not in others.

Of course each widget can have an individual setting of frame size, so there might be no problem at all. I'm thinking about the defaults however, introducing the concept of a style into alguichan, and that's where I want to have reasonable defaults that don't need much tweaking aside from setting values in the style object.

Is there any need for frames at all? If so, how can I specify which widgets should have a frame (with given size) with only a few numbers in the style object?

Here's the usual test program, showing almost all widgets, with all frames 0: {"name":"603404","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/7\/a\/7a128080f0ca944193e6ddfb51729ad7.jpg","w":645,"h":503,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/7\/a\/7a128080f0ca944193e6ddfb51729ad7"}

And here's the same with frame size 1 for 'buttons' and 'areas': {"name":"603405","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/d\/8\/d8e86ab9b04b292fb1e91cfba7266061.jpg","w":644,"h":502,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/d\/8\/d8e86ab9b04b292fb1e91cfba7266061"}

Note that the TextField and the DropDown seems to have a frame in the first image, but that's a border, like the border of the Button. This border is inside the widget, and it doesn't look completely consistent, given that most other widgets don't have a border.

So next question is, should all widgets (or at least most of them) have a border?

In my quest to skin my gui, I've collected a few images of UIs that have a generally nice and unimposing appearance. I have attached a bunch.

My latest iteration is drawn using only allegro primitives:{"name":"603417","src":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/0\/1\/01584578488c1c70315ff4b9e8bf8244.png","w":495,"h":188,"tn":"\/\/djungxnpq2nug.cloudfront.net\/image\/cache\/0\/1\/01584578488c1c70315ff4b9e8bf8244"}

By default, resizing the widget resizes the entire widget (the outer area, regardless of the inner area)

Each cell in the layout manager has a margin.

So I leave it up to the theme manager to decide how to do the border. My included theme has no concept of customizable borders. E.g., the button widget draws its border as part of the inner clipped contents.

The only widget so far that has a true border is the frame (window) widget. It overloads the resize method and resizes the inner clipped rectangle to the request size. Thus a algui_resize(window, 640, 480) creates a window with an inner width of 640x480.

For a widget with a border (e.g., a framed window), the theme would set the dimensions of the inner clipped rectangle. Then all of its widgets are drawn accordingly to that rectangle.

If somebody really wants to add borders to all items without redrawing all of the built-in widgets, my response is simply to create your own BORDER_WIDGET container and add things to it. e.g.:

So now you get a border wrapped around your object. Of course if the object already has a border, you'd get a double border. But, again, I consider this something that the theme creator gets to decide.

Personally, I didn't want to bother creating widgets with borders that both look good and can be modified, so I hardcoded them into the widget.

Matthew, I'm curious, have you considered menu dropdowns that show outside of the current display, eg this, when a window is at the edge of the screen? Perhaps as a separate frameless display (though frameless displays are not completely supported across platforms)?

Yes, the theme manager has a "place object" function it can override. By default it simply places the object at x,y on its parent. But it could then draw a shadow outside that on the parent's canvas. That's the tentative plan anyway.

I'm currently using that approach to draw shadows on framed windows.

Note that I implement both framed windows and pop-up menus as null-rooted components. So they aren't constrained to the apparent root desktop widget in any way. That is you may have:

display (640,480)

desktop (320x240 at 0,0)

button

window

(Any component can be null-rooted, although most commonly you'd have a desktop widget.)

Clicking the button creates the window, which is rooted at the display area. Now if that button were sitting on a corner and had a shadow that spilled outside the 320x240 bounds of its desktop, it wouldn't get drawn due to clipping. (Unless the theme manager cheated, and drew directly to the display buffer.)

But the window, as it sits outside of the desktop's constraints, can easily have a shadow drawn outside of its main canvas area without having to "cheat."

In this case, it's necessary for the dropdown menu to extend beyond the confines of the application-which-contains-the-gui's window, so it would (theoretically) create a separate ALLEGRO_DISPLAY for the list dropdown.

I wouldn't bother setting up a separate OS window for drop downs inside an allegro app.

I only ask because in Matthew's 3rd(?) algui video he shows a dialogue where a native dialogue window still retains as an extension of the underlying algui (a separate display with algui widgets, I'm assuming, as opposed to one of the native dialogues). It seems like a "pop-out" dropdown would be a consistent next step.

When I look at it, doing something like a theme (manager) or styles right is more difficult and complicated than I want to deal with now. So I think for me it's probably best to keep it as simple as possible for the time being. I'll think about these things though, and continue to make changes here and there. Thanks for all your input and thought!

I wouldn't bother setting up a separate OS window for drop downs inside an allegro app.

I don't. The only time I use a separate OS window is if the user requests one. The point of that video was to show that internally you can treat the widget as if it were drawn by algui.

Regarding pop-up menus, there could be some problems with clipping. I don't intend to solve the core one of not being able to draw outside of the ALLEGRO_DISPLAY area.* I will work around it by moving the dialog up/left such that you can see it. (Just like your OS would do if you tried to pop up a menu near the bottom of the desktop.)

What I was getting at earlier is that you don't have to worry about internal clipping issues with popup menus. Say you have:

The window, if owned by the desktop widget, is constrained to the 200x200 area. However, if you click on its menu bar and a menu item pops up, it is not constrained to the 100x50 area. Neither is it constrained to the 200x200 desktop widget, because it gets created as a stand alone component with full access to the 640x480 display. But it cannot draw beyond those constraints.

So in your screenshot, take the yellow outline and shove it up such that the bottom of it is aligned with the bottom of the cyan outline.

* Disclaimer: At least, I wouldn't try to solve it before the first released version.

In my GUI there's only one widget size, the one that the container widgets work with.Each widget has a view which renders it, when you set the size/content of a widget, the preferred size of the widget is decided by the Request_size function of its view.

How the size is handled by containers vary. I haven't put margin support in anywhere yet, but I think that should be handled in the containers , not the regular widgets.

If a widget should have a frame that goes outside its own area, I think I'd create a container with one child that has a view which renders the frame and the child, it would request a size that holds the childs requested size and the frames size. That way I could frame anything from a single widget to a whole sublayout.

The tab panel widget is composed of an implicit vbox container with a tab strip on the top and an empty stretched slot in the bottom (for the user's widget). Setting the tab panel margin actually sets the margin of the bottom slot of its vbox container: