Today''s Page Hits: 243
Databinding is a very useful feature to help us bind UI and model together, It decrease the line number of code of our project.;
Here, is example to show how to bind bean with macro component with data binding feature.
In this example, I have a PriceComp macro component , and have a Decimalbox inside it as a number member field. PriceComp delegates the number and forward the value to a decimalbox inside it.
public class PriceComp extends HtmlMacroComponent {
private int number;
Decimalbox db;
public void afterCompose(){
super.afterCompose();
db = (Decimalbox)getFellowIfAny("value");
if(db!=null){
db.setValue(new BigDecimal(number));
}else{
throw new IllegalStateException("component value not found");
}
}
public int getNumber() {
if(db!=null){
return db.getValue().intValue();
}
return number;
}
public void setNumber(int number) {
if(db!=null){
db.setValue(new BigDecimal(number));
}else{
this.number = number;
}
}
}
In the macro component template (~./myPrice.zul), it has a decimalbox , and it also forwards onChange event out to PriceComp as onNumberChange event
<zk>
<decimalbox id="value" forward="onChange=onNumberChange"/>
</zk>
You also need to write some configuration of this macro component. to enable default binding behavior, for example default save-when behavior of 'number' property is onNumberChange
<?xml version="1.0" encoding="UTF-8"?>
<language-addon>
<addon-name>testapp</addon-name>
<language-name>xul/html</language-name>
<component>
<component-name>myPriceComponent</component-name>
<component-class>com.test.PriceComp
</component-class>
<macro-uri>~./myPrice.zul</macro-uri>
<extends>decimalbox</extends>
<annotation>
<annotation-name>default-bind</annotation-name>
<property-name>number</property-name>
<attribute>
<attribute-name>access</attribute-name>
<attribute-value>both</attribute-value>
</attribute>
<attribute>
<attribute-name>save-when</attribute-name>
<attribute-value>self.onNumberChange</attribute-value>
</attribute>
</annotation>
</component>
</language-addon>
Finally, a example to use databinding with this macro component.
<?init class="org.zkoss.zkplus.databind.AnnotateDataBinderInit"?>
<zk>
<window title="bind macro component" border="normal" id="win">
<zscript><![CDATA[//@IMPORT
import com.test.*;
]]><![CDATA[//@DECLARATION
]]><![CDATA[
Bean bean = new Bean("Cat",35);
]]>
</zscript>
<hbox>
Name : <textbox value="@{bean.name}" /> |
Number : <myPriceComponent number="@{bean.amount}" />
</hbox>
<hbox>
Name : <label value="@{bean.name}" />
</hbox>
<hbox>
Number : <label value="@{bean.amount}" />
</hbox>
</window>
</zk>
Very tricky, use data binder can even link size of a window with other components.
try following example in zkdemo , click overlapped, resize the window.
<?init class="org.zkoss.zkplus.databind.AnnotateDataBinderInit"?>
<zk>
<button label="overlapped" onClick="winActif.doOverlapped()" />
<label id="info" />
<window visible="false" title="Les actifs" id="winActif"
border="normal" closable="true" left="300px" top="100px" width="200px"
height="200px"
onClose="self.setVisible(false); event.stopPropagation();"
onSize='info.setValue(winActif.getWidth()+","+winActif.getHeight());'
sizable="true">
</window>
<hbox style="background-color:red"
width="@{winActif.width,load-when=winActif.onSize}"
height="@{winActif.height,load-when=winActif.onSize}">
Connected Box
</hbox>
</zk>
Fileupload is a very convenient component to do uploading file in ZK.
But, it auto transfers uploaded content to Text or Binary, in memory, in inputstream or in file, depends on a assumption(MimeType, uploaded size).
I am not sure it is good or not to provide such automation on it. for some case this automation is good.
Ok, In some case, such as save ulpoad content to file system or DB, I would like to control all the uploaded content, in other words, I want to always get a InputStream and flush it to some destination.
To accomplish is very simple.
1, if you use FileUpload.get(max), then you just assign a option alwaysNative to true[FileUpload.get(max,true)] and get uploaded file by Media.getStreamData():InputStream.
2.if you use<fileupload/>, then you just assign the attribute native to true , <fileupload native="true"/> , don't forget to add onUpload listener and get InputStream by event.getMedia().getStreamData().
ZK announces a WYSIWYG feature preview of ZK Studio , the smalltalk here.
Here, I post another demo, it creates a Login window use ZULEditor, Palette and Outline.
Another feature not in the official demo, it doesn't break all the UI when you has a wrong zul file , for example a 'hbox' in a 'rows', or a 'row' in a 'column'. Visual Editor shows you the error message , not breaks full page.
In Eclipse, follow below steps.
1.Window >> Preferences >> Web and XML > XML Catalog > Add(Button)
2.fill 'Add XML Catalog Entry' Dialog
Location : [the zul.xsd file location] <- set this first
Key Type : Schema Location
Key : http://www.zkoss.org/2005/zul/zul.xsd
3.save the configuration.
In ZK Spreadsheet, it provides a convenient way to plug any custom formula into it - use tag library. Only few steps need to do to add a custom formula into ZK Spreadsheet. In following example, I add a simple formula "ECHO" which concatenate all value into a string
1.Write a tag lib functions class file, in those functions you must declare two arguments (Object [] and XelContext) just like following example
public class CustomFunction {
public static Object echo(java.lang.Object[] args, org.zkoss.xel.XelContext ctx){
StringBuffer sb = new StringBuffer();
sb.append("[");
if(args!=null){
for(int i=0;i<args.length;i++){
if(i>0) sb.append(", ");
if(args[i] instanceof RangeRef){
RangeRef ref = (RangeRef)args[i];
for(Iterator iter = ref.getCells().iterator();iter.hasNext();){
Cell cell = (Cell)iter.next();
sb.append(cell.getText());
if(iter.hasNext()) sb.append(", ");
}
}else if(args[i]!=null){
sb.append(args[i].toString());
}
}
}
sb.append("]");
return sb.toString();
}
}
2.Write a tld file(customfunction.tld in this example) in WEB-INF, and point to the function you want to add.
<taglib>
<uri>http://my.custom.function</uri>
<description>Custom Function</description>
<function>
<name>ECHO</name>
<function-class>
my.CustomFunction
</function-class>
<function-signature>
java.lang.Object echo(java.lang.Object[] args,
org.zkoss.xel.XelContext ctx)
</function-signature>
<description></description>
</function>
</taglib>
3.Add tab-lib directive in zul file and leave the prefix attribute a empty string.
<?taglib uri="/WEB-INF/customfunction.tld" prefix=""?>
<zk>
<spreadsheet id="ss1" url="/WEB-INF/empty.xls" maxrows="500" maxcolumns="80" width="90%" height="300px"/>
</zk>
4.Use custom function in ZK Spreadsheet, following is the live demo