Ask Reuben

Native to Universal Rendering (Reuben’s Commentary)

I can see the slides to a presentation at WWDC, what did you talk about?

At WWDC24, I gave a presentation titled “Native To Universal Rendering”,  The abstract for that presentation was …

In 2021, with the release of Genero 4.00, Genero front-ends standardised their rendering on ‘Universal Rendering’.  For customers who were already using the Genero Web Client, a lot of the concepts in the Universal Rendering interface were familiar to them.  For customers who had not used the Genero Web Client, some concepts such as “top most normal window”   are new to them, and the feedback was that it was a bigger step.

In this presentation, prepared and delivered by our Customer Care teams, we review some of the talking points you and your end users will encounter with Universal Rendering.  The aim being to raise your knowledge and via coding and customisation, be in a better position to utilise the strengths and avoid the weaknesses of Universal Rendering.

In this article, I’d like to expand on some of the key points in that presentation.  I would suggest opening the presentation, link here.  or open it from the page , and have it open in another window as you read this article.  The presentation was broken into a series of tips and in this article I will comment on each tip.


Tip #0: There is change when moving from Native to Universal Rendering !

We did not have this Top #0  in Melbourne, but I felt after that presentation we needed to introduce the topic better and get the attendees attention.

In the 20+ year history of Genero, the upgrade from 3.20 to 4.00 is probably the biggest disruption to your code base.  In your initial Genero transformation from Informix-4gl there was a big impact on your code base as you transformed it to a GUI interface and took advantage of the other offerings in the Genero tool-kit.  The jump from 3.20 to 4.00 is potentially the next biggest in the history of Genero as you move from Native to Universal Rendering if you have not already.

Unfortunately a lot of customers did not take the opportunity to participate in the 6 month long Early Access Program (EAP) for the 4.00 release at the beginning of 2021.  Despite the fact that we are mission-critical (page 8 of Bryants presentation) to your business, we often heard from you that “we are too busy to participate in the EAP”.  The movement to Universal Rendering has been a long one and as I showed in my Product & Customer Care Update, page 41-55, this has been something that has been worked on for 10+ years. We have sound reasons for that movement and in the long run I feel you will be better for it.

The amount of change is dependent on your previous usage of the Genero Web Client.  Customers who had already transformed their applications to run in a web browser have already encountered most of the change and so those customers have moved to Universal Rendering relatively smoothly.  It is customers who typically run with a Native User Interface using just one of Genero Desktop Client, Genero Mobile for iOS, Genero Mobile for Android that face the most disruption.

Why there is change is dependent on a number of factors.

  • We had four different user interfaces.  We wanted to move forward with only one.  It has not always been possible to consolidate features from all four user interfaces into the one Universal Rendering interface.
  • Browsers and Web Technologies impose limitations on the User Interface.  There are some things that the GDC allows  that Browsers prohibit.
  • We made some design decisions at our end.  The initial Universal Rendering was influenced by Material Design.  if you look at resources such as https://m3.material.io/ you may see some features that are incorporated in the Universal Rendering interface.
  • We were also conscious that we don’t want to allow many combinations of user interfaces that are available via flags and switches.  The more of these there are increases the QA load, performance, and slows development time as we have to factor in all these flags/switches into anything new.

A number of these changes were made in 2015, 2019, 2021 and it is very difficult for us now in 2024 to go back and revisit them.


Tip #1: Prepare your environment for monthly updates

Roughly every month there is a GBC maintenance release. It isn’t a fixed schedule like first of the month, 15th of the month, etc the gap can vary due to the workload and importance of issues to resolve.

You should configure your environment so that you are capable of receiving this update every month and testing and using the new release and have the ability to rollback as well.  This could be via:

In my environment which I would’ve demo’d, I install all the GBC releases and all my customisations into the directory specified by GBC_LOOKUP_PATH and can quickly change GBC release by appending ?gbc=version in the URL, or by changing GBC in my .xcf or by adjusting FGLGBCDIR in my Studio configuration.

After installing a new GBC version, you should always be in a position whereby you can rollback to the previous release if needed.  You want the ability to run with the previous release so if a user says something is different, you can verify this yourself by running against the old and new GBC releases.

