Qdabra FormsDesigner - User Manual Building form logic with rules All manuals

Chapter 11 - Custom CSS and JavaScript

First draft. This chapter has not been reviewed yet and may contain mistakes. Please read it with that in mind, and tell us about anything that does not match what you see.

Rules cover behaviour. Appearance beyond the built-in formatting options, and behaviour the rule engine does not offer, come from small CSS and JavaScript files stored inside the template. This chapter shows where those files live, how they are loaded, the screentip trick that lets you target controls from CSS without touching the view XSL, and three ready-made files you will see in most Qdabra starter templates.

11.1 Resource files

Open the Resource Files ribbon tab. It lists every file packaged in the template: style sheets, scripts, images, and the XML behind qRules and XTPs.

The Resource Files tab. Each row has view or edit, download, and delete icons; the drop zone on the right uploads new files.

Action How
Add a file Click or drop onto Click / Drop here to upload a file.
Edit text files in place The pencil icon opens an editor with syntax highlighting for .css, .js, .xml, .json, .txt. Save writes back into the template.
Download The download icon exports the file, for example to reuse in another template.
Delete The trash icon. Remove the matching LoadResource action too.

Uploading a file with an existing name replaces it; that is the normal way to ship a CSS fix.

11.2 Loading a file at start-up

A resource file does nothing until it is loaded. Loading is a qRules command; put it on QdabraRules > finishedLoading, the first rules to run when the form opens (Chapter 7, section 7.2):

  1. Data Fields > QdabraRules (Secondary) > select finishedLoading > Rules button.
  2. Add a rule, for example Load Responsive Design CSS.
  3. For each file add Run a qRules Command with "LoadResource /name=<file name with extension>", or build it in the Command Builder (Chapter 3, section 3.3.6).

The sample template loads its files in three rules at the top of the finishedLoading list: FVFlex.css and ScreentipSwap.js, then ToggleClass.js and DebugSlider.css, then the signature scripts. Resource loaders belong above Run Dynamic DCs; they touch no data connections.

LoadResource parameters: /name (required), /type script or style when the extension does not say, /unload to remove a previously loaded file, /allowexternal and /useproxy for files served from outside the template.

11.3 Turning a screentip into a CSS class

FormsViewer renders a control's ScreenTip as the HTML title attribute. That makes the screentip the easiest hook for CSS: you set it in the designer, per control, without editing the view. Two ways to use it:

ScreentipSwap.js as shipped in the sample template: for each supported element with a title starting "my_", add the title as a class and remove the title, on every afterRender.

Rules of the convention:

Rule Detail
Prefix The screentip must start with my_, case sensitive. Anything else is left alone, so ordinary screentips keep working as tooltips.
Name The screentip text becomes the class name verbatim: my_container, my_responsiveTable, my_overlay. Use CSS-safe names, no spaces.
Where to set it Select the control, Properties tab, ScreenTip.
Which controls Sections, expression boxes (calculated values), and picture buttons in the shipped script. Ordinary buttons are not covered (the designer does not let you set a screentip on them); use a picture button, or wrap the button in a section and target the section. Extend the selector list if you need text boxes or others.
Verify Open the form, press F12, search the Elements panel for the class name.

Because the class is on the section, you can style everything inside it with descendant selectors: .my_container .xdTextBox { ... }.

11.4 Relative widths instead of fixed widths

InfoPath layouts carry fixed pixel widths on tables, columns, and sections, which is why a form designed at 800 px stays 800 px on a wide screen and overflows on a phone. The sample template ships full_width.css (the training labs distribute the same file as fullwidth.css or full-width.css; the name inside your template is what LoadResource needs), a short style sheet that overrides those widths with percentages:

table { width: 100% !important; }
col   { width: 100% !important; }
.xdSection { width: 100% !important; }
.xdRepeatingSection.xdRepeating { width: 100% !important; }

full_width.css in the resource editor. The commented block shows how to give individual columns their own percentage by adding a class in the view.

Load it with "LoadResource /name=full_width.css" and the layout tables stretch to the container. For columns that must keep a proportion, the commented section shows the pattern: give the col element a class in the view and set width: 20% !important on that class. FVFlex.css, also in the sample template, goes further and rebuilds the layout with flexbox for a responsive form.

11.5 Custom JavaScript as a qRules command

JavaScript in a resource file can register new qRules commands, so the rest of the form calls them from ordinary action rules. ToggleClass.js is the shipped example:

ToggleClass.js: registers a ToggleClass command with selector, class, and include parameters, implemented with jQuery toggleClass.

The shape of such a file:

(function () {
    "use strict";
    formsViewer.getInstances().forEach(function (instance) {
        instance.qRules().registerCommand(
            'ToggleClass',
            { parameters: ['selector', 'class', 'include'] },
            function (params) {
                var include = params.get('include');
                if (include) {
                    $(params.get('selector')).toggleClass(params.get('class'), params.getBool('include'));
                } else {
                    $(params.get('selector')).toggleClass(params.get('class'));
                }
            });
    });
})();

Using it from a rule: FormsViewer exposes every command registered this way under the name with a Custom prefix, so the rule calls Run a qRules Command with "CustomToggleClass /selector=body /class=showOverlay /include=true" to add a class, /include=false to remove it, or no /include to toggle. Combined with a screentip class, this is how the sample template's Debug Slider opens: "CustomToggleClass /selector=.my_debug /class=open" on a picture button, and how the overlay lab in the training material shows its panel.

Notes for writing your own:

11.6 Putting it together

A typical modern-UI starter:

  1. Resource files: full_width.css (or FVFlex.css), ScreentipSwap.js, ToggleClass.js, your own theme.css.
  2. finishedLoading rule Load UI resources: one LoadResource action per file.
  3. Screentips my_header, my_main, my_actions on the main sections.
  4. theme.css styles those classes and their descendants.
  5. Buttons that need to show or hide a panel call CustomToggleClass on a my_ class.

11.7 Summary

Back to the table of contents.

© Qdabra Software  |  Questions and corrections: [email protected]  |  Preview copy, not linked from the public site.