Advanced UI Patterns
Scaffolding and RichWidgets
This lesson is part of the Developing OutSystems Web Applications course.

Hello and welcome to Scaffolding and RichWidgets in the Outsystems platform.
Service Studio provides several automation accelerators that increase the
developers productivity while he's developing the UI of their applications
and these are collectively called scaffolding. The scaffolding patterns
allow you to create screens or sections of the screens in a much faster way,
normally employing just a couple of drag and drops or right clicks. It's
important to note that scaffolding produces content that you're then free to
go and adapt to your specifics. They're just starting accelerators, they don't
produce black boxes where you need to keep everything that was generated. At
the highest level you're able to create full-blown list and detail screens that
use an entity of your model. Once you have a detail screen, say for example a
screen that displays a customer, you're able through scaffolding again to create
a detail table underneath, say for example which orders this customer has
placed. As you progress to lower-level patterns
it's also possible to generate pop-up dialogues and info balloons and also
have autocomplete inputs as an alternative to the combobox. This is just
a short selection of the patterns and you can find more about the other ones
on the product documentation. Let's look first at how you can create a full-blown
list and detail screen using the platform. If for example you have an entity called
cinema, if you drag and drop this entity into the flow canvas of screens you will
notice that the cursor will change to a screen, and it will indicate that what's
going to be generated upon dropping is a screen that will display cinemas,
therefore a list of the source entity. If you open this generated screen, this
scaffolded screen, it will look a little bit like this - and you can see already
quite a few patterns here that show how advanced,
out-of-the-box this screen already is. So you have filters and you have a couple
of artifacts that we will describe in a later slide. If you drag and drop again
cinema into the canvas of screens you'll notice that the suggestion will be to
create something that's going to be called CinemaDetail. This will create a
detail screen over the source entity, thus displaying one cinema. On the
right-hand side you can see a screenshot that shows this detail cinema. You can
see that it's a full-blown form with "Save" and "Cancel", and if you go back to
our list cinema screen generated previously, you will see that the list
has been augmented to have a link that allows you to open the details of the
cinema, so it actually will make changes to the list screen when you create a
detail screen. One other pattern we mentioned is the creation of a related
table inside the master entity detail screen. If you drag and drop an entity
that has a relationship, a foreign key, to this screen's entity, scaffolding will
generate what you see in the bottom section of the screenshot. In this case
dragging a movie session into a cinema detail will show all of the sessions
playing in the current cinema. Scaffolding will take care of generating
all of the queries with the needed filters and the UI that you see here. Now
if you pay close attention you will notice that there's quite a few
artifacts that we haven't seen in the past as we were developing. These are
what we call RichWidgets and we will describe some of the most interesting
ones that scaffolding is using here. Over there, there is the pop up, at the bottom
there is a list navigation and on each column there is a column sort.
It's important to note that these are just three of the many widgets that RichWidgets
employs and although we're
using scaffolding to show them being used
you can actually use them and drag and drop them directly into your own
manually created screens. Let's look at these three patterns that we saw in the
last screen in more detail then. The pop-up editor allows you to have one of
your screens being displayed as if it was a modal window overlaid over the
current screen. So for the purpose of this discussion let's call the "Source
Screen" the original screen that you are, and that launches an overlay and let's
call the "Target Screen" the pop-up that is opened over the source screen.
How can you then achieve this behavior in your code?
The first step is that, in the source screen, you need to make the pop-up
editor RichWidget take over the link that originally went to the normal
target screen, and to do this you have to start with a link of type Navigate,
drag-and-drop the pop-up editor next to this link and set it to point to the ID
of the link that it wants to take over. On the target screen, while you're free
to create whatever content you want, you normally want to go for a simpler
layout with no menu or footer so we suggest using the Layout Popup on the
target screen. Now this target screen behaves a little bit like a child, like a
widget of the big screen,
so therefore the way it interacts with the source screen is slightly different
from it being a full-blown screen, so therefore if ever there is a need
to notify the source screen of something, you have an action called Popup_Editor_Notify
that behaves very similarly to the Notify that we've learned when we
talked about Ajax. Finally if ever you want to dismiss the target screen, you use the
Popup_Editor_Close action rather than navigating away from this screen. In
closing, it's important to reinforce that the source screen as it contains now a
target screen that will notify potentially outwards, needs to grab this
as if it were an Ajax call so therefore you will need to set the On
Notify target screen action that will handle the notification from the target
screen. The list navigation scaffolding pattern, on the other hand, implements a
navigator for table records allowing the user to cycle through the multiple pages
that a table record might have. The first step in using one is dragging and
dropping the list navigation rich widget somewhere close to the table records
that you wanted to operate on. Next, you need to set up the list navigation so it
knows which table records it's taking over, and over here you have highlighted
the properties that you need to set so that the list navigation can take over
the table records. You need to specify the ID of the table records that it is
taking over,
what is the line count, i.e. the expected number of rows that the table records
will have, and also the total number of elements, in this case movies, that the
query has returned.
This way the navigator can select, for example, how many pages of results
it should be displaying. Finally, you also need to specify a destination for the
OnNotify. This is so that the screen realizes when the user presses a next
page or a page number and can react to move the query to that start index. From
all this it becomes obvious that the table records needs to obey the
navigator in so far as to what is the first index of the source list that
should be shown, for whatever page that is selected. We do this by
dynamically setting the start index property as shown in the screenshot. And
finally there's the list sort column pattern. This sort column allows you to
dynamically sort the aggregate that feeds this table record depending on the
user selecting the column. You start off first by dragging and dropping the
List_SortColumn RichWidget next to the title of the column that you want to
sort. You then need to set up each individual
List_SortColumn with the appropriate attribute by which the query should be
sorted when the user clicks on this column. It's important to note that the
format for specifying what column is related to this particular List_SortColumn
RichWidget has a very strict format: you should have your entity name
inside curly brackets followed by your attribute name inside square brackets.
Now when the user clicks this particular column, obviously the screen needs to be
notified of this event and that's why you need to specify again a handler for
the notification. The handler, very much like in the list navigation, will need to
refresh the data source in face of this new sort column and refresh the table
associated, so it responds to the new sorting. From all of this,
it's clear to see that the aggregate that sources the table records needs to
obey the List_SortColumn regarding what column it should sort by and this is
very similar in principle to what we saw in the list navigator pattern. We achieve
this variable-sort by dynamically setting the sorting on the aggregate as
it's shown in the screenshot. And this was a very quick overview of the power of
scaffolding and of the RichWidgets that are provided with the platform.
Don't forget, there are several scaffolding patterns that go from
creating full-blown screens, to adapting individual widgets and you have a
multitude of RichWidgets that do all sorts of things from sorting, navigation,
pop-ups, icons, etc. We expect that both the scaffolding patterns and the bundled
RichWidgets will be huge time savers in your future OutSystems developments.