This concept can also roll forward to your production environment.  You could even configure your environment so that some users get the new GBC version one day before others.


Tip #2: You will need to do some GBC Customization

There is a simple reason why you will probably want to do some GBC Customization.  Do you want your application identified by the Genero g icon, or do you want your application identified by your logo?

Answer is most likely your logo, so you will need to do some customisation to change the favicon to be your application logo.  See here for instructions.

You will probably also want to use a color that is identifiable with your application as the primary color of your application rather than our shade of Blue.  Changing this primary color can also be useful to identify multiple systems if you look after a number of systems or they have different purposes.  Having different primary colors for live, and training may help prevent misinterpretation of what system you are on.

My minimal customization involves changing the palette-primary color. to be a companys main color in their corporate look and feel (ideally a dark color and not a light color).


Tip #3: Future Proof Your Customization

There is a definite order of the techniques you should consider when doing customisation.  Have a read of this article.

The key is to consider the work that is required when updating GBC.

  • With replacing a file or setting Theme Variables it is unlikely that there would be any changes required to your customisation in a GBC maintenance release.  The only times would be if we decide to rename or remove a Theme Variable or if we split a Theme Variable in two.  You can go through the Upgrade notes to see how often this has occurred.
  • With Style Sheets, there is potential for a little more work at upgrade time.  Again it is rare but you may find that the .html used to render a widget changes and this may impact on the selectors you need to use.
  • The last resort is to make widget changes.  Say the function you are overriding has 100 lines and you override 10 lines.  Your code needs to have the 100 lines and there maybe a change in those other 90 lines you need to consider at upgrade time
  • I am not sure why the Front Calls entry is listed last in our documentation.  The protocol has stood the test of time and I’d consider it as stable as Theme Variables.

Tip #4: Preparing for Dark Mode Leads To Good Customization

In GBC 4.01.20 we introduced concept of Dark Theme.  What became apparent is how some code syntax could not be overidden by the Dark Theme.  When looking at this code, it was apparent that this code also restricted the ability to get the most out of GBC customisation.  This code includes:

  • TTY attributes.  ideally your initial Genero transformation should have removed TTY attributes.  If you left them in, now is a good time to remove them.  If you have DISPLAY BY NAME fieldname ATTRIBUTES(RED), this will still display light or dark or however you attempt to change it in your GBC customisation.
  • If you have color definitons defined in .4st e.g. StyleAttribute name=“textColor” value=”red”, this will still display red however you attempt to change it in your GBC customisation.  You can leave the STYLE= in your 4gl and per, but the style definition should be via GBC customisation rather than .4st.  That way you can apply a ‘red color to be used in default mode and a different ‘red’ color to be used in Dark mode.

One of the things that surprises me is when I encounter customer code that has a long .4st file.  Ideally your .4st is as short as possible, a long .4st signifies that you think you know better than the combined Windows, Mac, Linux UI design developers!

When I ask about entries in these long .4st, the reason given for an entry is because we added something else in the .4st.  That is the developers have what I call “Chased their tail”, because they added A, they needed to add B, and because they added B they needed to add C, and becuase of C they needed to add D and so on.  If they had questioned the need for A more at the beginning they would not have needed B,C,D.

My list of things I’d consider for .4st is short, it includes …

Anything else I start thinking what makes me think I know better than the Windows, Mac, and Linux UI design teams!


Tip #5: Know Your Style Sheet Selectors

It can be a little daunting trying to figure out what Style Sheet selector to use.  If you use your Browsers DevTools or equivalent, you should quickly observe that every widget has in their class values, selectors of “gbc_Widget_name” and “gbc_style_Style_name

If I had time, I would demo this with my demo from the Rounded Images Ask-Reuben article.  Note how the class values include gbc_ImageWidget and gbc_style_rounded in the screenshot below

Once you realise that every widget has these gbc prefixed class values added , you know you can select every instance of a particular widget, or more likely every widget that has STYLE=”Style name” via these CSS selectors.  There maybe some trickery to get the parent or a child node but you are looking in the right place straight away.



