Composite Control Development in OT Cordys

Composite Control Development in OT Cordys

Some background and basics

Cordys UI development enables development of ‘desktop-like’ UI’s running in a browser. Development itself is also browser hosted. In Cordys UI development, 2 layers can be distinguished as important to Application Developers: Web Toolkit and XForms. Web Toolkit is a library of components by which html can be enriched. It also has a component for communication to the Cordys Bus via web gateway. The components come as html components, residing in <cordys instance>/webroot/shared/wcp/library:

Toolkit Components Folder

When developing your own components, it can be useful to have a look at some sources of these components.

The other layer, the XForms layer, goes further than offering an API; XForms enables to model UI’s using WYSIWYG. The models are stored as XML in the XDS database. To run the UI’s, no code is generated beforehand – instead the model itself is executed in the XForm runtime. Server-side, the model translates to HTML/javascript, where use is made of both components from the Web Toolkit as well as components which come with XForms itself. An example of a component in XForms which makes use of a Web Toolkit component is the Tree component. From this, when exploring the tree functionality, it is useful to see both the XForms API documentation as well as the Web Toolkit API documentation. XForms are run with help of the formrunner host library.

XForms components can be found in <cordys instance>/webroot/shared/cas/xforms:

XForms Components Folder

UI components in Cordys do come as so called Type Libraries. They are dynamically loaded by Cordys, and can be attached to DOM objects. The low level API for this is the application.addType() method, enabling to add the library to the specified DOM object.

Add Type

Example: adding the upload component (by its fully qualified name) to a button with id ‘upload’ :

application.addType(upload, "wcp.library.util.Upload");

after which the methods from the upload type library are available on the upload button DOM object:

upload.browse(1);

The other way to attach a type library is by specifying the ‘cordysType’ attribute on the HTML element. For example for the web toolkit validate component:

<div cordysType=”wcp.library.util.Validate” id=”validateID”>
<div>

</div>
</div>

What happens is upon runtime loading the html, when the DOM has been populated, the onload event is used by Cordys to traverse the DOM for elements with the ‘cordysType’ attribute and attach the corresponding Type Library. For this, it is using the application.initializeHTMLElements() method:

InitializeHTMLElements

In above screenshot, another Cordys feature wrt Type Libraries can be seen: one type library can inherit the functions from another type library.

Above is some low level background on Cordys UI components and libraries. Normally when doing XForms development, these low level details are abstracted away from the application developer. However, when it comes to developing your own components, this knowledge will be relevant to you.

Cordys wiki links:
https://wiki.cordys.com/display/bop43/The+Type+Library
https://wiki.cordys.com/display/bop43/Migrating+Libraries+to+Type+Libraries
https://wiki.cordys.com/display/bop43/Using+Web+Components+in+XForms

Control Development

To learn on development of Composite Controls, next resources can be used.

From help documentation:
https://wiki.cordys.com/display/bop43/Working+with+Composite+Controls

Additional examples on control development:
https://wiki.cordys.com/display/DUI/How+to+create+Composite+Control-Sample+Composite+Control
https://wiki.cordys.com/display/DUI/Build+a+Composite+Control+based+on+Fusion+Widget

In the runtime library, there are 3 important lines in top:

// Set the mycontrol type to public so the Cordys composite control framework will
// be able to add this library type to the runtime control object
setPublic(mycontrol, “com.ekemait.controls.runtime”);
// Inherit the base functionality from CompositeControl (like text translate)
importType(“cas.xforms.runtimelibrary.CompositeControl”);
inherit(mycontrol, CompositeControl);

Your library will be attached to the control as passed to attachType:

mycontrol.attachType = function ( control )

You can use this control object here as to add properties which you can refer to in your library methods via the this object:

control.numberOfColumns = control.getAttribute(“numberOfColumns”);

mycontrol.prototype.addOptions = function(optionCollection)
{
var numberOfRows = Math.ceil(optionCollection.length / this.numberOfColumns);

Use next lines in case you want to add the autoextent feature to your control programmatically:

control.ownerDocument.defaultView.WebForm.getLayoutElement(control).className += ” autoextent”;
control.ownerDocument.defaultView.WebForm.getLayoutElement(control).style.height = “auto”;

In case you have a composite control in which you want to dynamically include other XForms alike components (like input control) with equal behavior, what you can do is inspect the XForms generated HTML by DOM explorer, and reuse that HTML, adding the regular XForms behavior by:

this.ownerDocument.defaultView.WebForm._initializeHTMLElements(this.cblContentNode, this.ownerDocument.defaultView, false, false);

where this.cblContentNode is the top node in your control. As you can see, this is an underscore API (also used in the std xforms upload component); alternatively you can see if you can use the webtoolkit behavior; disadvantage though is the look and feel will be different.

To have your methods listed in the Intellisense feature in the XForms designer script editor, include a scriptlet in your designtime library similar as illustrated by next example:

<script xmlns=”http://www.w3.org/2002/xforms/cr” type=”cordys/xml” id=”_methodsDefinition”>
<methods>
<method name=”addOptions”>
<parameter name=”optionCollection”/>
</method>
</methods>
</script>

Reload Library

When running a form which has a composite control, Cordys loads the runtime library. This can be seen in Web Task manager.

When changing and publishing the designtime/runtime library, the changes might not get effective immediately as Cordys might still have the old version loaded. To get your changes effective, either you need to refresh the browser, or use this provisional code:

unloadLibrary(“<design lib qualified name>”);
unloadLibrary(“<runtime lib qualified name>”);

function unloadLibrary(libraryURL)
{
application.removeType(<control id>, libraryURL);
system.containers[libraryURL].close(true);
delete system.libraries[libraryURL];
system.raiseEvent(“onunloadlibrary”, {libraryURL: libraryURL});
}

2 COMMENTS

comments user
Mark Wiseman

Would you know how to make an XForm use XMLUtil with type XML/Cordys data? Also, I looked at your User Admin Manager java, but how can we implement Dynamic Roles in Cordys?

    comments user
    Karel

    Hi Mark,
    Using the widget from the toolbox doesn’t do the job for you? You can pass in any XML document, eg

    xmlutil1.xmlPopup(menuData.XMLDocument.documentElement, model, "Formatted XML");

    Wrt Dynamic Roles, OT Cordys doesn’t have a feature translating 1 to 1 to the Metastorm feature. Instead, depending on your use case, you will need one of the individual access control features (db/webservice) and/or using dynamic assignments in your BPM. In case you need more help, you might give your use case on the wiki.cordys.com forum.
    Regards,
    Karel

Leave a Reply

Your email address will not be published. Required fields are marked *