|
|
|
Latest Published
|
API, examples, implementation details, etc.Bogdan Stefanescu, bs@nuxeo.com, NuxeoTable des matières This document describes the implementation of the XForms plug-in for Eclipse. The XForms engine is generating SWT forms from an input XForms file and optional XML Schema and CSS style sheet files. Only a subset of the XForms standard is supported for now (more feature will be added in future) which is detailed on XForms Implementation section. The XML Schema is supported for automatically validation of the generated forms. You can find more details about XML Schema support are in XML Schema Support section. The style sheet files are adapted to describes SWT widgets so that they are not compatible with HTML style sheets. Style sheets are described in SWT Style Sheets section In the last section of the document there are provided some examples on how to use the API. Anyway the API is still experimental and may change in the future. XForms - There are several limitations on the XForms implementation. Instead of listing what is not supported we describe every implemented XForms concept and what limitation it have if any. For more details see the XForms Implementation section. XML Schema - The XML Schema engine is not completely implementing the XML Schema specifications and it is not designed to do this --- TODO ---. It was designed only to validate user input for the document fields it changes. It is not serving to validate entire XML documents (including document structure) but only data types and constraints. The XML schema concepts that are not supported (like complexType) are ignored. Only the information on the element types and constraints are read from the XSD file. For information on every supported concept and it's limitations see the section XML Schema Implementation CSS - The Style Sheets implementation is not supporting inheritance and multiple styles defined on the same line (like input, label { ... } ) - this will change in the future. The XForms engine is ignoring any unknown tag or XForms concept it doesn't understand. So even if some concepts are not yet implemented the form is correctly displayed with the only limitation that unimplemented XForms concepts will not be available. XForms is not an XML document instead it is living inside other XML container documents like XHTML. The container document is ignored by the XForms engine and only the XForms elements are extracted and interpreted. So you may write your form inside any XML document you want, the form will be correctly interpreted. The only requirement is that the document containing the form should be a valid XML document (i.e. containing a root element). Any element in the XForms document may contains the attributes id, class and style. XForms control may be declared anywhere in the host document but when using the SWT generator it is recommended to use a top level group or a XHTML body element as a top level control container. This way you can control the style of the SWT composite, otherwise the controls will be put as is in the parent composite specified at runtime and you cannot control scrolling and stuff like this. The best is to use a XHTML body container because this is by default mapped to a ScrolledForm control. References to external documents such style sheets and XML schema may be specified as absolute URLs or as relative paths to the host document The most important limitations of the current implementation are:
The XForms engine is doing non-restrictive namespace checks on elements. This means elements that are not in any namespace are interpreted as XForms elements if they match an XForms tag. So for example if no default namespace was declared then the following tag declaration is recognized as a valid XForms input tag even if it's not decalred to be from XForms namespace:
Attributes are not checked for namespace. So, inside a XForms tag, if an attribute match a XForms attribute name that is valid for the tag then it will be considered a XForms attribute. Thus, the element namespace is inherited by attributes if no specific namespace is declared at attribute level. The following “ref” attributes are recognized as valid XForms attributes:
By convenience there are three XHTML tags interpreted by the XForms engine. These elements should be inside the XHTML namespace, but for convenience these elements are also recognized in the XForms namespace or if they are not declared inside a namespace.
You may declare several models in your XForms document. Each model may have the following attributes:
A model is supporting a single instance (and not multiple instances as in XForms specifications). Also it may contains several bind and submission elements. XForms Actions are ignored in the model tag and children. May contains the document model or a reference to an external instance document. Attributes:
The bind element is ignoring for now any other attribute than id, nodeset and type. Attributes:
Supported attributes:
All controls may contains the following attributes:
There is the list of the implemented controls:
There is a limitation on “select” and “select1” controls: only item and values are supported. The itemset element is not yet supported. The following actions are implemented:
The following XForms events are supported:
The following (DOM) events are generated by the SWT XForms implementation and can be used in the XForms document as events that trigger an action:
There are two type of bindings in the XForms document:
Thus, resolving the instance element type is done as follow:
The XML Schema engine is interpreting only simple types. The most important limitation is that attributes cannot be typed or constrained - this is expected to change in the future. Here is the complete list of element supported by the XML Schema engine. Any other element is ignored.
The SWT form builder is mapping XForms controls to SWT controls as follow.
Any of these default mapping can be changed using style sheet. To change the SWT control you may use the “control” style attribtue. Here is the complete list of style attributes supported by the SWT form builder.
Warning: The API is still under development so it may change in the future. The XForms core “org.nuxeo.xforms.core” is structured as follow:
The UI XForms module provides generic functionality and configuration through the XFormsProcessor class that is the main entry point to the XForms core. To begin a new XForms processing session you need to instantiated a XFormsProcessor and optionally configure it by adding custom event handlers. Then you may load an XForms from an input source like a file, URL, in-memory string or an opened input stream using the XInputSource abstraction. Example: XFormsProcessor proc = new XformsProcessor();
XInputSource src = new FileInputSource(new File("example1.xhtml"));
XForm form = proc.load(src);The loadForm() method is returning the loaded “XForm” object on success. The “XForm” object is the root object in the XForms object model. Using it you can query or modify the XForms tree. You can also retrieve the currently loaded “Xform” object later by calling ”XinputSource.getForm()” method. When loading another “XForm” using the same processor the current “XForm” object is disposed if any. After a XForm was loaded you can build a UIForm object using an existing UIBuilder implementation. The “org.nuxeo.xforms.ui” package is providing a SWT implementation of the UIBuilder: “SWTBuilder”. You can build a SWT form with There are two ways to do this.:
Using these methods we can write the following code that is adding a selection listener to a button so that when the button is clicked a message dialog is opened to show the current value of the control used to edit the UIControl control = uiForm.getControl("testButton");
if (control != null) {
final Button button = (Button)control.getControl();
button.addSelectionListener(new SelectionAdapter() {
public void widgetSelected(SelectionEvent event) {
UIControl title = uiForm.findControl("/document/metatada/title");
if (title != null) {
MessageDialog.openInformation(button.getShell(), "Example 1", "The title value is: "+title.getXMLValue());
} else {
MessageDialog.openError(button.getShell(), "Example 1", "Cannot find control bound to \"/document/metatada/title\"");
}
}
});
}Here is the complete example code:
public class Example1 {
public static void main(String[] args) {
Display display = null;
try {
display = new Display();
final Shell shell = new Shell(display);
shell.setText("SWT XForms - Example 1");
shell.setLayout( new FillLayout());
XFormsProcessor proc = new XformsProcessor();
XInputSource src = new URLInputSource (Example1.class.getResource("example1.xhtml"));
XForm form = proc.load(src);
final UIForm uiForm = new SWTBuilder().build(form, shell);
UIControl control = uiForm.getControl("testButton");
if (control != null) {
final Button button = (Button)control.getControl();
button.addSelectionListener(new SelectionAdapter() {
public void widgetSelected(SelectionEvent event) {
UIControl title = uiForm.findControl("/document/title");
if (title != null) {
MessageDialog.openInformation(button.getShell(), "Example 1","The title value is: "+title.getXMLValue());
} else {
MessageDialog.openError(button.getShell(), "Example 1", "Cannot find control bound to \"/document/title\"");
}
}
});
} shell.setBounds(10, 10, 400, 200);
shell.open();
while( !shell.isDisposed()) {
if(!display.readAndDispatch())
display.sleep();
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (display != null) display.dispose();
}
}
}This example may be run using the following XForms file You can find the example sources in plugin org.nuxeo.xforms.ui: org.nuxeo.xforms.ui.test.Example1.java
To run the example right click on the file in Eclipse Java perspective and choose Run SWT application. Here is the generated dialog: When you click on the button the current value of the title field will be displayed A more complex example can be found in the org.nuxeo.xforms.ui.editors plug-in. The FormViewer class is a generic form viewer that encapsulate a XFormsProcessor and display the current view loaded by the processor. The viewer also implements the auto-validation using XForms core API. There is an example of an XForms document described in three fiels:
These example files can be found in org.nuxeo.xforms.ui plug-in under the org.nuxeo.xforms.ui.test package: document.xhtml, document.xsd, document.css
<?xml version="1.0" encoding="UTF-8"?> <xs:schema xmlns="http://www.w3.org/2001/XMLSchema" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:myxs="http://www.w3.org/2001/MyXMLSchema" targetNamespace="http://www.w3.org/2001/MyXMLSchema"> <xs:element name="document"> <xs:complexType> <xs:sequence> <xs:element ref="metadata"/> <xs:element id="content" type="xs:string"/> </xs:sequence> </xs:complexType> </xs:element> <xs:element name="metadata"> <xs:complexType> <xs:sequence> <xs:element name="title" id="title" type="myxs:titleString"/> <xs:element name="author" id="author" type="myxs:authorString"/> <xs:element name="mdate" id="mdate" type="xs:string"/> <xs:element name="description" id="description" type="xs:string"/> <xs:element name="language" id="language" type="myxs:language"/> <xs:element name="ctype" id="ctype" type="xs:string"/> </xs:sequence> </xs:complexType> </xs:element> <xs:simpleType id="titleString" name="titleString"> <xs:restriction base="xs:string"> <xs:maxLength value="64"/> <xs:minLength value="8"/> </xs:restriction> </xs:simpleType> <xs:simpleType id="authorString" name="authorString"> <xs:restriction base="xs:string"> <xs:pattern value=".*@.*"/> </xs:restriction> </xs:simpleType> <xs:simpleType id="language" name="language"> <xs:restriction base="xs:string"> <xs:enumeration value="en"/> <xs:enumeration value="fr"/> <xs:enumeration value="ro"/> </xs:restriction> </xs:simpleType> </xs:schema> #document {
layout: table;
layout-padding: 10;
}
#metadata {
control: section;
section-description: false;
section-toggle: twistie;
section-expand: true;
layout: table;
layout-cols: 2;
hgrab: true;
align: fill;
}
#contentGroup {
control: section;
section-description: false;
section-toggle: twistie;
section-expand: true;
layout: table;
layout-cols: 1;
vgrab: true;
hgrab: true;
align: fill;
}
#buttonBar {
layout: fill;
align: right;
layout-spacing: 10;
}
#description {
border: true;
height: 100;
vscroll: true;
hscroll: true;
align: fill;
hgrab: true;
}
#content {
border: true;
vscroll: true;
hscroll: true;
wrap: true;
align: fill;
vgrab: true;
valign: fill;
hgrab: true;
height: 200;
}
.field {
border: true;
align: fill;
hgrab: true;
}
.fieldLabel {
align: left;
color: #0000ff;
}
.groupField {
border: true;
align: fill;
hgrab: true;
colspan: 2;
layout: fill;
layout-type: vertical;
layout-spacing: 5;
layout-padding: 5;
color: #0000ff;
}
|
|
|