Tip #6: Style Sheets More Powerful than .4st

Some developers have indicated that they prefer to make changes in a .4st as it requires no compilation, no need to deploy a customized GBC.  What you can change in the .4st is very limited. It is essentially what changes Four Js R&D developers thought you might need in the early 2000’s when Genero was developed, and what the Genero Desktop Client was capable of rendering via use of its Qt libraries.

Using GBC Customization you have access to the full range of web techologies in producing your user interface.  Anything a Web Developer can include in their User Interface, in theory you can include in your User Interface.  So for example, CSS Animations, CSS Gradients, etc are available to you.  You are not reliant on Four Js adding the appropriate syntax to the form compiler, or to the 4st schema.


Tip #7: W3Schools and StackOverflow Are Your Friends

In coding your GBC Customization, you are going to face the same problems and ask the same questions as any other web developers will do in constructing your User Interface. Any problem you have, chances are another Web Developer has asked the same question before.

A good example I like to use is Rounded Images.  Here is a Stack Overflow question from a web developer asking how to make rounded images. https://stackoverflow.com/questions/21677395/how-to-make-rounded-images.  The key answer was use of border-radius = 50%.  Here is the W3schools page on border radius https://www.w3schools.com/cssref/css3_pr_border-radius.php.  and also a little tutorial https://www.w3schools.com/howto/howto_css_rounded_images.asp.

It is resources like this that allowed me to write this article on how to do some customization in order to have Rounded Images.


Tip #8: Manage Expectations With Customization

In the early days of GBC Customization, there were a few instances where customers engaged a “Web Developer” and expected them to create a wonderful interface solely using GBC Customization.

The point to note is that there are some Genero BDL coding techniques that a Web Developer cannot overcome, and ideally in the initial stages as they learn the system, a Web Developer should work closely with a senior Genero developer to see if it is a Genero BDL change required, or if it is something that can be achieved via Customization.

  • TTY Attributes have the highest priority.  If your code has DISPLAY BY NAME fieldname ATTRIBUTES(RED) then Genero will always try and make this field red.  Ideally you removed any TTY attributes in your initial Genero transformation from Informix-4gl many years ago but if there are any remaining, it is up to your Genero BDL developer to remove them rather than expecting GBC Customization to override these TTY attributes.  Ideally these fields now use the STYLE attribute and thus the GBC Customizer can use this STYLE attribute value to select the fields to render in a different way.
  • When running a Genero application, when it is waiting for user input, the runtime is in one of the dialog statements, MENU, INPUT, CONSTRUCT, DISPLAY, ARRAY, PROMPT, DIALOG.  Customization cannot be used to change the Genero BDL code that is executing and the order and form of these dialog statements.  It maybe that what is required is a code change to use some of the newer syntax that is available via:
  • Customization cannot be used to override the relative positioning of fields as they are defined in the Form file (.per, .4fd).  Maybe what is required is modification of form files to control the relative positioning and alignment of fields.  The code I see that might require review is
    • the use of Layout Tags rather than having children of VBOX, HBOX.  I find that Layout Tags are overused
    • incorpoate the use of HBox Tags so that fields are not unnecessary aligned.  I find that HBox Tags are underused
    • use of SCROLL so that field grid with is not the same width as characters to be entered.

Tip #9: Manage Expectations With Browsers and Web Technologies – Less Tolerant of Bad Design

Universal Rendering is executed in a browser / WebView.  It uses html, css, and Javascript to render the user interface.  In a web browser this is what you would expect, in GDC, GMI, GMA this is inside a WebView widget inside a small native application.  The important thing to note is that Javascript is interpreted and so on the face of it, you should expect it to render slightly slower than the corresponding native user interface which is executed, not interpreted.

As a result, it is less tolerant of some design practices.

  • The biggest form I have seen in support had over 5000 lines.  There were 200+ Containers (Group, Table etc), 2000+ Form Fields, and 200 screen records.   All this is loaded into the rendering engine and maybe iterated through by the renderer as part of its calculations.  As well as being a nightmare to maintain, this code base would benefit by being broken down into a series of smaller forms.  Anything you load that the user can’t see or be expected to navigate to in one click is wasted effort.
  • Part of these big forms is to have lots of folder and folder pages.  To calculate the size of a folder requires calculating the size of every folder page and then sizing the folder as big as its biggest page.  We have made lots of optimisation in this area but in the early days one interesting case involved a BEFORE ROW changing a GROUP title.  This invalidated the folder page so its size needed to be recalculated, every other folder page was being recalculated (unnecessarily), and then the Folder was being made the size of the biggest page.  If you believe you have a Folder with many pages that is causing slow rendering, use the lateRendering presentation style or have a read of this article, or try to find a way to reduce the number of Pages.  Remember any calculations involving something the user can’t see and never clicks on is wasted effort.
  • Everytime there is a ui.Interface.refresh there is a roundtrip between the front-end and the back-end.  There are two bad cases of excessive use of  ui.Interface.refresh() I have seen.   (See here for an article on ui.Interface.refresh)
    • One was in a FOREACH loop, there was a ui.Interface.refresh every iteration to update a “Processing row X of Y message”.  This use of ui.Interface.refresh() should be behind an IF x MOD y = 0 to try and update this display at a rate a human can notice the change, so I aim for 24 times a second.
    • The second was where ui.Interface.refresh() was added to a library call to show/hide form elements.  If this library function was being called for the 40 elements on the form, there were 40 ui.Interface.refresh calls in a short period of time.  There is typically no need for ui.Interface.refresh() to be inside a library funciton like this.
  • An interesting technique you can use to measure performance is to utilise something in one of our QA front-calls so not documented.  I would’ve demonstrated the program in the code below.  The key thing it does is if I have initialised our QA harness, then an action qa_dialog_ready is fired when a screen finishes rendering.  I can use this to get a measure for how long it takes for the front-end to render a form by noticing the time when this action is fired and comparing to the time when the form was opened.   To test with this program, run it and click Go, OK, Go.  You will notice that a dialog with a time in it will display twice.  I take the time for the second window as it is has the benefit of any caching from the first time the form was displayed.  The times I get were
    • Chrome 0.024s
    • GDC Universal 0.038s
    • iOS Emulator 0.067s
    • GDC Native (3.21) 0.072s
    • Safari 0.089s
    • Chrome (Throttled to fast 4g via Dev Tools) 0.197s

This technique can be used to get an idea of what forms, presentation styles,  what dialog statements are rendering slowI  saw a support case very recently where a slow form was shown to be due to the presence of an EDIT or TEXTEDIT with STYLE=”html”.  That is something for us to resolve.

It can also be used to compare different environments.  You can see there is a spread in these numbers, you may find that some older PCs with non  updated graphics drivers are slow.  I would like to take this test and enhance it to get a benchmark number we can use for an environment


MAIN
    DEFINE rec RECORD
        field1 INTEGER,
        field2 STRING,
        field3 DATE
    END RECORD

    DEFINE program_name STRING

    DEFINE start_time, finish_time DATETIME YEAR TO FRACTION(3)
    DEFINE elapsed INTERVAL SECOND TO FRACTION(3)

    WHENEVER ANY ERROR STOP
    DEFER INTERRUPT
    DEFER QUIT
    OPTIONS FIELD ORDER FORM
    OPTIONS INPUT WRAP

    CONNECT TO ":memory:+driver='dbmsqt'"

    LET program_name = base.Application.getProgramName()

    #CALL ui.Interface.loadStyles(program_name)
    CALL ui.Dialog.setDefaultUnbuffered(TRUE)
    

    WHILE TRUE

        LET rec.field1 = 1
        LET rec.field2 = "Lorem Ipsum"
        LET rec.field3 = TODAY

        MENU ""
            COMMAND "GO"
                EXIT MENU
            COMMAND "Exit"
                EXIT WHILE
            ON ACTION CLOSE
                EXIT WHILE
        END MENU

        CALL ui.Interface.frontCall("qa", "startQA", [], []) -- Add this line

        LET start_time = CURRENT HOUR TO FRACTION(3)
        OPEN WINDOW w WITH FORM program_name ATTRIBUTES(TEXT = program_name)
        INPUT BY NAME rec.* ATTRIBUTES(WITHOUT DEFAULTS = TRUE)
           
            ON ACTION qa_dialog_ready ATTRIBUTES(DEFAULTVIEW=NO)
                LET finish_time = CURRENT HOUR TO FRACTION(3)

                LET elapsed = finish_time - start_time
                CALL fgl_winmessage("Info", "Time to render screen is " || elapsed, "info")
                EXIT INPUT
        END INPUT
        LET int_flag =0
        CLOSE WINDOW w
    END WHILE
END MAIN

LAYOUT
GRID
{
Integer [f01         ]
String  [f02         ]
Date    [f03         ]
}
END
END

ATTRIBUTES
EDIT f01 = formonly.field1 TYPE INTEGER;
EDIT f02 = formonly.field2 TYPE CHAR, SCROLL;
DATEEDIT f03 = formonly.field3 TYPE DATE;

INSTRUCTIONS
SCREEN RECORD scr(field1, field2, field3);

Tip #10: Manage Expectations With Browsers and Web Technologies – What Would a Malicious Web Site Do?

When frustrated that you cannot do something in a Web environment, ask yourself what would a malicious web site developer do if they could do what is being asked for?

  • what would a malicious web site developer do if they could print to your printer without you acknowledging that this is what you want to print?
  • what would a malicious web site developer do if they could save a file to your PC without you knowing about it?
  • what would a malicious web site developer do if they could execute a file on your PC without you knowing about it?
  • what would a malicious website developer do if they could take or delete files from your PC without you knowing about it?
  • what would a malicious website developer do if they could query your Clipboard on the off chance there is a password or bank account number sitting in your clipboard?

So in Universal Rendering, there maybe some extra UI steps that are forced upon us by operating in a web environment.


Tip #11: Top Most Normal Window

The TopMost Normal Window design is one of the first things you might notice when running your application via Universal Rendering.  This has been a feature of the Genero Web Client User Interface since the first days of the web interface and is the main reason why developers moving to Universal Rendering from the Web Client are less impacted than developers moving to Universal Rendering from the Desktop Client.

To explain to a Desktop user what this TopMost Normal Window looks like is to get them to run their application natively and whenever a new non-modal window opens, maximise it.

You will most likely notify this design characteristics in the following circumstances:

  • in native you might have multiple non-modal windows that user will resize and drag so that they can see what was in window A as they type in window B.  Now with Universal Rendering, when in Window B user will have to click on the Window List to see what was in Window A
  • you had multiple non-modal windows because the original 4gl program was constrained by the 8ox25 character screen.  Now in GUI interface you have the ability to have larger screens containing more information. I had a demo that showed you could use alternatives listed below to combine multiple fields into one …
    • FOLDER + PAGE
    • FOLDER + PAGE Accordion Style
    • Collapsible Group Box
    • HBOX + SPLIT (Swipe Between Panels of Information)
    • Pattern of  HBOX where in the left child you have DISPLAY ARRAY and BEFORE ROW on this array is used to show/hide the contents in the right child of the HBOX
  • a sparse / small non-modal window will now open the size of every other window and you may have a window with lots of blank space.  Consider using STRETCH=X to make the fields take up more space or to use centering window techniques.
  • non-standard modal window usage, a modal window is expected to be like a cul-de-sac, you go into it and you then return to where you were.  Whilst we don’t impose a restriction in the code base, it is not expected that you then open another window from a modal window
  • a variant of opening a modal window from another modal window is when you emulate a widget via a modal window i.e. you might have your own Calendar widget.  If you open this modal window from another modal window, only the top most modal window will render i.e the Calendar window will be visible but the modal window you were in will disappear.  Ideally there would be a third layer of windows to cater for widget emulation.  Personally this is one concept from the 4.00 EAP where it was disappointing that we still have not come up with a solution.  I thought the developers impacted had a sound case but we were unable to persuade our team of the merits of the case.
  • a form with no stretchable elements and multiple VBOX or HBOX children will render with white space as it is stretched.  Have a look at the packed Presentation Style Attribute to reduce the impact of this.

Tip #12:  Default User Experience Can Be Modified

Concepts such as Application List, Window List are new to the Genero User Interface.  There are a number of Presentation Styles and Theme Variables that can be used to alter the User Experience.  These include

  • applicationListVisible
  • windowListVisible
  • desktopMultiWindow
  • browserMultiPage

Have a look at the UserInterface style attributes.

One other point here concerns the case where you want to open two windows, drag one into your left monitor, and one into your right monitor. Using the desktopMultiWindow or browserMultiPage style is a potential solution.  Another potential solution is to launch the second application via launchUrl front-call.  Previously using launchUrl would have licensing complications as this would be seen as a second user but that problem was solved in 4.00

I find it interesting that we say we have removed the MDI Multiple Document Interface.  If anything the default Universal Rendering Interface is a form of MDI and it is the Single Document Interface SDI that is no longer possible due to Top Most Normal Window.

One thing I would say here is work closely with us.  For those missing tabbedContainer, AFAIK no one has ever suggested, can the Application List be rendered horizontally across rather than vertically down the left.  ActionPanel, ringMenu, ToolBar can all be positioned top|left|bottom|right so why can the same not apply to Application List?


Tip #13: Compact for Desktop

The default GBC User Rendering takes Touch Devices into consideration.  Hence there is space between fields, rows, buttons to help users touch fields, rows, buttons accurately.  This has the impact on making the default Universal Rendering interface slightly taller and wider than the corresponding Native interface.

When forms had been designed to be a certain size or to fit inside a certain sized display, what users reported was that their “perfectly” sized screens were now rendering with scroll bars, how can we not have these scrollbars.

GBC 4.01.05 introduced a new theme called the Compact Theme.  The sizes/ratios used in this theme are intended to mimc closely the sizing of the Native rendering.  So if you designed a form to be displayed in a certain sized monitor, you should find that the Universal Rendering interface would also display in that certain sized monitor without scrollbars when using the Compact Theme.

How this Compact Theme was implemented is a good example of the power of Theme Variables.  Have a look at the files in $GBC_PROJECT_DIR/theme/colors/compact and in particular the 28 Theme Variables in $GBC_PROJECT_DIR/theme/colors/compact/theme.scss.json


Tip #14: Don’t be Naughty

When you build a GBC Customisation, it is essentially taking your changes from GBC_PROJECT_DIR/customization and applying them to the standard GBC sources that are in GBC_PROJECT_DIR/src and placing the compiled GBC package somewhere beneath GBC_PROJECT_DIR/dist.  I expressed that as a formula …

Customsied GBC = f(Standard, Theme Variables) + Custom

… that is the Customised GBC is a function of the Standard sources with your Theme Variables applied, plus any custom code such as Style Sheets, Widget override, and Front-calls

In customizing, we are expecting you to change only what is beneath GBC_PROJECT_DIR/customization i.e Theme Variables and any Style Sheets, Widgets, and Front Calls).  What some developers have done is make changes to the Standard, that is what is beneath GBC_PROJECT_DIR/src !!!

There is nothing stopping you doing this but this means every new GBC release you have to review the changes you have made to these files in GBC_PROJECT_DIR/src in case we have made changes to the same files.

We would rather you tell us what change you think needs to be made to these files and we will try and figure out a way to incorporate your change, for example adding a Theme Variable.


Tip #15: Miscellaneous

If we had had more tracks at WWDC, I might have split this presentation and be able to spend more time with this tip.  In this section I just wanted to highlight things for you to note and to investigate in more detail when you got back of the office.

The use of the odd/even pseudo selectors should be replaced by use of the alternateRows style attribute.  The reason for this is a performance one.

Investigate the use of rowAspect=list presentation style with both Table and Scrollgrid. Reason I like to mention it is it means you have less being displayed in the highlight colour and you have less worry about the possibility of the same data being displayed dark on light and then light on dark when selected.  In particular images will display better.

Typeahead is often forgotten when evaluating a system but you should remember that your experienced keyboard users maybe hitting the keyboard many fields ahead of where they are on the screen. Make sure your experienced users are considered in any testing plan and get out in the field to watch your users use the system.

Pasting from Excel into an array is an advanced form of typeahead, in GBC 5.00.08 we implemented the ability to paste from Excel into an array and you no longer needed to use some advanced code.

When using GBC with Universal Rendering for the first time, you might wonder where your context menu has gone and why you get the browser right-click menu.  Read here on how you can control what menu appears.

If you had an Edit Topmenu or a Toolbar with Cut, Copy, Paste actions as every 1990/2000s application did 🙂 , you need to review this as you can no longer access these local actions via topmenu and toolbar buttons.

It is a lot better now but review Browser Compatibility on how each browser handles the clipboard.  Firefox was behind for a while.

Note the concept of a Secure Context and how it might impact your application.

MESSAGE and ERROR now appear as tiles in the bottom right.  You can use GBC Customization to change the position.  One thing to note is that if MESSAGE and ERROR occur at the same time, they will both be displayed.  Previously depending on the value of statusbar style type, if ERROR and MESSAGE were displayed in the same place, the last displayed would overwrite the first displayed.  You may need to add an explicit MESSAGE “” to clear the MESSAGE displayed if the ERROR is no longer overwriting it.

FGL_WINMESSAGE, FGL_WINERROR etc.were system dialogs with Native Rendering.  Now they are displayed as 4gl code via MENU statements you can see in FGLDIR/src/fgldialog.4gl.  They may render slightly differently (button at bottom right or button displayed bottom center).  You can overload the function in FGLDIR/src/fgldialog, or implement your own dialogs instead, see this article to get the rendeirng you want.

COMMENT also used to appear in the StatusBar alongside MESSAGE and ERROR.  With the removal of the status bar, comment near appears when you hover over a field.  There is a theme variable you can use to make it appear as a PLACEHOLDER but I typically find the widget is not big enough to display the entire comment.

We have still not implemented SAMPLE in the Universal Rendering.  You will most likely notice this with fields CHAR(7) or greater that maintained alpha-numberic codes.  The Native Solution was to use SAMPLE =”M” when the default rendering of 6 M’s then 0’s was too small.  With Universal Rendering you may need to make these field a little wider in your form, or use FONTPITCH=FIXED, or use STRETCH=X.

If you specify an image without an extension, there is an order of precedence where the runtime will look for the imagefile with certain extensions, (jpp, png, bmp etc) .  If you know the extension specify it to save these lookups occurring unncessarily.

If I was to expand the presentation, I might have gone over some of the techniques you can use for deprecated functionality.  For a lot of .4st, chances are you can use GBC Customisation via Style Sheets to achieve what you’d like.  I am not a fan of StartMenu and feel you could write a better StartMenu program using TREE container.   I also had some articles on Emualting Stack and Emulating ListView.  Those articles are two years old now and do with being updated.  For instance rowAspect=list with IMAGECOLUMN can be used instead of a SCROLLGRID now, see here.


Tip #16: Use New UI Syntax

In transforming your application to render better with Universal Rendering, take the opportunity to review and include newer UI syntax.  This includes

  • Responsive Syntax
    • STRETCH=X
    • FLIPPED
      • rowAspect=list
    • ModalOnlarge
  • SCROLLGRID WANTFIXEDPAGESIZE
  • COMPLETER
  • Clickable Images
  • Multiple Dialog
  • Web Components
  • Built-In Web Components
  • Folder Accordion
  • Collapsible Groups
  • DISPLAY ARRAY with Modification Triggers
  • Table Aggregates
  • Generic Dialogs
  • Replace StartMenu with TREE

There is a lot of new syntax and widgets that has been added to Genero over the years that we feel is under used.  If you are going to have to put some effort into a transformation of some code for Universal Rendering, you should illustrate the benefits of what Universal Rendering gives you.  As well we the new code listed above, consider adding functionality via customisation that web technologies give you.  That could include

  • Circular Images
  • Infographics via CSS
  • Animation, Gradients, Opacity
  • Custom Front-calls
  • your own corporate theme

If I had time I finished with Morgan ex_hr demo.  I’d like to think everyone has a screen that they can add as many GUI widgets too as possible that you roll out during sales demos.